EmbeddedRelated.com
Forums
Memfault Beyond the Launch

How do I get rid of a memory hole(in cortexm0plus)?

Started by Johann Klammer October 30, 2016
I have been playing with (gcc/binutils)-arm-none-eabi 
recently and they have this 'flash configuration field' 
in those cortex m0plus thingies. 
It is 16 bytes large and sits at address 0x400 of the 
flash memory. There's usable flash before and after it. 
Currently I am having this config field in its own section 
and I am using a linker script to place it at a fixed address. 
this does generate a memory hole before it. 

in the .S file:
[...]
.section .fconf
__fconf:
        .byte     BackDoorK0, BackDoorK1, BackDoorK2, BackDoorK3
        .byte     BackDoorK4, BackDoorK5, BackDoorK6, BackDoorK7
        .byte     0xFF,       0xFF,       0xFF,       0xFF
        .byte     EEPROT,      FPROT,     FSEC,       FOPT
        .size __fconf, . - __fconf
[...]

in the linker script:
[...]
SECTIONS
{
        .text :
        {
                KEEP(*(.isr_vector))
                KEEP(*(.isr_vector_noncore))
                . = 0x400;
                KEEP(*(.fconf))
                *(.text*)
[...]


Now I would like to use this space between the end of the 
isr vectors and the start of fconf. How to do that? 

On 30/10/16 09:29, Johann Klammer wrote:
> I have been playing with (gcc/binutils)-arm-none-eabi > recently and they have this 'flash configuration field' > in those cortex m0plus thingies. > It is 16 bytes large and sits at address 0x400 of the > flash memory. There's usable flash before and after it. > Currently I am having this config field in its own section > and I am using a linker script to place it at a fixed address. > this does generate a memory hole before it. > > in the .S file: > [...] > .section .fconf > __fconf: > .byte BackDoorK0, BackDoorK1, BackDoorK2, BackDoorK3 > .byte BackDoorK4, BackDoorK5, BackDoorK6, BackDoorK7 > .byte 0xFF, 0xFF, 0xFF, 0xFF > .byte EEPROT, FPROT, FSEC, FOPT > .size __fconf, . - __fconf > [...] > > in the linker script: > [...] > SECTIONS > { > .text : > { > KEEP(*(.isr_vector)) > KEEP(*(.isr_vector_noncore)) > . = 0x400; > KEEP(*(.fconf)) > *(.text*) > [...] > > > Now I would like to use this space between the end of the > isr vectors and the start of fconf. How to do that? >
There are a few linkers that can work with split output sections automatically, but it is not common practice on toolchains for bigger processors (because it is not often needed, and it is combinatorially hard to do optimally). Your best bet is probably to handle it manually - figure out how much space you have free, make a code section that you put there in the linker, and assign some read-only data table or function to that section explicitly (with the __attribute__((section)) compiler attribute).
Il giorno domenica 30 ottobre 2016 09:29:30 UTC+1, Johann Klammer ha scritto:
> I have been playing with (gcc/binutils)-arm-none-eabi > recently and they have this 'flash configuration field' > in those cortex m0plus thingies. > It is 16 bytes large and sits at address 0x400 of the > flash memory. There's usable flash before and after it. > Currently I am having this config field in its own section > and I am using a linker script to place it at a fixed address. > this does generate a memory hole before it. > > in the .S file: > [...] > .section .fconf > __fconf: > .byte BackDoorK0, BackDoorK1, BackDoorK2, BackDoorK3 > .byte BackDoorK4, BackDoorK5, BackDoorK6, BackDoorK7 > .byte 0xFF, 0xFF, 0xFF, 0xFF > .byte EEPROT, FPROT, FSEC, FOPT > .size __fconf, . - __fconf > [...] > > in the linker script: > [...] > SECTIONS > { > .text : > { > KEEP(*(.isr_vector)) > KEEP(*(.isr_vector_noncore)) > . = 0x400; > KEEP(*(.fconf)) > *(.text*) > [...] > > > Now I would like to use this space between the end of the > isr vectors and the start of fconf. How to do that?
You can delete the . = 0x400; line, so .fconf will be just after the .isr_vector_noncore section. But then the .fconf will not be at a fixed address so it really depends how you access the .fconf bytes in your code. There is a way to know the starting (and ending) address of every section, check the linker file manual. The best (and easiest) thing I think is is to put them at a fixed address, but at the end of the flash. Bye Jack
On 31/10/16 09:16, Jack wrote:
> Il giorno domenica 30 ottobre 2016 09:29:30 UTC+1, Johann Klammer ha scritto: >> I have been playing with (gcc/binutils)-arm-none-eabi >> recently and they have this 'flash configuration field' >> in those cortex m0plus thingies. >> It is 16 bytes large and sits at address 0x400 of the >> flash memory. There's usable flash before and after it. >> Currently I am having this config field in its own section >> and I am using a linker script to place it at a fixed address. >> this does generate a memory hole before it. >> >> in the .S file: >> [...] >> .section .fconf >> __fconf: >> .byte BackDoorK0, BackDoorK1, BackDoorK2, BackDoorK3 >> .byte BackDoorK4, BackDoorK5, BackDoorK6, BackDoorK7 >> .byte 0xFF, 0xFF, 0xFF, 0xFF >> .byte EEPROT, FPROT, FSEC, FOPT >> .size __fconf, . - __fconf >> [...] >> >> in the linker script: >> [...] >> SECTIONS >> { >> .text : >> { >> KEEP(*(.isr_vector)) >> KEEP(*(.isr_vector_noncore)) >> . = 0x400; >> KEEP(*(.fconf)) >> *(.text*) >> [...] >> >> >> Now I would like to use this space between the end of the >> isr vectors and the start of fconf. How to do that? > > You can delete the . = 0x400; line, so .fconf will be just after the .isr_vector_noncore section. > But then the .fconf will not be at a fixed address so it really depends how you access the .fconf bytes in your code. There is a way to know the starting (and ending) address of every section, check the linker file manual. > The best (and easiest) thing I think is is to put them at a fixed address, but at the end of the flash. > > Bye Jack >
The "fconf" section here must be at that specific address. Although the OP doesn't say so, I expect this is a Freescale/NXP Kinetis microcontroller. The microcontroller uses the configuration at that specific address to determine things like flash security.
Il giorno lunedì 31 ottobre 2016 10:24:15 UTC+1, David Brown ha scritto:

> The "fconf" section here must be at that specific address. Although the > OP doesn't say so, I expect this is a Freescale/NXP Kinetis > microcontroller. The microcontroller uses the configuration at that > specific address to determine things like flash security.
I supposed so. But if I remember correctly the place is not fixed and can be changed. you should be able to to something like: __start_fconf = .; #this is the address where fconf begins KEEP(*(.fconf)) __end_fconf = .; #this is the address after the end of fconf maybe some ALIGN() before or after is needed. And use __start_fconf as address in C code to access the needed bytes. For more info (for example): <http://www.nxp.com/files/soft_dev_tools/doc/app_note/AN4498.pdf?fasp=1&WT_TYPE=Application%20Notes&WT_VENDOR=FREESCALE&WT_FILE_FORMAT=pdf&WT_ASSET=Documentation&fileExt=.pdf> Bye Jack
On 31/10/16 10:43, Jack wrote:
> Il giorno luned&igrave; 31 ottobre 2016 10:24:15 UTC+1, David Brown ha scritto: > >> The "fconf" section here must be at that specific address. Although the >> OP doesn't say so, I expect this is a Freescale/NXP Kinetis >> microcontroller. The microcontroller uses the configuration at that >> specific address to determine things like flash security. > > I supposed so. > But if I remember correctly the place is not fixed and can be changed. > > you should be able to to something like: > > __start_fconf = .; #this is the address where fconf begins > KEEP(*(.fconf)) > __end_fconf = .; #this is the address after the end of fconf > > maybe some ALIGN() before or after is needed. > And use __start_fconf as address in C code to access the needed bytes. > > For more info (for example): > <http://www.nxp.com/files/soft_dev_tools/doc/app_note/AN4498.pdf?fasp=1&WT_TYPE=Application%20Notes&WT_VENDOR=FREESCALE&WT_FILE_FORMAT=pdf&WT_ASSET=Documentation&fileExt=.pdf> > > Bye Jack >
Certainly you can use the linker file to place the flash configuration segment somewhere else. But then it will not work as the flash configuration - because the Kinetis reads the values are addresses 0x400 to 0x40f at reset, with a total disregard for whatever linker file you use. The issue is the Kinetis hardware, not the linker file.
Il giorno luned&igrave; 31 ottobre 2016 11:12:25 UTC+1, David Brown ha scritto:

> > Certainly you can use the linker file to place the flash configuration > segment somewhere else. But then it will not work as the flash > configuration - because the Kinetis reads the values are addresses 0x400 > to 0x40f at reset, with a total disregard for whatever linker file you > use. The issue is the Kinetis hardware, not the linker file.
If it's HW then ok, didn't know that. If on the other hand is a value hardcoded in the startup routine then it can be changed... Bye Jack
Il giorno luned&igrave; 31 ottobre 2016 13:11:15 UTC+1, Jack ha scritto:

> > Certainly you can use the linker file to place the flash configuration > > segment somewhere else. But then it will not work as the flash > > configuration - because the Kinetis reads the values are addresses 0x400 > > to 0x40f at reset, with a total disregard for whatever linker file you > > use. The issue is the Kinetis hardware, not the linker file. > > If it's HW then ok, didn't know that. > If on the other hand is a value hardcoded in the startup routine then it can be changed...
just checked, it's really HW. anyway I find odd that they put it at 0x400... Bye Jack
On 31/10/16 13:23, Jack wrote:
> Il giorno luned&igrave; 31 ottobre 2016 13:11:15 UTC+1, Jack ha scritto: > >>> Certainly you can use the linker file to place the flash configuration >>> segment somewhere else. But then it will not work as the flash >>> configuration - because the Kinetis reads the values are addresses 0x400 >>> to 0x40f at reset, with a total disregard for whatever linker file you >>> use. The issue is the Kinetis hardware, not the linker file. >> >> If it's HW then ok, didn't know that. >> If on the other hand is a value hardcoded in the startup routine then it can be changed... > > just checked, it's really HW. anyway I find odd that they put it at 0x400... >
Well, the interrupt vectors are hard-coded at 0x0, so 0x400 is the start of the next 1K block that was available. The idea works quite well, except for one mind-bogglingly stupid decision. Erasing that area (setting it all to 0xff) locks the device and its flash. To /unlock/ it, so that you can program the thing with real code, you have to first program byte 0x40f to 0xfe. It is an insane idea that makes it easy to accidentally brick your devices if you are using simple standard ARM JTAG tools, and offers no benefits whatsoever. Apart from that, the Kinetis devices are very nice chips.

Memfault Beyond the Launch