Go Down

Topic: Compiler bug? (Read 1 time) previous topic - next topic

darksir

i porting my sketch from UNO to Atmega8 breadboard.
But I found one problem.
When I compilling sketch I get error about SoftwareSerial. (Is some problem with softwareserial function on Atmega8... But it is not needed in my sketch, I using sserial only for debugging).

So, software serial is forbidden via Debug function in my sketch. But why arduino compiler building software serial function, when I have commented it via debug function? Please, can you help me?

Code: [Select]


#include <avr/wdt.h>


//------------------------------------------------
//#define DEBUG    // Debug ON (this switch on software serial)                    DEBUG 1/2 !!!!
//------------------------------------------------
#ifdef DEBUG
#include <SoftwareSerial.h>
#endif

//SoftwareSerial mySerial(11, 12); // RX, TX
// if DEBUG, MUST be uncomment                                                  DEBUG 2/2 !!!!
// -------------------------------- debug
#ifdef DEBUG
#define DBG(x) x
#define DBG_PRINT(x) mySerial.println(x)
#define DBG_PRINTnoln(x) mySerial.print(x)
#else
#define DBG(x)
#define DBG_PRINT(x)
#define DBG_PRINTnoln(x)
#endif


void setup() {               
  wdt_enable(WDTO_2S); // have the wdt reset the chip
   
  // initialize the digital pin as an output.
  pinMode(led, OUTPUT);     
  pinMode(button, INPUT_PULLUP);
// initialize serial:
  Serial.begin(19200);

  #ifdef DEBUG
  mySerial.begin(19200);
  #endif

   DBG_PRINT("DBG: FUNCTION > =SETUP= is ending...");

}





In code I use this lines :

   DBG_PRINT("DBG> my debug note...");


Why compiler build sotfwareserial function, when I commented DEBUG variable? Is some error in my debug function or this is arduino bug? I donĀ“t use any softwareserial function in SETUP or LOOP. When I change line :

#include <SoftwareSerial.h>

to

#include <SoxxxareSerial.h>

Now everything is OK and builded code is shorted. So arduino use some cache of libraries or this is some bug?

Many thanks,
Petr

PaulS

The IDE copies file to another directory for compilation. It ignores preprocessor directives when doing that. So, SoftwareSerial.h (and SoftwareSerial.cpp) get copied, and added to the list of files to be compiled.

When the compiler compiles your sketch, it sees that SoftwareSerial is not actually needed, and the linker doesn't care whether SoftwareSerial compiled, or not, since it isn't planning to link anything from SoftwareSerial.o into the hex file.

So, no, it is not a compiler bug. It is an IDE feature.

bperrybap

#2
Feb 16, 2013, 04:49 pm Last Edit: Feb 16, 2013, 04:53 pm by bperrybap Reason: 1

The IDE copies file to another directory for compilation. It ignores preprocessor directives when doing that. So, SoftwareSerial.h (and SoftwareSerial.cpp) get copied, and added to the list of files to be compiled.

When the compiler compiles your sketch, it sees that SoftwareSerial is not actually needed, and the linker doesn't care whether SoftwareSerial compiled, or not, since it isn't planning to link anything from SoftwareSerial.o into the hex file.

So, no, it is not a compiler bug. It is an IDE feature.


If it were only that simple and actually worked that way.

In reality what happens is that the IDE tries to be "smart" and make things easier for the user by
not requiring the user to write valid/correct/proper C/C++ code.
In order to do this, it has to correct the users code for things like missing function prototypes
and forward variable references.
(That is why it must make a copy of your code into a temporary working area)
In order to do that, it goes in and tries to analyze your code to be able to create prototypes for the functions
and pull in the libraries "it thinks" the code uses and declare references for certain known objects.

And there is where the problem is.
The IDE is simply not smart enough to pull that off.
(BTW, that is a very difficult thing to do properly)
The code that does the analyzing is too simple and doesn't understand even some simple things
like conditional compilation.
As a result it will try to pull in code that is no used
and then depend on the linker to remove it later.

In this case, with the SoftSerial code, the linker cannot remove the code and
the code will be pulled in even though the user code is not referencing or using any of it.
This is because the SoftSerial code uses interrupts and has an ISR routine.
The way the code is written, declared ISR routines will always be pulled in, and because of that other SoftSerial routines
are pulled in, and then because of those, most if not all the  SoftSerial code and data variables
will be pulled in.

You can see this if you use avr-objdump to create a .lss file and then look at what code is actually
included into the final linked .elf file that will be used to create the final .hex image  which
is what will be uploaded to the AVR.

This is a great example of how the current Arduino build methodology simply doesn't work very well.
There are some simple things that could be done to avoid things like this but so far the Arduino Team
seems very unwilling to address things like this.

If you look at the .lss file you will also see the HardwarSerial code and data being pulled.
Similar thing going on there as well. It is part of the core code and since it has ISRs it
ends up getting pulled in.

This is all done because of combination of the build methodology and the way the code is written/declared/used.
There are some ways to fix this but it takes modifications to the actual library code and to the IDE
so it's not really something than an average Arduino user will be able to fix.

So from my point of view, I see this as a well intended "feature" that kind of sort of works,
but in reality creates many other subtle hard to work around issues.

--- bill



darksir

Ok, many thanks for explanation.
I can accept this reality if I used "IF" function :

Code: [Select]

#ifdef DEBUG
#include <SoftwareSerial.h>
#endif


But why compiller can not ignore this line when I commented this?

when I make :

Code: [Select]

//#ifdef DEBUG
//#include <SoftwareSerial.h>
//#endif


I thought comments are absolutely ignored. So why arduino IDE use this if methods and softwareserial include line when it is commented?

I will be confused when I must remove or update everything debug declarations and functions before compile code.

PaulS

Quote
But why compiller can not ignore this line when I commented this?

It does. It would really help if you explained the errors you are getting, instead of us guessing.

Go Up