Skip to content

Commit cad142a

Browse files
committed
Rework PLL calculation for system clock
Initially this should fix the case, that the system clock calculation assumed that HSI was always devided by 2 for any device. As the initial state hat some problems this ended up being a rework of the PLL calculation to resemble the clock tree setup of stm32f3xx mitrockrollers more closely. The difference between different devices can be divided into two categories: 1. Devices which have the possibility to configure HSI dividend The clock tree of the stm32f303xd as an example: https://www.st.com/content/ccc/resource/technical/document/reference_manual/4a/19/6e/18/9d/92/43/32/DM00043574.pdf/files/DM00043574.pdf/jcr:content/translations/en.DM00043574.pdf#page=127 2. Devices which always divide HSI by 2 The clock tree of the stm32f303x6 as an example: https://www.st.com/content/ccc/resource/technical/document/reference_manual/4a/19/6e/18/9d/92/43/32/DM00043574.pdf/files/DM00043574.pdf/jcr:content/translations/en.DM00043574.pdf#page=128 For [1] the HSI is not initially divided by 2 and both HSE and HSI can be changed via divisor block (PRE_DVI) and multiplier block (PLL_MUL). For [2] the HSI is **always** divided by by 2 and the divisor can only be used for the HSE. These differences also apply to the stm32f302x{b,c,d,e}, so these targets get added as a feature. With this rewrite it is now possible to get more fine grained control over the system clock we can choose. To find out the optimal values for both the multiplier and the divisor, a greatest common divisor calculation is used. Some examples: - If you want 72 Mhz system clock out of 32 Mhz oscillator clock the common divisor would be 8. Represented in a fraction this would look like this: 72 / 32 = (72 / 8) / (32 / 8) = 9 / 4 These values can be represented in the divisor and multiplier block, as these can take values up to 16. - If you want 26 Mhz system clock out of 8 Mhz oscillator clock the common divisor would be 2. Represented in a fraction this would look like this: 26 / 8 = (26 / 2) / (8 / 2) = 13 / 4
1 parent 20f42cc commit cad142a

File tree

2 files changed

+276
-68
lines changed

2 files changed

+276
-68
lines changed

CHANGELOG.md

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,32 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
77

88
## [Unreleased]
99

10+
### Fixed
11+
12+
- `PLL` was calculated wrong for devices, which do not divide `HSI` ([#67](https://github.com/stm32-rs/stm32f3xx-hal/pull/67))
13+
1014
### Changed
1115

1216
- **Breaking** The feature gate requires you to select a subvaraint if possible. ([#67](https://github.com/stm32-rs/stm32f3xx-hal/pull/67))
1317
- **Breaking** Split up `stm32f302` into sub-targets `stm32f302xb`,`stm32f302xc`,`stm32f302xd`,`stm32f302xe`
18+
- The system clock calculation is more fine grained now. ([#67](https://github.com/stm32-rs/stm32f3xx-hal/pull/67))
19+
Now the system clock can be some value, like 14 MHz, which can not a
20+
be represented as a multiple of the oscillator clock:
21+
```rust
22+
let clocks = rcc
23+
.cfgr
24+
.use_hse(8.mhz())
25+
.sysclk(14.mhz())
26+
27+
// or
28+
let clocks = rcc
29+
.cfgr
30+
.use_hse(32.mhz())
31+
.sysclk(72.mhz())
32+
```
33+
This is possible through utilizing the divider, which can devide the
34+
external oscillator clock on most devices. Some devices have even the
35+
possibility to divide the internal oscillator clock.
1436

1537
## [v0.4.3] - 2020-04-11
1638

0 commit comments

Comments
 (0)