I have a relatively small project with only a few files (.c and .h). I have been fighting multiple inclusion errors (I think). So, I created a master.h header file that has each of the other header files that are needed. ALL of the header files have the
#ifndef _MY_HEADER
#define _MY_HEADER
… Header body
#endif
guards to prevent multiple inclusion. Each of my files includes the master.h file at the top. Here is how I would expect this to work.
- The first file that was compiled would see the #include "master.h"
- Since this is the first time that this file is processed __MASTER would not have been defined yet, so it would process the file.
- The compiler would come to the inclusion of the next header file, an similarly, it would have not been processed yet, so the complier would process it, then it would be defined, and would not be processed again.
- This continues for all the header files in the master.h until all the files have been processed, and defined so they won't be processed again.
- The same is true of the master.h file. Once it's processed, and completed, it won't be processed again due to the guard.
Shouldn't this prevent multiple inclusion?
So here are the errors.
Building target: My_Project_Bootloader.axf
Invoking: GNU ARM C Linker
arm-none-eabi-gcc -g3 -gdwarf-2 -mcpu=cortex-m3 -mthumb -T "C:/Users/Greg/SimplicityStudio/v4_workspace/My_Project_Bootloader/GNU ARM v4.9.3 - Debug/My_Project_Bootloader_custom.ld" -nostdlib -L"C:\GCC_STUFF" --specs=nosys.specs -Xlinker --gc-sections -Xlinker -Map="My_Project_Bootloader.map" -lm -lgcc -lc -o My_Project_Bootloader.axf "./Source/aeabi_memset-thumb.o" "./Source/crt0.o" "./Source/em_emu.o" "./Source/functions.o" "./Source/main.o" "./Source/startup_efm32jg1b.o" "./Source/interrupts.o"
./Source/main.o:(.rodata.const_ModBusIDReg+0x0): multiple definition of `const_ModBusIDReg'
./Source/functions.o:(.rodata.const_ModBusIDReg+0x0): first defined here
collect2.exe: error: ld returned 1 exit status
make: *** [My_Project_Bootloader.axf] Error 1
I've edited/removed some of the information in this post because it turns out it is unrelated. It appears that the "multiple definition" problems the linker was having was not due to actual "multiple definitions", or inclusions for any variable. Instead, it appears as if it was due to declaring and defining the variable (in this case a const in flash) at the same time. Once I split the declaration(s) into a header file, and the actual definition or assignment into a .c file, the problems went away. Here is an example of the fix for one of the problem "variables". I will pay much closer attention to the declaration and definition aspects of variables now. The tools used was GCC. Thank you for all the comments.
// boot.h
// declare const array
const unsigned char const_ModBusIDReg[7][48];
// boot.c
#include boot.h
// define const array
const unsigned char const_ModBusIDReg[7][48] =
{
"String1", // reg00
"String2", // reg01
"String3", // reg02
"String4", // reg03
"String5", // reg04
"String6", // reg05
"String7" // reg06
};