Pages: 1 [2]   Go Down
Author Topic: Simpler alternative to #if ! defined() ... #endif ?  (Read 1383 times)
0 Members and 1 Guest are viewing this topic.
Offline Offline
Full Member
***
Karma: 1
Posts: 158
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset


that's what i need.
Does it mean i need to include according header file?
« Last Edit: December 11, 2013, 09:42:34 am by 4ntoine » Logged

Ayer, Massachusetts, USA
Offline Offline
Edison Member
*
Karma: 53
Posts: 1828
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

Is "__AVR_ATmega32__"  etc defined in the command line with a -D?...no I don't see it, there is a "-mmcu=" switch that I think gets its value from boards.txt. That probably causes the correct file to be included but the link escapes me at this point.
If you use -mmcu=<xxx>, the compiler will automatically define the appropriate __AVR_<xxx> macro.
Logged

Offline Offline
Full Member
***
Karma: 1
Posts: 158
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Is "__AVR_ATmega32__"  etc defined in the command line with a -D?...no I don't see it, there is a "-mmcu=" switch that I think gets its value from boards.txt. That probably causes the correct file to be included but the link escapes me at this point.
If you use -mmcu=<xxx>, the compiler will automatically define the appropriate __AVR_<xxx> macro.

How does it know what file needs to be included and what macro should be added?
Logged

Ayer, Massachusetts, USA
Offline Offline
Edison Member
*
Karma: 53
Posts: 1828
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

The IDE in boards.txt has a line <board>.build.mcu=<avr>.  When you select the board type (tools->board), it will look at boards.txt to see what options to pass.  The build.mcu option says to add the appropriate -mcu=<board> to the compile line.  So for an example, the lines for the Uno are:

Code:
uno.build.mcu=atmega328p
uno.build.f_cpu=16000000L
uno.build.core=arduino
uno.build.variant=standard

The uno.build.mcro=atmega328p line says to add the -mcu=atmega328p option to the compiler.

If you look in the compiler source, in <gcc>/gcc/config/avr/avr-mcus.def, there is the line for atmega328p board:

Code:
AVR_MCU ("atmega328p",           ARCH_AVR5, "__AVR_ATmega328P__",        0, 0, 0x0100, 1, "m328p")

The third argument gives the identifier to be defined (__AVR_ATmega328P__ in the case of the Uno).
Logged

Offline Offline
Full Member
***
Karma: 1
Posts: 158
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

The IDE in boards.txt has a line <board>.build.mcu=<avr>.  When you select the board type (tools->board), it will look at boards.txt to see what options to pass.  The build.mcu option says to add the appropriate -mcu=<board> to the compile line.  So for an example, the lines for the Uno are:

Code:
uno.build.mcu=atmega328p
uno.build.f_cpu=16000000L
uno.build.core=arduino
uno.build.variant=standard

The uno.build.mcro=atmega328p line says to add the -mcu=atmega328p option to the compiler.

If you look in the compiler source, in <gcc>/gcc/config/avr/avr-mcus.def, there is the line for atmega328p board:

Code:
AVR_MCU ("atmega328p",           ARCH_AVR5, "__AVR_ATmega328P__",        0, 0, 0x0100, 1, "m328p")

The third argument gives the identifier to be defined (__AVR_ATmega328P__ in the case of the Uno).

I'm getting closer and closer.
So in order to emulate this avr-gcc toolchain -mmcu arg usage i need to define __AVR_ATmega328P__ definition and include file "m328.h" in sketch code and it's path to I:

Code:
#define __AVR_ATmega328P__
#include <m328p.h>
#include <Arduino.h>
%sketch_code%

and execute compilation with params:
Code:
%sketch_filename%
-I%core_path%
-I%m328p.h_filepath%

All other things wil be done automatically according to definitions from "avr/io.h" which is included by "Arduino.h". Is it correct?
« Last Edit: December 11, 2013, 10:25:59 am by 4ntoine » Logged

SF Bay Area (USA)
Online Online
Tesla Member
***
Karma: 124
Posts: 6632
Strongly opinionated, but not official!
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
i need to define __AVR_ATmega328P__ definition and include file "m328.h" in sketch code
No, define __AVR_ATmega328P__ and then include avr/io.h (it will include iom328p.h for you, but it does some other things that you want as well.)

Actually, define __AVR_ATmega328P__ and then include Arduino.h; Arduino.h includes io.h, io.h includes iom328p.h
Logged

SF Bay Area (USA)
Online Online
Tesla Member
***
Karma: 124
Posts: 6632
Strongly opinionated, but not official!
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
i found avr, avr-3, avr-4 folders
There are two places where "avr-3" and "avr-4" shows up.

