Skip to content

Commit 08ca1a5

Browse files
committed
I2s::new
1 parent 0451b8f commit 08ca1a5

File tree

4 files changed

+54
-39
lines changed

4 files changed

+54
-39
lines changed

CHANGELOG.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,8 @@ and this project adheres to [Semantic Versioning](http://semver.org/).
4141

4242
### Changed
4343

44-
- Add `Spi::new`, `spi::Instance` and deprecate `Spi:spix`, deprecate `Serial::usartx`, remove deprecated `I2c::i2cx`
44+
- Add `Spi::new`, `I2s::new, `spi::Instance` and deprecate `Spi:spix`,
45+
deprecate `Serial::usartx`, remove deprecated `I2c::i2cx`
4546
- Deprecate `free` in favour of `release`
4647
- Clean features in `serial`, `spi`, `i2c`, `timer`
4748
- Internal implementation of GPIO Pin API changed to use Const Generics

examples/i2s-audio-out-dma.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,7 @@ fn main() -> ! {
126126
gpioc.pc7.into_alternate(),
127127
gpioc.pc12.into_alternate(),
128128
);
129-
let hal_i2s = I2s::i2s3(dp.SPI3, i2s_pins, clocks);
129+
let hal_i2s = I2s::new(dp.SPI3, i2s_pins, clocks);
130130
let i2s_clock = hal_i2s.input_clock();
131131

132132
// Audio timing configuration:

examples/i2s-audio-out.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,7 @@ fn main() -> ! {
123123
gpioc.pc7.into_alternate(),
124124
gpioc.pc12.into_alternate(),
125125
);
126-
let hal_i2s = I2s::i2s3(dp.SPI3, i2s_pins, clocks);
126+
let hal_i2s = I2s::new(dp.SPI3, i2s_pins, clocks);
127127
let i2s_clock = hal_i2s.input_clock();
128128

129129
// Audio timing configuration:

src/i2s.rs

Lines changed: 50 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
use stm32_i2s_v12x::{Instance, RegisterBlock};
66

77
use crate::pac::RCC;
8-
use crate::rcc::{Enable, Reset};
8+
use crate::rcc;
99
use crate::time::Hertz;
1010
use crate::{rcc::Clocks, spi};
1111

@@ -271,6 +271,10 @@ mod ws_pins {
271271
}
272272
}
273273

274+
pub trait I2sFreq {
275+
fn i2s_freq(clocks: &Clocks) -> Hertz;
276+
}
277+
274278
/// Implements Instance for I2s<$SPIX, _> and creates an I2s::$spix function to create and enable
275279
/// the peripheral
276280
///
@@ -281,49 +285,63 @@ mod ws_pins {
281285
/// to this SPI peripheral (i2s_cl, i2s_apb1_clk, or i2s2_apb_clk)
282286
macro_rules! i2s {
283287
($SPIX:ty, $i2sx:ident, $clock:ident) => {
288+
impl I2sFreq for $SPIX {
289+
fn i2s_freq(clocks: &Clocks) -> Hertz {
290+
clocks
291+
.$clock()
292+
.expect("I2S clock input for SPI not enabled")
293+
}
294+
}
295+
284296
impl<PINS> I2s<$SPIX, PINS>
285297
where
286298
PINS: Pins<$SPIX>,
287299
{
288-
/// Creates an I2s object around an SPI peripheral and pins
289-
///
290-
/// This function enables and resets the SPI peripheral, but does not configure it.
291-
///
292-
/// The returned I2s object implements [stm32_i2s_v12x::Instance], so it can be used
293-
/// to configure the peripheral and communicate.
294-
///
295-
/// # Panics
296-
///
297-
/// This function panics if the I2S clock input (from the I2S PLL or similar)
298-
/// is not configured.
300+
#[deprecated(since = "0.10.0", note = "Please use new instead")]
299301
pub fn $i2sx(spi: $SPIX, pins: PINS, clocks: Clocks) -> Self {
300-
let input_clock = clocks
301-
.$clock()
302-
.expect("I2S clock input for SPI not enabled");
303-
unsafe {
304-
// NOTE(unsafe) this reference will only be used for atomic writes with no side effects.
305-
let rcc = &(*RCC::ptr());
306-
// Enable clock, enable reset, clear, reset
307-
<$SPIX>::enable(rcc);
308-
<$SPIX>::reset(rcc);
309-
}
310-
I2s {
311-
_spi: spi,
312-
_pins: pins,
313-
input_clock,
314-
}
302+
Self::new(spi, pins, clocks)
315303
}
316304
}
317305
impl PinMck<$SPIX> for NoMasterClock {}
318-
unsafe impl<PINS> Instance for I2s<$SPIX, PINS>
319-
where
320-
PINS: Pins<$SPIX>,
321-
{
306+
unsafe impl<PINS> Instance for I2s<$SPIX, PINS> {
322307
const REGISTERS: *mut RegisterBlock = <$SPIX>::ptr() as *mut _;
323308
}
324309
};
325310
}
326311

312+
impl<SPI, PINS> I2s<SPI, PINS>
313+
where
314+
SPI: I2sFreq + rcc::Enable + rcc::Reset,
315+
PINS: Pins<SPI>,
316+
{
317+
/// Creates an I2s object around an SPI peripheral and pins
318+
///
319+
/// This function enables and resets the SPI peripheral, but does not configure it.
320+
///
321+
/// The returned I2s object implements [stm32_i2s_v12x::Instance], so it can be used
322+
/// to configure the peripheral and communicate.
323+
///
324+
/// # Panics
325+
///
326+
/// This function panics if the I2S clock input (from the I2S PLL or similar)
327+
/// is not configured.
328+
pub fn new(spi: SPI, pins: PINS, clocks: Clocks) -> Self {
329+
let input_clock = SPI::i2s_freq(&clocks);
330+
unsafe {
331+
// NOTE(unsafe) this reference will only be used for atomic writes with no side effects.
332+
let rcc = &(*RCC::ptr());
333+
// Enable clock, enable reset, clear, reset
334+
SPI::enable(rcc);
335+
SPI::reset(rcc);
336+
}
337+
I2s {
338+
_spi: spi,
339+
_pins: pins,
340+
input_clock,
341+
}
342+
}
343+
}
344+
327345
// Actually define the SPI instances that can be used for I2S
328346
// Each one has to be split into two declarations because the F412, F413, F423, and F446
329347
// have two different I2S clocks while other models have only one.
@@ -396,10 +414,7 @@ pub struct I2s<I, PINS> {
396414
input_clock: Hertz,
397415
}
398416

399-
impl<I, PINS> I2s<I, PINS>
400-
where
401-
PINS: Pins<I>,
402-
{
417+
impl<I, PINS> I2s<I, PINS> {
403418
/// Returns the frequency of the clock signal that the SPI peripheral is receiving from the
404419
/// I2S PLL or similar source
405420
pub fn input_clock(&self) -> Hertz {
@@ -435,7 +450,6 @@ mod dma {
435450
for stm32_i2s_v12x::I2s<I2s<SPI, PINS>, MODE>
436451
where
437452
SPI: DMASet<STREAM, CHANNEL, DIR>,
438-
PINS: Pins<SPI>,
439453
{
440454
}
441455
}

0 commit comments

Comments
 (0)