Hello to you all!
I'm working with TWRK60 and IAR Workbench.
I've got a doubt about how the linker arrange variables in memory. The way I'm used to work, if I declare a variable before another one, then the first one is located at a smaller memory address.
To my sourprise, I've got the following:
(Note: NVM_DATA is a macro for placing variables in an specific section)
NVM_DATA const tPARAM_MOVIL PROG_MOVIL;
NVM_DATA const tPARAM_RADIO PROG_RADIO;
and then in the MAP file:
PROG_MOVIL 0x0007f810 0xc Data Gb DataNVM.o [1]
PROG_RADIO 0x0007f800 0x10 Data Gb DataNVM.o [1]
As you can see, I declare PROG_MOVIL before PROG_RADIO, but it's placed after it.
Why's that?
For me this would represent a problem in the future, when updating the firmware via bootloader, because I can't guarantee that nonVolatileData would be where it is suppose to be.
Solved! Go to Solution.
Hello SebaS,
I use IAR V6.50.2 software with TWR-K40X256 board.
I config the .icf file below:
define symbol __ICFEDIT_region_ROM_DATA_start__ = 0x0003F800;
define symbol __ICFEDIT_region_ROM_DATA_end__ = 0x0003FFFF;
define region ROM_DATA_region = mem:[from __ICFEDIT_region_ROM_DATA_start__ to __ICFEDIT_region_ROM_DATA_end__];
place in ROM_DATA_region {readonly section NVM_DATA};
In C code, I use below codes:
#define NVM_DATA _Pragma("location=\"NVM_DATA\"")
NVM_DATA const int test1 = 0x1 ;
NVM_DATA const int test2 = 0x2;
Then after compile, I check the .map file and get below result:
test1 0x0003f800 0x4 Data Gb hello_world.o [1]
test2 0x0003f804 0x4 Data Gb hello_world.o [1]
It shows the variables place in ROM with initilization order.
I don't meet your description issue.
Thank you for the attention.
Hi,
I have tried to use below code to place variable in a specific address:
#pragma location=0x3000
const int test1 = 1;
const int test2 @ 0x3004 = 2;
Then in the map file, I could find below result:
test1 0x00003000 0x4 Data Gb hello_world.o [1]
test2 0x00003004 0x4 Data Gb hello_world.o [1]
If I use below code:
#pragma location=0x3000
const int test1 = 1;
const int test2 = 2;
Then there only place test1 variable in 0x3000, and test2 in another place, the map with below result:
test1 0x00003000 0x4 Data Gb hello_world.o [1]
test2 0x000016ec 0x4 Data Gb hello_world.o [1]
If it is possible, could you attatch your project .icf file and variable definition code?
Wish it helps.
Hello Hui_Ma!
In your example, the problem is that #pragma location only works for the following variable declaration. If you wish to declare 30 variables, you'll need 30 #pragma location.
Also, (I'm not sure) but I guess you'll need to change the address or it will throw you and overlap error
#pragma location=0x3000
const int test1 = 1;
#pragma location=0x3004
const int test2 = 2;
#pragma location=0x3008
Hope it help you out!
Best regards,
SebaS
Hi Sebasira,
Thank you for the info.
I want to regenerate your mentioned situation, while I could use the #pragma location works for the following variable.
I consult with IAR engineer, who show me below link:
http://supp.iar.com/Support/?note=36121
If you could send us your below variable define and related icf file, then I could consult with IAR to get some comments.
NVM_DATA const tPARAM_MOVIL PROG_MOVIL;
NVM_DATA const tPARAM_RADIO PROG_RADIO;
Thank you for the attention.
B.R.
Ma Hui
Hello Ma Hui!
I guess this is the info you need:
ICF File:
define symbol __ICFEDIT_region_ROM_DATA_start__ = 0x0007F800;
define symbol __ICFEDIT_region_ROM_DATA_end__ = 0x0007FFFF;
define region ROM_DATA_region = mem:[from __ICFEDIT_region_ROM_DATA_start__ to __ICFEDIT_region_ROM_DATA_end__];
place in ROM_DATA_region {readonly section NVM_DATA};
Then, in C file:
#define NVM_DATA _Pragma("location=\"NVM_DATA\"")
NVM_DATA const tPARAM_MOVIL PROG_MOVIL;
NVM_DATA const tPARAM_RADIO PROG_RADIO;
Notice that _Pragma("location=\"NVM_DATA\"") is the same as #pragma location="NVM_DATA". So the lines above could be read as:
#pragma location="NVM_DATA"
const tPARAM_MOVIL PROG_MOVIL;
#pragma location="NVM_DATA"
const tPARAM_RADIO PROG_RADIO;
tPARAM_MOVIL and tPARAM_RADIO are some data structures, and don't matter rigth now.
If you go back to the first post, you would see that the order (memory location) in the MAP file is not the same as the order I define the variables.
Best Regards,
SebaS
Hello SebaS,
I use IAR V6.50.2 software with TWR-K40X256 board.
I config the .icf file below:
define symbol __ICFEDIT_region_ROM_DATA_start__ = 0x0003F800;
define symbol __ICFEDIT_region_ROM_DATA_end__ = 0x0003FFFF;
define region ROM_DATA_region = mem:[from __ICFEDIT_region_ROM_DATA_start__ to __ICFEDIT_region_ROM_DATA_end__];
place in ROM_DATA_region {readonly section NVM_DATA};
In C code, I use below codes:
#define NVM_DATA _Pragma("location=\"NVM_DATA\"")
NVM_DATA const int test1 = 0x1 ;
NVM_DATA const int test2 = 0x2;
Then after compile, I check the .map file and get below result:
test1 0x0003f800 0x4 Data Gb hello_world.o [1]
test2 0x0003f804 0x4 Data Gb hello_world.o [1]
It shows the variables place in ROM with initilization order.
I don't meet your description issue.
Thank you for the attention.
Hello!
Thank you for testing it. I'll guess I'll just have to deal with it, and hopefully if it doesn't change in the future (the order) then maybe I won't have any problem.
Thank you very much!
Best Regards!
SebaS