Extract embassy support into esp-hal-embassy package (#1595)

* Extract embassy support into `esp-hal-embassy` package

* Update relevant packages/examples/tests to get CI green again

* Add back `defmt` support

* Re-export `Executor` and `InterruptExecutor` rather than making `executor` module public

* Document the `esp-hal-embassy` package

* Update `CHANGELOG.md`

* Hack together a "fix" for the `SYSTIMER` time driver

* Make `clippy` shut up
This commit is contained in:
Jesse Braham 2024-06-03 11:27:20 +00:00 committed by GitHub
parent cb91828e5e
commit 48e3e912f3
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
54 changed files with 660 additions and 346 deletions

View File

@ -6,6 +6,7 @@ exclude = [
"esp-backtrace", "esp-backtrace",
"esp-build", "esp-build",
"esp-hal", "esp-hal",
"esp-hal-embassy",
"esp-hal-procmacros", "esp-hal-procmacros",
"esp-hal-smartled", "esp-hal-smartled",
"esp-ieee802154", "esp-ieee802154",

View File

@ -0,0 +1,48 @@
[package]
name = "esp-hal-embassy"
version = "0.1.0"
edition = "2021"
rust-version = "1.76.0"
description = "Embassy support for esp-hal"
repository = "https://github.com/esp-rs/esp-hal"
license = "MIT OR Apache-2.0"
[package.metadata.docs.rs]
default-target = "riscv32imac-unknown-none-elf"
features = ["esp32c6", "time-timg0"]
[dependencies]
critical-section = "1.1.2"
defmt = { version = "0.3.8", optional = true }
document-features = "0.2.8"
embassy-executor = "0.5.0"
embassy-time-driver = "0.1.0"
esp-hal = { version = "0.17.0", path = "../esp-hal" }
portable-atomic = "1.6.0"
[build-dependencies]
cfg-if = "1.0.0"
esp-build = { version = "0.1.0", path = "../esp-build" }
esp-metadata = { version = "0.1.0", path = "../esp-metadata" }
[features]
esp32 = ["esp-hal/esp32"]
esp32c2 = ["esp-hal/esp32c2"]
esp32c3 = ["esp-hal/esp32c3"]
esp32c6 = ["esp-hal/esp32c6"]
esp32h2 = ["esp-hal/esp32h2"]
esp32s2 = ["esp-hal/esp32s2"]
esp32s3 = ["esp-hal/esp32s3"]
## Implement `defmt::Format` on certain types.
defmt = ["dep:defmt", "embassy-executor/defmt", "esp-hal/defmt"]
## Use the executor-integrated `embassy-time` timer queue.
integrated-timers = ["embassy-executor/integrated-timers"]
#! ### Time Driver Feature Flags
## SYSTIMER (16MHz)
time-systimer-16mhz = ["embassy-time-driver/tick-hz-16_000_000"]
## SYSTIMER (80MHz)
time-systimer-80mhz = ["embassy-time-driver/tick-hz-80_000_000"]
## TIMG0 (1MHz)
time-timg0 = ["embassy-time-driver/tick-hz-1_000_000"]

35
esp-hal-embassy/README.md Normal file
View File

@ -0,0 +1,35 @@
# esp-hal-embassy
[![Crates.io](https://img.shields.io/crates/v/esp-hal-embassy?labelColor=1C2C2E&color=C96329&logo=Rust&style=flat-square)](https://crates.io/crates/esp-hal-embassy)
[![docs.rs](https://img.shields.io/docsrs/esp-hal-embassy?labelColor=1C2C2E&color=C96329&logo=rust&style=flat-square)](https://docs.rs/esp-hal-embassy)
![MSRV](https://img.shields.io/badge/MSRV-1.76-blue?labelColor=1C2C2E&style=flat-square)
![Crates.io](https://img.shields.io/crates/l/esp-hal-embassy?labelColor=1C2C2E&style=flat-square)
[![Matrix](https://img.shields.io/matrix/esp-rs:matrix.org?label=join%20matrix&labelColor=1C2C2E&color=BEC5C9&logo=matrix&style=flat-square)](https://matrix.to/#/#esp-rs:matrix.org)
[Embassy] support for `esp-hal`.
[embassy]: https://github.com/embassy-rs/embassy
## [Documentation]
[documentation]: https://docs.rs/esp-hal-embassy/
## Minimum Supported Rust Version (MSRV)
This crate is guaranteed to compile on stable Rust 1.76 and up. It _might_
compile with older versions but that may change in any new patch release.
## License
Licensed under either of:
- Apache License, Version 2.0 ([LICENSE-APACHE](../LICENSE-APACHE) or http://www.apache.org/licenses/LICENSE-2.0)
- MIT license ([LICENSE-MIT](../LICENSE-MIT) or http://opensource.org/licenses/MIT)
at your option.
### Contribution
Unless you explicitly state otherwise, any contribution intentionally submitted for inclusion in
the work by you, as defined in the Apache-2.0 license, shall be dual licensed as above, without
any additional terms or conditions.

53
esp-hal-embassy/build.rs Normal file
View File

@ -0,0 +1,53 @@
use std::{error::Error, str::FromStr};
use esp_build::assert_unique_used_features;
use esp_metadata::{Chip, Config};
fn main() -> Result<(), Box<dyn Error>> {
// NOTE: update when adding new device support!
// Ensure that exactly one chip has been specified:
assert_unique_used_features!(
"esp32", "esp32c2", "esp32c3", "esp32c6", "esp32h2", "esp32s2", "esp32s3"
);
// If the `embassy` feature is enabled, ensure that a time driver implementation
// is available:
cfg_if::cfg_if! {
if #[cfg(feature = "esp32")] {
assert_unique_used_features!("time-timg0");
} else if #[cfg(feature = "esp32s2")] {
assert_unique_used_features!("time-systimer-80mhz", "time-timg0");
} else {
assert_unique_used_features!("time-systimer-16mhz", "time-timg0");
}
}
// NOTE: update when adding new device support!
// Determine the name of the configured device:
let device_name = if cfg!(feature = "esp32") {
"esp32"
} else if cfg!(feature = "esp32c2") {
"esp32c2"
} else if cfg!(feature = "esp32c3") {
"esp32c3"
} else if cfg!(feature = "esp32c6") {
"esp32c6"
} else if cfg!(feature = "esp32h2") {
"esp32h2"
} else if cfg!(feature = "esp32s2") {
"esp32s2"
} else if cfg!(feature = "esp32s3") {
"esp32s3"
} else {
unreachable!() // We've confirmed exactly one known device was selected
};
// Load the configuration file for the configured device:
let chip = Chip::from_str(device_name)?;
let config = Config::for_chip(&chip);
// Define all necessary configuration symbols for the configured device:
config.define_symbols();
Ok(())
}

View File

@ -1,14 +1,14 @@
//! Interrupt-mode executor. //! Interrupt-mode executor.
use core::{cell::UnsafeCell, mem::MaybeUninit}; use core::{cell::UnsafeCell, mem::MaybeUninit};
use embassy_executor::{raw, SendSpawner}; use embassy_executor::{raw, SendSpawner};
use portable_atomic::{AtomicUsize, Ordering}; use esp_hal::{
use crate::{
get_core, get_core,
interrupt::{self, InterruptHandler}, interrupt::{self, InterruptHandler},
system::SoftwareInterrupt, system::SoftwareInterrupt,
}; };
use portable_atomic::{AtomicUsize, Ordering};
static mut EXECUTORS: [CallbackContext; 4] = [ static mut EXECUTORS: [CallbackContext; 4] = [
CallbackContext::new(), CallbackContext::new(),
@ -43,7 +43,7 @@ impl CallbackContext {
} }
fn get(&self) -> *mut raw::Executor { fn get(&self) -> *mut raw::Executor {
unsafe { (*self.raw_executor.get()) as *mut raw::Executor } unsafe { *self.raw_executor.get() }
} }
fn set(&self, executor: *mut raw::Executor) { fn set(&self, executor: *mut raw::Executor) {
@ -58,7 +58,7 @@ fn handle_interrupt<const NUM: u8>() {
swi.reset(); swi.reset();
unsafe { unsafe {
let executor = EXECUTORS[NUM as usize].get().as_mut().unwrap(); let executor = unwrap!(EXECUTORS[NUM as usize].get().as_mut());
executor.poll(); executor.poll();
} }
} }
@ -151,7 +151,7 @@ impl<const SWI: u8> InterruptExecutor<SWI> {
if self.core.load(Ordering::Acquire) == usize::MAX { if self.core.load(Ordering::Acquire) == usize::MAX {
panic!("InterruptExecutor::spawner() called on uninitialized executor."); panic!("InterruptExecutor::spawner() called on uninitialized executor.");
} }
let executor = unsafe { (&*self.executor.get()).assume_init_ref() }; let executor = unsafe { (*self.executor.get()).assume_init_ref() };
executor.spawner().make_send() executor.spawner().make_send()
} }
} }

View File

@ -1,12 +1,11 @@
pub use self::{interrupt::*, thread::*};
mod interrupt; mod interrupt;
mod thread; mod thread;
pub use interrupt::*;
pub use thread::*;
#[export_name = "__pender"] #[export_name = "__pender"]
fn __pender(context: *mut ()) { fn __pender(context: *mut ()) {
use crate::system::SoftwareInterrupt; use esp_hal::system::SoftwareInterrupt;
let context = (context as usize).to_le_bytes(); let context = (context as usize).to_le_bytes();

View File

@ -1,14 +1,14 @@
//! Multicore-aware thread-mode embassy executor. //! Multicore-aware thread-mode embassy executor.
use core::marker::PhantomData; use core::marker::PhantomData;
use embassy_executor::{raw, Spawner}; use embassy_executor::{raw, Spawner};
use esp_hal::get_core;
#[cfg(multi_core)]
use esp_hal::macros::handler;
#[cfg(multi_core)]
use esp_hal::peripherals::SYSTEM;
use portable_atomic::{AtomicBool, Ordering}; use portable_atomic::{AtomicBool, Ordering};
#[cfg(multi_core)]
use procmacros::handler;
use crate::get_core;
#[cfg(multi_core)]
use crate::peripherals::SYSTEM;
pub(crate) const THREAD_MODE_CONTEXT: u8 = 16; pub(crate) const THREAD_MODE_CONTEXT: u8 = 16;
@ -39,7 +39,7 @@ pub(crate) fn pend_thread_mode(core: usize) {
// If we are pending a task on the current core, we're done. Otherwise, we // If we are pending a task on the current core, we're done. Otherwise, we
// need to make sure the other core wakes up. // need to make sure the other core wakes up.
#[cfg(multi_core)] #[cfg(multi_core)]
if core != crate::get_core() as usize { if core != get_core() as usize {
// We need to clear the interrupt from software. We don't actually // We need to clear the interrupt from software. We don't actually
// need it to trigger and run the interrupt handler, we just need to // need it to trigger and run the interrupt handler, we just need to
// kick waiti to return. // kick waiti to return.
@ -78,7 +78,7 @@ impl Executor {
pub fn new() -> Self { pub fn new() -> Self {
#[cfg(multi_core)] #[cfg(multi_core)]
unsafe { unsafe {
crate::system::SoftwareInterrupt::<3>::steal() esp_hal::system::SoftwareInterrupt::<3>::steal()
.set_interrupt_handler(software3_interrupt) .set_interrupt_handler(software3_interrupt)
} }
@ -179,3 +179,9 @@ impl Executor {
// here // here
} }
} }
impl Default for Executor {
fn default() -> Self {
Self::new()
}
}

226
esp-hal-embassy/src/fmt.rs Normal file
View File

@ -0,0 +1,226 @@
#![macro_use]
#![allow(unused_macros)]
#[cfg(all(feature = "defmt", feature = "log"))]
compile_error!("You may not enable both `defmt` and `log` features.");
macro_rules! assert {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::assert!($($x)*);
#[cfg(feature = "defmt")]
::defmt::assert!($($x)*);
}
};
}
macro_rules! assert_eq {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::assert_eq!($($x)*);
#[cfg(feature = "defmt")]
::defmt::assert_eq!($($x)*);
}
};
}
macro_rules! assert_ne {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::assert_ne!($($x)*);
#[cfg(feature = "defmt")]
::defmt::assert_ne!($($x)*);
}
};
}
macro_rules! debug_assert {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::debug_assert!($($x)*);
#[cfg(feature = "defmt")]
::defmt::debug_assert!($($x)*);
}
};
}
macro_rules! debug_assert_eq {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::debug_assert_eq!($($x)*);
#[cfg(feature = "defmt")]
::defmt::debug_assert_eq!($($x)*);
}
};
}
macro_rules! debug_assert_ne {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::debug_assert_ne!($($x)*);
#[cfg(feature = "defmt")]
::defmt::debug_assert_ne!($($x)*);
}
};
}
macro_rules! todo {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::todo!($($x)*);
#[cfg(feature = "defmt")]
::defmt::todo!($($x)*);
}
};
}
macro_rules! unreachable {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::unreachable!($($x)*);
#[cfg(feature = "defmt")]
::defmt::unreachable!($($x)*);
}
};
}
macro_rules! panic {
($($x:tt)*) => {
{
#[cfg(not(feature = "defmt"))]
::core::panic!($($x)*);
#[cfg(feature = "defmt")]
::defmt::panic!($($x)*);
}
};
}
macro_rules! trace {
($s:literal $(, $x:expr)* $(,)?) => {
{
#[cfg(feature = "log")]
::log::trace!($s $(, $x)*);
#[cfg(feature = "defmt")]
::defmt::trace!($s $(, $x)*);
#[cfg(not(any(feature = "log", feature="defmt")))]
let _ = ($( & $x ),*);
}
};
}
macro_rules! debug {
($s:literal $(, $x:expr)* $(,)?) => {
{
#[cfg(feature = "log")]
::log::debug!($s $(, $x)*);
#[cfg(feature = "defmt")]
::defmt::debug!($s $(, $x)*);
#[cfg(not(any(feature = "log", feature="defmt")))]
let _ = ($( & $x ),*);
}
};
}
macro_rules! info {
($s:literal $(, $x:expr)* $(,)?) => {
{
#[cfg(feature = "log")]
::log::info!($s $(, $x)*);
#[cfg(feature = "defmt")]
::defmt::info!($s $(, $x)*);
#[cfg(not(any(feature = "log", feature="defmt")))]
let _ = ($( & $x ),*);
}
};
}
macro_rules! warn {
($s:literal $(, $x:expr)* $(,)?) => {
{
#[cfg(feature = "log")]
::log::warn!($s $(, $x)*);
#[cfg(feature = "defmt")]
::defmt::warn!($s $(, $x)*);
#[cfg(not(any(feature = "log", feature="defmt")))]
let _ = ($( & $x ),*);
}
};
}
macro_rules! error {
($s:literal $(, $x:expr)* $(,)?) => {
{
#[cfg(feature = "log")]
::log::error!($s $(, $x)*);
#[cfg(feature = "defmt")]
::defmt::error!($s $(, $x)*);
#[cfg(not(any(feature = "log", feature="defmt")))]
let _ = ($( & $x ),*);
}
};
}
#[cfg(feature = "defmt")]
macro_rules! unwrap {
($($x:tt)*) => {
::defmt::unwrap!($($x)*)
};
}
#[cfg(not(feature = "defmt"))]
macro_rules! unwrap {
($arg:expr) => {
match $crate::fmt::Try::into_result($arg) {
::core::result::Result::Ok(t) => t,
::core::result::Result::Err(e) => {
::core::panic!("unwrap of `{}` failed: {:?}", ::core::stringify!($arg), e);
}
}
};
($arg:expr, $($msg:expr),+ $(,)? ) => {
match $crate::fmt::Try::into_result($arg) {
::core::result::Result::Ok(t) => t,
::core::result::Result::Err(e) => {
::core::panic!("unwrap of `{}` failed: {}: {:?}", ::core::stringify!($arg), ::core::format_args!($($msg,)*), e);
}
}
}
}
#[derive(Debug, Copy, Clone, Eq, PartialEq)]
pub struct NoneError;
pub trait Try {
type Ok;
type Error;
#[allow(unused)]
fn into_result(self) -> Result<Self::Ok, Self::Error>;
}
impl<T> Try for Option<T> {
type Ok = T;
type Error = NoneError;
#[inline]
fn into_result(self) -> Result<T, NoneError> {
self.ok_or(NoneError)
}
}
impl<T, E> Try for Result<T, E> {
type Ok = T;
type Error = E;
#[inline]
fn into_result(self) -> Self {
self
}
}

