diff options
| author | Dario Nieuwenhuis <[email protected]> | 2025-03-25 20:33:47 +0100 |
|---|---|---|
| committer | Dario Nieuwenhuis <[email protected]> | 2025-03-25 20:49:09 +0100 |
| commit | f007b53db3b850e1186f9cde26160951b14ba2e7 (patch) | |
| tree | 0a28649725ba7f9a37984bf62e121050aee322d5 | |
| parent | 17cce79807ff978270b96ba081a4ee2ed5604dcd (diff) | |
stm32/dac: dedup pin and DMA traits, demacrofify.
| -rw-r--r-- | embassy-stm32/build.rs | 17 | ||||
| -rw-r--r-- | embassy-stm32/src/dac/mod.rs | 216 |
2 files changed, 113 insertions, 120 deletions
diff --git a/embassy-stm32/build.rs b/embassy-stm32/build.rs index eb0437bc2..8ca79eadf 100644 --- a/embassy-stm32/build.rs +++ b/embassy-stm32/build.rs | |||
| @@ -1151,6 +1151,8 @@ fn main() { | |||
| 1151 | (("tsc", "G8_IO2"), quote!(crate::tsc::G8IO2Pin)), | 1151 | (("tsc", "G8_IO2"), quote!(crate::tsc::G8IO2Pin)), |
| 1152 | (("tsc", "G8_IO3"), quote!(crate::tsc::G8IO3Pin)), | 1152 | (("tsc", "G8_IO3"), quote!(crate::tsc::G8IO3Pin)), |
| 1153 | (("tsc", "G8_IO4"), quote!(crate::tsc::G8IO4Pin)), | 1153 | (("tsc", "G8_IO4"), quote!(crate::tsc::G8IO4Pin)), |
| 1154 | (("dac", "OUT1"), quote!(crate::dac::DacPin<Ch1>)), | ||
| 1155 | (("dac", "OUT2"), quote!(crate::dac::DacPin<Ch2>)), | ||
| 1154 | ].into(); | 1156 | ].into(); |
| 1155 | 1157 | ||
| 1156 | for p in METADATA.peripherals { | 1158 | for p in METADATA.peripherals { |
| @@ -1250,17 +1252,6 @@ fn main() { | |||
| 1250 | } | 1252 | } |
| 1251 | } | 1253 | } |
| 1252 | 1254 | ||
| 1253 | // DAC is special | ||
| 1254 | if regs.kind == "dac" { | ||
| 1255 | let peri = format_ident!("{}", p.name); | ||
| 1256 | let pin_name = format_ident!("{}", pin.pin); | ||
| 1257 | let ch: u8 = pin.signal.strip_prefix("OUT").unwrap().parse().unwrap(); | ||
| 1258 | |||
| 1259 | g.extend(quote! { | ||
| 1260 | impl_dac_pin!( #peri, #pin_name, #ch); | ||
| 1261 | }) | ||
| 1262 | } | ||
| 1263 | |||
| 1264 | if regs.kind == "spdifrx" { | 1255 | if regs.kind == "spdifrx" { |
| 1265 | let peri = format_ident!("{}", p.name); | 1256 | let peri = format_ident!("{}", p.name); |
| 1266 | let pin_name = format_ident!("{}", pin.pin); | 1257 | let pin_name = format_ident!("{}", pin.pin); |
| @@ -1304,8 +1295,8 @@ fn main() { | |||
| 1304 | (("quadspi", "QUADSPI"), quote!(crate::qspi::QuadDma)), | 1295 | (("quadspi", "QUADSPI"), quote!(crate::qspi::QuadDma)), |
| 1305 | (("octospi", "OCTOSPI1"), quote!(crate::ospi::OctoDma)), | 1296 | (("octospi", "OCTOSPI1"), quote!(crate::ospi::OctoDma)), |
| 1306 | (("hspi", "HSPI1"), quote!(crate::hspi::HspiDma)), | 1297 | (("hspi", "HSPI1"), quote!(crate::hspi::HspiDma)), |
| 1307 | (("dac", "CH1"), quote!(crate::dac::DacDma1)), | 1298 | (("dac", "CH1"), quote!(crate::dac::Dma<Ch1>)), |
| 1308 | (("dac", "CH2"), quote!(crate::dac::DacDma2)), | 1299 | (("dac", "CH2"), quote!(crate::dac::Dma<Ch2>)), |
| 1309 | (("timer", "UP"), quote!(crate::timer::UpDma)), | 1300 | (("timer", "UP"), quote!(crate::timer::UpDma)), |
| 1310 | (("hash", "IN"), quote!(crate::hash::Dma)), | 1301 | (("hash", "IN"), quote!(crate::hash::Dma)), |
| 1311 | (("cryp", "IN"), quote!(crate::cryp::DmaIn)), | 1302 | (("cryp", "IN"), quote!(crate::cryp::DmaIn)), |
diff --git a/embassy-stm32/src/dac/mod.rs b/embassy-stm32/src/dac/mod.rs index 8bba5ded0..4406f2960 100644 --- a/embassy-stm32/src/dac/mod.rs +++ b/embassy-stm32/src/dac/mod.rs | |||
| @@ -100,20 +100,18 @@ pub enum ValueArray<'a> { | |||
| 100 | /// | 100 | /// |
| 101 | /// If you want to use both channels, either together or independently, | 101 | /// If you want to use both channels, either together or independently, |
| 102 | /// create a [`Dac`] first and use it to access each channel. | 102 | /// create a [`Dac`] first and use it to access each channel. |
| 103 | pub struct DacChannel<'d, T: Instance, const N: u8, DMA = NoDma> { | 103 | pub struct DacChannel<'d, T: Instance, C: Channel, DMA = NoDma> { |
| 104 | phantom: PhantomData<&'d mut T>, | 104 | phantom: PhantomData<&'d mut (T, C)>, |
| 105 | #[allow(unused)] | 105 | #[allow(unused)] |
| 106 | dma: PeripheralRef<'d, DMA>, | 106 | dma: PeripheralRef<'d, DMA>, |
| 107 | } | 107 | } |
| 108 | 108 | ||
| 109 | /// DAC channel 1 type alias. | 109 | /// DAC channel 1 type alias. |
| 110 | pub type DacCh1<'d, T, DMA = NoDma> = DacChannel<'d, T, 1, DMA>; | 110 | pub type DacCh1<'d, T, DMA = NoDma> = DacChannel<'d, T, Ch1, DMA>; |
| 111 | /// DAC channel 2 type alias. | 111 | /// DAC channel 2 type alias. |
| 112 | pub type DacCh2<'d, T, DMA = NoDma> = DacChannel<'d, T, 2, DMA>; | 112 | pub type DacCh2<'d, T, DMA = NoDma> = DacChannel<'d, T, Ch2, DMA>; |
| 113 | |||
| 114 | impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | ||
| 115 | const IDX: usize = (N - 1) as usize; | ||
| 116 | 113 | ||
| 114 | impl<'d, T: Instance, C: Channel, DMA> DacChannel<'d, T, C, DMA> { | ||
| 117 | /// Create a new `DacChannel` instance, consuming the underlying DAC peripheral. | 115 | /// Create a new `DacChannel` instance, consuming the underlying DAC peripheral. |
| 118 | /// | 116 | /// |
| 119 | /// If you're not using DMA, pass [`dma::NoDma`] for the `dma` argument. | 117 | /// If you're not using DMA, pass [`dma::NoDma`] for the `dma` argument. |
| @@ -127,7 +125,7 @@ impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | |||
| 127 | pub fn new( | 125 | pub fn new( |
| 128 | _peri: impl Peripheral<P = T> + 'd, | 126 | _peri: impl Peripheral<P = T> + 'd, |
| 129 | dma: impl Peripheral<P = DMA> + 'd, | 127 | dma: impl Peripheral<P = DMA> + 'd, |
| 130 | pin: impl Peripheral<P = impl DacPin<T, N> + crate::gpio::Pin> + 'd, | 128 | pin: impl Peripheral<P = impl DacPin<T, C> + crate::gpio::Pin> + 'd, |
| 131 | ) -> Self { | 129 | ) -> Self { |
| 132 | into_ref!(dma, pin); | 130 | into_ref!(dma, pin); |
| 133 | pin.set_as_analog(); | 131 | pin.set_as_analog(); |
| @@ -173,7 +171,7 @@ impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | |||
| 173 | pub fn set_enable(&mut self, on: bool) { | 171 | pub fn set_enable(&mut self, on: bool) { |
| 174 | critical_section::with(|_| { | 172 | critical_section::with(|_| { |
| 175 | T::regs().cr().modify(|reg| { | 173 | T::regs().cr().modify(|reg| { |
| 176 | reg.set_en(Self::IDX, on); | 174 | reg.set_en(C::IDX, on); |
| 177 | }); | 175 | }); |
| 178 | }); | 176 | }); |
| 179 | } | 177 | } |
| @@ -194,8 +192,8 @@ impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | |||
| 194 | pub fn set_trigger(&mut self, source: TriggerSel) { | 192 | pub fn set_trigger(&mut self, source: TriggerSel) { |
| 195 | critical_section::with(|_| { | 193 | critical_section::with(|_| { |
| 196 | T::regs().cr().modify(|reg| { | 194 | T::regs().cr().modify(|reg| { |
| 197 | reg.set_en(Self::IDX, false); | 195 | reg.set_en(C::IDX, false); |
| 198 | reg.set_tsel(Self::IDX, source as u8); | 196 | reg.set_tsel(C::IDX, source as u8); |
| 199 | }); | 197 | }); |
| 200 | }); | 198 | }); |
| 201 | } | 199 | } |
| @@ -204,7 +202,7 @@ impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | |||
| 204 | pub fn set_triggering(&mut self, on: bool) { | 202 | pub fn set_triggering(&mut self, on: bool) { |
| 205 | critical_section::with(|_| { | 203 | critical_section::with(|_| { |
| 206 | T::regs().cr().modify(|reg| { | 204 | T::regs().cr().modify(|reg| { |
| 207 | reg.set_ten(Self::IDX, on); | 205 | reg.set_ten(C::IDX, on); |
| 208 | }); | 206 | }); |
| 209 | }); | 207 | }); |
| 210 | } | 208 | } |
| @@ -212,7 +210,7 @@ impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | |||
| 212 | /// Software trigger this channel. | 210 | /// Software trigger this channel. |
| 213 | pub fn trigger(&mut self) { | 211 | pub fn trigger(&mut self) { |
| 214 | T::regs().swtrigr().write(|reg| { | 212 | T::regs().swtrigr().write(|reg| { |
| 215 | reg.set_swtrig(Self::IDX, true); | 213 | reg.set_swtrig(C::IDX, true); |
| 216 | }); | 214 | }); |
| 217 | } | 215 | } |
| 218 | 216 | ||
| @@ -223,10 +221,10 @@ impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | |||
| 223 | pub fn set_mode(&mut self, mode: Mode) { | 221 | pub fn set_mode(&mut self, mode: Mode) { |
| 224 | critical_section::with(|_| { | 222 | critical_section::with(|_| { |
| 225 | T::regs().cr().modify(|reg| { | 223 | T::regs().cr().modify(|reg| { |
| 226 | reg.set_en(Self::IDX, false); | 224 | reg.set_en(C::IDX, false); |
| 227 | }); | 225 | }); |
| 228 | T::regs().mcr().modify(|reg| { | 226 | T::regs().mcr().modify(|reg| { |
| 229 | reg.set_mode(Self::IDX, mode.mode()); | 227 | reg.set_mode(C::IDX, mode.mode()); |
| 230 | }); | 228 | }); |
| 231 | }); | 229 | }); |
| 232 | } | 230 | } |
| @@ -237,15 +235,15 @@ impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | |||
| 237 | /// it will be output after the next trigger. | 235 | /// it will be output after the next trigger. |
| 238 | pub fn set(&mut self, value: Value) { | 236 | pub fn set(&mut self, value: Value) { |
| 239 | match value { | 237 | match value { |
| 240 | Value::Bit8(v) => T::regs().dhr8r(Self::IDX).write(|reg| reg.set_dhr(v)), | 238 | Value::Bit8(v) => T::regs().dhr8r(C::IDX).write(|reg| reg.set_dhr(v)), |
| 241 | Value::Bit12Left(v) => T::regs().dhr12l(Self::IDX).write(|reg| reg.set_dhr(v)), | 239 | Value::Bit12Left(v) => T::regs().dhr12l(C::IDX).write(|reg| reg.set_dhr(v)), |
| 242 | Value::Bit12Right(v) => T::regs().dhr12r(Self::IDX).write(|reg| reg.set_dhr(v)), | 240 | Value::Bit12Right(v) => T::regs().dhr12r(C::IDX).write(|reg| reg.set_dhr(v)), |
| 243 | } | 241 | } |
| 244 | } | 242 | } |
| 245 | 243 | ||
| 246 | /// Read the current output value of the DAC. | 244 | /// Read the current output value of the DAC. |
| 247 | pub fn read(&self) -> u16 { | 245 | pub fn read(&self) -> u16 { |
| 248 | T::regs().dor(Self::IDX).read().dor() | 246 | T::regs().dor(C::IDX).read().dor() |
| 249 | } | 247 | } |
| 250 | 248 | ||
| 251 | /// Set HFSEL as appropriate for the current peripheral clock frequency. | 249 | /// Set HFSEL as appropriate for the current peripheral clock frequency. |
| @@ -277,84 +275,75 @@ impl<'d, T: Instance, const N: u8, DMA> DacChannel<'d, T, N, DMA> { | |||
| 277 | }); | 275 | }); |
| 278 | } | 276 | } |
| 279 | } | 277 | } |
| 280 | } | ||
| 281 | 278 | ||
| 282 | macro_rules! impl_dma_methods { | 279 | /// Write `data` to this channel via DMA. |
| 283 | ($n:literal, $trait:ident) => { | 280 | /// |
| 284 | impl<'d, T: Instance, DMA> DacChannel<'d, T, $n, DMA> | 281 | /// To prevent delays or glitches when outputing a periodic waveform, the `circular` |
| 285 | where | 282 | /// flag can be set. This configures a circular DMA transfer that continually outputs |
| 286 | DMA: $trait<T>, | 283 | /// `data`. Note that for performance reasons in circular mode the transfer-complete |
| 287 | { | 284 | /// interrupt is disabled. |
| 288 | /// Write `data` to this channel via DMA. | 285 | #[cfg(not(gpdma))] |
| 289 | /// | 286 | pub async fn write(&mut self, data: ValueArray<'_>, circular: bool) |
| 290 | /// To prevent delays or glitches when outputing a periodic waveform, the `circular` | 287 | where |
| 291 | /// flag can be set. This configures a circular DMA transfer that continually outputs | 288 | DMA: Dma<T, C>, |
| 292 | /// `data`. Note that for performance reasons in circular mode the transfer-complete | 289 | { |
| 293 | /// interrupt is disabled. | 290 | // Enable DAC and DMA |
| 294 | #[cfg(not(gpdma))] | 291 | T::regs().cr().modify(|w| { |
| 295 | pub async fn write(&mut self, data: ValueArray<'_>, circular: bool) { | 292 | w.set_en(C::IDX, true); |
| 296 | // Enable DAC and DMA | 293 | w.set_dmaen(C::IDX, true); |
| 297 | T::regs().cr().modify(|w| { | 294 | }); |
| 298 | w.set_en(Self::IDX, true); | ||
| 299 | w.set_dmaen(Self::IDX, true); | ||
| 300 | }); | ||
| 301 | 295 | ||
| 302 | let tx_request = self.dma.request(); | 296 | let tx_request = self.dma.request(); |
| 303 | let dma_channel = &mut self.dma; | 297 | let dma_channel = &mut self.dma; |
| 304 | 298 | ||
| 305 | let tx_options = crate::dma::TransferOptions { | 299 | let tx_options = crate::dma::TransferOptions { |
| 306 | circular, | 300 | circular, |
| 307 | half_transfer_ir: false, | 301 | half_transfer_ir: false, |
| 308 | complete_transfer_ir: !circular, | 302 | complete_transfer_ir: !circular, |
| 309 | ..Default::default() | 303 | ..Default::default() |
| 310 | }; | 304 | }; |
| 311 | 305 | ||
| 312 | // Initiate the correct type of DMA transfer depending on what data is passed | 306 | // Initiate the correct type of DMA transfer depending on what data is passed |
| 313 | let tx_f = match data { | 307 | let tx_f = match data { |
| 314 | ValueArray::Bit8(buf) => unsafe { | 308 | ValueArray::Bit8(buf) => unsafe { |
| 315 | crate::dma::Transfer::new_write( | 309 | crate::dma::Transfer::new_write( |
| 316 | dma_channel, | 310 | dma_channel, |
| 317 | tx_request, | 311 | tx_request, |
| 318 | buf, | 312 | buf, |
| 319 | T::regs().dhr8r(Self::IDX).as_ptr() as *mut u8, | 313 | T::regs().dhr8r(C::IDX).as_ptr() as *mut u8, |
| 320 | tx_options, | 314 | tx_options, |
| 321 | ) | 315 | ) |
| 322 | }, | 316 | }, |
| 323 | ValueArray::Bit12Left(buf) => unsafe { | 317 | ValueArray::Bit12Left(buf) => unsafe { |
| 324 | crate::dma::Transfer::new_write( | 318 | crate::dma::Transfer::new_write( |
| 325 | dma_channel, | 319 | dma_channel, |
| 326 | tx_request, | 320 | tx_request, |
| 327 | buf, | 321 | buf, |
| 328 | T::regs().dhr12l(Self::IDX).as_ptr() as *mut u16, | 322 | T::regs().dhr12l(C::IDX).as_ptr() as *mut u16, |
| 329 | tx_options, | 323 | tx_options, |
| 330 | ) | 324 | ) |
| 331 | }, | 325 | }, |
| 332 | ValueArray::Bit12Right(buf) => unsafe { | 326 | ValueArray::Bit12Right(buf) => unsafe { |
| 333 | crate::dma::Transfer::new_write( | 327 | crate::dma::Transfer::new_write( |
| 334 | dma_channel, | 328 | dma_channel, |
| 335 | tx_request, | 329 | tx_request, |
| 336 | buf, | 330 | buf, |
| 337 | T::regs().dhr12r(Self::IDX).as_ptr() as *mut u16, | 331 | T::regs().dhr12r(C::IDX).as_ptr() as *mut u16, |
| 338 | tx_options, | 332 | tx_options, |
| 339 | ) | 333 | ) |
| 340 | }, | 334 | }, |
| 341 | }; | 335 | }; |
| 342 | |||
| 343 | tx_f.await; | ||
| 344 | |||
| 345 | T::regs().cr().modify(|w| { | ||
| 346 | w.set_en(Self::IDX, false); | ||
| 347 | w.set_dmaen(Self::IDX, false); | ||
| 348 | }); | ||
| 349 | } | ||
| 350 | } | ||
| 351 | }; | ||
| 352 | } | ||
| 353 | 336 | ||
| 354 | impl_dma_methods!(1, DacDma1); | 337 | tx_f.await; |
| 355 | impl_dma_methods!(2, DacDma2); | ||
| 356 | 338 | ||
| 357 | impl<'d, T: Instance, const N: u8, DMA> Drop for DacChannel<'d, T, N, DMA> { | 339 | T::regs().cr().modify(|w| { |
| 340 | w.set_en(C::IDX, false); | ||
| 341 | w.set_dmaen(C::IDX, false); | ||
| 342 | }); | ||
| 343 | } | ||
| 344 | } | ||
| 345 | |||
| 346 | impl<'d, T: Instance, C: Channel, DMA> Drop for DacChannel<'d, T, C, DMA> { | ||
| 358 | fn drop(&mut self) { | 347 | fn drop(&mut self) { |
| 359 | rcc::disable::<T>(); | 348 | rcc::disable::<T>(); |
| 360 | } | 349 | } |
| @@ -371,8 +360,8 @@ impl<'d, T: Instance, const N: u8, DMA> Drop for DacChannel<'d, T, N, DMA> { | |||
| 371 | /// let (dac_ch1, dac_ch2) = embassy_stm32::dac::Dac::new(p.DAC1, NoDma, NoDma, p.PA4, p.PA5).split(); | 360 | /// let (dac_ch1, dac_ch2) = embassy_stm32::dac::Dac::new(p.DAC1, NoDma, NoDma, p.PA4, p.PA5).split(); |
| 372 | /// ``` | 361 | /// ``` |
| 373 | pub struct Dac<'d, T: Instance, DMACh1 = NoDma, DMACh2 = NoDma> { | 362 | pub struct Dac<'d, T: Instance, DMACh1 = NoDma, DMACh2 = NoDma> { |
| 374 | ch1: DacChannel<'d, T, 1, DMACh1>, | 363 | ch1: DacChannel<'d, T, Ch1, DMACh1>, |
| 375 | ch2: DacChannel<'d, T, 2, DMACh2>, | 364 | ch2: DacChannel<'d, T, Ch2, DMACh2>, |
| 376 | } | 365 | } |
| 377 | 366 | ||
| 378 | impl<'d, T: Instance, DMACh1, DMACh2> Dac<'d, T, DMACh1, DMACh2> { | 367 | impl<'d, T: Instance, DMACh1, DMACh2> Dac<'d, T, DMACh1, DMACh2> { |
| @@ -392,8 +381,8 @@ impl<'d, T: Instance, DMACh1, DMACh2> Dac<'d, T, DMACh1, DMACh2> { | |||
| 392 | _peri: impl Peripheral<P = T> + 'd, | 381 | _peri: impl Peripheral<P = T> + 'd, |
| 393 | dma_ch1: impl Peripheral<P = DMACh1> + 'd, | 382 | dma_ch1: impl Peripheral<P = DMACh1> + 'd, |
| 394 | dma_ch2: impl Peripheral<P = DMACh2> + 'd, | 383 | dma_ch2: impl Peripheral<P = DMACh2> + 'd, |
| 395 | pin_ch1: impl Peripheral<P = impl DacPin<T, 1> + crate::gpio::Pin> + 'd, | 384 | pin_ch1: impl Peripheral<P = impl DacPin<T, Ch1> + crate::gpio::Pin> + 'd, |
| 396 | pin_ch2: impl Peripheral<P = impl DacPin<T, 2> + crate::gpio::Pin> + 'd, | 385 | pin_ch2: impl Peripheral<P = impl DacPin<T, Ch2> + crate::gpio::Pin> + 'd, |
| 397 | ) -> Self { | 386 | ) -> Self { |
| 398 | into_ref!(dma_ch1, dma_ch2, pin_ch1, pin_ch2); | 387 | into_ref!(dma_ch1, dma_ch2, pin_ch1, pin_ch2); |
| 399 | pin_ch1.set_as_analog(); | 388 | pin_ch1.set_as_analog(); |
| @@ -514,11 +503,30 @@ trait SealedInstance { | |||
| 514 | /// DAC instance. | 503 | /// DAC instance. |
| 515 | #[allow(private_bounds)] | 504 | #[allow(private_bounds)] |
| 516 | pub trait Instance: SealedInstance + RccPeripheral + 'static {} | 505 | pub trait Instance: SealedInstance + RccPeripheral + 'static {} |
| 517 | dma_trait!(DacDma1, Instance); | ||
| 518 | dma_trait!(DacDma2, Instance); | ||
| 519 | 506 | ||
| 520 | /// Marks a pin that can be used with the DAC | 507 | /// Channel 1 marker type. |
| 521 | pub trait DacPin<T: Instance, const C: u8>: crate::gpio::Pin + 'static {} | 508 | pub enum Ch1 {} |
| 509 | /// Channel 2 marker type. | ||
| 510 | pub enum Ch2 {} | ||
| 511 | |||
| 512 | trait SealedChannel { | ||
| 513 | const IDX: usize; | ||
| 514 | } | ||
| 515 | /// DAC channel trait. | ||
| 516 | #[allow(private_bounds)] | ||
| 517 | pub trait Channel: SealedChannel {} | ||
| 518 | |||
| 519 | impl SealedChannel for Ch1 { | ||
| 520 | const IDX: usize = 0; | ||
| 521 | } | ||
| 522 | impl SealedChannel for Ch2 { | ||
| 523 | const IDX: usize = 1; | ||
| 524 | } | ||
| 525 | impl Channel for Ch1 {} | ||
| 526 | impl Channel for Ch2 {} | ||
| 527 | |||
| 528 | dma_trait!(Dma, Instance, Channel); | ||
| 529 | pin_trait!(DacPin, Instance, Channel); | ||
| 522 | 530 | ||
| 523 | foreach_peripheral!( | 531 | foreach_peripheral!( |
| 524 | (dac, $inst:ident) => { | 532 | (dac, $inst:ident) => { |
| @@ -531,9 +539,3 @@ foreach_peripheral!( | |||
| 531 | impl crate::dac::Instance for peripherals::$inst {} | 539 | impl crate::dac::Instance for peripherals::$inst {} |
| 532 | }; | 540 | }; |
| 533 | ); | 541 | ); |
| 534 | |||
| 535 | macro_rules! impl_dac_pin { | ||
| 536 | ($inst:ident, $pin:ident, $ch:expr) => { | ||
| 537 | impl crate::dac::DacPin<peripherals::$inst, $ch> for crate::peripherals::$pin {} | ||
| 538 | }; | ||
| 539 | } | ||
