diff options
| -rw-r--r-- | embassy-rp/src/pio.rs | 59 | ||||
| -rw-r--r-- | examples/rp/src/bin/pio_async.rs | 10 | ||||
| -rw-r--r-- | examples/rp/src/bin/pio_dma.rs | 2 | ||||
| -rw-r--r-- | examples/rp/src/bin/pio_hd44780.rs | 4 | ||||
| -rw-r--r-- | examples/rp/src/bin/ws2812-pio.rs | 9 |
5 files changed, 30 insertions, 54 deletions
diff --git a/embassy-rp/src/pio.rs b/embassy-rp/src/pio.rs index 97e97b749..6827e5119 100644 --- a/embassy-rp/src/pio.rs +++ b/embassy-rp/src/pio.rs | |||
| @@ -792,7 +792,7 @@ pub trait PioStateMachine: sealed::PioStateMachine + Sized + Unpin { | |||
| 792 | } | 792 | } |
| 793 | } | 793 | } |
| 794 | 794 | ||
| 795 | pub struct PioCommonInstance<'d, PIO: PioInstance> { | 795 | pub struct PioCommon<'d, PIO: PioInstance> { |
| 796 | instructions_used: u32, | 796 | instructions_used: u32, |
| 797 | pio: PhantomData<&'d PIO>, | 797 | pio: PhantomData<&'d PIO>, |
| 798 | } | 798 | } |
| @@ -802,11 +802,8 @@ pub struct PioInstanceMemory<'d, PIO: PioInstance> { | |||
| 802 | pio: PhantomData<&'d PIO>, | 802 | pio: PhantomData<&'d PIO>, |
| 803 | } | 803 | } |
| 804 | 804 | ||
| 805 | impl<'d, PIO: PioInstance> sealed::PioCommon for PioCommonInstance<'d, PIO> { | 805 | impl<'d, PIO: PioInstance> PioCommon<'d, PIO> { |
| 806 | type Pio = PIO; | 806 | pub fn write_instr<I>(&mut self, start: usize, instrs: I) -> PioInstanceMemory<'d, PIO> |
| 807 | } | ||
| 808 | impl<'d, PIO: PioInstance> PioCommon for PioCommonInstance<'d, PIO> { | ||
| 809 | fn write_instr<I>(&mut self, start: usize, instrs: I) -> PioInstanceMemory<'d, Self::Pio> | ||
| 810 | where | 807 | where |
| 811 | I: Iterator<Item = u16>, | 808 | I: Iterator<Item = u16>, |
| 812 | { | 809 | { |
| @@ -833,58 +830,50 @@ impl<'d, PIO: PioInstance> PioCommon for PioCommonInstance<'d, PIO> { | |||
| 833 | } | 830 | } |
| 834 | } | 831 | } |
| 835 | 832 | ||
| 836 | fn free_instr(&mut self, instrs: PioInstanceMemory<Self::Pio>) { | 833 | // TODO make instruction memory that is currently in use unfreeable |
| 834 | pub fn free_instr(&mut self, instrs: PioInstanceMemory<PIO>) { | ||
| 837 | self.instructions_used &= !instrs.used_mask; | 835 | self.instructions_used &= !instrs.used_mask; |
| 838 | } | 836 | } |
| 839 | } | ||
| 840 | |||
| 841 | pub trait PioCommon: sealed::PioCommon + Sized { | ||
| 842 | fn write_instr<I>(&mut self, start: usize, instrs: I) -> PioInstanceMemory<Self::Pio> | ||
| 843 | where | ||
| 844 | I: Iterator<Item = u16>; | ||
| 845 | 837 | ||
| 846 | // TODO make instruction memory that is currently in use unfreeable | 838 | pub fn is_irq_set(&self, irq_no: u8) -> bool { |
| 847 | fn free_instr(&mut self, instrs: PioInstanceMemory<Self::Pio>); | ||
| 848 | |||
| 849 | fn is_irq_set(&self, irq_no: u8) -> bool { | ||
| 850 | assert!(irq_no < 8); | 839 | assert!(irq_no < 8); |
| 851 | unsafe { | 840 | unsafe { |
| 852 | let irq_flags = Self::Pio::PIO.irq(); | 841 | let irq_flags = PIO::PIO.irq(); |
| 853 | irq_flags.read().0 & (1 << irq_no) != 0 | 842 | irq_flags.read().0 & (1 << irq_no) != 0 |
| 854 | } | 843 | } |
| 855 | } | 844 | } |
| 856 | 845 | ||
| 857 | fn clear_irq(&mut self, irq_no: usize) { | 846 | pub fn clear_irq(&mut self, irq_no: usize) { |
| 858 | assert!(irq_no < 8); | 847 | assert!(irq_no < 8); |
| 859 | unsafe { Self::Pio::PIO.irq().write(|w| w.set_irq(1 << irq_no)) } | 848 | unsafe { PIO::PIO.irq().write(|w| w.set_irq(1 << irq_no)) } |
| 860 | } | 849 | } |
| 861 | 850 | ||
| 862 | fn clear_irqs(&mut self, mask: u8) { | 851 | pub fn clear_irqs(&mut self, mask: u8) { |
| 863 | unsafe { Self::Pio::PIO.irq().write(|w| w.set_irq(mask)) } | 852 | unsafe { PIO::PIO.irq().write(|w| w.set_irq(mask)) } |
| 864 | } | 853 | } |
| 865 | 854 | ||
| 866 | fn force_irq(&mut self, irq_no: usize) { | 855 | pub fn force_irq(&mut self, irq_no: usize) { |
| 867 | assert!(irq_no < 8); | 856 | assert!(irq_no < 8); |
| 868 | unsafe { Self::Pio::PIO.irq_force().write(|w| w.set_irq_force(1 << irq_no)) } | 857 | unsafe { PIO::PIO.irq_force().write(|w| w.set_irq_force(1 << irq_no)) } |
| 869 | } | 858 | } |
| 870 | 859 | ||
| 871 | fn set_input_sync_bypass<'a>(&'a mut self, bypass: u32, mask: u32) { | 860 | pub fn set_input_sync_bypass<'a>(&'a mut self, bypass: u32, mask: u32) { |
| 872 | unsafe { | 861 | unsafe { |
| 873 | // this can interfere with per-pin bypass functions. splitting the | 862 | // this can interfere with per-pin bypass functions. splitting the |
| 874 | // modification is going to be fine since nothing that relies on | 863 | // modification is going to be fine since nothing that relies on |
| 875 | // it can reasonably run before we finish. | 864 | // it can reasonably run before we finish. |
| 876 | Self::Pio::PIO.input_sync_bypass().write_set(|w| *w = mask & bypass); | 865 | PIO::PIO.input_sync_bypass().write_set(|w| *w = mask & bypass); |
| 877 | Self::Pio::PIO.input_sync_bypass().write_clear(|w| *w = mask & !bypass); | 866 | PIO::PIO.input_sync_bypass().write_clear(|w| *w = mask & !bypass); |
| 878 | } | 867 | } |
| 879 | } | 868 | } |
| 880 | 869 | ||
| 881 | fn get_input_sync_bypass(&self) -> u32 { | 870 | pub fn get_input_sync_bypass(&self) -> u32 { |
| 882 | unsafe { Self::Pio::PIO.input_sync_bypass().read() } | 871 | unsafe { PIO::PIO.input_sync_bypass().read() } |
| 883 | } | 872 | } |
| 884 | 873 | ||
| 885 | fn make_pio_pin(&self, pin: impl Pin) -> PioPin<Self::Pio> { | 874 | pub fn make_pio_pin(&self, pin: impl Pin) -> PioPin<PIO> { |
| 886 | unsafe { | 875 | unsafe { |
| 887 | pin.io().ctrl().write(|w| w.set_funcsel(Self::Pio::FUNCSEL.0)); | 876 | pin.io().ctrl().write(|w| w.set_funcsel(PIO::FUNCSEL.0)); |
| 888 | } | 877 | } |
| 889 | PioPin { | 878 | PioPin { |
| 890 | pin_bank: pin.pin_bank(), | 879 | pin_bank: pin.pin_bank(), |
| @@ -904,7 +893,7 @@ impl<const SM_NO: u8> sealed::SmInstance for SmInstanceBase<SM_NO> { | |||
| 904 | impl<const SM_NO: u8> SmInstance for SmInstanceBase<SM_NO> {} | 893 | impl<const SM_NO: u8> SmInstance for SmInstanceBase<SM_NO> {} |
| 905 | 894 | ||
| 906 | pub struct Pio<'d, PIO: PioInstance> { | 895 | pub struct Pio<'d, PIO: PioInstance> { |
| 907 | pub common: PioCommonInstance<'d, PIO>, | 896 | pub common: PioCommon<'d, PIO>, |
| 908 | pub sm0: PioStateMachineInstance<'d, PIO, SmInstanceBase<0>>, | 897 | pub sm0: PioStateMachineInstance<'d, PIO, SmInstanceBase<0>>, |
| 909 | pub sm1: PioStateMachineInstance<'d, PIO, SmInstanceBase<1>>, | 898 | pub sm1: PioStateMachineInstance<'d, PIO, SmInstanceBase<1>>, |
| 910 | pub sm2: PioStateMachineInstance<'d, PIO, SmInstanceBase<2>>, | 899 | pub sm2: PioStateMachineInstance<'d, PIO, SmInstanceBase<2>>, |
| @@ -914,7 +903,7 @@ pub struct Pio<'d, PIO: PioInstance> { | |||
| 914 | impl<'d, PIO: PioInstance> Pio<'d, PIO> { | 903 | impl<'d, PIO: PioInstance> Pio<'d, PIO> { |
| 915 | pub fn new(_pio: impl Peripheral<P = PIO> + 'd) -> Self { | 904 | pub fn new(_pio: impl Peripheral<P = PIO> + 'd) -> Self { |
| 916 | Self { | 905 | Self { |
| 917 | common: PioCommonInstance { | 906 | common: PioCommon { |
| 918 | instructions_used: 0, | 907 | instructions_used: 0, |
| 919 | pio: PhantomData, | 908 | pio: PhantomData, |
| 920 | }, | 909 | }, |
| @@ -945,10 +934,6 @@ pub trait PioInstance: sealed::PioInstance + Sized + Unpin { | |||
| 945 | } | 934 | } |
| 946 | 935 | ||
| 947 | mod sealed { | 936 | mod sealed { |
| 948 | pub trait PioCommon { | ||
| 949 | type Pio: super::PioInstance; | ||
| 950 | } | ||
| 951 | |||
| 952 | pub trait PioStateMachine { | 937 | pub trait PioStateMachine { |
| 953 | type Pio: super::PioInstance; | 938 | type Pio: super::PioInstance; |
| 954 | type Sm: super::SmInstance; | 939 | type Sm: super::SmInstance; |
diff --git a/examples/rp/src/bin/pio_async.rs b/examples/rp/src/bin/pio_async.rs index 69a22f238..50b001b69 100644 --- a/examples/rp/src/bin/pio_async.rs +++ b/examples/rp/src/bin/pio_async.rs | |||
| @@ -5,14 +5,12 @@ use defmt::info; | |||
| 5 | use embassy_executor::Spawner; | 5 | use embassy_executor::Spawner; |
| 6 | use embassy_rp::gpio::{AnyPin, Pin}; | 6 | use embassy_rp::gpio::{AnyPin, Pin}; |
| 7 | use embassy_rp::peripherals::PIO0; | 7 | use embassy_rp::peripherals::PIO0; |
| 8 | use embassy_rp::pio::{ | 8 | use embassy_rp::pio::{Pio, PioCommon, PioStateMachine, PioStateMachineInstance, ShiftDirection, Sm0, Sm1, Sm2}; |
| 9 | Pio, PioCommon, PioCommonInstance, PioStateMachine, PioStateMachineInstance, ShiftDirection, Sm0, Sm1, Sm2, | ||
| 10 | }; | ||
| 11 | use embassy_rp::pio_instr_util; | 9 | use embassy_rp::pio_instr_util; |
| 12 | use embassy_rp::relocate::RelocatedProgram; | 10 | use embassy_rp::relocate::RelocatedProgram; |
| 13 | use {defmt_rtt as _, panic_probe as _}; | 11 | use {defmt_rtt as _, panic_probe as _}; |
| 14 | 12 | ||
| 15 | fn setup_pio_task_sm0(pio: &mut PioCommonInstance<PIO0>, sm: &mut PioStateMachineInstance<PIO0, Sm0>, pin: AnyPin) { | 13 | fn setup_pio_task_sm0(pio: &mut PioCommon<PIO0>, sm: &mut PioStateMachineInstance<PIO0, Sm0>, pin: AnyPin) { |
| 16 | // Setup sm0 | 14 | // Setup sm0 |
| 17 | 15 | ||
| 18 | // Send data serially to pin | 16 | // Send data serially to pin |
| @@ -51,7 +49,7 @@ async fn pio_task_sm0(mut sm: PioStateMachineInstance<'static, PIO0, Sm0>) { | |||
| 51 | } | 49 | } |
| 52 | } | 50 | } |
| 53 | 51 | ||
| 54 | fn setup_pio_task_sm1(pio: &mut PioCommonInstance<PIO0>, sm: &mut PioStateMachineInstance<PIO0, Sm1>) { | 52 | fn setup_pio_task_sm1(pio: &mut PioCommon<PIO0>, sm: &mut PioStateMachineInstance<PIO0, Sm1>) { |
| 55 | // Setupm sm1 | 53 | // Setupm sm1 |
| 56 | 54 | ||
| 57 | // Read 0b10101 repeatedly until ISR is full | 55 | // Read 0b10101 repeatedly until ISR is full |
| @@ -78,7 +76,7 @@ async fn pio_task_sm1(mut sm: PioStateMachineInstance<'static, PIO0, Sm1>) { | |||
| 78 | } | 76 | } |
| 79 | } | 77 | } |
| 80 | 78 | ||
| 81 | fn setup_pio_task_sm2(pio: &mut PioCommonInstance<PIO0>, sm: &mut PioStateMachineInstance<PIO0, Sm2>) { | 79 | fn setup_pio_task_sm2(pio: &mut PioCommon<PIO0>, sm: &mut PioStateMachineInstance<PIO0, Sm2>) { |
| 82 | // Setup sm2 | 80 | // Setup sm2 |
| 83 | 81 | ||
| 84 | // Repeatedly trigger IRQ 3 | 82 | // Repeatedly trigger IRQ 3 |
diff --git a/examples/rp/src/bin/pio_dma.rs b/examples/rp/src/bin/pio_dma.rs index 33c320b8f..0f1f6df12 100644 --- a/examples/rp/src/bin/pio_dma.rs +++ b/examples/rp/src/bin/pio_dma.rs | |||
| @@ -4,7 +4,7 @@ | |||
| 4 | use defmt::info; | 4 | use defmt::info; |
| 5 | use embassy_executor::Spawner; | 5 | use embassy_executor::Spawner; |
| 6 | use embassy_futures::join::join; | 6 | use embassy_futures::join::join; |
| 7 | use embassy_rp::pio::{Pio, PioCommon, PioStateMachine, ShiftDirection}; | 7 | use embassy_rp::pio::{Pio, PioStateMachine, ShiftDirection}; |
| 8 | use embassy_rp::relocate::RelocatedProgram; | 8 | use embassy_rp::relocate::RelocatedProgram; |
| 9 | use embassy_rp::{pio_instr_util, Peripheral}; | 9 | use embassy_rp::{pio_instr_util, Peripheral}; |
| 10 | use {defmt_rtt as _, panic_probe as _}; | 10 | use {defmt_rtt as _, panic_probe as _}; |
diff --git a/examples/rp/src/bin/pio_hd44780.rs b/examples/rp/src/bin/pio_hd44780.rs index 994d4600a..20c6a0565 100644 --- a/examples/rp/src/bin/pio_hd44780.rs +++ b/examples/rp/src/bin/pio_hd44780.rs | |||
| @@ -8,9 +8,7 @@ use embassy_executor::Spawner; | |||
| 8 | use embassy_rp::dma::{AnyChannel, Channel}; | 8 | use embassy_rp::dma::{AnyChannel, Channel}; |
| 9 | use embassy_rp::gpio::Pin; | 9 | use embassy_rp::gpio::Pin; |
| 10 | use embassy_rp::peripherals::PIO0; | 10 | use embassy_rp::peripherals::PIO0; |
| 11 | use embassy_rp::pio::{ | 11 | use embassy_rp::pio::{FifoJoin, Pio, PioStateMachine, PioStateMachineInstance, ShiftDirection, SmInstanceBase}; |
| 12 | FifoJoin, Pio, PioCommon, PioStateMachine, PioStateMachineInstance, ShiftDirection, SmInstanceBase, | ||
| 13 | }; | ||
| 14 | use embassy_rp::pwm::{Config, Pwm}; | 12 | use embassy_rp::pwm::{Config, Pwm}; |
| 15 | use embassy_rp::relocate::RelocatedProgram; | 13 | use embassy_rp::relocate::RelocatedProgram; |
| 16 | use embassy_rp::{into_ref, Peripheral, PeripheralRef}; | 14 | use embassy_rp::{into_ref, Peripheral, PeripheralRef}; |
diff --git a/examples/rp/src/bin/ws2812-pio.rs b/examples/rp/src/bin/ws2812-pio.rs index 42c731bd7..a2121df42 100644 --- a/examples/rp/src/bin/ws2812-pio.rs +++ b/examples/rp/src/bin/ws2812-pio.rs | |||
| @@ -6,8 +6,7 @@ use defmt::*; | |||
| 6 | use embassy_executor::Spawner; | 6 | use embassy_executor::Spawner; |
| 7 | use embassy_rp::gpio::{self, Pin}; | 7 | use embassy_rp::gpio::{self, Pin}; |
| 8 | use embassy_rp::pio::{ | 8 | use embassy_rp::pio::{ |
| 9 | FifoJoin, Pio, PioCommon, PioCommonInstance, PioInstance, PioStateMachine, PioStateMachineInstance, ShiftDirection, | 9 | FifoJoin, Pio, PioCommon, PioInstance, PioStateMachine, PioStateMachineInstance, ShiftDirection, SmInstance, |
| 10 | SmInstance, | ||
| 11 | }; | 10 | }; |
| 12 | use embassy_rp::pio_instr_util; | 11 | use embassy_rp::pio_instr_util; |
| 13 | use embassy_rp::relocate::RelocatedProgram; | 12 | use embassy_rp::relocate::RelocatedProgram; |
| @@ -19,11 +18,7 @@ pub struct Ws2812<'d, P: PioInstance, S: SmInstance> { | |||
| 19 | } | 18 | } |
| 20 | 19 | ||
| 21 | impl<'d, P: PioInstance, S: SmInstance> Ws2812<'d, P, S> { | 20 | impl<'d, P: PioInstance, S: SmInstance> Ws2812<'d, P, S> { |
| 22 | pub fn new( | 21 | pub fn new(mut pio: PioCommon<'d, P>, mut sm: PioStateMachineInstance<'d, P, S>, pin: gpio::AnyPin) -> Self { |
| 23 | mut pio: PioCommonInstance<'d, P>, | ||
| 24 | mut sm: PioStateMachineInstance<'d, P, S>, | ||
| 25 | pin: gpio::AnyPin, | ||
| 26 | ) -> Self { | ||
| 27 | // Setup sm0 | 22 | // Setup sm0 |
| 28 | 23 | ||
| 29 | // prepare the PIO program | 24 | // prepare the PIO program |
