Browse Source

stm32/powerctrl: Deselect PLLSAI as 48MHz src before turning off PLLSAI.

On the STM32F722 (at least, but STM32F767 is not affected) the CK48MSEL bit
must be deselected before PLLSAION is turned off, or else the 48MHz
peripherals (RNG, SDMMC, USB) may get stuck without a clock source.

In such "lock up" cases it seems that these peripherals are still being
clocked from the PLLSAI even though the CK48MSEL bit is turned off.  A hard
reset does not get them out of this stuck state.  Enabling the PLLSAI and
then disabling it does get them out.  A test case to see this is:

    import machine, pyb
    for i in range(100):
        machine.freq(122_000000)
        machine.freq(120_000000)
        print(i, [pyb.rng() for _ in range(4)])

On occasion the RNG will just return 0's, but will get fixed again on the
next loop (when PLLSAI is enabled by the change to a SYSCLK of 122MHz).

Fixes issue #4696.
pull/4739/head
Damien George 6 years ago
parent
commit
8031b7a25c
  1. 4
      ports/stm32/powerctrl.c

4
ports/stm32/powerctrl.c

@ -54,8 +54,6 @@ int powerctrl_rcc_clock_config_pll(RCC_ClkInitTypeDef *rcc_init, uint32_t sysclk
} }
} }
RCC->DCKCFGR2 |= RCC_DCKCFGR2_CK48MSEL; RCC->DCKCFGR2 |= RCC_DCKCFGR2_CK48MSEL;
} else {
RCC->DCKCFGR2 &= ~RCC_DCKCFGR2_CK48MSEL;
} }
// If possible, scale down the internal voltage regulator to save power // If possible, scale down the internal voltage regulator to save power
@ -208,6 +206,8 @@ set_clk:
} }
#if defined(STM32F7) #if defined(STM32F7)
// Deselect PLLSAI as 48MHz source if we were using it
RCC->DCKCFGR2 &= ~RCC_DCKCFGR2_CK48MSEL;
// Turn PLLSAI off because we are changing PLLM (which drives PLLSAI) // Turn PLLSAI off because we are changing PLLM (which drives PLLSAI)
RCC->CR &= ~RCC_CR_PLLSAION; RCC->CR &= ~RCC_CR_PLLSAION;
#endif #endif

Loading…
Cancel
Save