diff options
| author | Dario Nieuwenhuis <[email protected]> | 2024-05-27 17:28:13 +0000 |
|---|---|---|
| committer | GitHub <[email protected]> | 2024-05-27 17:28:13 +0000 |
| commit | 8d7c3f7de137d0669f829af3df17e0f6ef87c30a (patch) | |
| tree | e40be336916a696c96bef8d639fb7c2dbf35bd28 | |
| parent | 8b9e2efec25ae36041038b70f608fe55f5061a1f (diff) | |
| parent | ec6cfc1f21ad043e10daf03a302342a295febbdd (diff) | |
Merge pull request #3008 from aurelj/stm32-rcc-hsi
stm32: ensure the core runs on HSI clock while setting up rcc
| -rw-r--r-- | embassy-stm32/src/rcc/c0.rs | 44 | ||||
| -rw-r--r-- | embassy-stm32/src/rcc/f013.rs | 24 | ||||
| -rw-r--r-- | embassy-stm32/src/rcc/g0.rs | 25 | ||||
| -rw-r--r-- | embassy-stm32/src/rcc/g4.rs | 25 | ||||
| -rw-r--r-- | embassy-stm32/src/rcc/h.rs | 33 |
5 files changed, 95 insertions, 56 deletions
diff --git a/embassy-stm32/src/rcc/c0.rs b/embassy-stm32/src/rcc/c0.rs index 349f978c5..5adf37941 100644 --- a/embassy-stm32/src/rcc/c0.rs +++ b/embassy-stm32/src/rcc/c0.rs | |||
| @@ -76,25 +76,29 @@ impl Default for Config { | |||
| 76 | } | 76 | } |
| 77 | 77 | ||
| 78 | pub(crate) unsafe fn init(config: Config) { | 78 | pub(crate) unsafe fn init(config: Config) { |
| 79 | // Turn on the HSI | ||
| 80 | match config.hsi { | ||
| 81 | None => RCC.cr().modify(|w| w.set_hsion(true)), | ||
| 82 | Some(hsi) => RCC.cr().modify(|w| { | ||
| 83 | w.set_hsidiv(hsi.sys_div); | ||
| 84 | w.set_hsikerdiv(hsi.ker_div); | ||
| 85 | w.set_hsion(true); | ||
| 86 | }), | ||
| 87 | } | ||
| 88 | while !RCC.cr().read().hsirdy() {} | ||
| 89 | |||
| 90 | // Use the HSI clock as system clock during the actual clock setup | ||
| 91 | RCC.cfgr().modify(|w| w.set_sw(Sysclk::HSISYS)); | ||
| 92 | while RCC.cfgr().read().sws() != Sysclk::HSISYS {} | ||
| 93 | |||
| 79 | // Configure HSI | 94 | // Configure HSI |
| 80 | let (hsi, hsisys, hsiker) = match config.hsi { | 95 | let (hsi, hsisys, hsiker) = match config.hsi { |
| 81 | None => { | 96 | None => (None, None, None), |
| 82 | RCC.cr().modify(|w| w.set_hsion(false)); | 97 | Some(hsi) => ( |
| 83 | (None, None, None) | 98 | Some(HSI_FREQ), |
| 84 | } | 99 | Some(HSI_FREQ / hsi.sys_div), |
| 85 | Some(hsi) => { | 100 | Some(HSI_FREQ / hsi.ker_div), |
| 86 | RCC.cr().modify(|w| { | 101 | ), |
| 87 | w.set_hsidiv(hsi.sys_div); | ||
| 88 | w.set_hsikerdiv(hsi.ker_div); | ||
| 89 | w.set_hsion(true); | ||
| 90 | }); | ||
| 91 | while !RCC.cr().read().hsirdy() {} | ||
| 92 | ( | ||
| 93 | Some(HSI_FREQ), | ||
| 94 | Some(HSI_FREQ / hsi.sys_div), | ||
| 95 | Some(HSI_FREQ / hsi.ker_div), | ||
| 96 | ) | ||
| 97 | } | ||
| 98 | }; | 102 | }; |
| 99 | 103 | ||
| 100 | // Configure HSE | 104 | // Configure HSE |
| @@ -150,6 +154,12 @@ pub(crate) unsafe fn init(config: Config) { | |||
| 150 | w.set_hpre(config.ahb_pre); | 154 | w.set_hpre(config.ahb_pre); |
| 151 | w.set_ppre(config.apb1_pre); | 155 | w.set_ppre(config.apb1_pre); |
| 152 | }); | 156 | }); |
| 157 | while RCC.cfgr().read().sws() != config.sys {} | ||
| 158 | |||
| 159 | // Disable HSI if not used | ||
| 160 | if config.hsi.is_none() { | ||
| 161 | RCC.cr().modify(|w| w.set_hsion(false)); | ||
| 162 | } | ||
| 153 | 163 | ||
| 154 | let rtc = config.ls.init(); | 164 | let rtc = config.ls.init(); |
| 155 | 165 | ||
diff --git a/embassy-stm32/src/rcc/f013.rs b/embassy-stm32/src/rcc/f013.rs index f33351e74..0946287ea 100644 --- a/embassy-stm32/src/rcc/f013.rs +++ b/embassy-stm32/src/rcc/f013.rs | |||
| @@ -135,17 +135,18 @@ impl Default for Config { | |||
| 135 | 135 | ||
| 136 | /// Initialize and Set the clock frequencies | 136 | /// Initialize and Set the clock frequencies |
| 137 | pub(crate) unsafe fn init(config: Config) { | 137 | pub(crate) unsafe fn init(config: Config) { |
| 138 | // Turn on the HSI | ||
| 139 | RCC.cr().modify(|w| w.set_hsion(true)); | ||
| 140 | while !RCC.cr().read().hsirdy() {} | ||
| 141 | |||
| 142 | // Use the HSI clock as system clock during the actual clock setup | ||
| 143 | RCC.cfgr().modify(|w| w.set_sw(Sysclk::HSI)); | ||
| 144 | while RCC.cfgr().read().sws() != Sysclk::HSI {} | ||
| 145 | |||
| 138 | // Configure HSI | 146 | // Configure HSI |
| 139 | let hsi = match config.hsi { | 147 | let hsi = match config.hsi { |
| 140 | false => { | 148 | false => None, |
| 141 | RCC.cr().modify(|w| w.set_hsion(false)); | 149 | true => Some(HSI_FREQ), |
| 142 | None | ||
| 143 | } | ||
| 144 | true => { | ||
| 145 | RCC.cr().modify(|w| w.set_hsion(true)); | ||
| 146 | while !RCC.cr().read().hsirdy() {} | ||
| 147 | Some(HSI_FREQ) | ||
| 148 | } | ||
| 149 | }; | 150 | }; |
| 150 | 151 | ||
| 151 | // Configure HSE | 152 | // Configure HSE |
| @@ -297,6 +298,11 @@ pub(crate) unsafe fn init(config: Config) { | |||
| 297 | RCC.cfgr().modify(|w| w.set_sw(config.sys)); | 298 | RCC.cfgr().modify(|w| w.set_sw(config.sys)); |
| 298 | while RCC.cfgr().read().sws() != config.sys {} | 299 | while RCC.cfgr().read().sws() != config.sys {} |
| 299 | 300 | ||
| 301 | // Disable HSI if not used | ||
| 302 | if !config.hsi { | ||
| 303 | RCC.cr().modify(|w| w.set_hsion(false)); | ||
| 304 | } | ||
| 305 | |||
| 300 | let rtc = config.ls.init(); | 306 | let rtc = config.ls.init(); |
| 301 | 307 | ||
| 302 | // TODO: all this ADC stuff should probably go into the ADC module, not here. | 308 | // TODO: all this ADC stuff should probably go into the ADC module, not here. |
diff --git a/embassy-stm32/src/rcc/g0.rs b/embassy-stm32/src/rcc/g0.rs index ea4422ccc..c2fa0ca39 100644 --- a/embassy-stm32/src/rcc/g0.rs +++ b/embassy-stm32/src/rcc/g0.rs | |||
| @@ -116,17 +116,18 @@ pub struct PllFreq { | |||
| 116 | } | 116 | } |
| 117 | 117 | ||
| 118 | pub(crate) unsafe fn init(config: Config) { | 118 | pub(crate) unsafe fn init(config: Config) { |
| 119 | // Turn on the HSI | ||
| 120 | RCC.cr().modify(|w| w.set_hsion(true)); | ||
| 121 | while !RCC.cr().read().hsirdy() {} | ||
| 122 | |||
| 123 | // Use the HSI clock as system clock during the actual clock setup | ||
| 124 | RCC.cfgr().modify(|w| w.set_sw(Sysclk::HSI)); | ||
| 125 | while RCC.cfgr().read().sws() != Sysclk::HSI {} | ||
| 126 | |||
| 119 | // Configure HSI | 127 | // Configure HSI |
| 120 | let hsi = match config.hsi { | 128 | let hsi = match config.hsi { |
| 121 | false => { | 129 | false => None, |
| 122 | RCC.cr().modify(|w| w.set_hsion(false)); | 130 | true => Some(HSI_FREQ), |
| 123 | None | ||
| 124 | } | ||
| 125 | true => { | ||
| 126 | RCC.cr().modify(|w| w.set_hsion(true)); | ||
| 127 | while !RCC.cr().read().hsirdy() {} | ||
| 128 | Some(HSI_FREQ) | ||
| 129 | } | ||
| 130 | }; | 131 | }; |
| 131 | 132 | ||
| 132 | // Configure HSE | 133 | // Configure HSE |
| @@ -259,6 +260,12 @@ pub(crate) unsafe fn init(config: Config) { | |||
| 259 | w.set_hpre(config.ahb_pre); | 260 | w.set_hpre(config.ahb_pre); |
| 260 | w.set_ppre(config.apb1_pre); | 261 | w.set_ppre(config.apb1_pre); |
| 261 | }); | 262 | }); |
| 263 | while RCC.cfgr().read().sws() != config.sys {} | ||
| 264 | |||
| 265 | // Disable HSI if not used | ||
| 266 | if !config.hsi { | ||
| 267 | RCC.cr().modify(|w| w.set_hsion(false)); | ||
| 268 | } | ||
| 262 | 269 | ||
| 263 | if config.low_power_run { | 270 | if config.low_power_run { |
| 264 | assert!(sys <= Hertz(2_000_000)); | 271 | assert!(sys <= Hertz(2_000_000)); |
diff --git a/embassy-stm32/src/rcc/g4.rs b/embassy-stm32/src/rcc/g4.rs index cd2d2a8a2..c261c0fed 100644 --- a/embassy-stm32/src/rcc/g4.rs +++ b/embassy-stm32/src/rcc/g4.rs | |||
| @@ -117,17 +117,18 @@ pub struct PllFreq { | |||
| 117 | } | 117 | } |
| 118 | 118 | ||
| 119 | pub(crate) unsafe fn init(config: Config) { | 119 | pub(crate) unsafe fn init(config: Config) { |
| 120 | // Turn on the HSI | ||
| 121 | RCC.cr().modify(|w| w.set_hsion(true)); | ||
| 122 | while !RCC.cr().read().hsirdy() {} | ||
| 123 | |||
| 124 | // Use the HSI clock as system clock during the actual clock setup | ||
| 125 | RCC.cfgr().modify(|w| w.set_sw(Sysclk::HSI)); | ||
| 126 | while RCC.cfgr().read().sws() != Sysclk::HSI {} | ||
| 127 | |||
| 120 | // Configure HSI | 128 | // Configure HSI |
| 121 | let hsi = match config.hsi { | 129 | let hsi = match config.hsi { |
| 122 | false => { | 130 | false => None, |
| 123 | RCC.cr().modify(|w| w.set_hsion(false)); | 131 | true => Some(HSI_FREQ), |
| 124 | None | ||
| 125 | } | ||
| 126 | true => { | ||
| 127 | RCC.cr().modify(|w| w.set_hsion(true)); | ||
| 128 | while !RCC.cr().read().hsirdy() {} | ||
| 129 | Some(HSI_FREQ) | ||
| 130 | } | ||
| 131 | }; | 132 | }; |
| 132 | 133 | ||
| 133 | // Configure HSE | 134 | // Configure HSE |
| @@ -285,6 +286,12 @@ pub(crate) unsafe fn init(config: Config) { | |||
| 285 | w.set_ppre1(config.apb1_pre); | 286 | w.set_ppre1(config.apb1_pre); |
| 286 | w.set_ppre2(config.apb2_pre); | 287 | w.set_ppre2(config.apb2_pre); |
| 287 | }); | 288 | }); |
| 289 | while RCC.cfgr().read().sws() != config.sys {} | ||
| 290 | |||
| 291 | // Disable HSI if not used | ||
| 292 | if !config.hsi { | ||
| 293 | RCC.cr().modify(|w| w.set_hsion(false)); | ||
| 294 | } | ||
| 288 | 295 | ||
| 289 | if config.low_power_run { | 296 | if config.low_power_run { |
| 290 | assert!(sys <= Hertz(2_000_000)); | 297 | assert!(sys <= Hertz(2_000_000)); |
diff --git a/embassy-stm32/src/rcc/h.rs b/embassy-stm32/src/rcc/h.rs index 4d7004872..e3c7dd158 100644 --- a/embassy-stm32/src/rcc/h.rs +++ b/embassy-stm32/src/rcc/h.rs | |||
| @@ -402,20 +402,24 @@ pub(crate) unsafe fn init(config: Config) { | |||
| 402 | } | 402 | } |
| 403 | } | 403 | } |
| 404 | 404 | ||
| 405 | // Turn on the HSI | ||
| 406 | match config.hsi { | ||
| 407 | None => RCC.cr().modify(|w| w.set_hsion(true)), | ||
| 408 | Some(hsidiv) => RCC.cr().modify(|w| { | ||
| 409 | w.set_hsidiv(hsidiv); | ||
| 410 | w.set_hsion(true); | ||
| 411 | }), | ||
| 412 | } | ||
| 413 | while !RCC.cr().read().hsirdy() {} | ||
| 414 | |||
| 415 | // Use the HSI clock as system clock during the actual clock setup | ||
| 416 | RCC.cfgr().modify(|w| w.set_sw(Sysclk::HSI)); | ||
| 417 | while RCC.cfgr().read().sws() != Sysclk::HSI {} | ||
| 418 | |||
| 405 | // Configure HSI | 419 | // Configure HSI |
| 406 | let hsi = match config.hsi { | 420 | let hsi = match config.hsi { |
| 407 | None => { | 421 | None => None, |
| 408 | RCC.cr().modify(|w| w.set_hsion(false)); | 422 | Some(hsidiv) => Some(HSI_FREQ / hsidiv), |
| 409 | None | ||
| 410 | } | ||
| 411 | Some(hsidiv) => { | ||
| 412 | RCC.cr().modify(|w| { | ||
| 413 | w.set_hsidiv(hsidiv); | ||
| 414 | w.set_hsion(true); | ||
| 415 | }); | ||
| 416 | while !RCC.cr().read().hsirdy() {} | ||
| 417 | Some(HSI_FREQ / hsidiv) | ||
| 418 | } | ||
| 419 | }; | 423 | }; |
| 420 | 424 | ||
| 421 | // Configure HSE | 425 | // Configure HSE |
| @@ -608,6 +612,11 @@ pub(crate) unsafe fn init(config: Config) { | |||
| 608 | RCC.cfgr().modify(|w| w.set_sw(config.sys)); | 612 | RCC.cfgr().modify(|w| w.set_sw(config.sys)); |
| 609 | while RCC.cfgr().read().sws() != config.sys {} | 613 | while RCC.cfgr().read().sws() != config.sys {} |
| 610 | 614 | ||
| 615 | // Disable HSI if not used | ||
| 616 | if config.hsi.is_none() { | ||
| 617 | RCC.cr().modify(|w| w.set_hsion(false)); | ||
| 618 | } | ||
| 619 | |||
| 611 | // IO compensation cell - Requires CSI clock and SYSCFG | 620 | // IO compensation cell - Requires CSI clock and SYSCFG |
| 612 | #[cfg(any(stm32h7))] // TODO h5, h7rs | 621 | #[cfg(any(stm32h7))] // TODO h5, h7rs |
| 613 | if csi.is_some() { | 622 | if csi.is_some() { |
