Skip to main content
Visitor II
July 13, 2026
Question

RTC Wake-up Issue SPC560B40L5

  • July 13, 2026
  • 0 replies
  • 10 views

Hi,

I am using an SPC560B40L5 with ChibiOS/AutoDevKit Studio.

The hardware design is already finalized, so I cannot change the wake-up circuitry. Because of this limitation, I use the RTC to wake the MCU periodically every 200 ms. After each wake-up, I only check a few GPIOs to determine whether a real wake-up event has occurred. If no event is detected, the MCU immediately enters STOP mode again. No peripherals are reinitialized unless a valid wake-up event is detected.

The sleep/wake-up sequence works correctly during normal operation. However, I am facing a strange issue after reprogramming the MCU.

After downloading new firmware (without removing power), the MCU freezes in:

while (ME.IS.R == 0U)
{
}

inside:

SPCSetRunMode(SPC5_RUNMODE_STOP);

The board must support in-field reprogramming through the diagnostic interface (without a power cycle), but after programming the MCU usually remains stuck until the power is removed and applied again.

Interestingly, if I disable the periodic RTC wake-up and instead use only an external wake-up pin, both problems disappear:

  • The MCU no longer freezes in SPCSetRunMode().
  • Reprogramming works correctly without requiring a power cycle.

My sleep sequence is:

prepareForSleep();
gotoSleep();

where prepareForSleep() stops all peripherals (CAN, LIN, ADC, SPI, PWM, watchdog, etc.) and suspends all RTOS tasks.

The relevant part of gotoSleep() is shown below:

void prepareForSleep(void)
{
    //stop watchdog
    swt_lld_stop(&SWTD1);

    //suspend tasks
    vTaskSuspend(HandleInput);
    vTaskSuspend(HandleCanHighTx);
    vTaskSuspend(HandleCanLowTx);
    vTaskSuspend(HandleAnti);
    vTaskSuspend(HandleEeprom);
    vTaskSuspend(HandleRemote);
    vTaskSuspend(HandleDiagnostic);
    vTaskSuspend(HandleOutput);

    //disable inputs
    SIU.GPDO[10].R = 0;

    //stop pwm
    pwm_lld_stop(&PWMD1);
    pwm_lld_stop(&PWMD4);

    //stop tle
    tleStandby(&SPID1);
    UJA1078_ENpinSetState(&SPID1,0); //set tle's RST pin to zero -> puts ic in standby mode
    //stop uja
    UJA1078_EnableCANINT(&SPID1);
    UJA1078_GoStandby(&SPID1);
    //stop spi1
    spi_lld_stop(&SPID1);

    //stop adc
    adc_lld_stop_conversion(&ADCD1);

    vTaskDelay(50);
    adc_lld_stop(&ADCD1);

    // vTaskDelay(10);
    osalThreadDelayMicroseconds(10);

    //stop can
    can_lld_stop(&CAND1);
//    can_lld_stop(&CAND2);

    //stop lin
    lin_lld_stop(&LD2);
    //lin_lld_stop(&LD3);

    // stop eeprom
    FSL_AbortFunction(&eepromConf);

    SIU.GPDO[2].R = 0;

    disablePins();

}

