2

I want to share a variable (a boolean is enough) between bootloader and application. Bootloader should write a boolean instead the application should read it.

I thought I can write 1 or a 0 to a certain address (0x40000100), like this:

uint8_t *microType = (uint8_t *)0x40000100;

microType = 1;

Is it right?

As microprocessor I'm using NXP MPC5645C Thank you in advance.

Drake
  • 21
  • 2
  • Please [edit] your question to specify what platform you're using (what CPU/architecture) – Mat Aug 22 '22 at 13:54
  • And what is your question? – the busybee Aug 22 '22 at 14:00
  • 1
    A lot of this depends on if there will be a MCU reset between bootloader execution and application execution. – Lundin Aug 22 '22 at 14:05
  • 1
    `microType = 1;` must be `*microType = 1;`. Apart from that, I don't know that micro and have no idea if this simple way of sharing memory is possible there... – Gerhardh Aug 22 '22 at 14:06
  • Yes, but make sure there is memory at that address and the application and bootloader are not overwriting that address. You can't just pick an address at random. – user253751 Aug 22 '22 at 14:15
  • Byte in EEPROM/FLASH? – i486 Aug 22 '22 at 14:21
  • @i486 These parts don't have any eeprom/data flash, unfortunately. Major design mistake. So you'll have to grab program flash, and guess what, smallest page erase size is something like 32kb. Such a waste of space, but no can do. – Lundin Aug 22 '22 at 14:43

2 Answers2

0
  1. You need to create the section in the bootloader and application linker script. It is required that the compiler and linker do not place any other variables in this chunk of memory. The best place is the beginning or end of RAM as other sections cannot have "gaps". The section should have fixed address and to be the first (or last if it is placed at the end of RAM) defined in the linker script.

Then you simply create the variable(s) and place them in those section.

ejohnso49
  • 1,336
  • 1
  • 15
  • 20
0___________
  • 60,014
  • 4
  • 34
  • 74
0

To do this, you will need to set up and reserve a dedicated RAM segment at an absolute address. You obviously cannot use 0x40000100 because that points into the middle of the stack and the stack can't be used for this. You also can't just use any variable identifier to something located in .bss/.data, because that one may translate to a different physical address at any point, whenever the program is changed.

Also, you shouldn't rely on values in RAM getting preserved after reset, so if you execute the bootloader, then MCU reset and execute the application, that's not a good idea for the average kind of mission-/safety-critical applications MPC56 are usually used for. NXP microcontrollers have a tradition of well-defined value preservation of variables in RAM upon "soft reset" such as watchdog timeout, but I don't remember if this applies to MPC56.

Furthermore, if the value is to be preserved between resets, you have to consider how to initialize this custom RAM segment manually. Doing so means you'll have to tweak the CRT code, which isn't trivial. You'll want to zero-out the segment upon power-on reset and similar, but to leave it untouched upon watchdog reset etc.

As for how to make a custom memory segment, that depends on the tool chain. In Codewarrior you'd have to tweak the linker script (.lcf file), creating one memory range below MEMORY and add a GROUP below SECTIONS. Be careful with alignment; it will expect at least 32 bit alignment but there might be other considerations too (check the friendly manual). Then add some icky pragma to the actual variable declaration, along the lines of this:

#pragma section RW ".my_section"
__declspec(section ".my_section") 
volatile uint32_t the_variable;

Once you've gotten that far, this variable should be accessible from both the bootloader and the application. It has to be volatile so that the compiler compiling the application doesn't make strange assumptions about the variable never getting written to.

Lundin
  • 195,001
  • 40
  • 254
  • 396