aboutsummaryrefslogtreecommitdiff
path: root/embassy-stm32/src
diff options
context:
space:
mode:
Diffstat (limited to 'embassy-stm32/src')
-rw-r--r--embassy-stm32/src/flash/h7.rs12
-rw-r--r--embassy-stm32/src/flash/mod.rs4
-rw-r--r--embassy-stm32/src/rcc/h7.rs49
3 files changed, 60 insertions, 5 deletions
diff --git a/embassy-stm32/src/flash/h7.rs b/embassy-stm32/src/flash/h7.rs
index bb429d773..625bf13fc 100644
--- a/embassy-stm32/src/flash/h7.rs
+++ b/embassy-stm32/src/flash/h7.rs
@@ -11,7 +11,7 @@ pub const fn is_default_layout() -> bool {
11} 11}
12 12
13const fn is_dual_bank() -> bool { 13const fn is_dual_bank() -> bool {
14 FLASH_REGIONS.len() == 2 14 FLASH_REGIONS.len() >= 2
15} 15}
16 16
17pub fn get_flash_regions() -> &'static [&'static FlashRegion] { 17pub fn get_flash_regions() -> &'static [&'static FlashRegion] {
@@ -49,6 +49,7 @@ pub(crate) unsafe fn blocking_write(start_address: u32, buf: &[u8; WRITE_SIZE])
49 }; 49 };
50 bank.cr().write(|w| { 50 bank.cr().write(|w| {
51 w.set_pg(true); 51 w.set_pg(true);
52 #[cfg(flash_h7)]
52 w.set_psize(2); // 32 bits at once 53 w.set_psize(2); // 32 bits at once
53 }); 54 });
54 cortex_m::asm::isb(); 55 cortex_m::asm::isb();
@@ -85,7 +86,10 @@ pub(crate) unsafe fn blocking_erase_sector(sector: &FlashSector) -> Result<(), E
85 let bank = pac::FLASH.bank(sector.bank as usize); 86 let bank = pac::FLASH.bank(sector.bank as usize);
86 bank.cr().modify(|w| { 87 bank.cr().modify(|w| {
87 w.set_ser(true); 88 w.set_ser(true);
88 w.set_snb(sector.index_in_bank) 89 #[cfg(flash_h7)]
90 w.set_snb(sector.index_in_bank);
91 #[cfg(flash_h7ab)]
92 w.set_ssn(sector.index_in_bank);
89 }); 93 });
90 94
91 bank.cr().modify(|w| { 95 bank.cr().modify(|w| {
@@ -126,6 +130,10 @@ unsafe fn blocking_wait_ready(bank: pac::flash::Bank) -> Result<(), Error> {
126 error!("incerr"); 130 error!("incerr");
127 return Err(Error::Seq); 131 return Err(Error::Seq);
128 } 132 }
133 if sr.crcrderr() {
134 error!("crcrderr");
135 return Err(Error::Seq);
136 }
129 if sr.operr() { 137 if sr.operr() {
130 return Err(Error::Prog); 138 return Err(Error::Prog);
131 } 139 }
diff --git a/embassy-stm32/src/flash/mod.rs b/embassy-stm32/src/flash/mod.rs
index 4308037f2..fb20dcd38 100644
--- a/embassy-stm32/src/flash/mod.rs
+++ b/embassy-stm32/src/flash/mod.rs
@@ -65,9 +65,11 @@ impl FlashRegion {
65#[cfg_attr(flash_f7, path = "f7.rs")] 65#[cfg_attr(flash_f7, path = "f7.rs")]
66#[cfg_attr(flash_g0, path = "g0.rs")] 66#[cfg_attr(flash_g0, path = "g0.rs")]
67#[cfg_attr(flash_h7, path = "h7.rs")] 67#[cfg_attr(flash_h7, path = "h7.rs")]
68#[cfg_attr(flash_h7ab, path = "h7.rs")]
68#[cfg_attr( 69#[cfg_attr(
69 not(any( 70 not(any(
70 flash_l0, flash_l1, flash_l4, flash_wl, flash_wb, flash_f0, flash_f3, flash_f4, flash_f7, flash_g0, flash_h7 71 flash_l0, flash_l1, flash_l4, flash_wl, flash_wb, flash_f0, flash_f3, flash_f4, flash_f7, flash_g0, flash_h7,
72 flash_h7ab
71 )), 73 )),
72 path = "other.rs" 74 path = "other.rs"
73)] 75)]
diff --git a/embassy-stm32/src/rcc/h7.rs b/embassy-stm32/src/rcc/h7.rs
index 0788b0640..7fb4fb95b 100644
--- a/embassy-stm32/src/rcc/h7.rs
+++ b/embassy-stm32/src/rcc/h7.rs
@@ -200,6 +200,7 @@ fn flash_setup(rcc_aclk: u32, vos: VoltageScale) {
200 200
201 // See RM0433 Rev 7 Table 17. FLASH recommended number of wait 201 // See RM0433 Rev 7 Table 17. FLASH recommended number of wait
202 // states and programming delay 202 // states and programming delay
203 #[cfg(flash_h7)]
203 let (wait_states, progr_delay) = match vos { 204 let (wait_states, progr_delay) = match vos {
204 // VOS 0 range VCORE 1.26V - 1.40V 205 // VOS 0 range VCORE 1.26V - 1.40V
205 VoltageScale::Scale0 => match rcc_aclk_mhz { 206 VoltageScale::Scale0 => match rcc_aclk_mhz {
@@ -239,6 +240,50 @@ fn flash_setup(rcc_aclk: u32, vos: VoltageScale) {
239 }, 240 },
240 }; 241 };
241 242
243 // See RM0455 Rev 10 Table 16. FLASH recommended number of wait
244 // states and programming delay
245 #[cfg(flash_h7ab)]
246 let (wait_states, progr_delay) = match vos {
247 // VOS 0 range VCORE 1.25V - 1.35V
248 VoltageScale::Scale0 => match rcc_aclk_mhz {
249 0..=42 => (0, 0),
250 43..=84 => (1, 0),
251 85..=126 => (2, 1),
252 127..=168 => (3, 1),
253 169..=210 => (4, 2),
254 211..=252 => (5, 2),
255 253..=280 => (6, 3),
256 _ => (7, 3),
257 },
258 // VOS 1 range VCORE 1.15V - 1.25V
259 VoltageScale::Scale1 => match rcc_aclk_mhz {
260 0..=38 => (0, 0),
261 39..=76 => (1, 0),
262 77..=114 => (2, 1),
263 115..=152 => (3, 1),
264 153..=190 => (4, 2),
265 191..=225 => (5, 2),
266 _ => (7, 3),
267 },
268 // VOS 2 range VCORE 1.05V - 1.15V
269 VoltageScale::Scale2 => match rcc_aclk_mhz {
270 0..=34 => (0, 0),
271 35..=68 => (1, 0),
272 69..=102 => (2, 1),
273 103..=136 => (3, 1),
274 137..=160 => (4, 2),
275 _ => (7, 3),
276 },
277 // VOS 3 range VCORE 0.95V - 1.05V
278 VoltageScale::Scale3 => match rcc_aclk_mhz {
279 0..=22 => (0, 0),
280 23..=44 => (1, 0),
281 45..=66 => (2, 1),
282 67..=88 => (3, 1),
283 _ => (7, 3),
284 },
285 };
286
242 FLASH.acr().write(|w| { 287 FLASH.acr().write(|w| {
243 w.set_wrhighfreq(progr_delay); 288 w.set_wrhighfreq(progr_delay);
244 w.set_latency(wait_states) 289 w.set_latency(wait_states)
@@ -538,8 +583,6 @@ pub(crate) unsafe fn init(mut config: Config) {
538 let requested_pclk4 = config.pclk4.map(|v| v.0).unwrap_or_else(|| pclk_max.min(rcc_hclk / 2)); 583 let requested_pclk4 = config.pclk4.map(|v| v.0).unwrap_or_else(|| pclk_max.min(rcc_hclk / 2));
539 let (rcc_pclk4, ppre4_bits, ppre4, _) = ppre_calculate(requested_pclk4, rcc_hclk, pclk_max, None); 584 let (rcc_pclk4, ppre4_bits, ppre4, _) = ppre_calculate(requested_pclk4, rcc_hclk, pclk_max, None);
540 585
541 flash_setup(rcc_aclk, pwr_vos);
542
543 // Start switching clocks ------------------- 586 // Start switching clocks -------------------
544 587
545 // Ensure CSI is on and stable 588 // Ensure CSI is on and stable
@@ -595,6 +638,8 @@ pub(crate) unsafe fn init(mut config: Config) {
595 // core voltage 638 // core voltage
596 while RCC.d1cfgr().read().d1cpre().to_bits() != d1cpre_bits {} 639 while RCC.d1cfgr().read().d1cpre().to_bits() != d1cpre_bits {}
597 640
641 flash_setup(rcc_aclk, pwr_vos);
642
598 // APB1 / APB2 Prescaler 643 // APB1 / APB2 Prescaler
599 RCC.d2cfgr().modify(|w| { 644 RCC.d2cfgr().modify(|w| {
600 w.set_d2ppre1(Dppre::from_bits(ppre1_bits)); 645 w.set_d2ppre1(Dppre::from_bits(ppre1_bits));