aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristian Perez Llamas <[email protected]>2022-11-09 22:47:55 +0100
committerChristian Perez Llamas <[email protected]>2022-11-09 23:08:09 +0100
commit356beabc3b11d78612c6958d1cfe542209e43558 (patch)
tree9a8ae6fdb8a2f98ae16f17b8fbd45702f15ff066
parent3760b60db382c8c4f8d7067a8d472affa6db928b (diff)
Apply config
-rw-r--r--embassy-nrf/src/i2s.rs85
-rw-r--r--examples/nrf/src/bin/i2s.rs2
2 files changed, 65 insertions, 22 deletions
diff --git a/embassy-nrf/src/i2s.rs b/embassy-nrf/src/i2s.rs
index e0fe6a6eb..8752dfdef 100644
--- a/embassy-nrf/src/i2s.rs
+++ b/embassy-nrf/src/i2s.rs
@@ -9,11 +9,10 @@
9//use embassy_hal_common::drop::OnDrop; 9//use embassy_hal_common::drop::OnDrop;
10use embassy_hal_common::{into_ref, PeripheralRef}; 10use embassy_hal_common::{into_ref, PeripheralRef};
11 11
12//use crate::pac::i2s::config::mcken;
13
14//use crate::gpio::sealed::Pin as _; 12//use crate::gpio::sealed::Pin as _;
15use crate::gpio::{AnyPin, Pin as GpioPin}; 13use crate::gpio::{AnyPin, Pin as GpioPin};
16use crate::interrupt::Interrupt; 14use crate::interrupt::Interrupt;
15use crate::pac::i2s::CONFIG;
17use crate::Peripheral; 16use crate::Peripheral;
18 17
19// TODO: Define those in lib.rs somewhere else 18// TODO: Define those in lib.rs somewhere else
@@ -40,7 +39,7 @@ pub enum Error {
40#[non_exhaustive] 39#[non_exhaustive]
41pub struct Config { 40pub struct Config {
42 pub ratio: Ratio, 41 pub ratio: Ratio,
43 pub sample_width: SampleWidth, 42 pub swidth: SampleWidth,
44 pub align: Align, 43 pub align: Align,
45 pub format: Format, 44 pub format: Format,
46 pub channels: Channels, 45 pub channels: Channels,
@@ -50,7 +49,7 @@ impl Default for Config {
50 fn default() -> Self { 49 fn default() -> Self {
51 Self { 50 Self {
52 ratio: Ratio::_32x, 51 ratio: Ratio::_32x,
53 sample_width: SampleWidth::_16bit, 52 swidth: SampleWidth::_16bit,
54 align: Align::Left, 53 align: Align::Left,
55 format: Format::I2S, 54 format: Format::I2S,
56 channels: Channels::Stereo, 55 channels: Channels::Stereo,
@@ -165,7 +164,7 @@ pub enum Mode {
165/// Interface to the UARTE peripheral using EasyDMA to offload the transmission and reception workload. 164/// Interface to the UARTE peripheral using EasyDMA to offload the transmission and reception workload.
166/// 165///
167/// For more details about EasyDMA, consult the module documentation. 166/// For more details about EasyDMA, consult the module documentation.
168pub struct I2s<'d, T: Instance> { 167pub struct I2S<'d, T: Instance> {
169 output: I2sOutput<'d, T>, 168 output: I2sOutput<'d, T>,
170 _input: I2sInput<'d, T>, 169 _input: I2sInput<'d, T>,
171} 170}
@@ -182,7 +181,7 @@ pub struct I2sInput<'d, T: Instance> {
182 _p: PeripheralRef<'d, T>, 181 _p: PeripheralRef<'d, T>,
183} 182}
184 183
185impl<'d, T: Instance> I2s<'d, T> { 184impl<'d, T: Instance> I2S<'d, T> {
186 /// Create a new I2S 185 /// Create a new I2S
187 pub fn new( 186 pub fn new(
188 i2s: impl Peripheral<P = T> + 'd, 187 i2s: impl Peripheral<P = T> + 'd,
@@ -215,25 +214,13 @@ impl<'d, T: Instance> I2s<'d, T> {
215 lrck: PeripheralRef<'d, AnyPin>, 214 lrck: PeripheralRef<'d, AnyPin>,
216 sdin: PeripheralRef<'d, AnyPin>, 215 sdin: PeripheralRef<'d, AnyPin>,
217 sdout: PeripheralRef<'d, AnyPin>, 216 sdout: PeripheralRef<'d, AnyPin>,
218 _config: Config, 217 config: Config,
219 ) -> Self { 218 ) -> Self {
220 into_ref!( 219 into_ref!(i2s, /* irq, */ mck, sck, lrck, sdin, sdout);
221 i2s, // irq,
222 mck, sck, lrck, sdin, sdout
223 );
224 220
225 let r = T::regs(); 221 let r = T::regs();
226 222
227 // TODO get configuration rather than hardcoding ratio, swidth, align, format, channels 223 Self::apply_config(&r.config, &config);
228
229 r.config.mcken.write(|w| w.mcken().enabled());
230 r.config.mckfreq.write(|w| w.mckfreq()._32mdiv16());
231 r.config.ratio.write(|w| w.ratio()._192x());
232 r.config.mode.write(|w| w.mode().master());
233 r.config.swidth.write(|w| w.swidth()._16bit());
234 r.config.align.write(|w| w.align().left());
235 r.config.format.write(|w| w.format().i2s());
236 r.config.channels.write(|w| w.channels().stereo());
237 224
238 r.psel.mck.write(|w| { 225 r.psel.mck.write(|w| {
239 unsafe { w.bits(mck.psel_bits()) }; 226 unsafe { w.bits(mck.psel_bits()) };
@@ -325,6 +312,62 @@ impl<'d, T: Instance> I2s<'d, T> {
325 pub async fn tx(&mut self, ptr: *const u8, len: usize) -> Result<(), Error> { 312 pub async fn tx(&mut self, ptr: *const u8, len: usize) -> Result<(), Error> {
326 self.output.tx(ptr, len).await 313 self.output.tx(ptr, len).await
327 } 314 }
315
316 fn apply_config(c: &CONFIG, config: &Config) {
317 // TODO support slave too
318 c.mcken.write(|w| w.mcken().enabled());
319 c.mckfreq.write(|w| w.mckfreq()._32mdiv16());
320 c.mode.write(|w| w.mode().master());
321
322 c.ratio.write(|w| {
323 let ratio = w.ratio();
324 match config.ratio {
325 Ratio::_32x => ratio._32x(),
326 Ratio::_48x => ratio._48x(),
327 Ratio::_64x => ratio._64x(),
328 Ratio::_96x => ratio._96x(),
329 Ratio::_128x => ratio._128x(),
330 Ratio::_192x => ratio._192x(),
331 Ratio::_256x => ratio._256x(),
332 Ratio::_384x => ratio._384x(),
333 Ratio::_512x => ratio._512x(),
334 }
335 });
336
337 c.swidth.write(|w| {
338 let swidth = w.swidth();
339 match config.swidth {
340 SampleWidth::_8bit => swidth._8bit(),
341 SampleWidth::_16bit => swidth._16bit(),
342 SampleWidth::_24bit => swidth._24bit(),
343 }
344 });
345
346 c.align.write(|w| {
347 let align = w.align();
348 match config.align {
349 Align::Left => align.left(),
350 Align::Right => align.right(),
351 }
352 });
353
354 c.format.write(|w| {
355 let format = w.format();
356 match config.format {
357 Format::I2S => format.i2s(),
358 Format::Aligned => format.aligned(),
359 }
360 });
361
362 c.channels.write(|w| {
363 let channels = w.channels();
364 match config.channels {
365 Channels::Stereo => channels.stereo(),
366 Channels::Left => channels.left(),
367 Channels::Right => channels.right(),
368 }
369 });
370 }
328} 371}
329 372
330impl<'d, T: Instance> I2sOutput<'d, T> { 373impl<'d, T: Instance> I2sOutput<'d, T> {
diff --git a/examples/nrf/src/bin/i2s.rs b/examples/nrf/src/bin/i2s.rs
index 60cde3b65..a395c7141 100644
--- a/examples/nrf/src/bin/i2s.rs
+++ b/examples/nrf/src/bin/i2s.rs
@@ -17,7 +17,7 @@ async fn main(_spawner: Spawner) {
17 let p = embassy_nrf::init(Default::default()); 17 let p = embassy_nrf::init(Default::default());
18 let config = i2s::Config::default(); 18 let config = i2s::Config::default();
19 19
20 let mut i2s = i2s::I2s::new(p.I2S, p.P0_28, p.P0_29, p.P0_31, p.P0_11, p.P0_30, config); 20 let mut i2s = i2s::I2S::new(p.I2S, p.P0_28, p.P0_29, p.P0_31, p.P0_11, p.P0_30, config);
21 21
22 let mut signal_buf: Aligned<[i16; 32]> = Aligned([0i16; 32]); 22 let mut signal_buf: Aligned<[i16; 32]> = Aligned([0i16; 32]);
23 let len = signal_buf.0.len() / 2; 23 let len = signal_buf.0.len() / 2;