102
esp-hal-embassy/src/lib.rs Normal file
View File

@ -0,0 +1,102 @@
//! Embassy support for [esp-hal].
//!
//! [Embassy] is a modern asynchronous framework intended for use with embedded
//! systems. This package provides support for building applications using
//! Embassy with [esp-hal].
//!
//! [esp-hal]: https://github.com/esp-rs/esp-hal
//! [embassy]: https://github.com/embassy-rs/embassy
//!
//! ## Executors
//!
//! Two types of executors are provided:
//!
//! - [Executor]: A thread-mode executor
//! - [InterruptExecutor]: An interrupt-mode executor
//!
//! [InterruptExecutor] can be used to achieve preemptive multitasking in
//! asynchronous applications, which is typically something reserved for more
//! traditional RTOS. More information can be found in the [Embassy
//! documentation].
//!
//! [embassy documentation]: https://embassy.dev/book/dev/runtime.html
//!
//! ## Initialization
//!
//! Embassy **must** be initialized by calling the [init] function. This
//! initialization must be performed *prior* to spawning any tasks.
//!
//! ## Feature Flags
#![doc = document_features::document_features!()]
#![doc(html_logo_url = "https://avatars.githubusercontent.com/u/46717278")]
#![deny(missing_docs)]
#![cfg_attr(xtensa, feature(asm_experimental_arch))]
#![no_std]
// MUST be the first module
mod fmt;
use core::cell::Cell;
use embassy_time_driver::{AlarmHandle, Driver};
use esp_hal::clock::Clocks;
pub use self::executor::{Executor, InterruptExecutor};
use self::time_driver::{EmbassyTimer, TimerType};
mod executor;
mod time_driver;
/// Initialize embassy
pub fn init(clocks: &Clocks, time_driver: TimerType) {
EmbassyTimer::init(clocks, time_driver)
}
#[allow(clippy::type_complexity)]
pub(crate) struct AlarmState {
pub callback: Cell<Option<(fn(*mut ()), *mut ())>>,
pub allocated: Cell<bool>,
}
unsafe impl Send for AlarmState {}
impl AlarmState {
pub const fn new() -> Self {
Self {
callback: Cell::new(None),
allocated: Cell::new(false),
}
}
}
impl Driver for EmbassyTimer {
fn now(&self) -> u64 {
EmbassyTimer::now()
}
unsafe fn allocate_alarm(&self) -> Option<AlarmHandle> {
critical_section::with(|cs| {
for (i, alarm) in self.alarms.borrow(cs).iter().enumerate() {
if !alarm.allocated.get() {
// set alarm so it is not overwritten
alarm.allocated.set(true);
self.on_alarm_allocated(i);
return Some(AlarmHandle::new(i as u8));
}
}
None
})
}
fn set_alarm_callback(&self, alarm: AlarmHandle, callback: fn(*mut ()), ctx: *mut ()) {
let n = alarm.id() as usize;
critical_section::with(|cs| {
let alarm = &self.alarms.borrow(cs)[n];
alarm.callback.set(Some((callback, ctx)));
})
}
fn set_alarm(&self, alarm: AlarmHandle, timestamp: u64) -> bool {
self.set_alarm(alarm, timestamp)
}
}

