I try to use linker-generated region symbols to programmatically obtain the size of flash memory consumed by my app. When I compile it, compiler gives me this:
Program Size: Code=11688 RO-data=576 RW-data=28 ZI-data=6068
So I figure out that used flash size is Code+Ro = 11688 + 576 = 12264 bytes.
Then I write this code to obtaint this size programmatically:
extern unsigned int Image$$ER_IROM1$$Length; static const uint32_t size_bytes = (uint32_t) &(Image$$ER_IROM1$$Length);
However this variable is equal to 11892 (0x2E74) which is less then shown by compiler output. I then go and obtain linker symbol Image$$ER_IROM1$$Limit and it's equal to 0x08002E74. My flash memory begins at 0x08000000 so it also shows less used memory.
I then go and check memory window and I see that there is some non-zero values beyond address 0x08002E74 so I guess linker is indeed wrong here.
I use this (generated by Keil) scatter file:
LR_IROM1 0x08000000 0x00030000 { ; load region size_region ER_IROM1 0x08000000 0x00030000 { ; load address = execution address *.o (RESET, +First) *(InRoot$$Sections) .ANY (+RO) } RW_IRAM1 0x20000000 0x00007000 { ; RW data .ANY (+RW +ZI) } RW_IRAM2 0x20007000 0x00001000 { MDR32F9Qx_eeprom.o (+RO) .ANY (+RW +ZI) } }
What am I doing wrong? How can I obtain the correct size of used flash?
This is a slightly different symbol than a standard load execution region symbols
What you described is a load region symbol Load$$LR$$... :
www.keil.com/.../armlink_pge1362065953823.htm
The article you originally linked to was for **execution region** symbols.
The **load region** or (load view) is the power-on view of the device, i.e. the layout of your memory before the scatterloader has zero-initialized you stack, copied initialized variables into ram.
The **Execution region** or (Execution view) is the memory layout when your main() is running, everything is ready to execute. See:
www.keil.com/.../armlink_pge1362065902090.htm
Hope that helps.