diff options
| author | nikvoid <[email protected]> | 2025-01-23 13:34:54 +0200 |
|---|---|---|
| committer | nikvoid <[email protected]> | 2025-01-23 13:34:54 +0200 |
| commit | afe6b9a192f1434bb024040a20cef9509c307871 (patch) | |
| tree | 987143883bc31e1d4d5b6b6091d5cb044dc413fc | |
| parent | dff8be9bb6b02c0162bcc595df34b0bc0c3e0e83 (diff) | |
split PHY constructor to `new` and `new_auto`
| -rw-r--r-- | embassy-stm32/src/eth/generic_smi.rs | 35 |
1 files changed, 31 insertions, 4 deletions
diff --git a/embassy-stm32/src/eth/generic_smi.rs b/embassy-stm32/src/eth/generic_smi.rs index 41d19e921..239c52634 100644 --- a/embassy-stm32/src/eth/generic_smi.rs +++ b/embassy-stm32/src/eth/generic_smi.rs | |||
| @@ -3,7 +3,7 @@ | |||
| 3 | use core::task::Context; | 3 | use core::task::Context; |
| 4 | 4 | ||
| 5 | #[cfg(feature = "time")] | 5 | #[cfg(feature = "time")] |
| 6 | use embassy_time::{Delay, Duration, Timer}; | 6 | use embassy_time::{Duration, Timer}; |
| 7 | #[cfg(feature = "time")] | 7 | #[cfg(feature = "time")] |
| 8 | use futures_util::FutureExt; | 8 | use futures_util::FutureExt; |
| 9 | 9 | ||
| @@ -52,20 +52,46 @@ pub struct GenericSMI { | |||
| 52 | impl GenericSMI { | 52 | impl GenericSMI { |
| 53 | /// Construct the PHY. It assumes the address `phy_addr` in the SMI communication | 53 | /// Construct the PHY. It assumes the address `phy_addr` in the SMI communication |
| 54 | /// | 54 | /// |
| 55 | /// Set `phy_addr` to `0xFF` for automatic detection (only with `time` feature enabled) | 55 | /// # Panics |
| 56 | /// `phy_addr` must be in range `0..32` | ||
| 56 | pub fn new(phy_addr: u8) -> Self { | 57 | pub fn new(phy_addr: u8) -> Self { |
| 58 | assert!(phy_addr < 32); | ||
| 57 | Self { | 59 | Self { |
| 58 | phy_addr, | 60 | phy_addr, |
| 59 | #[cfg(feature = "time")] | 61 | #[cfg(feature = "time")] |
| 60 | poll_interval: Duration::from_millis(500), | 62 | poll_interval: Duration::from_millis(500), |
| 61 | } | 63 | } |
| 62 | } | 64 | } |
| 65 | |||
| 66 | /// Construct the PHY. Try to probe all addresses from 0 to 31 during initialization | ||
| 67 | /// | ||
| 68 | /// # Panics | ||
| 69 | /// Initialization panics if PHY didn't respond on any address | ||
| 70 | pub fn new_auto() -> Self { | ||
| 71 | Self { | ||
| 72 | phy_addr: 0xFF, | ||
| 73 | #[cfg(feature = "time")] | ||
| 74 | poll_interval: Duration::from_millis(500), | ||
| 75 | } | ||
| 76 | } | ||
| 77 | } | ||
| 78 | |||
| 79 | // TODO: Factor out to shared functionality | ||
| 80 | fn blocking_delay_us(us: u32) { | ||
| 81 | #[cfg(feature = "time")] | ||
| 82 | embassy_time::block_for(Duration::from_micros(us as u64)); | ||
| 83 | #[cfg(not(feature = "time"))] | ||
| 84 | { | ||
| 85 | let freq = unsafe { crate::rcc::get_freqs() }.sys.to_hertz().unwrap().0 as u64; | ||
| 86 | let us = us as u64; | ||
| 87 | let cycles = freq * us / 1_000_000; | ||
| 88 | cortex_m::asm::delay(cycles as u32); | ||
| 89 | } | ||
| 63 | } | 90 | } |
| 64 | 91 | ||
| 65 | unsafe impl PHY for GenericSMI { | 92 | unsafe impl PHY for GenericSMI { |
| 66 | fn phy_reset<S: StationManagement>(&mut self, sm: &mut S) { | 93 | fn phy_reset<S: StationManagement>(&mut self, sm: &mut S) { |
| 67 | // Detect SMI address | 94 | // Detect SMI address |
| 68 | #[cfg(feature = "time")] | ||
| 69 | if self.phy_addr == 0xFF { | 95 | if self.phy_addr == 0xFF { |
| 70 | for addr in 0..32 { | 96 | for addr in 0..32 { |
| 71 | sm.smi_write(addr, PHY_REG_BCR, PHY_REG_BCR_RESET); | 97 | sm.smi_write(addr, PHY_REG_BCR, PHY_REG_BCR_RESET); |
| @@ -75,7 +101,8 @@ unsafe impl PHY for GenericSMI { | |||
| 75 | self.phy_addr = addr; | 101 | self.phy_addr = addr; |
| 76 | return; | 102 | return; |
| 77 | } | 103 | } |
| 78 | embedded_hal_1::delay::DelayNs::delay_us(&mut Delay, 1000); | 104 | // Give PHY a total of 100ms to respond |
| 105 | blocking_delay_us(10000); | ||
| 79 | } | 106 | } |
| 80 | } | 107 | } |
| 81 | panic!("PHY did not respond"); | 108 | panic!("PHY did not respond"); |