View File

@ -0,0 +1,9 @@
#[cfg(any(feature = "time-systimer-16mhz", feature = "time-systimer-80mhz"))]
pub use self::systimer::*;
#[cfg(feature = "time-timg0")]
pub use self::timg::*;
#[cfg(any(feature = "time-systimer-16mhz", feature = "time-systimer-80mhz"))]
mod systimer;
#[cfg(feature = "time-timg0")]
mod timg;

View File

@ -1,35 +1,35 @@
use critical_section::{CriticalSection, Mutex}; use critical_section::{CriticalSection, Mutex};
use procmacros::handler; use embassy_time_driver::AlarmHandle;
use esp_hal::{
use super::AlarmState;
use crate::{
clock::Clocks, clock::Clocks,
peripherals, interrupt,
peripherals::Interrupt,
prelude::*, prelude::*,
timer::{ timer::systimer::{Alarm, SystemTimer, Target},
systimer::{Alarm, SystemTimer, Target}, Async,
Timer as _,
},
}; };
use crate::AlarmState;
pub const ALARM_COUNT: usize = 3; pub const ALARM_COUNT: usize = 3;
pub type TimerType = SystemTimer<'static, crate::Async>; pub type TimerType = SystemTimer<'static, Async>;
pub struct EmbassyTimer { pub struct EmbassyTimer {
pub(crate) alarms: Mutex<[AlarmState; ALARM_COUNT]>, pub(crate) alarms: Mutex<[AlarmState; ALARM_COUNT]>,
pub(crate) alarm0: Alarm<Target, crate::Async, 0>, pub(crate) alarm0: Alarm<Target, Async, 0>,
pub(crate) alarm1: Alarm<Target, crate::Async, 1>, pub(crate) alarm1: Alarm<Target, Async, 1>,
pub(crate) alarm2: Alarm<Target, crate::Async, 2>, pub(crate) alarm2: Alarm<Target, Async, 2>,
} }
#[allow(clippy::declare_interior_mutable_const)]
const ALARM_STATE_NONE: AlarmState = AlarmState::new(); const ALARM_STATE_NONE: AlarmState = AlarmState::new();
embassy_time_driver::time_driver_impl!(static DRIVER: EmbassyTimer = EmbassyTimer { embassy_time_driver::time_driver_impl!(static DRIVER: EmbassyTimer = EmbassyTimer {
alarms: Mutex::new([ALARM_STATE_NONE; ALARM_COUNT]), alarms: Mutex::new([ALARM_STATE_NONE; ALARM_COUNT]),
alarm0: unsafe { Alarm::<_, crate::Async, 0>::conjure() }, alarm0: unsafe { Alarm::<_, Async, 0>::conjure() },
alarm1: unsafe { Alarm::<_, crate::Async, 1>::conjure() }, alarm1: unsafe { Alarm::<_, Async, 1>::conjure() },
alarm2: unsafe { Alarm::<_, crate::Async, 2>::conjure() }, alarm2: unsafe { Alarm::<_, Async, 2>::conjure() },
}); });
impl EmbassyTimer { impl EmbassyTimer {
@ -45,7 +45,7 @@ impl EmbassyTimer {
} }
} }
pub(super) fn on_alarm_allocated(&self, n: usize) { pub(crate) fn on_alarm_allocated(&self, n: usize) {
match n { match n {
0 => self.alarm0.enable_interrupt(true), 0 => self.alarm0.enable_interrupt(true),
1 => self.alarm1.enable_interrupt(true), 1 => self.alarm1.enable_interrupt(true),
@ -63,30 +63,21 @@ impl EmbassyTimer {
pub fn init(_clocks: &Clocks, _systimer: TimerType) { pub fn init(_clocks: &Clocks, _systimer: TimerType) {
unsafe { unsafe {
crate::interrupt::bind_interrupt( interrupt::bind_interrupt(Interrupt::SYSTIMER_TARGET0, target0_handler.handler());
peripherals::Interrupt::SYSTIMER_TARGET0, unwrap!(interrupt::enable(
target0_handler.handler(), Interrupt::SYSTIMER_TARGET0,
);
unwrap!(crate::interrupt::enable(
peripherals::Interrupt::SYSTIMER_TARGET0,
target0_handler.priority() target0_handler.priority()
)); ));
crate::interrupt::bind_interrupt( interrupt::bind_interrupt(Interrupt::SYSTIMER_TARGET1, target1_handler.handler());
peripherals::Interrupt::SYSTIMER_TARGET1, unwrap!(interrupt::enable(
target1_handler.handler(), Interrupt::SYSTIMER_TARGET1,
);
unwrap!(crate::interrupt::enable(
peripherals::Interrupt::SYSTIMER_TARGET1,
target1_handler.priority() target1_handler.priority()
)); ));
crate::interrupt::bind_interrupt( interrupt::bind_interrupt(Interrupt::SYSTIMER_TARGET2, target2_handler.handler());
peripherals::Interrupt::SYSTIMER_TARGET2, unwrap!(interrupt::enable(
target2_handler.handler(), Interrupt::SYSTIMER_TARGET2,
);
unwrap!(crate::interrupt::enable(
peripherals::Interrupt::SYSTIMER_TARGET2,
target2_handler.priority() target2_handler.priority()
)); ));
} }
@ -107,11 +98,7 @@ impl EmbassyTimer {
} }
} }
pub(crate) fn set_alarm( pub(crate) fn set_alarm(&self, alarm: AlarmHandle, timestamp: u64) -> bool {
&self,
alarm: embassy_time_driver::AlarmHandle,
timestamp: u64,
) -> bool {
critical_section::with(|_cs| { critical_section::with(|_cs| {
let n = alarm.id() as usize; let n = alarm.id() as usize;
@ -139,9 +126,9 @@ impl EmbassyTimer {
fn arm(&self, id: usize, timestamp: u64) { fn arm(&self, id: usize, timestamp: u64) {
match id { match id {
0 => self.alarm0.load_value(timestamp.micros()).unwrap(), 0 => self.alarm0.set_target(timestamp),
1 => self.alarm1.load_value(timestamp.micros()).unwrap(), 1 => self.alarm1.set_target(timestamp),
2 => self.alarm2.load_value(timestamp.micros()).unwrap(), 2 => self.alarm2.set_target(timestamp),
_ => {} _ => {}
} }
} }

View File

@ -1,27 +1,30 @@
use critical_section::{CriticalSection, Mutex}; use critical_section::{CriticalSection, Mutex};
use peripherals::TIMG0; use embassy_time_driver::AlarmHandle;
use super::AlarmState;
#[cfg(any(esp32, esp32s2, esp32s3))] #[cfg(any(esp32, esp32s2, esp32s3))]
use crate::timer::timg::Timer1; use esp_hal::timer::timg::Timer1;
use crate::{ use esp_hal::{
clock::Clocks, clock::Clocks,
peripherals, interrupt::{self, Priority},
peripherals::{Interrupt, TIMG0},
prelude::*, prelude::*,
timer::timg::{Instance, Timer0, TimerGroup}, timer::timg::{Instance, Timer0, TimerGroup},
Async,
}; };
use crate::AlarmState;
#[cfg(not(any(esp32, esp32s2, esp32s3)))] #[cfg(not(any(esp32, esp32s2, esp32s3)))]
pub const ALARM_COUNT: usize = 1; pub const ALARM_COUNT: usize = 1;
#[cfg(any(esp32, esp32s2, esp32s3))] #[cfg(any(esp32, esp32s2, esp32s3))]
pub const ALARM_COUNT: usize = 2; pub const ALARM_COUNT: usize = 2;
pub type TimerType = TimerGroup<'static, TIMG0, crate::Async>; pub type TimerType = TimerGroup<'static, TIMG0, Async>;
pub struct EmbassyTimer { pub struct EmbassyTimer {
pub(crate) alarms: Mutex<[AlarmState; ALARM_COUNT]>, pub(crate) alarms: Mutex<[AlarmState; ALARM_COUNT]>,
} }
#[allow(clippy::declare_interior_mutable_const)]
const ALARM_STATE_NONE: AlarmState = AlarmState::new(); const ALARM_STATE_NONE: AlarmState = AlarmState::new();
embassy_time_driver::time_driver_impl!(static DRIVER: EmbassyTimer = EmbassyTimer { embassy_time_driver::time_driver_impl!(static DRIVER: EmbassyTimer = EmbassyTimer {
@ -41,7 +44,7 @@ impl EmbassyTimer {
} }
} }
pub(super) fn on_alarm_allocated(&self, _n: usize) {} pub(crate) fn on_alarm_allocated(&self, _n: usize) {}
fn on_interrupt<Timer: Instance>(&self, id: u8, timer: Timer) { fn on_interrupt<Timer: Instance>(&self, id: u8, timer: Timer) {
critical_section::with(|cs| { critical_section::with(|cs| {
@ -62,48 +65,36 @@ impl EmbassyTimer {
} }
unsafe { unsafe {
crate::interrupt::bind_interrupt( interrupt::bind_interrupt(Interrupt::TG0_T0_LEVEL, tg0_t0_level.handler());
crate::peripherals::Interrupt::TG0_T0_LEVEL, unwrap!(interrupt::enable(
tg0_t0_level.handler(), Interrupt::TG0_T0_LEVEL,
); tg0_t0_level.priority()
crate::interrupt::enable( ));
crate::peripherals::Interrupt::TG0_T0_LEVEL,
tg0_t0_level.priority(),
)
.unwrap();
} }
#[cfg(any(esp32, esp32s2, esp32s3))] #[cfg(any(esp32, esp32s2, esp32s3))]
unsafe { unsafe {
crate::interrupt::bind_interrupt( interrupt::bind_interrupt(Interrupt::TG0_T1_LEVEL, tg0_t1_level.handler());
crate::peripherals::Interrupt::TG0_T1_LEVEL, unwrap!(interrupt::enable(
tg0_t1_level.handler(), Interrupt::TG0_T1_LEVEL,
); tg0_t1_level.priority()
crate::interrupt::enable( ));
crate::peripherals::Interrupt::TG0_T1_LEVEL,
tg0_t1_level.priority(),
)
.unwrap();
} }
#[handler(priority = crate::interrupt::Priority::max())] #[handler(priority = Priority::max())]
fn tg0_t0_level() { fn tg0_t0_level() {
let timer = unsafe { Timer0::<TIMG0>::steal() }; let timer = unsafe { Timer0::<TIMG0>::steal() };
DRIVER.on_interrupt(0, timer); DRIVER.on_interrupt(0, timer);
} }
#[cfg(any(esp32, esp32s2, esp32s3))] #[cfg(any(esp32, esp32s2, esp32s3))]
#[handler(priority = crate::interrupt::Priority::max())] #[handler(priority = Priority::max())]
fn tg0_t1_level() { fn tg0_t1_level() {
let timer = unsafe { Timer1::<TIMG0>::steal() }; let timer = unsafe { Timer1::<TIMG0>::steal() };
DRIVER.on_interrupt(1, timer); DRIVER.on_interrupt(1, timer);
} }
} }
pub(crate) fn set_alarm( pub(crate) fn set_alarm(&self, _alarm: AlarmHandle, timestamp: u64) -> bool {
&self,
_alarm: embassy_time_driver::AlarmHandle,
timestamp: u64,
) -> bool {
critical_section::with(|_cs| { critical_section::with(|_cs| {
// The hardware fires the alarm even if timestamp is lower than the current // The hardware fires the alarm even if timestamp is lower than the current
// time. In this case the interrupt handler will pend a wakeup when we exit the // time. In this case the interrupt handler will pend a wakeup when we exit the
@ -122,7 +113,10 @@ impl EmbassyTimer {
true true
} }
fn arm<Timer: Instance>(tg: &mut Timer, timestamp: u64) { fn arm<T>(tg: &mut T, timestamp: u64)
where
T: Instance,
{
tg.load_alarm_value(timestamp); tg.load_alarm_value(timestamp);
tg.listen(); tg.listen();
tg.set_counter_decrementing(false); tg.set_counter_decrementing(false);

View File

@ -22,8 +22,7 @@ pub(crate) mod main {
use std::{cell::RefCell, fmt::Display, thread}; use std::{cell::RefCell, fmt::Display, thread};
use darling::{export::NestedMeta, FromMeta}; use darling::{export::NestedMeta, FromMeta};
use proc_macro2::{Ident, Span, TokenStream}; use proc_macro2::TokenStream;
use proc_macro_crate::{crate_name, FoundCrate};
use quote::{quote, ToTokens}; use quote::{quote, ToTokens};
use syn::{ReturnType, Type}; use syn::{ReturnType, Type};
@ -157,23 +156,10 @@ pub(crate) mod main {
} }
pub fn main() -> TokenStream { pub fn main() -> TokenStream {
let hal_crate = if cfg!(any(feature = "is-lp-core", feature = "is-ulp-core")) {
crate_name("esp-lp-hal")
} else {
crate_name("esp-hal")
};
let executor = if let Ok(FoundCrate::Name(ref name)) = hal_crate {
let ident = Ident::new(&name, Span::call_site().into());
quote!( #ident::embassy::executor::Executor )
} else {
quote!(crate::embassy::executor::Executor)
};
quote! { quote! {
#[entry] #[entry]
fn main() -> ! { fn main() -> ! {
let mut executor = #executor::new(); let mut executor = ::esp_hal_embassy::Executor::new();
let executor = unsafe { __make_static(&mut executor) }; let executor = unsafe { __make_static(&mut executor) };
executor.run(|spawner| { executor.run(|spawner| {
spawner.must_spawn(__embassy_main(spawner)); spawner.must_spawn(__embassy_main(spawner));

View File

@ -52,6 +52,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Removed the `SystemExt` trait (#1495) - Removed the `SystemExt` trait (#1495)
- Removed the `GpioExt` trait (#1496) - Removed the `GpioExt` trait (#1496)
- Embassy support (and all related features) has been removed, now available in the `esp-hal-embassy` package instead (#1595)
## [0.17.0] - 2024-04-18 ## [0.17.0] - 2024-04-18

View File

@ -22,10 +22,8 @@ critical-section = "1.1.2"
defmt = { version = "0.3.6", optional = true } defmt = { version = "0.3.6", optional = true }
delegate = "0.12.0" delegate = "0.12.0"
document-features = "0.2.8" document-features = "0.2.8"
embassy-executor = { version = "0.5.0", optional = true }
embassy-futures = { version = "0.1.1", optional = true } embassy-futures = { version = "0.1.1", optional = true }
embassy-sync = { version = "0.5.0", optional = true } embassy-sync = { version = "0.5.0", optional = true }
embassy-time-driver = { version = "0.1.0", optional = true }
embassy-usb-driver = { version = "0.1.0", optional = true } embassy-usb-driver = { version = "0.1.0", optional = true }
embassy-usb-synopsys-otg = { version = "0.1.0", optional = true } embassy-usb-synopsys-otg = { version = "0.1.0", optional = true }
embedded-can = { version = "0.4.1", optional = true } embedded-can = { version = "0.4.1", optional = true }
@ -43,7 +41,7 @@ log = { version = "0.4.21", optional = true }
nb = "1.1.0" nb = "1.1.0"
paste = "1.0.14" paste = "1.0.14"
portable-atomic = { version = "1.6.0", default-features = false } portable-atomic = { version = "1.6.0", default-features = false }
procmacros = { version = "0.10.0", features = ["enum-dispatch", "interrupt", "ram"], package = "esp-hal-procmacros", path = "../esp-hal-procmacros" } procmacros = { version = "0.10.0", features = ["embassy", "enum-dispatch", "interrupt", "ram"], package = "esp-hal-procmacros", path = "../esp-hal-procmacros" }
riscv = { version = "0.11.1", optional = true } riscv = { version = "0.11.1", optional = true }
strum = { version = "0.26.2", default-features = false, features = ["derive"] } strum = { version = "0.26.2", default-features = false, features = ["derive"] }
void = { version = "1.0.2", default-features = false } void = { version = "1.0.2", default-features = false }
@ -145,7 +143,6 @@ async = [
## Implement `defmt::Format` on certain types. ## Implement `defmt::Format` on certain types.
defmt = [ defmt = [
"dep:defmt", "dep:defmt",
"embassy-executor?/defmt",
"embassy-futures?/defmt", "embassy-futures?/defmt",
"embassy-sync?/defmt", "embassy-sync?/defmt",
"embedded-hal?/defmt-03", "embedded-hal?/defmt-03",
@ -169,25 +166,6 @@ embedded-io = ["dep:embedded-io"]
## Implement the `ufmt_write::uWrite` trait for certain peripherals. ## Implement the `ufmt_write::uWrite` trait for certain peripherals.
ufmt = ["dep:ufmt-write"] ufmt = ["dep:ufmt-write"]
#! ### Embassy Feature Flags
## Enable support for `embassy`, a modern asynchronous embedded framework.
embassy = ["embassy-time-driver", "procmacros/embassy", "embassy-executor"]
## Uses hardware timers as alarms for the executors. Using this feature
## limits the number of executors to the number of hardware alarms provided
## by the time driver.
embassy-integrated-timers = ["embassy-executor?/integrated-timers"]
## Enable the embassy time driver using the `SYSTIMER` peripheral. The
## `SYSTIMER` peripheral has three alarams available for use. Do **not**
## use when targeting an `esp32s2`.
embassy-time-systick-16mhz = ["embassy-time-driver/tick-hz-16_000_000"]
## Enable the embassy time driver using the `SYSTIMER` peripheral. The
## `SYSTIMER` peripheral has three alarams available for use. Must only
## be used when targeting an `esp32s2`.
embassy-time-systick-80mhz = ["embassy-time-driver/tick-hz-80_000_000"]
## Enable the embassy time driver using the `TIMG0` peripheral. The `TIMG0`
## peripheral has two alarms available for use.
embassy-time-timg0 = ["embassy-time-driver/tick-hz-1_000_000"]
#! ### PSRAM Feature Flags #! ### PSRAM Feature Flags
## Use externally connected PSRAM (2MB). ## Use externally connected PSRAM (2MB).
psram-2m = [] psram-2m = []
@ -209,15 +187,7 @@ opsram-8m = []
opsram-16m = [] opsram-16m = []
# This feature is intended for testing; you probably don't want to enable it: # This feature is intended for testing; you probably don't want to enable it:
ci = [ ci = ["async", "embedded-hal-02", "embedded-io", "ufmt"]
"default",
"embedded-hal-02",
"ufmt",
"async",
"embassy",
"embassy-time-timg0",
"embedded-io"
]
[lints.clippy] [lints.clippy]
mixed_attributes_style = "allow" mixed_attributes_style = "allow"

View File

@ -26,19 +26,6 @@ fn main() -> Result<(), Box<dyn Error>> {
"esp32", "esp32c2", "esp32c3", "esp32c6", "esp32h2", "esp32s2", "esp32s3" "esp32", "esp32c2", "esp32c3", "esp32c6", "esp32h2", "esp32s2", "esp32s3"
); );
// If the `embassy` feature is enabled, ensure that a time driver implementation
// is available:
#[cfg(feature = "embassy")]
cfg_if::cfg_if! {
if #[cfg(feature = "esp32")] {
assert_unique_used_features!("embassy-time-timg0");
} else if #[cfg(feature = "esp32s2")] {
assert_unique_used_features!("embassy-time-systick-80mhz", "embassy-time-timg0");
} else {
assert_unique_used_features!("embassy-time-systick-16mhz", "embassy-time-timg0");
}
}
#[cfg(all( #[cfg(all(
feature = "flip-link", feature = "flip-link",
not(any(feature = "esp32c6", feature = "esp32h2")) not(any(feature = "esp32c6", feature = "esp32h2"))

View File

@ -1,107 +0,0 @@
//! # Embassy
//!
//! The [embassy](https://github.com/embassy-rs/embassy) project is a toolkit to leverage async Rust
//! in embedded applications. This module adds the required
//! support to use embassy on Espressif chips.
//!
//! ## Initialization
//!
//! Embassy **must** be initialized by calling [`init`], before beginning any
//! async operations.
//!
//! [`init`] installs a [global time driver](https://github.com/embassy-rs/embassy/tree/main/embassy-time#global-time-driver)
//! allowing users to use [embassy-time](https://docs.rs/embassy-time/latest/embassy_time/) APIs in any async context
//! within their application. A time driver must be chosen by enabling the
//! correct feature on esp-hal, see the crate level documentation for more
//! details.
//!
//! ## Executors
//!
//! We offer two executor types, a thread mode [`Executor`](executor::Executor)
//! and [`InterruptExecutor`](executor::InterruptExecutor).
//! An [`InterruptExecutor`](executor::InterruptExecutor) can be used to achieve
//! preemptive multitasking in async applications, which is usually something reserved for more traditional RTOS systems, read more about it in [the embassy documentation](https://embassy.dev/book/dev/runtime.html).
pub mod executor;
use core::cell::Cell;
use embassy_time_driver::{AlarmHandle, Driver};
#[cfg_attr(
all(
systimer,
any(
feature = "embassy-time-systick-16mhz",
feature = "embassy-time-systick-80mhz"
)
),
path = "time_driver_systimer.rs"
)]
#[cfg_attr(
all(timg0, feature = "embassy-time-timg0"),
path = "time_driver_timg.rs"
)]
mod time_driver;
use time_driver::EmbassyTimer;
use crate::clock::Clocks;
/// Initialize embassy
pub fn init(clocks: &Clocks, time_driver: time_driver::TimerType) {
EmbassyTimer::init(clocks, time_driver)
}
pub(crate) struct AlarmState {
pub callback: Cell<Option<(fn(*mut ()), *mut ())>>,
pub allocated: Cell<bool>,
}
unsafe impl Send for AlarmState {}
impl AlarmState {
pub const fn new() -> Self {
Self {
callback: Cell::new(None),
allocated: Cell::new(false),
}
}
}
impl Driver for EmbassyTimer {
fn now(&self) -> u64 {
EmbassyTimer::now()
}
unsafe fn allocate_alarm(&self) -> Option<AlarmHandle> {
critical_section::with(|cs| {
for (i, alarm) in self.alarms.borrow(cs).iter().enumerate() {
if !alarm.allocated.get() {
// set alarm so it is not overwritten
alarm.allocated.set(true);
self.on_alarm_allocated(i);
return Some(AlarmHandle::new(i as u8));
}
}
None
})
}
fn set_alarm_callback(
&self,
alarm: embassy_time_driver::AlarmHandle,
callback: fn(*mut ()),
ctx: *mut (),
) {
let n = alarm.id() as usize;
critical_section::with(|cs| {
let alarm = &self.alarms.borrow(cs)[n];
alarm.callback.set(Some((callback, ctx)));
})
}
fn set_alarm(&self, alarm: embassy_time_driver::AlarmHandle, timestamp: u64) -> bool {
self.set_alarm(alarm, timestamp)
}
}

View File

@ -104,8 +104,6 @@ pub mod delay;
pub mod dma; pub mod dma;
#[cfg(ecc)] #[cfg(ecc)]
pub mod ecc; pub mod ecc;
#[cfg(feature = "embassy")]
pub mod embassy;
#[cfg(soc_etm)] #[cfg(soc_etm)]
pub mod etm; pub mod etm;
#[cfg(gpio)] #[cfg(gpio)]

View File

@ -227,7 +227,7 @@ where
DM: Mode, DM: Mode,
{ {
/// Set the target value of this [Alarm] /// Set the target value of this [Alarm]
pub fn set_target(&mut self, timestamp: u64) { pub fn set_target(&self, timestamp: u64) {
self.configure(|tconf, target| unsafe { self.configure(|tconf, target| unsafe {
tconf.write(|w| w.period_mode().clear_bit()); // target mode tconf.write(|w| w.period_mode().clear_bit()); // target mode
target.hi().write(|w| w.hi().bits((timestamp >> 32) as u32)); target.hi().write(|w| w.hi().bits((timestamp >> 32) as u32));
@ -238,7 +238,7 @@ where
} }
/// Block waiting until the timer reaches the `timestamp` /// Block waiting until the timer reaches the `timestamp`
pub fn wait_until(&mut self, timestamp: u64) { pub fn wait_until(&self, timestamp: u64) {
self.clear_interrupt(); self.clear_interrupt();
self.set_target(timestamp); self.set_target(timestamp);
@ -261,7 +261,7 @@ where
DM: Mode, DM: Mode,
{ {
/// Set the period of this [Alarm] /// Set the period of this [Alarm]
pub fn set_period(&mut self, period: MicrosDurationU32) { pub fn set_period(&self, period: MicrosDurationU32) {
let us = period.ticks(); let us = period.ticks();
let ticks = us * (SystemTimer::TICKS_PER_SECOND / 1_000_000) as u32; let ticks = us * (SystemTimer::TICKS_PER_SECOND / 1_000_000) as u32;

View File

@ -611,8 +611,14 @@ impl<TG, const T: u8> TimerX<TG, T>
where where
TG: TimerGroupInstance, TG: TimerGroupInstance,
{ {
/// Unsafely create an instance of this peripheral out of thin air.
///
/// # Safety
///
/// You must ensure that you're only using one instance of this type at a
/// time.
#[allow(unused)] #[allow(unused)]
pub(crate) unsafe fn steal() -> Self { pub unsafe fn steal() -> Self {
Self { Self {
phantom: PhantomData, phantom: PhantomData,
} }

View File

@ -13,6 +13,7 @@ categories = ["embedded", "hardware-support", "no-std"]
[dependencies] [dependencies]
defmt = { version = "0.3.6", optional = true } defmt = { version = "0.3.6", optional = true }
esp-hal = { version = "0.17.0", path = "../esp-hal", default-features = false } esp-hal = { version = "0.17.0", path = "../esp-hal", default-features = false }
esp-hal-embassy = { version = "0.1.0", path = "../esp-hal-embassy", optional = true }
smoltcp = { version = "0.11.0", default-features = false, features = [ smoltcp = { version = "0.11.0", default-features = false, features = [
"medium-ethernet", "medium-ethernet",
"socket-raw", "socket-raw",
@ -61,30 +62,37 @@ default = ["log"]
# chip features # chip features
esp32c2 = [ esp32c2 = [
"esp-hal/esp32c2", "esp-hal/esp32c2",
"esp-hal-embassy?/esp32c2",
"esp-wifi-sys/esp32c2", "esp-wifi-sys/esp32c2",
] ]
esp32c3 = [ esp32c3 = [
"esp-hal/esp32c3", "esp-hal/esp32c3",
"esp-hal-embassy?/esp32c3",
"esp-wifi-sys/esp32c3", "esp-wifi-sys/esp32c3",
] ]
esp32c6 = [ esp32c6 = [
"esp-hal/esp32c6", "esp-hal/esp32c6",
"esp-hal-embassy?/esp32c6",
"esp-wifi-sys/esp32c6", "esp-wifi-sys/esp32c6",
] ]
esp32h2 = [ esp32h2 = [
"esp-hal/esp32h2", "esp-hal/esp32h2",
"esp-hal-embassy?/esp32h2",
"esp-wifi-sys/esp32h2", "esp-wifi-sys/esp32h2",
] ]
esp32 = [ esp32 = [
"esp-hal/esp32", "esp-hal/esp32",
"esp-hal-embassy?/esp32",
"esp-wifi-sys/esp32", "esp-wifi-sys/esp32",
] ]
esp32s2 = [ esp32s2 = [
"esp-hal/esp32s2", "esp-hal/esp32s2",
"esp-hal-embassy?/esp32s2",
"esp-wifi-sys/esp32s2", "esp-wifi-sys/esp32s2",
] ]
esp32s3 = [ esp32s3 = [
"esp-hal/esp32s3", "esp-hal/esp32s3",
"esp-hal-embassy?/esp32s3",
"esp-wifi-sys/esp32s3", "esp-wifi-sys/esp32s3",
] ]
@ -93,6 +101,8 @@ async = [
"dep:embassy-sync", "dep:embassy-sync",
"dep:embassy-futures", "dep:embassy-futures",
"dep:embedded-io-async", "dep:embedded-io-async",
"dep:esp-hal-embassy",
"esp-hal/async",
] ]
embassy-net = ["dep:embassy-net-driver", "async"] embassy-net = ["dep:embassy-net-driver", "async"]
@ -131,7 +141,7 @@ features = [
"coex", "coex",
"async", "async",
"embassy-net", "embassy-net",
"esp-hal/embassy-time-timg0", "esp-hal-embassy/time-timg0",
"esp-hal/default", "esp-hal/default",
] ]
default-target = "riscv32imc-unknown-none-elf" default-target = "riscv32imc-unknown-none-elf"

View File

@ -30,7 +30,7 @@ pub fn setup_timer(systimer: TimeBase) -> Result<(), esp_hal::timer::Error> {
// make sure the scheduling won't start before everything is setup // make sure the scheduling won't start before everything is setup
riscv::interrupt::disable(); riscv::interrupt::disable();
let mut alarm0 = systimer.into_periodic(); let alarm0 = systimer.into_periodic();
alarm0.set_period(TIMESLICE_FREQUENCY.into_duration()); alarm0.set_period(TIMESLICE_FREQUENCY.into_duration());
alarm0.clear_interrupt(); alarm0.clear_interrupt();
alarm0.enable_interrupt(true); alarm0.enable_interrupt(true);
@ -83,8 +83,8 @@ extern "C" fn FROM_CPU_INTR3(trap_frame: &mut TrapFrame) {
} }
critical_section::with(|cs| { critical_section::with(|cs| {
let mut alarm0 = ALARM0.borrow_ref_mut(cs); let alarm0 = ALARM0.borrow_ref(cs);
let alarm0 = unwrap!(alarm0.as_mut()); let alarm0 = unwrap!(alarm0.as_ref());
alarm0.set_period(TIMESLICE_FREQUENCY.into_duration()); alarm0.set_period(TIMESLICE_FREQUENCY.into_duration());
alarm0.clear_interrupt(); alarm0.clear_interrupt();

View File

@ -28,6 +28,11 @@ rustflags = [
[env] [env]
ESP_LOGLEVEL = "info" ESP_LOGLEVEL = "info"
SSID = "SSID"
PASSWORD = "PASSWORD"
STATIC_IP = "1.1.1.1 "
GATEWAY_IP = "1.1.1.1"
HOST_IP = "1.1.1.1"
[unstable] [unstable]
build-std = ["alloc", "core"] build-std = ["alloc", "core"]

View File

@ -31,6 +31,7 @@ embedded-storage = "0.3.0"
esp-alloc = { path = "../esp-alloc" } esp-alloc = { path = "../esp-alloc" }
esp-backtrace = { path = "../esp-backtrace", features = ["exception-handler", "panic-handler", "println"] } esp-backtrace = { path = "../esp-backtrace", features = ["exception-handler", "panic-handler", "println"] }
esp-hal = { path = "../esp-hal", features = ["log"] } esp-hal = { path = "../esp-hal", features = ["log"] }
esp-hal-embassy = { path = "../esp-hal-embassy", optional = true }
esp-hal-smartled = { path = "../esp-hal-smartled", optional = true } esp-hal-smartled = { path = "../esp-hal-smartled", optional = true }
esp-ieee802154 = { path = "../esp-ieee802154", optional = true } esp-ieee802154 = { path = "../esp-ieee802154", optional = true }
esp-println = { path = "../esp-println", features = ["log"] } esp-println = { path = "../esp-println", features = ["log"] }
@ -56,13 +57,13 @@ usb-device = "0.3.2"
usbd-serial = "0.2.1" usbd-serial = "0.2.1"
[features] [features]
esp32 = ["esp-hal/esp32", "esp-backtrace/esp32", "esp-println/esp32", "esp-hal-smartled/esp32", "esp-wifi?/esp32", "esp-storage?/esp32"] esp32 = ["esp-hal/esp32", "esp-backtrace/esp32", "esp-hal-embassy?/esp32", "esp-println/esp32", "esp-storage?/esp32", "esp-wifi?/esp32", "esp-hal-smartled/esp32"]
esp32c2 = ["esp-hal/esp32c2", "esp-backtrace/esp32c2", "esp-println/esp32c2", "esp-wifi?/esp32c2", "esp-storage?/esp32c2"] esp32c2 = ["esp-hal/esp32c2", "esp-backtrace/esp32c2", "esp-hal-embassy?/esp32c2", "esp-println/esp32c2", "esp-storage?/esp32c2", "esp-wifi?/esp32c2", ]
esp32c3 = ["esp-hal/esp32c3", "esp-backtrace/esp32c3", "esp-println/esp32c3", "esp-hal-smartled/esp32c3", "esp-wifi?/esp32c3", "esp-storage?/esp32c3"] esp32c3 = ["esp-hal/esp32c3", "esp-backtrace/esp32c3", "esp-hal-embassy?/esp32c3", "esp-println/esp32c3", "esp-storage?/esp32c3", "esp-wifi?/esp32c3", "esp-hal-smartled/esp32c3"]
esp32c6 = ["esp-hal/esp32c6", "esp-backtrace/esp32c6", "esp-println/esp32c6", "esp-hal-smartled/esp32c6", "esp-ieee802154/esp32c6", "esp-wifi?/esp32c6", "esp-storage?/esp32c6"] esp32c6 = ["esp-hal/esp32c6", "esp-backtrace/esp32c6", "esp-hal-embassy?/esp32c6", "esp-println/esp32c6", "esp-storage?/esp32c6", "esp-wifi?/esp32c6", "esp-hal-smartled/esp32c6", "esp-ieee802154/esp32c6"]
esp32h2 = ["esp-hal/esp32h2", "esp-backtrace/esp32h2", "esp-println/esp32h2", "esp-hal-smartled/esp32h2", "esp-ieee802154/esp32h2", "esp-wifi?/esp32h2", "esp-storage?/esp32h2"] esp32h2 = ["esp-hal/esp32h2", "esp-backtrace/esp32h2", "esp-hal-embassy?/esp32h2", "esp-println/esp32h2", "esp-storage?/esp32h2", "esp-wifi?/esp32h2", "esp-hal-smartled/esp32h2", "esp-ieee802154/esp32h2"]
esp32s2 = ["esp-hal/esp32s2", "esp-backtrace/esp32s2", "esp-println/esp32s2", "esp-hal-smartled/esp32s2", "esp-wifi?/esp32s2", "esp-storage?/esp32s2"] esp32s2 = ["esp-hal/esp32s2", "esp-backtrace/esp32s2", "esp-hal-embassy?/esp32s2", "esp-println/esp32s2", "esp-storage?/esp32s2", "esp-wifi?/esp32s2", "esp-hal-smartled/esp32s2"]
esp32s3 = ["esp-hal/esp32s3", "esp-backtrace/esp32s3", "esp-println/esp32s3", "esp-hal-smartled/esp32s3", "esp-wifi?/esp32s3", "esp-storage?/esp32s3"] esp32s3 = ["esp-hal/esp32s3", "esp-backtrace/esp32s3", "esp-hal-embassy?/esp32s3", "esp-println/esp32s3", "esp-storage?/esp32s3", "esp-wifi?/esp32s3", "esp-hal-smartled/esp32s3"]
esp-wifi = ["dep:esp-wifi"] esp-wifi = ["dep:esp-wifi"]
@ -71,10 +72,10 @@ async = ["esp-hal/async", "embassy-usb"]
embedded-hal-02 = ["esp-hal/embedded-hal-02"] embedded-hal-02 = ["esp-hal/embedded-hal-02"]
embedded-hal = ["esp-hal/embedded-hal"] embedded-hal = ["esp-hal/embedded-hal"]
embassy = ["esp-hal/embassy"] embassy = ["dep:esp-hal-embassy"]
embassy-time-systick-16mhz = ["esp-hal/embassy-time-systick-16mhz"] embassy-time-systimer-16mhz = ["esp-hal-embassy/time-systimer-16mhz"]
embassy-time-timg0 = ["esp-hal/embassy-time-timg0"] embassy-time-timg0 = ["esp-hal-embassy/time-timg0"]
embassy-generic-timers = ["embassy-time/generic-queue-8"] embassy-generic-timers = ["embassy-time/generic-queue-8"]
opsram-2m = ["esp-hal/opsram-2m"] opsram-2m = ["esp-hal/opsram-2m"]

View File

@ -14,7 +14,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy::{self},
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
system::SystemControl, system::SystemControl,
@ -37,7 +36,7 @@ async fn main(spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
spawner.spawn(run()).ok(); spawner.spawn(run()).ok();

View File

@ -21,7 +21,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy::{self},
gpio::Io, gpio::Io,
i2c::I2C, i2c::I2C,
peripherals::Peripherals, peripherals::Peripherals,
@ -38,7 +37,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -22,7 +22,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy::{self},
gpio::Io, gpio::Io,
i2c::I2C, i2c::I2C,
peripherals::Peripherals, peripherals::Peripherals,
@ -38,7 +37,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -23,7 +23,6 @@ use esp_hal::{
clock::ClockControl, clock::ClockControl,
dma::{Dma, DmaPriority}, dma::{Dma, DmaPriority},
dma_buffers, dma_buffers,
embassy,
gpio::Io, gpio::Io,
i2s::{asynch::*, DataFormat, I2s, Standard}, i2s::{asynch::*, DataFormat, I2s, Standard},
peripherals::Peripherals, peripherals::Peripherals,
@ -41,7 +40,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -38,7 +38,6 @@ use esp_hal::{
clock::ClockControl, clock::ClockControl,
dma::{Dma, DmaPriority}, dma::{Dma, DmaPriority},
dma_buffers, dma_buffers,
embassy::{self},
gpio::Io, gpio::Io,
i2s::{asynch::*, DataFormat, I2s, Standard}, i2s::{asynch::*, DataFormat, I2s, Standard},
peripherals::Peripherals, peripherals::Peripherals,
@ -64,7 +63,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -18,7 +18,6 @@ use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
cpu_control::{CpuControl, Stack}, cpu_control::{CpuControl, Stack},
embassy::{self, executor::Executor},
get_core, get_core,
gpio::{AnyOutput, Io, Level}, gpio::{AnyOutput, Io, Level},
peripherals::Peripherals, peripherals::Peripherals,
@ -26,6 +25,7 @@ use esp_hal::{
system::SystemControl, system::SystemControl,
timer::timg::TimerGroup, timer::timg::TimerGroup,
}; };
use esp_hal_embassy::Executor;
use esp_println::println; use esp_println::println;
use static_cell::StaticCell; use static_cell::StaticCell;
@ -59,7 +59,7 @@ async fn main(_spawner: Spawner) {
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let mut cpu_control = CpuControl::new(peripherals.CPU_CTRL); let mut cpu_control = CpuControl::new(peripherals.CPU_CTRL);

View File

@ -17,7 +17,6 @@ use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
cpu_control::{CpuControl, Stack}, cpu_control::{CpuControl, Stack},
embassy::{self, executor::InterruptExecutor},
get_core, get_core,
gpio::{AnyOutput, Io, Level}, gpio::{AnyOutput, Io, Level},
interrupt::Priority, interrupt::Priority,
@ -26,6 +25,7 @@ use esp_hal::{
system::SystemControl, system::SystemControl,
timer::timg::TimerGroup, timer::timg::TimerGroup,
}; };
use esp_hal_embassy::InterruptExecutor;
use esp_println::println; use esp_println::println;
use static_cell::StaticCell; use static_cell::StaticCell;
@ -78,7 +78,7 @@ fn main() -> ! {
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let mut cpu_control = CpuControl::new(peripherals.CPU_CTRL); let mut cpu_control = CpuControl::new(peripherals.CPU_CTRL);

View File

@ -25,13 +25,13 @@ use embassy_time::{Duration, Instant, Ticker, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy::{self, executor::InterruptExecutor},
interrupt::Priority, interrupt::Priority,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
system::SystemControl, system::SystemControl,
timer::timg::TimerGroup, timer::timg::TimerGroup,
}; };
use esp_hal_embassy::InterruptExecutor;
use esp_println::println; use esp_println::println;
use static_cell::StaticCell; use static_cell::StaticCell;
@ -79,7 +79,7 @@ async fn main(low_prio_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
static EXECUTOR: StaticCell<InterruptExecutor<2>> = StaticCell::new(); static EXECUTOR: StaticCell<InterruptExecutor<2>> = StaticCell::new();
let executor = InterruptExecutor::new(system.software_interrupt_control.software_interrupt2); let executor = InterruptExecutor::new(system.software_interrupt_control.software_interrupt2);

View File

@ -16,7 +16,6 @@ use esp_hal::{
clock::ClockControl, clock::ClockControl,
dma::{Dma, DmaPriority}, dma::{Dma, DmaPriority},
dma_buffers, dma_buffers,
embassy,
gpio::Io, gpio::Io,
parl_io::{no_clk_pin, BitPackOrder, ParlIoRxOnly, RxFourBits}, parl_io::{no_clk_pin, BitPackOrder, ParlIoRxOnly, RxFourBits},
peripherals::Peripherals, peripherals::Peripherals,
@ -34,7 +33,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -20,7 +20,6 @@ use esp_hal::{
clock::ClockControl, clock::ClockControl,
dma::{Dma, DmaPriority}, dma::{Dma, DmaPriority},
dma_buffers, dma_buffers,
embassy,
gpio::Io, gpio::Io,
parl_io::{ parl_io::{
BitPackOrder, BitPackOrder,
@ -45,7 +44,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -12,7 +12,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy::{self},
gpio::{Gpio5, Io, Level, Output}, gpio::{Gpio5, Io, Level, Output},
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
@ -45,7 +44,7 @@ async fn main(spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timer_group0 = esp_hal::timer::timg::TimerGroup::new_async(peripherals.TIMG0, &clocks); let timer_group0 = esp_hal::timer::timg::TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timer_group0); esp_hal_embassy::init(&clocks, timer_group0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -13,7 +13,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
gpio::Io, gpio::Io,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
@ -31,7 +30,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -14,7 +14,6 @@ use embassy_sync::{blocking_mutex::raw::NoopRawMutex, signal::Signal};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
peripherals::{Peripherals, UART0}, peripherals::{Peripherals, UART0},
prelude::*, prelude::*,
system::SystemControl, system::SystemControl,
@ -81,7 +80,7 @@ async fn main(spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let mut uart0 = Uart::new_async(peripherals.UART0, &clocks); let mut uart0 = Uart::new_async(peripherals.UART0, &clocks);
uart0.set_at_cmd(AtCmdConfig::new(None, None, None, AT_CMD, None)); uart0.set_at_cmd(AtCmdConfig::new(None, None, None, AT_CMD, None));

View File

@ -27,7 +27,6 @@ use esp_hal::{
clock::ClockControl, clock::ClockControl,
dma::*, dma::*,
dma_descriptors, dma_descriptors,
embassy::{self},
gpio::Io, gpio::Io,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
@ -47,7 +46,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);
let sclk = io.pins.gpio0; let sclk = io.pins.gpio0;

View File

@ -22,7 +22,6 @@ use embedded_can::{Frame, Id};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy::{self},
gpio::Io, gpio::Io,
interrupt, interrupt,
peripherals::{self, Peripherals, TWAI0}, peripherals::{self, Peripherals, TWAI0},
@ -87,7 +86,7 @@ async fn main(spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);

View File

@ -18,7 +18,6 @@ use embassy_usb::{
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
gpio::Io, gpio::Io,
otg_fs::{ otg_fs::{
asynch::{Config, Driver}, asynch::{Config, Driver},
@ -37,7 +36,7 @@ async fn main(_spawner: Spawner) -> () {
let system = SystemControl::new(peripherals.SYSTEM); let system = SystemControl::new(peripherals.SYSTEM);
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
embassy::init(&clocks, TimerGroup::new_async(peripherals.TIMG0, &clocks)); esp_hal_embassy::init(&clocks, TimerGroup::new_async(peripherals.TIMG0, &clocks));
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);
let usb = Usb::new(peripherals.USB0, io.pins.gpio19, io.pins.gpio20); let usb = Usb::new(peripherals.USB0, io.pins.gpio19, io.pins.gpio20);

View File

@ -13,7 +13,6 @@ use embassy_sync::{blocking_mutex::raw::NoopRawMutex, signal::Signal};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
system::SystemControl, system::SystemControl,
@ -71,7 +70,7 @@ async fn main(spawner: Spawner) -> () {
let system = SystemControl::new(peripherals.SYSTEM); let system = SystemControl::new(peripherals.SYSTEM);
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
embassy::init(&clocks, TimerGroup::new_async(peripherals.TIMG0, &clocks)); esp_hal_embassy::init(&clocks, TimerGroup::new_async(peripherals.TIMG0, &clocks));
let (tx, rx) = UsbSerialJtag::new_async(peripherals.USB_DEVICE).split(); let (tx, rx) = UsbSerialJtag::new_async(peripherals.USB_DEVICE).split();

View File

@ -13,7 +13,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
gpio::{Input, Io, Pull}, gpio::{Input, Io, Pull},
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
@ -29,7 +28,7 @@ async fn main(_spawner: Spawner) {
let clocks = ClockControl::boot_defaults(system.clock_control).freeze(); let clocks = ClockControl::boot_defaults(system.clock_control).freeze();
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
let io = Io::new(peripherals.GPIO, peripherals.IO_MUX); let io = Io::new(peripherals.GPIO, peripherals.IO_MUX);
#[cfg(any(feature = "esp32", feature = "esp32s2", feature = "esp32s3"))] #[cfg(any(feature = "esp32", feature = "esp32s2", feature = "esp32s3"))]

View File

@ -29,7 +29,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
rng::Rng, rng::Rng,
@ -87,7 +86,7 @@ async fn main(spawner: Spawner) -> ! {
esp_wifi::wifi::new_with_mode(&init, wifi, WifiApDevice).unwrap(); esp_wifi::wifi::new_with_mode(&init, wifi, WifiApDevice).unwrap();
let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timer_group0); esp_hal_embassy::init(&clocks, timer_group0);
let config = Config::ipv4_static(StaticConfigV4 { let config = Config::ipv4_static(StaticConfigV4 {
address: Ipv4Cidr::new(Ipv4Address::new(192, 168, 2, 1), 24), address: Ipv4Cidr::new(Ipv4Address::new(192, 168, 2, 1), 24),

View File

@ -32,7 +32,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
rng::Rng, rng::Rng,
@ -95,7 +94,7 @@ async fn main(spawner: Spawner) -> ! {
esp_wifi::wifi::new_ap_sta(&init, wifi).unwrap(); esp_wifi::wifi::new_ap_sta(&init, wifi).unwrap();
let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timer_group0); esp_hal_embassy::init(&clocks, timer_group0);
let ap_config = Config::ipv4_static(StaticConfigV4 { let ap_config = Config::ipv4_static(StaticConfigV4 {
address: Ipv4Cidr::new(Ipv4Address::new(192, 168, 2, 1), 24), address: Ipv4Cidr::new(Ipv4Address::new(192, 168, 2, 1), 24),

View File

@ -23,7 +23,6 @@ use embassy_time::{with_timeout, Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
rng::Rng, rng::Rng,
@ -99,7 +98,7 @@ async fn main(spawner: Spawner) -> ! {
esp_wifi::wifi::new_with_mode(&init, wifi, WifiStaDevice).unwrap(); esp_wifi::wifi::new_with_mode(&init, wifi, WifiStaDevice).unwrap();
let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timer_group0); esp_hal_embassy::init(&clocks, timer_group0);
let config = Config::dhcpv4(Default::default()); let config = Config::dhcpv4(Default::default());

View File

@ -28,7 +28,6 @@ use embassy_executor::Spawner;
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
gpio::{Input, Io, Pull}, gpio::{Input, Io, Pull},
peripherals::*, peripherals::*,
prelude::*, prelude::*,
@ -73,7 +72,7 @@ async fn main(_spawner: Spawner) -> ! {
let button = Input::new(io.pins.gpio9, Pull::Down); let button = Input::new(io.pins.gpio9, Pull::Down);
let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timer_group0); esp_hal_embassy::init(&clocks, timer_group0);
let mut bluetooth = peripherals.BT; let mut bluetooth = peripherals.BT;

View File

@ -19,7 +19,6 @@ use embassy_time::{Duration, Timer};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
rng::Rng, rng::Rng,
@ -80,7 +79,7 @@ async fn main(spawner: Spawner) -> ! {
esp_wifi::wifi::new_with_mode(&init, wifi, WifiStaDevice).unwrap(); esp_wifi::wifi::new_with_mode(&init, wifi, WifiStaDevice).unwrap();
let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timer_group0); esp_hal_embassy::init(&clocks, timer_group0);
let config = Config::dhcpv4(Default::default()); let config = Config::dhcpv4(Default::default());

View File

@ -16,7 +16,6 @@ use embassy_time::{Duration, Ticker};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
rng::Rng, rng::Rng,
@ -57,7 +56,7 @@ async fn main(_spawner: Spawner) -> ! {
println!("esp-now version {}", esp_now.get_version().unwrap()); println!("esp-now version {}", esp_now.get_version().unwrap());
let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timer_group0); esp_hal_embassy::init(&clocks, timer_group0);
let mut ticker = Ticker::every(Duration::from_secs(5)); let mut ticker = Ticker::every(Duration::from_secs(5));
loop { loop {

View File

@ -16,7 +16,6 @@ use embassy_time::{Duration, Ticker};
use esp_backtrace as _; use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
embassy,
peripherals::Peripherals, peripherals::Peripherals,
prelude::*, prelude::*,
rng::Rng, rng::Rng,
@ -66,7 +65,7 @@ async fn main(spawner: Spawner) -> ! {
println!("esp-now version {}", esp_now.get_version().unwrap()); println!("esp-now version {}", esp_now.get_version().unwrap());
let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timer_group0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timer_group0); esp_hal_embassy::init(&clocks, timer_group0);
let (manager, sender, receiver) = esp_now.split(); let (manager, sender, receiver) = esp_now.split();
let manager = mk_static!(EspNowManager<'static>, manager); let manager = mk_static!(EspNowManager<'static>, manager);

View File

@ -82,6 +82,7 @@ embedded-hal-async = { version = "1.0.0", optional = true }
embedded-hal-nb = { version = "1.0.0", optional = true } embedded-hal-nb = { version = "1.0.0", optional = true }
esp-backtrace = { path = "../esp-backtrace", default-features = false, features = ["exception-handler", "panic-handler", "defmt", "semihosting"] } esp-backtrace = { path = "../esp-backtrace", default-features = false, features = ["exception-handler", "panic-handler", "defmt", "semihosting"] }
esp-hal = { path = "../esp-hal", features = ["defmt", "embedded-hal", "embedded-hal-02"], optional = true } esp-hal = { path = "../esp-hal", features = ["defmt", "embedded-hal", "embedded-hal-02"], optional = true }
esp-hal-embassy = { path = "../esp-hal-embassy", optional = true }
portable-atomic = "1.6.0" portable-atomic = "1.6.0"
[dev-dependencies] [dev-dependencies]
@ -103,31 +104,34 @@ esp32 = [
"embedded-test/xtensa-semihosting", "embedded-test/xtensa-semihosting",
"esp-backtrace/esp32", "esp-backtrace/esp32",
"esp-hal/esp32", "esp-hal/esp32",
"esp-hal-embassy/esp32",
] ]
esp32c2 = ["esp-backtrace/esp32c2", "esp-hal/esp32c2"] esp32c2 = ["esp-backtrace/esp32c2", "esp-hal/esp32c2", "esp-hal-embassy/esp32c2"]
esp32c3 = ["esp-backtrace/esp32c3", "esp-hal/esp32c3"] esp32c3 = ["esp-backtrace/esp32c3", "esp-hal/esp32c3", "esp-hal-embassy/esp32c3"]
esp32c6 = ["esp-backtrace/esp32c6", "esp-hal/esp32c6"] esp32c6 = ["esp-backtrace/esp32c6", "esp-hal/esp32c6", "esp-hal-embassy/esp32c6"]
esp32h2 = ["esp-backtrace/esp32h2", "esp-hal/esp32h2"] esp32h2 = ["esp-backtrace/esp32h2", "esp-hal/esp32h2", "esp-hal-embassy/esp32h2"]
esp32s2 = [ esp32s2 = [
"embedded-test/xtensa-semihosting", "embedded-test/xtensa-semihosting",
"esp-backtrace/esp32s2", "esp-backtrace/esp32s2",
"esp-hal/esp32s2", "esp-hal/esp32s2",
"esp-hal-embassy/esp32s2",
] ]
esp32s3 = [ esp32s3 = [
"embedded-test/xtensa-semihosting", "embedded-test/xtensa-semihosting",
"esp-backtrace/esp32s3", "esp-backtrace/esp32s3",
"esp-hal/esp32s3", "esp-hal/esp32s3",
"esp-hal-embassy/esp32s3",
] ]
# Async & Embassy: # Async & Embassy:
async = ["dep:embedded-hal-async", "esp-hal?/async"] async = ["dep:embedded-hal-async", "esp-hal?/async"]
embassy = [ embassy = [
"embedded-test/embassy", "embedded-test/embassy",
"embedded-test/external-executor", "embedded-test/external-executor",
"esp-hal?/embassy", "dep:esp-hal-embassy",
] ]
embassy-time-systick-16mhz = ["esp-hal?/embassy-time-systick-16mhz"] embassy-time-systimer-16mhz = ["esp-hal-embassy/time-systimer-16mhz"]
embassy-time-systick-80mhz = ["esp-hal?/embassy-time-systick-80mhz"] embassy-time-systimer-80mhz = ["esp-hal-embassy/time-systimer-80mhz"]
embassy-time-timg0 = ["esp-hal?/embassy-time-timg0"] embassy-time-timg0 = ["esp-hal-embassy/time-timg0"]
# https://doc.rust-lang.org/cargo/reference/profiles.html#test # https://doc.rust-lang.org/cargo/reference/profiles.html#test
# Test and bench profiles inherit from dev and release respectively. # Test and bench profiles inherit from dev and release respectively.

View File

@ -17,7 +17,6 @@ use esp_backtrace as _;
use esp_hal::{ use esp_hal::{
clock::ClockControl, clock::ClockControl,
delay::Delay, delay::Delay,
embassy,
gpio::{Gpio2, Gpio4, GpioPin, Input, Io, Level, Output, Pull}, gpio::{Gpio2, Gpio4, GpioPin, Input, Io, Level, Output, Pull},
macros::handler, macros::handler,
peripherals::Peripherals, peripherals::Peripherals,
@ -46,7 +45,7 @@ impl<'d> Context<'d> {
let delay = Delay::new(&clocks); let delay = Delay::new(&clocks);
let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks); let timg0 = TimerGroup::new_async(peripherals.TIMG0, &clocks);
embassy::init(&clocks, timg0); esp_hal_embassy::init(&clocks, timg0);
Context { Context {
io2: Input::new(io.pins.gpio2, Pull::Down), io2: Input::new(io.pins.gpio2, Pull::Down),
@ -68,7 +67,7 @@ pub fn interrupt_handler() {
} }
#[cfg(test)] #[cfg(test)]
#[embedded_test::tests(executor = esp_hal::embassy::executor::Executor::new())] #[embedded_test::tests(executor = esp_hal_embassy::Executor::new())]
mod tests { mod tests {
use defmt::assert_eq; use defmt::assert_eq;
use embassy_time::{Duration, Timer}; use embassy_time::{Duration, Timer};

View File

@ -44,7 +44,7 @@ impl Context {
} }
#[cfg(test)] #[cfg(test)]
#[embedded_test::tests(executor = esp_hal::embassy::executor::Executor::new())] #[embedded_test::tests(executor = esp_hal_embassy::Executor::new())]
mod tests { mod tests {
use defmt::assert_eq; use defmt::assert_eq;

View File

@ -22,6 +22,7 @@ pub enum Package {
EspBacktrace, EspBacktrace,
EspBuild, EspBuild,
EspHal, EspHal,
EspHalEmbassy,
EspHalProcmacros, EspHalProcmacros,
EspHalSmartled, EspHalSmartled,
EspIeee802154, EspIeee802154,

View File

@ -467,6 +467,21 @@ fn lint_packages(workspace: &Path, _args: LintPackagesArgs) -> Result<()> {
} }
} }
Package::EspHalEmbassy => {
// We need to specify a time driver, so we will check all
// options here (as the modules themselves are feature-gated):
for feature in ["time-systimer-16mhz", "time-timg0"] {
lint_package(
&path,
&[
"-Zbuild-std=core",
"--target=riscv32imac-unknown-none-elf",
&format!("--features=esp32c6,{feature}"),
],
)?;
}
}
Package::EspHalProcmacros | Package::EspRiscvRt => lint_package( Package::EspHalProcmacros | Package::EspRiscvRt => lint_package(
&path, &path,
&["-Zbuild-std=core", "--target=riscv32imc-unknown-none-elf"], &["-Zbuild-std=core", "--target=riscv32imc-unknown-none-elf"],
@ -504,7 +519,7 @@ fn lint_packages(workspace: &Path, _args: LintPackagesArgs) -> Result<()> {
&[ &[
"-Zbuild-std=core", "-Zbuild-std=core",
"--target=riscv32imc-unknown-none-elf", "--target=riscv32imc-unknown-none-elf",
"--features=esp32c3,wifi-default,ble,esp-now,async,embassy-net", "--features=esp32c3,wifi-default,ble,esp-now,async,embassy-net,esp-hal-embassy/time-timg0",
], ],
)?, )?,