diff options
Diffstat (limited to 'embassy-nrf/src')
| -rw-r--r-- | embassy-nrf/src/buffered_uarte.rs | 50 | ||||
| -rw-r--r-- | embassy-nrf/src/gpiote.rs | 75 | ||||
| -rw-r--r-- | embassy-nrf/src/lib.rs | 4 |
3 files changed, 63 insertions, 66 deletions
diff --git a/embassy-nrf/src/buffered_uarte.rs b/embassy-nrf/src/buffered_uarte.rs index 9e138ad4f..db6a83fb4 100644 --- a/embassy-nrf/src/buffered_uarte.rs +++ b/embassy-nrf/src/buffered_uarte.rs | |||
| @@ -17,10 +17,10 @@ use embedded_hal::digital::v2::OutputPin; | |||
| 17 | 17 | ||
| 18 | use crate::hal::gpio::{Floating, Input, Output, Pin as GpioPin, Port as GpioPort, PushPull}; | 18 | use crate::hal::gpio::{Floating, Input, Output, Pin as GpioPin, Port as GpioPort, PushPull}; |
| 19 | use crate::interrupt; | 19 | use crate::interrupt; |
| 20 | use crate::interrupt::CriticalSection; | 20 | use crate::interrupt::{CriticalSection, OwnedInterrupt}; |
| 21 | #[cfg(any(feature = "52833", feature = "52840", feature = "9160"))] | 21 | #[cfg(any(feature = "52833", feature = "52840", feature = "9160"))] |
| 22 | use crate::pac::UARTE1; | 22 | use crate::pac::UARTE1; |
| 23 | use crate::pac::{uarte0, Interrupt, UARTE0}; | 23 | use crate::pac::{uarte0, UARTE0}; |
| 24 | 24 | ||
| 25 | // Re-export SVD variants to allow user to directly set values | 25 | // Re-export SVD variants to allow user to directly set values |
| 26 | pub use uarte0::{baudrate::BAUDRATE_A as Baudrate, config::PARITY_A as Parity}; | 26 | pub use uarte0::{baudrate::BAUDRATE_A as Baudrate, config::PARITY_A as Parity}; |
| @@ -141,8 +141,9 @@ pub struct BufferedUarte<T: Instance> { | |||
| 141 | // public because it needs to be used in Instance::{get_state, set_state}, but | 141 | // public because it needs to be used in Instance::{get_state, set_state}, but |
| 142 | // should not be used outside the module | 142 | // should not be used outside the module |
| 143 | #[doc(hidden)] | 143 | #[doc(hidden)] |
| 144 | pub struct UarteState<T> { | 144 | pub struct UarteState<T: Instance> { |
| 145 | inner: T, | 145 | inner: T, |
| 146 | irq: T::Interrupt, | ||
| 146 | 147 | ||
| 147 | rx: RingBuf, | 148 | rx: RingBuf, |
| 148 | rx_state: RxState, | 149 | rx_state: RxState, |
| @@ -164,7 +165,13 @@ fn port_bit(port: GpioPort) -> bool { | |||
| 164 | } | 165 | } |
| 165 | 166 | ||
| 166 | impl<T: Instance> BufferedUarte<T> { | 167 | impl<T: Instance> BufferedUarte<T> { |
| 167 | pub fn new(uarte: T, mut pins: Pins, parity: Parity, baudrate: Baudrate) -> Self { | 168 | pub fn new( |
| 169 | uarte: T, | ||
| 170 | irq: T::Interrupt, | ||
| 171 | mut pins: Pins, | ||
| 172 | parity: Parity, | ||
| 173 | baudrate: Baudrate, | ||
| 174 | ) -> Self { | ||
| 168 | // Select pins | 175 | // Select pins |
| 169 | uarte.psel.rxd.write(|w| { | 176 | uarte.psel.rxd.write(|w| { |
| 170 | let w = unsafe { w.pin().bits(pins.rxd.pin()) }; | 177 | let w = unsafe { w.pin().bits(pins.rxd.pin()) }; |
| @@ -222,6 +229,7 @@ impl<T: Instance> BufferedUarte<T> { | |||
| 222 | started: false, | 229 | started: false, |
| 223 | state: UnsafeCell::new(UarteState { | 230 | state: UnsafeCell::new(UarteState { |
| 224 | inner: uarte, | 231 | inner: uarte, |
| 232 | irq, | ||
| 225 | 233 | ||
| 226 | rx: RingBuf::new(), | 234 | rx: RingBuf::new(), |
| 227 | rx_state: RxState::Idle, | 235 | rx_state: RxState::Idle, |
| @@ -287,9 +295,12 @@ impl<T: Instance> AsyncWrite for BufferedUarte<T> { | |||
| 287 | 295 | ||
| 288 | impl<T: Instance> UarteState<T> { | 296 | impl<T: Instance> UarteState<T> { |
| 289 | pub fn start(self: Pin<&mut Self>) { | 297 | pub fn start(self: Pin<&mut Self>) { |
| 290 | interrupt::set_priority(T::interrupt(), interrupt::Priority::Level7); | 298 | self.irq.set_handler(|| unsafe { |
| 291 | interrupt::enable(T::interrupt()); | 299 | interrupt::free(|cs| T::get_state(cs).as_mut().unwrap().on_interrupt()); |
| 292 | interrupt::pend(T::interrupt()); | 300 | }); |
| 301 | |||
| 302 | self.irq.pend(); | ||
| 303 | self.irq.enable(); | ||
| 293 | } | 304 | } |
| 294 | 305 | ||
| 295 | fn poll_fill_buf(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<&[u8]>> { | 306 | fn poll_fill_buf(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Result<&[u8]>> { |
| @@ -324,7 +335,7 @@ impl<T: Instance> UarteState<T> { | |||
| 324 | let this = unsafe { self.get_unchecked_mut() }; | 335 | let this = unsafe { self.get_unchecked_mut() }; |
| 325 | trace!("consume {:?}", amt); | 336 | trace!("consume {:?}", amt); |
| 326 | this.rx.pop(amt); | 337 | this.rx.pop(amt); |
| 327 | interrupt::pend(T::interrupt()); | 338 | this.irq.pend(); |
| 328 | } | 339 | } |
| 329 | 340 | ||
| 330 | fn poll_write(self: Pin<&mut Self>, cx: &mut Context<'_>, buf: &[u8]) -> Poll<Result<usize>> { | 341 | fn poll_write(self: Pin<&mut Self>, cx: &mut Context<'_>, buf: &[u8]) -> Poll<Result<usize>> { |
| @@ -350,7 +361,7 @@ impl<T: Instance> UarteState<T> { | |||
| 350 | // before any DMA action has started | 361 | // before any DMA action has started |
| 351 | compiler_fence(Ordering::SeqCst); | 362 | compiler_fence(Ordering::SeqCst); |
| 352 | 363 | ||
| 353 | interrupt::pend(T::interrupt()); | 364 | this.irq.pend(); |
| 354 | 365 | ||
| 355 | Poll::Ready(Ok(n)) | 366 | Poll::Ready(Ok(n)) |
| 356 | } | 367 | } |
| @@ -509,7 +520,7 @@ mod private { | |||
| 509 | } | 520 | } |
| 510 | 521 | ||
| 511 | pub trait Instance: Deref<Target = uarte0::RegisterBlock> + Sized + private::Sealed { | 522 | pub trait Instance: Deref<Target = uarte0::RegisterBlock> + Sized + private::Sealed { |
| 512 | fn interrupt() -> Interrupt; | 523 | type Interrupt: OwnedInterrupt; |
| 513 | 524 | ||
| 514 | #[doc(hidden)] | 525 | #[doc(hidden)] |
| 515 | fn get_state(_cs: &CriticalSection) -> *mut UarteState<Self>; | 526 | fn get_state(_cs: &CriticalSection) -> *mut UarteState<Self>; |
| @@ -518,25 +529,12 @@ pub trait Instance: Deref<Target = uarte0::RegisterBlock> + Sized + private::Sea | |||
| 518 | fn set_state(_cs: &CriticalSection, state: *mut UarteState<Self>); | 529 | fn set_state(_cs: &CriticalSection, state: *mut UarteState<Self>); |
| 519 | } | 530 | } |
| 520 | 531 | ||
| 521 | #[interrupt] | ||
| 522 | unsafe fn UARTE0_UART0() { | ||
| 523 | interrupt::free(|cs| UARTE0::get_state(cs).as_mut().unwrap().on_interrupt()); | ||
| 524 | } | ||
| 525 | |||
| 526 | #[cfg(any(feature = "52833", feature = "52840", feature = "9160"))] | ||
| 527 | #[interrupt] | ||
| 528 | unsafe fn UARTE1() { | ||
| 529 | interrupt::free(|cs| UARTE1::get_state(cs).as_mut().unwrap().on_interrupt()); | ||
| 530 | } | ||
| 531 | |||
| 532 | static mut UARTE0_STATE: *mut UarteState<UARTE0> = ptr::null_mut(); | 532 | static mut UARTE0_STATE: *mut UarteState<UARTE0> = ptr::null_mut(); |
| 533 | #[cfg(any(feature = "52833", feature = "52840", feature = "9160"))] | 533 | #[cfg(any(feature = "52833", feature = "52840", feature = "9160"))] |
| 534 | static mut UARTE1_STATE: *mut UarteState<UARTE1> = ptr::null_mut(); | 534 | static mut UARTE1_STATE: *mut UarteState<UARTE1> = ptr::null_mut(); |
| 535 | 535 | ||
| 536 | impl Instance for UARTE0 { | 536 | impl Instance for UARTE0 { |
| 537 | fn interrupt() -> Interrupt { | 537 | type Interrupt = interrupt::UARTE0_UART0Interrupt; |
| 538 | Interrupt::UARTE0_UART0 | ||
| 539 | } | ||
| 540 | 538 | ||
| 541 | fn get_state(_cs: &CriticalSection) -> *mut UarteState<Self> { | 539 | fn get_state(_cs: &CriticalSection) -> *mut UarteState<Self> { |
| 542 | unsafe { UARTE0_STATE } // Safe because of CriticalSection | 540 | unsafe { UARTE0_STATE } // Safe because of CriticalSection |
| @@ -548,9 +546,7 @@ impl Instance for UARTE0 { | |||
| 548 | 546 | ||
| 549 | #[cfg(any(feature = "52833", feature = "52840", feature = "9160"))] | 547 | #[cfg(any(feature = "52833", feature = "52840", feature = "9160"))] |
| 550 | impl Instance for UARTE1 { | 548 | impl Instance for UARTE1 { |
| 551 | fn interrupt() -> Interrupt { | 549 | type Interrupt = interrupt::UARTE1Interrupt; |
| 552 | Interrupt::UARTE1 | ||
| 553 | } | ||
| 554 | 550 | ||
| 555 | fn get_state(_cs: &CriticalSection) -> *mut UarteState<Self> { | 551 | fn get_state(_cs: &CriticalSection) -> *mut UarteState<Self> { |
| 556 | unsafe { UARTE1_STATE } // Safe because of CriticalSection | 552 | unsafe { UARTE1_STATE } // Safe because of CriticalSection |
diff --git a/embassy-nrf/src/gpiote.rs b/embassy-nrf/src/gpiote.rs index 069e9140b..353f6a94c 100644 --- a/embassy-nrf/src/gpiote.rs +++ b/embassy-nrf/src/gpiote.rs | |||
| @@ -7,6 +7,7 @@ use embassy::util::Signal; | |||
| 7 | 7 | ||
| 8 | use crate::hal::gpio::{Input, Level, Output, Pin, Port}; | 8 | use crate::hal::gpio::{Input, Level, Output, Pin, Port}; |
| 9 | use crate::interrupt; | 9 | use crate::interrupt; |
| 10 | use crate::interrupt::OwnedInterrupt; | ||
| 10 | use crate::pac::generic::Reg; | 11 | use crate::pac::generic::Reg; |
| 11 | use crate::pac::gpiote::_TASKS_OUT; | 12 | use crate::pac::gpiote::_TASKS_OUT; |
| 12 | #[cfg(any(feature = "52833", feature = "52840"))] | 13 | #[cfg(any(feature = "52833", feature = "52840"))] |
| @@ -58,7 +59,7 @@ pub enum NewChannelError { | |||
| 58 | } | 59 | } |
| 59 | 60 | ||
| 60 | impl Gpiote { | 61 | impl Gpiote { |
| 61 | pub fn new(gpiote: GPIOTE) -> Self { | 62 | pub fn new(gpiote: GPIOTE, irq: interrupt::GPIOTEInterrupt) -> Self { |
| 62 | #[cfg(any(feature = "52833", feature = "52840"))] | 63 | #[cfg(any(feature = "52833", feature = "52840"))] |
| 63 | let ports = unsafe { &[&*P0::ptr(), &*P1::ptr()] }; | 64 | let ports = unsafe { &[&*P0::ptr(), &*P1::ptr()] }; |
| 64 | #[cfg(not(any(feature = "52833", feature = "52840")))] | 65 | #[cfg(not(any(feature = "52833", feature = "52840")))] |
| @@ -74,8 +75,9 @@ impl Gpiote { | |||
| 74 | // Enable interrupts | 75 | // Enable interrupts |
| 75 | gpiote.events_port.write(|w| w); | 76 | gpiote.events_port.write(|w| w); |
| 76 | gpiote.intenset.write(|w| w.port().set()); | 77 | gpiote.intenset.write(|w| w.port().set()); |
| 77 | interrupt::unpend(interrupt::GPIOTE); | 78 | irq.set_handler(Self::on_irq); |
| 78 | interrupt::enable(interrupt::GPIOTE); | 79 | irq.unpend(); |
| 80 | irq.enable(); | ||
| 79 | 81 | ||
| 80 | Self { | 82 | Self { |
| 81 | inner: gpiote, | 83 | inner: gpiote, |
| @@ -293,6 +295,39 @@ impl Gpiote { | |||
| 293 | }) | 295 | }) |
| 294 | }) | 296 | }) |
| 295 | } | 297 | } |
| 298 | |||
| 299 | unsafe fn on_irq() { | ||
| 300 | let s = &(*INSTANCE); | ||
| 301 | |||
| 302 | for i in 0..8 { | ||
| 303 | if s.inner.events_in[i].read().bits() != 0 { | ||
| 304 | s.inner.events_in[i].write(|w| w); | ||
| 305 | s.channel_signals[i].signal(()); | ||
| 306 | } | ||
| 307 | } | ||
| 308 | |||
| 309 | if s.inner.events_port.read().bits() != 0 { | ||
| 310 | s.inner.events_port.write(|w| w); | ||
| 311 | |||
| 312 | #[cfg(any(feature = "52833", feature = "52840"))] | ||
| 313 | let ports = &[&*P0::ptr(), &*P1::ptr()]; | ||
| 314 | #[cfg(not(any(feature = "52833", feature = "52840")))] | ||
| 315 | let ports = &[&*P0::ptr()]; | ||
| 316 | |||
| 317 | let mut work = true; | ||
| 318 | while work { | ||
| 319 | work = false; | ||
| 320 | for (port, &p) in ports.iter().enumerate() { | ||
| 321 | for pin in BitIter(p.latch.read().bits()) { | ||
| 322 | work = true; | ||
| 323 | p.pin_cnf[pin as usize].modify(|_, w| w.sense().disabled()); | ||
| 324 | p.latch.write(|w| w.bits(1 << pin)); | ||
| 325 | s.port_signals[port * 32 + pin as usize].signal(()); | ||
| 326 | } | ||
| 327 | } | ||
| 328 | } | ||
| 329 | } | ||
| 330 | } | ||
| 296 | } | 331 | } |
| 297 | 332 | ||
| 298 | pub struct PortInputFuture<'a, T> { | 333 | pub struct PortInputFuture<'a, T> { |
| @@ -413,40 +448,6 @@ impl<'a> OutputChannel<'a> { | |||
| 413 | } | 448 | } |
| 414 | } | 449 | } |
| 415 | 450 | ||
| 416 | #[interrupt] | ||
| 417 | unsafe fn GPIOTE() { | ||
| 418 | let s = &(*INSTANCE); | ||
| 419 | |||
| 420 | for i in 0..8 { | ||
| 421 | if s.inner.events_in[i].read().bits() != 0 { | ||
| 422 | s.inner.events_in[i].write(|w| w); | ||
| 423 | s.channel_signals[i].signal(()); | ||
| 424 | } | ||
| 425 | } | ||
| 426 | |||
| 427 | if s.inner.events_port.read().bits() != 0 { | ||
| 428 | s.inner.events_port.write(|w| w); | ||
| 429 | |||
| 430 | #[cfg(any(feature = "52833", feature = "52840"))] | ||
| 431 | let ports = &[&*P0::ptr(), &*P1::ptr()]; | ||
| 432 | #[cfg(not(any(feature = "52833", feature = "52840")))] | ||
| 433 | let ports = &[&*P0::ptr()]; | ||
| 434 | |||
| 435 | let mut work = true; | ||
| 436 | while work { | ||
| 437 | work = false; | ||
| 438 | for (port, &p) in ports.iter().enumerate() { | ||
| 439 | for pin in BitIter(p.latch.read().bits()) { | ||
| 440 | work = true; | ||
| 441 | p.pin_cnf[pin as usize].modify(|_, w| w.sense().disabled()); | ||
| 442 | p.latch.write(|w| w.bits(1 << pin)); | ||
| 443 | s.port_signals[port * 32 + pin as usize].signal(()); | ||
| 444 | } | ||
| 445 | } | ||
| 446 | } | ||
| 447 | } | ||
| 448 | } | ||
| 449 | |||
| 450 | struct BitIter(u32); | 451 | struct BitIter(u32); |
| 451 | 452 | ||
| 452 | impl Iterator for BitIter { | 453 | impl Iterator for BitIter { |
diff --git a/embassy-nrf/src/lib.rs b/embassy-nrf/src/lib.rs index c63bfd995..0ca328138 100644 --- a/embassy-nrf/src/lib.rs +++ b/embassy-nrf/src/lib.rs | |||
| @@ -51,8 +51,8 @@ pub use nrf52840_hal as hal; | |||
| 51 | // This mod MUST go first, so that the others see its macros. | 51 | // This mod MUST go first, so that the others see its macros. |
| 52 | pub(crate) mod fmt; | 52 | pub(crate) mod fmt; |
| 53 | 53 | ||
| 54 | //pub mod buffered_uarte; | 54 | pub mod buffered_uarte; |
| 55 | //pub mod gpiote; | 55 | pub mod gpiote; |
| 56 | pub mod interrupt; | 56 | pub mod interrupt; |
| 57 | #[cfg(feature = "52840")] | 57 | #[cfg(feature = "52840")] |
| 58 | pub mod qspi; | 58 | pub mod qspi; |