void gotoSleep(void)
{
ME.STOP0.B.PDO = 0;
ME.STOP0.B.MVRON = 0;
ME.STOP0.B.DFLAON = 0;
ME.STOP0.B.CFLAON = 0;
ME.STOP0.B.FMPLLON = 0;
ME.STOP0.B.FXOSC0ON = 0;
ME.STOP0.B.FIRCON = 0;
ME.STOP0.B.SYSCLK = 0xF;

ME.LPPC[0].B.STOP0 = 0;
ME.LPPC[1].B.STOP0 = 0;

// set RTC registers for periodic wake-up
RTC.RTCS.B.RTCF = 1;
RTC.RTCC.B.FRZEN = 1;
RTC.RTCC.B.CLKSEL = 1;
RTC.RTCC.B.RTCVAL = 6;
RTC.RTCC.B.APIEN = 1;
RTC.RTCC.B.RTCIE = 1;
RTC.RTCC.B.DIV32EN = 0;
RTC.RTCC.B.DIV512EN = 0;

gotoSTOP:
RTC.RTCC.B.CNTEN = 1;
// RTC.RTCC.R = 0x60069000;

// enable wake-up on RTC interrupt
WKUP.WIFEER.B.IFEE = 0;
WKUP.WIREER.B.IREE = 0x2;
WKUP.WRER.B.WRE = 0x2;
WKUP.WISR.R = 0xFFFFFFFFU;

// enable RTC counter

if (SPCSetRunMode(SPC5_RUNMODE_STOP) == CLOCK_FAILED)
{
SPC5_CLOCK_FAILURE_HOOK();
}

RTC.RTCC.B.CNTEN = 0;

// osalThreadDelayMilliseconds(200);

// ME.MCTL.R = 0xA0005AF0; // Puts uC in Stop mode
// ME.MCTL.R = 0xA000A50F; // Puts uC in Stop mode

// // waits until stop
// while(ME.GS.B.S_MTRANS != 0){}

SIU.PCR[PIN_NUM_INPUT_ENABLE].B.PA = 0; // GPIO
SIU.PCR[PIN_NUM_INPUT_ENABLE].B.OBE = 1; // Output enable
SIU.PCR[PIN_NUM_INPUT_ENABLE].B.IBE = 0; // Input disable
SIU.PCR[PIN_NUM_INPUT_ENABLE].B.ODE = 0; // Push-pull
SIU.PCR[PIN_NUM_INPUT_ENABLE].B.SRC = 1; // Medium slew rate

SIU.GPDO[PIN_NUM_INPUT_ENABLE].R = 1; // PIN_NUM_INPUT_ENABLE high

RTC.RTCS.R = 0xFFFFFFFF;
WKUP.WISR.R = 0xFFFFFFFF;

osalThreadDelayMilliseconds(1);

if(!checkWakeup())
{
SIU.GPDO[PIN_NUM_INPUT_ENABLE].R = 0;
deInitPin(PIN_NUM_INPUT_ENABLE);
goto gotoSTOP;
}

boardInit();
clockInit();
// initCanLowSpeed();
initCanHighSpeed();
startUJA(&SPID1, &spi_config_SPI0);
adc_lld_start(&ADCD1, NULL);
swt_lld_start(&SWTD1, &swt0_config);

pal_lld_setpad(PORT_G, VSEN);

UJA1078_ENpinSetState(&SPID1, 0);
tleInit(&SPID1);
digitalInputs.BrakeOilLevelSwitch = 1;
FSL_InitEeprom(&eepromConf, NULL_CALLBACK);

INPUT_ENABLE();

lin_lld_start(&LD2, &lin_config_LIN1);
RPASensor.tick = xTaskGetTickCount();
// RPAsensor_init(&LD2);

pwm_lld_start(&PWMD1, &pwm_config_ROOFLAMP);
pwm_lld_start(&PWMD4, &pwm_config_BUZZER);
pwm_lld_enable_channel(&PWMD4, 5, 50);
// BUZZER(1);
SET_VECO(0);

vTaskResume(HandleInput);
vTaskResume(HandleCanHighTx);
vTaskResume(HandleCanLowTx);
vTaskResume(HandleAnti);
vTaskResume(HandleEeprom);
vTaskResume(HandleRemote);
vTaskResume(HandleDiagnostic);
vTaskResume(HandleOutput);
}

My questions are:

  1. Is there any known limitation or erratum regarding periodic RTC wake-up followed by repeated STOP mode entries on the SPC560B40L5?
  2. Is any additional RTC or WKUP register handling required before re-entering STOP mode?
  3. Could the periodic RTC wake-up interfere with the ME mode transition mechanism, causing ME.IS never to be updated?

Any suggestions would be greatly appreciated.


with regard,
Milan.