Skip to main content
VRodr.2
Associate
August 7, 2025
Question

SPC58NH92: Intermittent Cold Boot Halt When Accessing Variable in Custom .noinit Section (DRAM2)

  • August 7, 2025
  • 0 replies
  • 1235 views

Hello everyone,

I am working with an SPC58NH92C5RMI0X microcontroller using SPC5Studio v6.0 and the corresponding GCC toolchain.

Objective: I am trying to implement a persistent variable that survives warm resets (debugger or pin resets) but is initialized in a controlled manner on a cold boot (power-on). To achieve this, I have created a custom .noinit section in memory.

Symptoms: The system's behavior is inconsistent and depends on the boot type:

  1. Under the Debugger (Warm Resets): The system works perfectly. I can write a value to my persistent variable, perform a reset via the debugger, and the correct value is read in the next session.

  2. On Power-On (Cold Boot): The system behaves erratically. Sometimes it boots correctly, but most of the time it halts/crashes.

  3. Point of Failure: When the system halts, the crash occurs precisely at the instruction that attempts to read the persisted variable for the first time in my main() function.

Implementation:

To isolate the variable from the standard RAM clearing routines (_sysraminit in boot.s and the BSS clear in crt0.s), I have modified my linker script to create a dedicated memory region at the end of dram2.

 

1. C Code Variable:

__attribute__((section(".noinit"), used))
volatile uint32_t persisted;

int main(void) {
 // ... initializations ...

 pal_lld_setpad(PORT_LED2_KIT, LED2_KIT); // Turn on LED to indicate main has started

 // >>> THE CODE CRASHES HERE ON COLD BOOT <<<
 if (persisted == 0xdeadbeef) {
 pal_lld_setpad(PORT_LED1_KIT, LED1_KIT); // Indicates the value was read successfully
 } else {
 pal_lld_setpad(PORT_LED3_KIT, LED3_KIT); // Indicates the value was different
 }
 
 // ...
}

 

2. Linker Script (user.ld):

MEMORY
{
 dataflash : org = 0x00800000, len = 256k
 flash : org = 0x00FC0000, len = 10M 
 ram : org = 0x40028000, len = 1376k - 288k
 iram0 : org = 0x50000000, len = 32k
 iram1 : org = 0x51000000, len = 32k
 iram2 : org = 0x52000000, len = 32k
 dram0 : org = 0x50800000, len = 64k
 dram1 : org = 0x51800000, len = 64k
 dram2 : org = 0x52800000, len = 64k - 4k
 noinit_ram : org = 0x52800000 + (64k - 4k), len = 4k
}

SECTIONS
{
 /* ... other sections ... */

 .noinit (NOLOAD):
 {
 . = ALIGN(4);
 __noinit_start__ = .;
 *(.noinit)
 *(.noinit.*)
 . = ALIGN(4);
 __noinit_end__ = .;
 } > noinit_ram

 __heap_base__ = __bss_end__;
 __heap_end__ = __ram_end__;
}

 

Any help or insight would be greatly appreciated. Thank you.