One is near the top-level of the toolchain directory, and is a consequence of some sort of incompatibility between compiler versions 4.3.x and 3.4.x;  I don't know the details, but avr-gcc packages (winavr, crosspack, linux installs) from those days include TWO versions of the compiler, selectable with avr-gcc-select.  Arduino only uses 4.x  Hopefully there are lots of symlinks involved, but I'm not sure that they survive the sort of packaging and unpackaging and re-packaging that has gone on.

The other is that in addition to the specific CPUs like __AVR_ATmega328P__, the avr chips are also divided into several "architectures" with minor but significant differences to compiler tools.  These are unimaginatively called "avr1", "avr3.5", and so on, and affect things like libraries, startup code, and linker scripts.
Logged

Ayer, Massachusetts, USA
Offline Offline
Edison Member
*
Karma: 53
Posts: 1828
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

You really want to use -mcu=<xxx> and not just define the appropriate macros.  The -mcu=<xxx> option controls what instructions the compiler generates.  Different boards might have different instructions.  If whatever default your gcc was built for uses instructions that your machine does not support, your program won't run.  If the default is the least common denominator, your program might be bigger and slower than if you used the correct -mcu=<xxx> option.
Logged

Offline Offline
Full Member
***
Karma: 1
Posts: 158
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
i found avr, avr-3, avr-4 folders
There are two places where "avr-3" and "avr-4" shows up.

One is near the top-level of the toolchain directory, and is a consequence of some sort of incompatibility between compiler versions 4.3.x and 3.4.x;  I don't know the details, but avr-gcc packages (winavr, crosspack, linux installs) from those days include TWO versions of the compiler, selectable with avr-gcc-select.  Arduino only uses 4.x  Hopefully there are lots of symlinks involved, but I'm not sure that they survive the sort of packaging and unpackaging and re-packaging that has gone on.
okay, now i know it.

Quote
The other is that in addition to the specific CPUs like __AVR_ATmega328P__, the avr chips are also divided into several "architectures" with minor but significant differences to compiler tools.  These are unimaginatively called "avr1", "avr3.5", and so on, and affect things like libraries, startup code, and linker scripts.

great to know that too! (i've seen that folders but also did not understand the meaning). that relates to these link too: http://gcc.gnu.org/onlinedocs/gcc/AVR-Options.html

thank you, now it becomes more and more clear
Logged

Offline Offline
Full Member
***
Karma: 1
Posts: 158
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

You really want to use -mcu=<xxx> and not just define the appropriate macros.  The -mcu=<xxx> option controls what instructions the compiler generates.  Different boards might have different instructions.  If whatever default your gcc was built for uses instructions that your machine does not support, your program won't run.  If the default is the least common denominator, your program might be bigger and slower than if you used the correct -mcu=<xxx> option.

i would be happy to just use it, but unfortunately i can't as my toolchain is not gcc and i have to do pretty the same as avr-gcc does behind the scene. fortunately, the community is very experienced and friendly to help me with it.
« Last Edit: December 11, 2013, 01:09:53 pm by 4ntoine » Logged

Ayer, Massachusetts, USA
Offline Offline
Edison Member
*
Karma: 53
Posts: 1828
View Profile
WWW
 Bigger Bigger  Smaller Smaller  Reset Reset

i would be happy to just use it, but unfortunately i can't as my toolchain is not gcc and i have to do pretty the same as avr-gcc does behind the scene. fortunately, the community is very experienced and friendly to help me with it.
Fair enough, but the point is you should use whatever options are appropriate to your compiler to target the exact board you are using.
Logged

SF Bay Area (USA)
Online Online
Tesla Member
***
Karma: 124
Posts: 6632
Strongly opinionated, but not official!
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
Also i can see desktop IDE adds core includes (i know core for the board - it's written in boards.txt file):
all .h files in core folder so for "Uno" it will be all .h files in ../cores/arduino:
-I ... /cores/arduino
These are the Arduino core libraries, appropriate to have paths added via -I

Quote
then i add constant includes for all the board types
-I ... avr/avr/include
-I ... "avr/lib/gcc/avr/4.7/include
   :
Ive found "UBRRH" definition in files:
tools/avr/avr-3/include/avr/iom163.h
tools/avr/avr-3/include/avr/iom165.h
and this makes me think i have to add such files into include list/paths, but i need to know the correlation between board type and header filename.
These however, are "system" include files, whose path should be inherent in the compiler build/installation.
tools/avr/include is essentially equivalent to /usr/include  on a native compiler installation.  It will be a symlink that points to either the avr-3 or avr-4 directory depending on which one has been set up (always 4 for Arduino.)  This is where the includes for the compiler core defines and avr-libc live, and I'm not sure that you should be adding explicit -I options for them
Logged

Offline Offline
Full Member
***
Karma: 1
Posts: 158
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

I can confirm it works now and Serial extern var (as HardwareSerial) is available now (it confirms avr/io.h included needed file and HardwareSerial found required definition) though autocomplete feature works not as i expect. Thank you, guys!
Logged

Pages: 1 [2]   Go Up
Jump to: