Merge pull request #3158 from diondokter/stm-dualcore

Stm dualcore better init
This commit is contained in:
Ulf Lilleengen 2024-08-05 13:18:45 +00:00 committed by GitHub
commit 059c7b582c
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
55 changed files with 737 additions and 108 deletions

8
ci.sh
View File

@ -179,7 +179,7 @@ cargo batch \
--- build --release --manifest-path embassy-boot-nrf/Cargo.toml --target thumbv8m.main-none-eabihf --features embassy-nrf/nrf9160-ns \
--- build --release --manifest-path embassy-boot-nrf/Cargo.toml --target thumbv8m.main-none-eabihf --features embassy-nrf/nrf9120-ns \
--- build --release --manifest-path embassy-boot-rp/Cargo.toml --target thumbv6m-none-eabi \
--- build --release --manifest-path embassy-boot-stm32/Cargo.toml --target thumbv7em-none-eabi --features embassy-stm32/stm32wl55jc-cm4 \
--- build --release --manifest-path embassy-boot-stm32/Cargo.toml --target thumbv7em-none-eabi --features embassy-stm32/stm32l496zg \
--- build --release --manifest-path docs/examples/basic/Cargo.toml --target thumbv7em-none-eabi \
--- build --release --manifest-path docs/examples/layer-by-layer/blinky-pac/Cargo.toml --target thumbv7em-none-eabi \
--- build --release --manifest-path docs/examples/layer-by-layer/blinky-hal/Cargo.toml --target thumbv7em-none-eabi \
@ -207,6 +207,8 @@ cargo batch \
--- build --release --manifest-path examples/stm32h5/Cargo.toml --target thumbv8m.main-none-eabihf --out-dir out/examples/stm32h5 \
--- build --release --manifest-path examples/stm32h7/Cargo.toml --target thumbv7em-none-eabi --out-dir out/examples/stm32h7 \
--- build --release --manifest-path examples/stm32h735/Cargo.toml --target thumbv7em-none-eabi --out-dir out/examples/stm32h735 \
--- build --release --manifest-path examples/stm32h755cm4/Cargo.toml --target thumbv7em-none-eabi --out-dir out/examples/stm32h755cm4 \
--- build --release --manifest-path examples/stm32h755cm7/Cargo.toml --target thumbv7em-none-eabi --out-dir out/examples/stm32h755cm7 \
--- build --release --manifest-path examples/stm32h7rs/Cargo.toml --target thumbv7em-none-eabi --out-dir out/examples/stm32h7rs \
--- build --release --manifest-path examples/stm32l0/Cargo.toml --target thumbv6m-none-eabi --out-dir out/examples/stm32l0 \
--- build --release --manifest-path examples/stm32l1/Cargo.toml --target thumbv7m-none-eabi --out-dir out/examples/stm32l1 \
@ -233,9 +235,9 @@ cargo batch \
--- build --release --manifest-path examples/boot/bootloader/nrf/Cargo.toml --target thumbv8m.main-none-eabihf --features embassy-nrf/nrf9160-ns \
--- build --release --manifest-path examples/boot/bootloader/nrf/Cargo.toml --target thumbv8m.main-none-eabihf --features embassy-nrf/nrf9120-ns \
--- build --release --manifest-path examples/boot/bootloader/rp/Cargo.toml --target thumbv6m-none-eabi \
--- build --release --manifest-path examples/boot/bootloader/stm32/Cargo.toml --target thumbv7em-none-eabi --features embassy-stm32/stm32wl55jc-cm4 \
--- build --release --manifest-path examples/boot/bootloader/stm32/Cargo.toml --target thumbv7em-none-eabi --features embassy-stm32/stm32l496zg \
--- build --release --manifest-path examples/boot/bootloader/stm32wb-dfu/Cargo.toml --target thumbv7em-none-eabi --features embassy-stm32/stm32wb55rg \
--- build --release --manifest-path examples/boot/bootloader/stm32-dual-bank/Cargo.toml --target thumbv7em-none-eabi --features embassy-stm32/stm32h747xi-cm7 \
--- build --release --manifest-path examples/boot/bootloader/stm32-dual-bank/Cargo.toml --target thumbv7em-none-eabi --features embassy-stm32/stm32h743zi \
--- build --release --manifest-path examples/wasm/Cargo.toml --target wasm32-unknown-unknown --out-dir out/examples/wasm \
--- build --release --manifest-path tests/stm32/Cargo.toml --target thumbv7m-none-eabi --features stm32f103c8 --out-dir out/tests/stm32f103c8 \
--- build --release --manifest-path tests/stm32/Cargo.toml --target thumbv7em-none-eabi --features stm32f429zi --out-dir out/tests/stm32f429zi \

View File

@ -80,7 +80,7 @@ stm32-fmc = "0.3.0"
cfg-if = "1.0.0"
embedded-io = { version = "0.6.0" }
embedded-io-async = { version = "0.6.1" }
chrono = { version = "^0.4", default-features = false, optional = true}
chrono = { version = "^0.4", default-features = false, optional = true }
bit_field = "0.10.2"
document-features = "0.2.7"
@ -181,6 +181,9 @@ split-pc3 = ["_split-pins-enabled"]
## internal use only
_split-pins-enabled = []
## internal use only
_dual-core = []
#! ## Chip-selection features
#! Select your chip by specifying the model as a feature, e.g. `stm32c011d6`.
#! Check the `Cargo.toml` for the latest list of supported chips.
@ -1004,40 +1007,40 @@ stm32h743xg = [ "stm32-metapac/stm32h743xg" ]
stm32h743xi = [ "stm32-metapac/stm32h743xi" ]
stm32h743zg = [ "stm32-metapac/stm32h743zg" ]
stm32h743zi = [ "stm32-metapac/stm32h743zi" ]
stm32h745bg-cm7 = [ "stm32-metapac/stm32h745bg-cm7" ]
stm32h745bg-cm4 = [ "stm32-metapac/stm32h745bg-cm4" ]
stm32h745bi-cm7 = [ "stm32-metapac/stm32h745bi-cm7" ]
stm32h745bi-cm4 = [ "stm32-metapac/stm32h745bi-cm4" ]
stm32h745ig-cm7 = [ "stm32-metapac/stm32h745ig-cm7" ]
stm32h745ig-cm4 = [ "stm32-metapac/stm32h745ig-cm4" ]
stm32h745ii-cm7 = [ "stm32-metapac/stm32h745ii-cm7" ]
stm32h745ii-cm4 = [ "stm32-metapac/stm32h745ii-cm4" ]
stm32h745xg-cm7 = [ "stm32-metapac/stm32h745xg-cm7" ]
stm32h745xg-cm4 = [ "stm32-metapac/stm32h745xg-cm4" ]
stm32h745xi-cm7 = [ "stm32-metapac/stm32h745xi-cm7" ]
stm32h745xi-cm4 = [ "stm32-metapac/stm32h745xi-cm4" ]
stm32h745zg-cm7 = [ "stm32-metapac/stm32h745zg-cm7" ]
stm32h745zg-cm4 = [ "stm32-metapac/stm32h745zg-cm4" ]
stm32h745zi-cm7 = [ "stm32-metapac/stm32h745zi-cm7" ]
stm32h745zi-cm4 = [ "stm32-metapac/stm32h745zi-cm4" ]
stm32h747ag-cm7 = [ "stm32-metapac/stm32h747ag-cm7" ]
stm32h747ag-cm4 = [ "stm32-metapac/stm32h747ag-cm4" ]
stm32h747ai-cm7 = [ "stm32-metapac/stm32h747ai-cm7" ]
stm32h747ai-cm4 = [ "stm32-metapac/stm32h747ai-cm4" ]
stm32h747bg-cm7 = [ "stm32-metapac/stm32h747bg-cm7" ]
stm32h747bg-cm4 = [ "stm32-metapac/stm32h747bg-cm4" ]
stm32h747bi-cm7 = [ "stm32-metapac/stm32h747bi-cm7" ]
stm32h747bi-cm4 = [ "stm32-metapac/stm32h747bi-cm4" ]
stm32h747ig-cm7 = [ "stm32-metapac/stm32h747ig-cm7" ]
stm32h747ig-cm4 = [ "stm32-metapac/stm32h747ig-cm4" ]
stm32h747ii-cm7 = [ "stm32-metapac/stm32h747ii-cm7" ]
stm32h747ii-cm4 = [ "stm32-metapac/stm32h747ii-cm4" ]
stm32h747xg-cm7 = [ "stm32-metapac/stm32h747xg-cm7" ]
stm32h747xg-cm4 = [ "stm32-metapac/stm32h747xg-cm4" ]
stm32h747xi-cm7 = [ "stm32-metapac/stm32h747xi-cm7" ]
stm32h747xi-cm4 = [ "stm32-metapac/stm32h747xi-cm4" ]
stm32h747zi-cm7 = [ "stm32-metapac/stm32h747zi-cm7" ]
stm32h747zi-cm4 = [ "stm32-metapac/stm32h747zi-cm4" ]
stm32h745bg-cm7 = [ "stm32-metapac/stm32h745bg-cm7", "_dual-core" ]
stm32h745bg-cm4 = [ "stm32-metapac/stm32h745bg-cm4", "_dual-core" ]
stm32h745bi-cm7 = [ "stm32-metapac/stm32h745bi-cm7", "_dual-core" ]
stm32h745bi-cm4 = [ "stm32-metapac/stm32h745bi-cm4", "_dual-core" ]
stm32h745ig-cm7 = [ "stm32-metapac/stm32h745ig-cm7", "_dual-core" ]
stm32h745ig-cm4 = [ "stm32-metapac/stm32h745ig-cm4", "_dual-core" ]
stm32h745ii-cm7 = [ "stm32-metapac/stm32h745ii-cm7", "_dual-core" ]
stm32h745ii-cm4 = [ "stm32-metapac/stm32h745ii-cm4", "_dual-core" ]
stm32h745xg-cm7 = [ "stm32-metapac/stm32h745xg-cm7", "_dual-core" ]
stm32h745xg-cm4 = [ "stm32-metapac/stm32h745xg-cm4", "_dual-core" ]
stm32h745xi-cm7 = [ "stm32-metapac/stm32h745xi-cm7", "_dual-core" ]
stm32h745xi-cm4 = [ "stm32-metapac/stm32h745xi-cm4", "_dual-core" ]
stm32h745zg-cm7 = [ "stm32-metapac/stm32h745zg-cm7", "_dual-core" ]
stm32h745zg-cm4 = [ "stm32-metapac/stm32h745zg-cm4", "_dual-core" ]
stm32h745zi-cm7 = [ "stm32-metapac/stm32h745zi-cm7", "_dual-core" ]
stm32h745zi-cm4 = [ "stm32-metapac/stm32h745zi-cm4", "_dual-core" ]
stm32h747ag-cm7 = [ "stm32-metapac/stm32h747ag-cm7", "_dual-core" ]
stm32h747ag-cm4 = [ "stm32-metapac/stm32h747ag-cm4", "_dual-core" ]
stm32h747ai-cm7 = [ "stm32-metapac/stm32h747ai-cm7", "_dual-core" ]
stm32h747ai-cm4 = [ "stm32-metapac/stm32h747ai-cm4", "_dual-core" ]
stm32h747bg-cm7 = [ "stm32-metapac/stm32h747bg-cm7", "_dual-core" ]
stm32h747bg-cm4 = [ "stm32-metapac/stm32h747bg-cm4", "_dual-core" ]
stm32h747bi-cm7 = [ "stm32-metapac/stm32h747bi-cm7", "_dual-core" ]
stm32h747bi-cm4 = [ "stm32-metapac/stm32h747bi-cm4", "_dual-core" ]
stm32h747ig-cm7 = [ "stm32-metapac/stm32h747ig-cm7", "_dual-core" ]
stm32h747ig-cm4 = [ "stm32-metapac/stm32h747ig-cm4", "_dual-core" ]
stm32h747ii-cm7 = [ "stm32-metapac/stm32h747ii-cm7", "_dual-core" ]
stm32h747ii-cm4 = [ "stm32-metapac/stm32h747ii-cm4", "_dual-core" ]
stm32h747xg-cm7 = [ "stm32-metapac/stm32h747xg-cm7", "_dual-core" ]
stm32h747xg-cm4 = [ "stm32-metapac/stm32h747xg-cm4", "_dual-core" ]
stm32h747xi-cm7 = [ "stm32-metapac/stm32h747xi-cm7", "_dual-core" ]
stm32h747xi-cm4 = [ "stm32-metapac/stm32h747xi-cm4", "_dual-core" ]
stm32h747zi-cm7 = [ "stm32-metapac/stm32h747zi-cm7", "_dual-core" ]
stm32h747zi-cm4 = [ "stm32-metapac/stm32h747zi-cm4", "_dual-core" ]
stm32h750ib = [ "stm32-metapac/stm32h750ib" ]
stm32h750vb = [ "stm32-metapac/stm32h750vb" ]
stm32h750xb = [ "stm32-metapac/stm32h750xb" ]
@ -1048,24 +1051,24 @@ stm32h753ii = [ "stm32-metapac/stm32h753ii" ]
stm32h753vi = [ "stm32-metapac/stm32h753vi" ]
stm32h753xi = [ "stm32-metapac/stm32h753xi" ]
stm32h753zi = [ "stm32-metapac/stm32h753zi" ]
stm32h755bi-cm7 = [ "stm32-metapac/stm32h755bi-cm7" ]
stm32h755bi-cm4 = [ "stm32-metapac/stm32h755bi-cm4" ]
stm32h755ii-cm7 = [ "stm32-metapac/stm32h755ii-cm7" ]
stm32h755ii-cm4 = [ "stm32-metapac/stm32h755ii-cm4" ]
stm32h755xi-cm7 = [ "stm32-metapac/stm32h755xi-cm7" ]
stm32h755xi-cm4 = [ "stm32-metapac/stm32h755xi-cm4" ]
stm32h755zi-cm7 = [ "stm32-metapac/stm32h755zi-cm7" ]
stm32h755zi-cm4 = [ "stm32-metapac/stm32h755zi-cm4" ]
stm32h757ai-cm7 = [ "stm32-metapac/stm32h757ai-cm7" ]
stm32h757ai-cm4 = [ "stm32-metapac/stm32h757ai-cm4" ]
stm32h757bi-cm7 = [ "stm32-metapac/stm32h757bi-cm7" ]
stm32h757bi-cm4 = [ "stm32-metapac/stm32h757bi-cm4" ]
stm32h757ii-cm7 = [ "stm32-metapac/stm32h757ii-cm7" ]
stm32h757ii-cm4 = [ "stm32-metapac/stm32h757ii-cm4" ]
stm32h757xi-cm7 = [ "stm32-metapac/stm32h757xi-cm7" ]
stm32h757xi-cm4 = [ "stm32-metapac/stm32h757xi-cm4" ]
stm32h757zi-cm7 = [ "stm32-metapac/stm32h757zi-cm7" ]
stm32h757zi-cm4 = [ "stm32-metapac/stm32h757zi-cm4" ]
stm32h755bi-cm7 = [ "stm32-metapac/stm32h755bi-cm7", "_dual-core" ]
stm32h755bi-cm4 = [ "stm32-metapac/stm32h755bi-cm4", "_dual-core" ]
stm32h755ii-cm7 = [ "stm32-metapac/stm32h755ii-cm7", "_dual-core" ]
stm32h755ii-cm4 = [ "stm32-metapac/stm32h755ii-cm4", "_dual-core" ]
stm32h755xi-cm7 = [ "stm32-metapac/stm32h755xi-cm7", "_dual-core" ]
stm32h755xi-cm4 = [ "stm32-metapac/stm32h755xi-cm4", "_dual-core" ]
stm32h755zi-cm7 = [ "stm32-metapac/stm32h755zi-cm7", "_dual-core" ]
stm32h755zi-cm4 = [ "stm32-metapac/stm32h755zi-cm4", "_dual-core" ]
stm32h757ai-cm7 = [ "stm32-metapac/stm32h757ai-cm7", "_dual-core" ]
stm32h757ai-cm4 = [ "stm32-metapac/stm32h757ai-cm4", "_dual-core" ]
stm32h757bi-cm7 = [ "stm32-metapac/stm32h757bi-cm7", "_dual-core" ]
stm32h757bi-cm4 = [ "stm32-metapac/stm32h757bi-cm4", "_dual-core" ]
stm32h757ii-cm7 = [ "stm32-metapac/stm32h757ii-cm7", "_dual-core" ]
stm32h757ii-cm4 = [ "stm32-metapac/stm32h757ii-cm4", "_dual-core" ]
stm32h757xi-cm7 = [ "stm32-metapac/stm32h757xi-cm7", "_dual-core" ]
stm32h757xi-cm4 = [ "stm32-metapac/stm32h757xi-cm4", "_dual-core" ]
stm32h757zi-cm7 = [ "stm32-metapac/stm32h757zi-cm7", "_dual-core" ]
stm32h757zi-cm4 = [ "stm32-metapac/stm32h757zi-cm4", "_dual-core" ]
stm32h7a3ag = [ "stm32-metapac/stm32h7a3ag" ]
stm32h7a3ai = [ "stm32-metapac/stm32h7a3ai" ]
stm32h7a3ig = [ "stm32-metapac/stm32h7a3ig" ]
@ -1598,14 +1601,14 @@ stm32wba55he = [ "stm32-metapac/stm32wba55he" ]
stm32wba55hg = [ "stm32-metapac/stm32wba55hg" ]
stm32wba55ue = [ "stm32-metapac/stm32wba55ue" ]
stm32wba55ug = [ "stm32-metapac/stm32wba55ug" ]
stm32wl54cc-cm4 = [ "stm32-metapac/stm32wl54cc-cm4" ]
stm32wl54cc-cm0p = [ "stm32-metapac/stm32wl54cc-cm0p" ]
stm32wl54jc-cm4 = [ "stm32-metapac/stm32wl54jc-cm4" ]
stm32wl54jc-cm0p = [ "stm32-metapac/stm32wl54jc-cm0p" ]
stm32wl55cc-cm4 = [ "stm32-metapac/stm32wl55cc-cm4" ]
stm32wl55cc-cm0p = [ "stm32-metapac/stm32wl55cc-cm0p" ]
stm32wl55jc-cm4 = [ "stm32-metapac/stm32wl55jc-cm4" ]
stm32wl55jc-cm0p = [ "stm32-metapac/stm32wl55jc-cm0p" ]
stm32wl54cc-cm4 = [ "stm32-metapac/stm32wl54cc-cm4", "_dual-core" ]
stm32wl54cc-cm0p = [ "stm32-metapac/stm32wl54cc-cm0p", "_dual-core" ]
stm32wl54jc-cm4 = [ "stm32-metapac/stm32wl54jc-cm4", "_dual-core" ]
stm32wl54jc-cm0p = [ "stm32-metapac/stm32wl54jc-cm0p", "_dual-core" ]
stm32wl55cc-cm4 = [ "stm32-metapac/stm32wl55cc-cm4", "_dual-core" ]
stm32wl55cc-cm0p = [ "stm32-metapac/stm32wl55cc-cm0p", "_dual-core" ]
stm32wl55jc-cm4 = [ "stm32-metapac/stm32wl55jc-cm4", "_dual-core" ]
stm32wl55jc-cm0p = [ "stm32-metapac/stm32wl55jc-cm0p", "_dual-core" ]
stm32wle4c8 = [ "stm32-metapac/stm32wle4c8" ]
stm32wle4cb = [ "stm32-metapac/stm32wle4cb" ]
stm32wle4cc = [ "stm32-metapac/stm32wle4cc" ]

View File

@ -480,7 +480,7 @@ fn main() {
self.clock_names.insert(name.to_ascii_lowercase());
quote!(unsafe {
unwrap!(
crate::rcc::get_freqs().#clock_name,
crate::rcc::get_freqs().#clock_name.to_hertz(),
"peripheral '{}' is configured to use the '{}' clock, which is not running. \
Either enable it in 'config.rcc' or change 'config.rcc.mux' to use another clock",
#peripheral,
@ -713,9 +713,10 @@ fn main() {
g.extend(quote! {
#[derive(Clone, Copy, Debug)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
#[repr(C)]
pub struct Clocks {
#(
pub #clock_idents: Option<crate::time::Hertz>,
pub #clock_idents: crate::time::MaybeHertz,
)*
}
});
@ -732,7 +733,7 @@ fn main() {
$($(#[$m])* $k: $v,)*
};
crate::rcc::set_freqs(crate::rcc::Clocks {
#( #clock_idents: all.#clock_idents, )*
#( #clock_idents: all.#clock_idents.into(), )*
});
}
};

View File

@ -78,7 +78,7 @@ pub(crate) fn blocking_delay_us(us: u32) {
embassy_time::block_for(embassy_time::Duration::from_micros(us as u64));
#[cfg(not(feature = "time"))]
{
let freq = unsafe { crate::rcc::get_freqs() }.sys.unwrap().0 as u64;
let freq = unsafe { crate::rcc::get_freqs() }.sys.to_hertz().unwrap().0 as u64;
let us = us as u64;
let cycles = freq * us / 1_000_000;
cortex_m::asm::delay(cycles as u32);

View File

@ -14,7 +14,7 @@ pub fn blocking_delay_ms(ms: u32) {
#[cfg(feature = "time")]
embassy_time::block_for(embassy_time::Duration::from_millis(ms as u64));
#[cfg(not(feature = "time"))]
cortex_m::asm::delay(unsafe { crate::rcc::get_freqs() }.sys.unwrap().0 / 1_000 * ms);
cortex_m::asm::delay(unsafe { crate::rcc::get_freqs() }.sys.to_hertz().unwrap().0 / 1_000 * ms);
}
/// PacketTypes extracted from CubeMX

View File

@ -273,7 +273,120 @@ impl Default for Config {
/// This returns the peripheral singletons that can be used for creating drivers.
///
/// This should only be called once at startup, otherwise it panics.
#[cfg(not(feature = "_dual-core"))]
pub fn init(config: Config) -> Peripherals {
init_hw(config)
}
#[cfg(feature = "_dual-core")]
mod dual_core {
use core::cell::UnsafeCell;
use core::mem::MaybeUninit;
use core::sync::atomic::{AtomicUsize, Ordering};
use rcc::Clocks;
use super::*;
/// Object containing data that embassy needs to share between cores.
///
/// It cannot be initialized by the user. The intended use is:
///
/// ```
/// #[link_section = ".ram_d3"]
/// static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
///
/// init_secondary(&SHARED_DATA);
/// ```
///
/// This static must be placed in the same position for both cores. How and where this is done is left to the user.
pub struct SharedData {
init_flag: AtomicUsize,
clocks: UnsafeCell<MaybeUninit<Clocks>>,
}
unsafe impl Sync for SharedData {}
const INIT_DONE_FLAG: usize = 0xca11ab1e;
/// Initialize the `embassy-stm32` HAL with the provided configuration.
/// This function does the actual initialization of the hardware, in contrast to [init_secondary] or [try_init_secondary].
/// Any core can do the init, but it's important only one core does it.
///
/// This returns the peripheral singletons that can be used for creating drivers.
///
/// This should only be called once at startup, otherwise it panics.
///
/// The `shared_data` is used to coordinate the init with the second core. Read the [SharedData] docs
/// for more information on its requirements.
pub fn init_primary(config: Config, shared_data: &'static MaybeUninit<SharedData>) -> Peripherals {
let shared_data = unsafe { shared_data.assume_init_ref() };
rcc::set_freqs_ptr(shared_data.clocks.get());
let p = init_hw(config);
shared_data.init_flag.store(INIT_DONE_FLAG, Ordering::SeqCst);
p
}
/// Try to initialize the `embassy-stm32` HAL based on the init done by the other core using [init_primary].
///
/// This returns the peripheral singletons that can be used for creating drivers if the other core is done with its init.
/// If the other core is not done yet, this will return `None`.
///
/// This should only be called once at startup, otherwise it may panic.
///
/// The `shared_data` is used to coordinate the init with the second core. Read the [SharedData] docs
/// for more information on its requirements.
pub fn try_init_secondary(shared_data: &'static MaybeUninit<SharedData>) -> Option<Peripherals> {
let shared_data = unsafe { shared_data.assume_init_ref() };
if shared_data.init_flag.load(Ordering::SeqCst) != INIT_DONE_FLAG {
return None;
}
// Separate load and store to support the CM0 of the STM32WL
shared_data.init_flag.store(0, Ordering::SeqCst);
Some(init_secondary_hw(shared_data))
}
/// Initialize the `embassy-stm32` HAL based on the init done by the other core using [init_primary].
///
/// This returns the peripheral singletons that can be used for creating drivers when the other core is done with its init.
/// If the other core is not done yet, this will spinloop wait on it.
///
/// This should only be called once at startup, otherwise it may panic.
///
/// The `shared_data` is used to coordinate the init with the second core. Read the [SharedData] docs
/// for more information on its requirements.
pub fn init_secondary(shared_data: &'static MaybeUninit<SharedData>) -> Peripherals {
loop {
if let Some(p) = try_init_secondary(shared_data) {
return p;
}
}
}
fn init_secondary_hw(shared_data: &'static SharedData) -> Peripherals {
rcc::set_freqs_ptr(shared_data.clocks.get());
// We use different timers on the different cores, so we have to still initialize one here
#[cfg(feature = "_time-driver")]
critical_section::with(|cs| {
// must be after rcc init
time_driver::init(cs);
});
Peripherals::take()
}
}
#[cfg(feature = "_dual-core")]
pub use dual_core::*;
fn init_hw(config: Config) -> Peripherals {
critical_section::with(|cs| {
let p = Peripherals::take_with_cs(cs);

View File

@ -48,11 +48,22 @@ pub(crate) static mut REFCOUNT_STOP1: u32 = 0;
/// May be read without a critical section
pub(crate) static mut REFCOUNT_STOP2: u32 = 0;
#[cfg(not(feature = "_dual-core"))]
/// Frozen clock frequencies
///
/// The existence of this value indicates that the clock configuration can no longer be changed
static mut CLOCK_FREQS: MaybeUninit<Clocks> = MaybeUninit::uninit();
#[cfg(feature = "_dual-core")]
static CLOCK_FREQS_PTR: core::sync::atomic::AtomicPtr<MaybeUninit<Clocks>> =
core::sync::atomic::AtomicPtr::new(core::ptr::null_mut());
#[cfg(feature = "_dual-core")]
pub(crate) fn set_freqs_ptr(freqs: *mut MaybeUninit<Clocks>) {
CLOCK_FREQS_PTR.store(freqs, core::sync::atomic::Ordering::SeqCst);
}
#[cfg(not(feature = "_dual-core"))]
/// Sets the clock frequencies
///
/// Safety: Sets a mutable global.
@ -61,11 +72,29 @@ pub(crate) unsafe fn set_freqs(freqs: Clocks) {
CLOCK_FREQS = MaybeUninit::new(freqs);
}
#[cfg(feature = "_dual-core")]
/// Sets the clock frequencies
///
/// Safety: Sets a mutable global.
pub(crate) unsafe fn set_freqs(freqs: Clocks) {
debug!("rcc: {:?}", freqs);
CLOCK_FREQS_PTR
.load(core::sync::atomic::Ordering::SeqCst)
.write(MaybeUninit::new(freqs));
}
#[cfg(not(feature = "_dual-core"))]
/// Safety: Reads a mutable global.
pub(crate) unsafe fn get_freqs() -> &'static Clocks {
CLOCK_FREQS.assume_init_ref()
}
#[cfg(feature = "_dual-core")]
/// Safety: Reads a mutable global.
pub(crate) unsafe fn get_freqs() -> &'static Clocks {
unwrap!(CLOCK_FREQS_PTR.load(core::sync::atomic::Ordering::SeqCst).as_ref()).assume_init_ref()
}
pub(crate) trait SealedRccPeripheral {
fn frequency() -> Hertz;
const RCC_INFO: RccInfo;

View File

@ -132,7 +132,7 @@ impl Rtc {
// Panic if the rcc mod knows we're not using low-power rtc
#[cfg(any(rcc_wb, rcc_f4, rcc_f410))]
unsafe { crate::rcc::get_freqs() }.rtc.unwrap();
unsafe { crate::rcc::get_freqs() }.rtc.to_hertz().unwrap();
let requested_duration = requested_duration.as_ticks().clamp(0, u32::MAX as u64);
let rtc_hz = Self::frequency().0 as u64;

View File

@ -168,7 +168,7 @@ impl Rtc {
fn frequency() -> Hertz {
let freqs = unsafe { crate::rcc::get_freqs() };
freqs.rtc.unwrap()
freqs.rtc.to_hertz().unwrap()
}
/// Acquire a [`RtcTimeProvider`] instance.

View File

@ -87,3 +87,39 @@ impl Div<Hertz> for Hertz {
self.0 / rhs.0
}
}
#[repr(C)]
#[derive(Eq, PartialEq, Ord, PartialOrd, Clone, Copy, Debug, Default)]
#[cfg_attr(feature = "defmt", derive(defmt::Format))]
/// A variant on [Hertz] that acts as an `Option<Hertz>` that is smaller and repr C.
///
/// An `Option<Hertz>` can be `.into()`'d into this type and back.
/// The only restriction is that that [Hertz] cannot have the value 0 since that's
/// seen as the `None` variant.
pub struct MaybeHertz(u32);
impl MaybeHertz {
/// Same as calling the `.into()` function, but without type inference.
pub fn to_hertz(self) -> Option<Hertz> {
self.into()
}
}
impl From<Option<Hertz>> for MaybeHertz {
fn from(value: Option<Hertz>) -> Self {
match value {
Some(Hertz(0)) => panic!("Hertz cannot be 0"),
Some(Hertz(val)) => Self(val),
None => Self(0),
}
}
}
impl From<MaybeHertz> for Option<Hertz> {
fn from(value: MaybeHertz) -> Self {
match value {
MaybeHertz(0) => None,
MaybeHertz(val) => Some(Hertz(val)),
}
}
}

View File

@ -270,7 +270,7 @@ impl<'d, T: Instance> Driver<'d, T> {
#[cfg(feature = "time")]
embassy_time::block_for(embassy_time::Duration::from_millis(100));
#[cfg(not(feature = "time"))]
cortex_m::asm::delay(unsafe { crate::rcc::get_freqs() }.sys.unwrap().0 / 10);
cortex_m::asm::delay(unsafe { crate::rcc::get_freqs() }.sys.to_hertz().unwrap().0 / 10);
#[cfg(not(usb_v4))]
regs.btable().write(|w| w.set_btable(0));

View File

@ -5,7 +5,8 @@ MEMORY
BOOTLOADER_STATE : ORIGIN = 0x08006000, LENGTH = 4K
FLASH : ORIGIN = 0x08008000, LENGTH = 64K
DFU : ORIGIN = 0x08018000, LENGTH = 68K
RAM (rwx) : ORIGIN = 0x20000000, LENGTH = 32K
SHARED_RAM (rwx) : ORIGIN = 0x20000000, LENGTH = 64
RAM (rwx) : ORIGIN = 0x20000040, LENGTH = 32K - 64
}
__bootloader_state_start = ORIGIN(BOOTLOADER_STATE) - ORIGIN(BOOTLOADER);
@ -13,3 +14,11 @@ __bootloader_state_end = ORIGIN(BOOTLOADER_STATE) + LENGTH(BOOTLOADER_STATE) - O
__bootloader_dfu_start = ORIGIN(DFU) - ORIGIN(BOOTLOADER);
__bootloader_dfu_end = ORIGIN(DFU) + LENGTH(DFU) - ORIGIN(BOOTLOADER);
SECTIONS
{
.shared_data :
{
*(.shared_data)
} > SHARED_RAM
}

View File

@ -1,6 +1,8 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
#[cfg(feature = "defmt")]
use defmt_rtt::*;
use embassy_boot_stm32::{AlignedBuffer, FirmwareUpdater, FirmwareUpdaterConfig};
@ -9,6 +11,7 @@ use embassy_executor::Spawner;
use embassy_stm32::exti::ExtiInput;
use embassy_stm32::flash::{Flash, WRITE_SIZE};
use embassy_stm32::gpio::{Level, Output, Pull, Speed};
use embassy_stm32::SharedData;
use embassy_sync::mutex::Mutex;
use panic_reset as _;
@ -17,9 +20,12 @@ static APP_B: &[u8] = &[0, 1, 2, 3];
#[cfg(not(feature = "skip-include"))]
static APP_B: &[u8] = include_bytes!("../../b.bin");
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(Default::default());
let p = embassy_stm32::init_primary(Default::default(), &SHARED_DATA);
let flash = Flash::new_blocking(p.FLASH);
let flash = Mutex::new(BlockingAsync::new(flash));

View File

@ -1,16 +1,22 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
#[cfg(feature = "defmt")]
use defmt_rtt::*;
use embassy_executor::Spawner;
use embassy_stm32::gpio::{Level, Output, Speed};
use embassy_stm32::SharedData;
use embassy_time::Timer;
use panic_reset as _;
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(Default::default());
let p = embassy_stm32::init_primary(Default::default(), &SHARED_DATA);
let mut led = Output::new(p.PB15, Level::High, Speed::Low);
loop {

View File

@ -0,0 +1,8 @@
[target.thumbv7em-none-eabihf]
runner = 'probe-rs run --chip STM32H755ZITx --catch-hardfault --always-print-stacktrace'
[build]
target = "thumbv7em-none-eabihf" # Cortex-M4F and Cortex-M7F (with FPU)
[env]
DEFMT_LOG = "trace"

View File

@ -0,0 +1,75 @@
[package]
edition = "2021"
name = "embassy-stm32h7-examples"
version = "0.1.0"
license = "MIT OR Apache-2.0"
[dependencies]
# Change stm32h755zi-cm4 to your chip name, if necessary.
embassy-stm32 = { version = "0.1.0", path = "../../embassy-stm32", features = ["defmt", "stm32h755zi-cm4", "time-driver-tim2", "exti", "memory-x", "unstable-pac", "chrono"] }
embassy-sync = { version = "0.6.0", path = "../../embassy-sync", features = ["defmt"] }
embassy-embedded-hal = { version = "0.2.0", path = "../../embassy-embedded-hal" }
embassy-executor = { version = "0.6.0", path = "../../embassy-executor", features = ["task-arena-size-32768", "arch-cortex-m", "executor-thread", "executor-interrupt", "defmt", "integrated-timers"] }
embassy-time = { version = "0.3.1", path = "../../embassy-time", features = ["defmt", "defmt-timestamp-uptime", "tick-hz-32_768"] }
embassy-net = { version = "0.4.0", path = "../../embassy-net", features = ["defmt", "tcp", "dhcpv4", "medium-ethernet", "proto-ipv6", "dns"] }
embassy-usb = { version = "0.3.0", path = "../../embassy-usb", features = ["defmt"] }
embassy-futures = { version = "0.1.0", path = "../../embassy-futures" }
defmt = "0.3"
defmt-rtt = "0.4"
cortex-m = { version = "0.7.6", features = ["inline-asm", "critical-section-single-core"] }
cortex-m-rt = "0.7.0"
embedded-hal = "0.2.6"
embedded-hal-1 = { package = "embedded-hal", version = "1.0" }
embedded-hal-async = { version = "1.0" }
embedded-nal-async = { version = "0.7.1" }
embedded-io-async = { version = "0.6.1" }
panic-probe = { version = "0.3", features = ["print-defmt"] }
heapless = { version = "0.8", default-features = false }
rand_core = "0.6.3"
critical-section = "1.1"
micromath = "2.0.0"
stm32-fmc = "0.3.0"
embedded-storage = "0.3.1"
static_cell = "2"
chrono = { version = "^0.4", default-features = false }
grounded = "0.2.0"
# cargo build/run
[profile.dev]
codegen-units = 1
debug = 2
debug-assertions = true # <-
incremental = false
opt-level = 3 # <-
overflow-checks = true # <-
# cargo test
[profile.test]
codegen-units = 1
debug = 2
debug-assertions = true # <-
incremental = false
opt-level = 3 # <-
overflow-checks = true # <-
# cargo build/run --release
[profile.release]
codegen-units = 1
debug = 2
debug-assertions = false # <-
incremental = false
lto = 'fat'
opt-level = 3 # <-
overflow-checks = false # <-
# cargo test --release
[profile.bench]
codegen-units = 1
debug = 2
debug-assertions = false # <-
incremental = false
lto = 'fat'
opt-level = 3 # <-
overflow-checks = false # <-

View File

@ -0,0 +1,35 @@
//! This build script copies the `memory.x` file from the crate root into
//! a directory where the linker can always find it at build time.
//! For many projects this is optional, as the linker always searches the
//! project root directory -- wherever `Cargo.toml` is. However, if you
//! are using a workspace or have a more complicated build setup, this
//! build script becomes required. Additionally, by requesting that
//! Cargo re-run the build script whenever `memory.x` is changed,
//! updating `memory.x` ensures a rebuild of the application with the
//! new memory settings.
use std::env;
use std::fs::File;
use std::io::Write;
use std::path::PathBuf;
fn main() {
// Put `memory.x` in our output directory and ensure it's
// on the linker search path.
let out = &PathBuf::from(env::var_os("OUT_DIR").unwrap());
File::create(out.join("memory.x"))
.unwrap()
.write_all(include_bytes!("memory.x"))
.unwrap();
println!("cargo:rustc-link-search={}", out.display());
// By default, Cargo will re-run a build script whenever
// any file in the project changes. By specifying `memory.x`
// here, we ensure the build script is only re-run when
// `memory.x` is changed.
println!("cargo:rerun-if-changed=memory.x");
println!("cargo:rustc-link-arg-bins=--nmagic");
println!("cargo:rustc-link-arg-bins=-Tlink.x");
println!("cargo:rustc-link-arg-bins=-Tdefmt.x");
}

View File

@ -0,0 +1,15 @@
MEMORY
{
FLASH : ORIGIN = 0x08100000, LENGTH = 1024K /* BANK_2 */
RAM : ORIGIN = 0x10000000, LENGTH = 128K /* SRAM1 */
RAM_D3 : ORIGIN = 0x38000000, LENGTH = 64K /* SRAM4 */
}
SECTIONS
{
.ram_d3 :
{
*(.ram_d3.shared_data)
*(.ram_d3)
} > RAM_D3
}

View File

@ -0,0 +1,32 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use defmt::*;
use embassy_executor::Spawner;
use embassy_stm32::gpio::{Level, Output, Speed};
use embassy_stm32::SharedData;
use embassy_time::Timer;
use {defmt_rtt as _, panic_probe as _};
#[link_section = ".ram_d3.shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init_secondary(&SHARED_DATA);
info!("Hello World!");
let mut led = Output::new(p.PE1, Level::High, Speed::Low);
loop {
info!("high");
led.set_high();
Timer::after_millis(250).await;
info!("low");
led.set_low();
Timer::after_millis(250).await;
}
}

View File

@ -0,0 +1,8 @@
[target.thumbv7em-none-eabihf]
runner = 'probe-rs run --chip STM32H755ZITx --catch-hardfault --always-print-stacktrace'
[build]
target = "thumbv7em-none-eabihf" # Cortex-M4F and Cortex-M7F (with FPU)
[env]
DEFMT_LOG = "trace"

View File

@ -0,0 +1,75 @@
[package]
edition = "2021"
name = "embassy-stm32h7-examples"
version = "0.1.0"
license = "MIT OR Apache-2.0"
[dependencies]
# Change stm32h743bi to your chip name, if necessary.
embassy-stm32 = { version = "0.1.0", path = "../../embassy-stm32", features = ["defmt", "stm32h755zi-cm7", "time-driver-tim3", "exti", "memory-x", "unstable-pac", "chrono"] }
embassy-sync = { version = "0.6.0", path = "../../embassy-sync", features = ["defmt"] }
embassy-embedded-hal = { version = "0.2.0", path = "../../embassy-embedded-hal" }
embassy-executor = { version = "0.6.0", path = "../../embassy-executor", features = ["task-arena-size-32768", "arch-cortex-m", "executor-thread", "executor-interrupt", "defmt", "integrated-timers"] }
embassy-time = { version = "0.3.1", path = "../../embassy-time", features = ["defmt", "defmt-timestamp-uptime", "tick-hz-32_768"] }
embassy-net = { version = "0.4.0", path = "../../embassy-net", features = ["defmt", "tcp", "dhcpv4", "medium-ethernet", "proto-ipv6", "dns"] }
embassy-usb = { version = "0.3.0", path = "../../embassy-usb", features = ["defmt"] }
embassy-futures = { version = "0.1.0", path = "../../embassy-futures" }
defmt = "0.3"
defmt-rtt = "0.4"
cortex-m = { version = "0.7.6", features = ["inline-asm", "critical-section-single-core"] }
cortex-m-rt = "0.7.0"
embedded-hal = "0.2.6"
embedded-hal-1 = { package = "embedded-hal", version = "1.0" }
embedded-hal-async = { version = "1.0" }
embedded-nal-async = { version = "0.7.1" }
embedded-io-async = { version = "0.6.1" }
panic-probe = { version = "0.3", features = ["print-defmt"] }
heapless = { version = "0.8", default-features = false }
rand_core = "0.6.3"
critical-section = "1.1"
micromath = "2.0.0"
stm32-fmc = "0.3.0"
embedded-storage = "0.3.1"
static_cell = "2"
chrono = { version = "^0.4", default-features = false }
grounded = "0.2.0"
# cargo build/run
[profile.dev]
codegen-units = 1
debug = 2
debug-assertions = true # <-
incremental = false
opt-level = 3 # <-
overflow-checks = true # <-
# cargo test
[profile.test]
codegen-units = 1
debug = 2
debug-assertions = true # <-
incremental = false
opt-level = 3 # <-
overflow-checks = true # <-
# cargo build/run --release
[profile.release]
codegen-units = 1
debug = 2
debug-assertions = false # <-
incremental = false
lto = 'fat'
opt-level = 3 # <-
overflow-checks = false # <-
# cargo test --release
[profile.bench]
codegen-units = 1
debug = 2
debug-assertions = false # <-
incremental = false
lto = 'fat'
opt-level = 3 # <-
overflow-checks = false # <-

View File

@ -0,0 +1,35 @@
//! This build script copies the `memory.x` file from the crate root into
//! a directory where the linker can always find it at build time.
//! For many projects this is optional, as the linker always searches the
//! project root directory -- wherever `Cargo.toml` is. However, if you
//! are using a workspace or have a more complicated build setup, this
//! build script becomes required. Additionally, by requesting that
//! Cargo re-run the build script whenever `memory.x` is changed,
//! updating `memory.x` ensures a rebuild of the application with the
//! new memory settings.
use std::env;
use std::fs::File;
use std::io::Write;
use std::path::PathBuf;
fn main() {
// Put `memory.x` in our output directory and ensure it's
// on the linker search path.
let out = &PathBuf::from(env::var_os("OUT_DIR").unwrap());
File::create(out.join("memory.x"))
.unwrap()
.write_all(include_bytes!("memory.x"))
.unwrap();
println!("cargo:rustc-link-search={}", out.display());
// By default, Cargo will re-run a build script whenever
// any file in the project changes. By specifying `memory.x`
// here, we ensure the build script is only re-run when
// `memory.x` is changed.
println!("cargo:rerun-if-changed=memory.x");
println!("cargo:rustc-link-arg-bins=--nmagic");
println!("cargo:rustc-link-arg-bins=-Tlink.x");
println!("cargo:rustc-link-arg-bins=-Tdefmt.x");
}

View File

@ -0,0 +1,15 @@
MEMORY
{
FLASH : ORIGIN = 0x08000000, LENGTH = 1024K /* BANK_1 */
RAM : ORIGIN = 0x24000000, LENGTH = 512K /* AXIRAM */
RAM_D3 : ORIGIN = 0x38000000, LENGTH = 64K /* SRAM4 */
}
SECTIONS
{
.ram_d3 :
{
*(.ram_d3.shared_data)
*(.ram_d3)
} > RAM_D3
}

View File

@ -0,0 +1,54 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use defmt::*;
use embassy_executor::Spawner;
use embassy_stm32::gpio::{Level, Output, Speed};
use embassy_stm32::SharedData;
use embassy_time::Timer;
use {defmt_rtt as _, panic_probe as _};
#[link_section = ".ram_d3.shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let mut config = embassy_stm32::Config::default();
{
use embassy_stm32::rcc::*;
config.rcc.hsi = Some(HSIPrescaler::DIV1);
config.rcc.csi = true;
config.rcc.pll1 = Some(Pll {
source: PllSource::HSI,
prediv: PllPreDiv::DIV4,
mul: PllMul::MUL50,
divp: Some(PllDiv::DIV2),
divq: Some(PllDiv::DIV8), // 100mhz
divr: None,
});
config.rcc.sys = Sysclk::PLL1_P; // 400 Mhz
config.rcc.ahb_pre = AHBPrescaler::DIV2; // 200 Mhz
config.rcc.apb1_pre = APBPrescaler::DIV2; // 100 Mhz
config.rcc.apb2_pre = APBPrescaler::DIV2; // 100 Mhz
config.rcc.apb3_pre = APBPrescaler::DIV2; // 100 Mhz
config.rcc.apb4_pre = APBPrescaler::DIV2; // 100 Mhz
config.rcc.voltage_scale = VoltageScale::Scale1;
config.rcc.supply_config = SupplyConfig::DirectSMPS;
}
let p = embassy_stm32::init_primary(config, &SHARED_DATA);
info!("Hello World!");
let mut led = Output::new(p.PB14, Level::High, Speed::Low);
loop {
info!("high");
led.set_high();
Timer::after_millis(500).await;
info!("low");
led.set_low();
Timer::after_millis(500).await;
}
}

15
examples/stm32wl/memory.x Normal file
View File

@ -0,0 +1,15 @@
MEMORY
{
/* NOTE 1 K = 1 KiBi = 1024 bytes */
FLASH : ORIGIN = 0x08000000, LENGTH = 256K
SHARED_RAM (rwx) : ORIGIN = 0x20000000, LENGTH = 64
RAM (rwx) : ORIGIN = 0x20000040, LENGTH = 64K - 64
}
SECTIONS
{
.shared_data :
{
*(.shared_data)
} > SHARED_RAM
}

View File

@ -1,15 +1,21 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use defmt::*;
use embassy_executor::Spawner;
use embassy_stm32::gpio::{Level, Output, Speed};
use embassy_stm32::SharedData;
use embassy_time::Timer;
use {defmt_rtt as _, panic_probe as _};
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(Default::default());
let p = embassy_stm32::init_primary(Default::default(), &SHARED_DATA);
info!("Hello World!");
let mut led = Output::new(p.PB15, Level::High, Speed::Low);

View File

@ -1,16 +1,22 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use cortex_m_rt::entry;
use defmt::*;
use embassy_stm32::gpio::{Input, Level, Output, Pull, Speed};
use embassy_stm32::SharedData;
use {defmt_rtt as _, panic_probe as _};
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[entry]
fn main() -> ! {
info!("Hello World!");
let p = embassy_stm32::init(Default::default());
let p = embassy_stm32::init_primary(Default::default(), &SHARED_DATA);
let button = Input::new(p.PA0, Pull::Up);
let mut led1 = Output::new(p.PB15, Level::High, Speed::Low);

View File

@ -1,15 +1,21 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use defmt::*;
use embassy_executor::Spawner;
use embassy_stm32::exti::ExtiInput;
use embassy_stm32::gpio::Pull;
use embassy_stm32::SharedData;
use {defmt_rtt as _, panic_probe as _};
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(Default::default());
let p = embassy_stm32::init_primary(Default::default(), &SHARED_DATA);
info!("Hello World!");
let mut button = ExtiInput::new(p.PA0, p.EXTI0, Pull::Up);

View File

@ -1,14 +1,20 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use defmt::{info, unwrap};
use embassy_executor::Spawner;
use embassy_stm32::flash::Flash;
use embassy_stm32::SharedData;
use {defmt_rtt as _, panic_probe as _};
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(Default::default());
let p = embassy_stm32::init_primary(Default::default(), &SHARED_DATA);
info!("Hello Flash!");
const ADDR: u32 = 0x36000;

View File

@ -1,17 +1,22 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use defmt::*;
use embassy_executor::Spawner;
use embassy_stm32::rng::{self, Rng};
use embassy_stm32::time::Hertz;
use embassy_stm32::{bind_interrupts, peripherals};
use embassy_stm32::{bind_interrupts, peripherals, SharedData};
use {defmt_rtt as _, panic_probe as _};
bind_interrupts!(struct Irqs{
RNG => rng::InterruptHandler<peripherals::RNG>;
});
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let mut config = embassy_stm32::Config::default();
@ -32,7 +37,7 @@ async fn main(_spawner: Spawner) {
divr: Some(PllRDiv::DIV2), // sysclk 48Mhz clock (32 / 2 * 6 / 2)
});
}
let p = embassy_stm32::init(config);
let p = embassy_stm32::init_primary(config, &SHARED_DATA);
info!("Hello World!");

View File

@ -1,15 +1,20 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use chrono::{NaiveDate, NaiveDateTime};
use defmt::*;
use embassy_executor::Spawner;
use embassy_stm32::rtc::{Rtc, RtcConfig};
use embassy_stm32::time::Hertz;
use embassy_stm32::Config;
use embassy_stm32::{Config, SharedData};
use embassy_time::Timer;
use {defmt_rtt as _, panic_probe as _};
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let mut config = Config::default();
@ -31,7 +36,7 @@ async fn main(_spawner: Spawner) {
divr: Some(PllRDiv::DIV2), // sysclk 48Mhz clock (32 / 2 * 6 / 2)
});
}
let p = embassy_stm32::init(config);
let p = embassy_stm32::init_primary(config, &SHARED_DATA);
info!("Hello World!");
let now = NaiveDate::from_ymd_opt(2020, 5, 15)

View File

@ -1,10 +1,12 @@
#![no_std]
#![no_main]
use core::mem::MaybeUninit;
use defmt::*;
use embassy_executor::Spawner;
use embassy_stm32::usart::{Config, InterruptHandler, Uart};
use embassy_stm32::{bind_interrupts, peripherals};
use embassy_stm32::{bind_interrupts, peripherals, SharedData};
use {defmt_rtt as _, panic_probe as _};
bind_interrupts!(struct Irqs{
@ -12,6 +14,9 @@ bind_interrupts!(struct Irqs{
LPUART1 => InterruptHandler<peripherals::LPUART1>;
});
#[link_section = ".shared_data"]
static SHARED_DATA: MaybeUninit<SharedData> = MaybeUninit::uninit();
/*
Pass Incoming data from LPUART1 to USART1
Example is written for the LoRa-E5 mini v1.0,
@ -21,7 +26,7 @@ but can be surely changed for your needs.
async fn main(_spawner: Spawner) {
let mut config = embassy_stm32::Config::default();
config.rcc.sys = embassy_stm32::rcc::Sysclk::HSE;
let p = embassy_stm32::init(config);
let p = embassy_stm32::init_primary(config, &SHARED_DATA);
defmt::info!("Starting system");

View File

@ -27,7 +27,7 @@ bind_interrupts!(struct Irqs {
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
let options = TestOptions {

View File

@ -29,7 +29,7 @@ const OUTPUT_LENGTH: usize = (INPUT_U32_COUNT - 1) * 2;
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let dp = embassy_stm32::init(config());
let dp = init();
//
// use RNG generate random Q1.31 value

View File

@ -20,7 +20,7 @@ bind_interrupts!(struct Irqs {
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p: embassy_stm32::Peripherals = embassy_stm32::init(config());
let p: embassy_stm32::Peripherals = init();
const PAYLOAD1: &[u8] = b"payload data 1 ;zdfhzdfhS;GKJASBDG;ASKDJBAL,zdfhzdfhzdfhzdfhvljhb,jhbjhb,sdhsdghsdhsfhsghzdfhzdfhzdfhzdfdhsdthsthsdhsgaadfhhgkdgfuoyguoft6783567";
const PAYLOAD2: &[u8] = b"payload data 2 ;SKEzdfhzdfhzbhgvljhb,jhbjhb,sdhsdghsdhsfhsghshsfhshstsdthadfhsdfjhsfgjsfgjxfgjzdhgDFghSDGHjtfjtjszftjzsdtjhstdsdhsdhsdhsdhsdthsthsdhsgfh";

View File

@ -20,7 +20,7 @@ use {defmt_rtt as _, panic_probe as _};
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
// Initialize the board and obtain a Peripherals instance
let p: embassy_stm32::Peripherals = embassy_stm32::init(config());
let p: embassy_stm32::Peripherals = init();
let adc = peri!(p, ADC);
let dac = peri!(p, DAC);

View File

@ -25,7 +25,7 @@ bind_interrupts!(struct Irqs {
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
// Initialize the board and obtain a Peripherals instance
let p: embassy_stm32::Peripherals = embassy_stm32::init(config());
let p: embassy_stm32::Peripherals = init();
let adc = peri!(p, ADC);
let dac = peri!(p, DAC);

View File

@ -38,7 +38,7 @@ async fn net_task(stack: &'static Stack<Device>) -> ! {
#[embassy_executor::main]
async fn main(spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
// Generate random seed.

View File

@ -102,10 +102,10 @@ fn options() -> (Config, TestOptions) {
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
//let peripherals = embassy_stm32::init(config());
//let peripherals = init();
let (config, options) = options();
let peripherals = embassy_stm32::init(config);
let peripherals = init_with_config(config);
let mut can = can::CanConfigurator::new(peripherals.FDCAN1, peripherals.PB8, peripherals.PB9, Irqs1);
let mut can2 = can::CanConfigurator::new(peripherals.FDCAN2, peripherals.PB12, peripherals.PB13, Irqs2);

View File

@ -10,7 +10,7 @@ use embassy_stm32::gpio::{Flex, Input, Level, Output, OutputOpenDrain, Pull, Spe
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
// Arduino pins D0 and D1

View File

@ -35,7 +35,7 @@ bind_interrupts!(struct Irqs {
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p: embassy_stm32::Peripherals = embassy_stm32::init(config());
let p: embassy_stm32::Peripherals = init();
let mut hw_hasher = Hash::new(p.HASH, NoDma, Irqs);
let test_1: &[u8] = b"as;dfhaslfhas;oifvnasd;nifvnhasd;nifvhndlkfghsd;nvfnahssdfgsdafgsasdfasdfasdfasdfasdfghjklmnbvcalskdjghalskdjgfbaslkdjfgbalskdjgbalskdjbdfhsdfhsfghsfghfgh";

View File

@ -41,7 +41,7 @@ bind_interrupts!(struct Irqs {
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p: embassy_stm32::Peripherals = embassy_stm32::init(config());
let p: embassy_stm32::Peripherals = init();
let mut rng = Rng::new(p.RNG, Irqs);

View File

@ -18,7 +18,7 @@ async fn main(_spawner: Spawner) {
let mut config = config();
config.rcc.ls = LsConfig::default_lse();
let p = embassy_stm32::init(config);
let p = init_with_config(config);
info!("Hello World!");
let now = NaiveDate::from_ymd_opt(2020, 5, 15)

View File

@ -20,7 +20,7 @@ bind_interrupts!(struct Irqs {
async fn main(_spawner: Spawner) {
info!("Hello World!");
let p = embassy_stm32::init(config());
let p = init();
let (mut sdmmc, mut dma, mut clk, mut cmd, mut d0, mut d1, mut d2, mut d3) =
(p.SDIO, p.DMA2_CH3, p.PC12, p.PD2, p.PC8, p.PC9, p.PC10, p.PC11);

View File

@ -12,7 +12,7 @@ use embassy_stm32::time::Hertz;
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
let mut spi_peri = peri!(p, SPI);

View File

@ -12,7 +12,7 @@ use embassy_stm32::time::Hertz;
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
let mut spi_peri = peri!(p, SPI);

View File

@ -58,7 +58,7 @@ async fn async_main(spawner: Spawner) {
config.rcc.hsi = Some(HSIPrescaler::DIV4); // 64 MHz HSI will need a /4
}
let p = embassy_stm32::init(config);
let p = init_with_config(config);
info!("Hello World!");
let now = NaiveDate::from_ymd_opt(2020, 5, 15)

View File

@ -10,7 +10,7 @@ use embassy_time::{Instant, Timer};
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let _p = embassy_stm32::init(config());
let _p = init();
info!("Hello World!");
let start = Instant::now();

View File

@ -102,7 +102,7 @@ async fn sink(
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
// Wire between PD0 and PA8

View File

@ -11,7 +11,7 @@ use embassy_time::{block_for, Duration, Instant};
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
// Arduino pins D0 and D1

View File

@ -11,7 +11,7 @@ use embassy_stm32::usart::{Config, Uart};
#[embassy_executor::main]
async fn main(_spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
// Arduino pins D0 and D1

View File

@ -18,7 +18,7 @@ const DMA_BUF_SIZE: usize = 256;
#[embassy_executor::main]
async fn main(spawner: Spawner) {
let p = embassy_stm32::init(config());
let p = init();
info!("Hello World!");
// Arduino pins D0 and D1

View File

@ -41,7 +41,7 @@ async fn main(spawner: Spawner) {
let mut config = config();
config.rcc = WPAN_DEFAULT;
let p = embassy_stm32::init(config);
let p = init_with_config(config);
info!("Hello World!");
let config = Config::default();

View File

@ -34,7 +34,7 @@ async fn main(spawner: Spawner) {
let mut config = config();
config.rcc = WPAN_DEFAULT;
let p = embassy_stm32::init(config);
let p = init_with_config(config);
info!("Hello World!");
let config = Config::default();

View File

@ -699,3 +699,21 @@ pub fn config() -> Config {
config
}
#[allow(unused)]
pub fn init() -> embassy_stm32::Peripherals {
init_with_config(config())
}
#[allow(unused)]
pub fn init_with_config(config: Config) -> embassy_stm32::Peripherals {
#[cfg(any(feature = "stm32wl55jc", feature = "stm32h755zi"))]
{
// Not in shared memory, but we're not running the second core, so it's fine
static SHARED_DATA: core::mem::MaybeUninit<embassy_stm32::SharedData> = core::mem::MaybeUninit::uninit();
embassy_stm32::init_primary(config, &SHARED_DATA)
}
#[cfg(not(any(feature = "stm32wl55jc", feature = "stm32h755zi")))]
embassy_stm32::init(config)
}