2023-07-16 02:15:01 +02:00
|
|
|
#![allow(incomplete_features)]
|
|
|
|
#![deny(unused_must_use)]
|
|
|
|
|
2023-07-18 02:26:58 +02:00
|
|
|
use core::task::Context;
|
2023-07-16 02:15:01 +02:00
|
|
|
|
2023-07-31 10:40:48 +02:00
|
|
|
use embassy_net_driver::{Capabilities, HardwareAddress, LinkState, Medium};
|
2023-07-19 01:28:12 +02:00
|
|
|
use embassy_sync::blocking_mutex::raw::CriticalSectionRawMutex;
|
|
|
|
use embassy_sync::channel::Channel;
|
2023-07-16 02:15:01 +02:00
|
|
|
|
2023-07-20 23:45:04 +02:00
|
|
|
use crate::mac::event::MacEvent;
|
2023-07-18 02:26:58 +02:00
|
|
|
use crate::mac::runner::Runner;
|
|
|
|
use crate::mac::MTU;
|
2023-07-16 02:15:01 +02:00
|
|
|
|
2023-07-18 02:26:58 +02:00
|
|
|
pub struct Driver<'d> {
|
2023-07-19 01:28:12 +02:00
|
|
|
runner: &'d Runner<'d>,
|
2023-07-16 02:15:01 +02:00
|
|
|
}
|
|
|
|
|
2023-07-18 02:26:58 +02:00
|
|
|
impl<'d> Driver<'d> {
|
2023-07-19 01:28:12 +02:00
|
|
|
pub(crate) fn new(runner: &'d Runner<'d>) -> Self {
|
2023-07-18 02:26:58 +02:00
|
|
|
Self { runner: runner }
|
2023-07-16 02:15:01 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-07-18 02:26:58 +02:00
|
|
|
impl<'d> embassy_net_driver::Driver for Driver<'d> {
|
|
|
|
// type RxToken<'a> = RxToken<'a, 'd> where Self: 'a;
|
|
|
|
// type TxToken<'a> = TxToken<'a, 'd> where Self: 'a;
|
2023-07-19 01:28:12 +02:00
|
|
|
type RxToken<'a> = RxToken<'d> where Self: 'a;
|
|
|
|
type TxToken<'a> = TxToken<'d> where Self: 'a;
|
2023-07-18 02:26:58 +02:00
|
|
|
|
|
|
|
fn receive(&mut self, cx: &mut Context) -> Option<(Self::RxToken<'_>, Self::TxToken<'_>)> {
|
2023-08-11 11:15:17 +02:00
|
|
|
if self.runner.rx_channel.poll_ready_to_receive(cx).is_ready()
|
|
|
|
&& self.runner.tx_buf_channel.poll_ready_to_receive(cx).is_ready()
|
|
|
|
{
|
2023-07-19 01:28:12 +02:00
|
|
|
Some((
|
|
|
|
RxToken {
|
|
|
|
rx: &self.runner.rx_channel,
|
|
|
|
},
|
|
|
|
TxToken {
|
|
|
|
tx: &self.runner.tx_channel,
|
2023-07-19 03:52:03 +02:00
|
|
|
tx_buf: &self.runner.tx_buf_channel,
|
2023-07-19 01:28:12 +02:00
|
|
|
},
|
|
|
|
))
|
|
|
|
} else {
|
|
|
|
None
|
|
|
|
}
|
2023-07-18 02:26:58 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
fn transmit(&mut self, cx: &mut Context) -> Option<Self::TxToken<'_>> {
|
2023-08-11 11:30:29 +02:00
|
|
|
if self.runner.tx_buf_channel.poll_ready_to_receive(cx).is_ready() {
|
2023-07-19 01:28:12 +02:00
|
|
|
Some(TxToken {
|
|
|
|
tx: &self.runner.tx_channel,
|
2023-07-19 03:52:03 +02:00
|
|
|
tx_buf: &self.runner.tx_buf_channel,
|
2023-07-19 01:28:12 +02:00
|
|
|
})
|
|
|
|
} else {
|
|
|
|
None
|
|
|
|
}
|
2023-07-18 02:26:58 +02:00
|
|
|
}
|
2023-07-16 02:15:01 +02:00
|
|
|
|
2023-07-18 02:26:58 +02:00
|
|
|
fn capabilities(&self) -> Capabilities {
|
|
|
|
let mut caps = Capabilities::default();
|
|
|
|
caps.max_transmission_unit = MTU;
|
|
|
|
// caps.max_burst_size = Some(self.tx.len());
|
2023-07-16 02:15:01 +02:00
|
|
|
|
2023-07-18 02:26:58 +02:00
|
|
|
caps.medium = Medium::Ieee802154;
|
|
|
|
caps
|
|
|
|
}
|
2023-07-16 02:15:01 +02:00
|
|
|
|
2023-07-20 00:49:08 +02:00
|
|
|
fn link_state(&mut self, _cx: &mut Context) -> LinkState {
|
2023-07-18 02:26:58 +02:00
|
|
|
// if self.phy.poll_link(&mut self.station_management, cx) {
|
|
|
|
// LinkState::Up
|
|
|
|
// } else {
|
|
|
|
// LinkState::Down
|
|
|
|
// }
|
2023-07-16 02:15:01 +02:00
|
|
|
|
2023-07-18 02:26:58 +02:00
|
|
|
LinkState::Down
|
|
|
|
}
|
|
|
|
|
2023-07-28 16:19:24 +02:00
|
|
|
fn hardware_address(&self) -> HardwareAddress {
|
2023-07-18 02:26:58 +02:00
|
|
|
// self.mac_addr
|
2023-07-16 02:15:01 +02:00
|
|
|
|
2023-07-31 10:40:48 +02:00
|
|
|
HardwareAddress::Ieee802154([0; 8])
|
2023-07-16 02:15:01 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-07-19 01:28:12 +02:00
|
|
|
pub struct RxToken<'d> {
|
2023-07-20 23:45:04 +02:00
|
|
|
rx: &'d Channel<CriticalSectionRawMutex, MacEvent<'d>, 1>,
|
2023-07-18 02:26:58 +02:00
|
|
|
}
|
|
|
|
|
2023-07-19 01:28:12 +02:00
|
|
|
impl<'d> embassy_net_driver::RxToken for RxToken<'d> {
|
2023-07-18 02:26:58 +02:00
|
|
|
fn consume<R, F>(self, f: F) -> R
|
|
|
|
where
|
|
|
|
F: FnOnce(&mut [u8]) -> R,
|
|
|
|
{
|
2023-07-19 01:28:12 +02:00
|
|
|
// Only valid data events should be put into the queue
|
|
|
|
|
2023-07-20 23:45:04 +02:00
|
|
|
let data_event = match self.rx.try_recv().unwrap() {
|
2023-07-19 01:28:12 +02:00
|
|
|
MacEvent::McpsDataInd(data_event) => data_event,
|
|
|
|
_ => unreachable!(),
|
|
|
|
};
|
2023-07-18 02:26:58 +02:00
|
|
|
|
2023-07-20 00:49:08 +02:00
|
|
|
f(&mut data_event.payload())
|
2023-07-18 02:26:58 +02:00
|
|
|
}
|
2023-07-16 02:15:01 +02:00
|
|
|
}
|
|
|
|
|
2023-07-19 01:28:12 +02:00
|
|
|
pub struct TxToken<'d> {
|
2023-07-20 00:49:08 +02:00
|
|
|
tx: &'d Channel<CriticalSectionRawMutex, (&'d mut [u8; MTU], usize), 5>,
|
|
|
|
tx_buf: &'d Channel<CriticalSectionRawMutex, &'d mut [u8; MTU], 5>,
|
2023-07-16 02:15:01 +02:00
|
|
|
}
|
|
|
|
|
2023-07-19 01:28:12 +02:00
|
|
|
impl<'d> embassy_net_driver::TxToken for TxToken<'d> {
|
2023-07-18 02:26:58 +02:00
|
|
|
fn consume<R, F>(self, len: usize, f: F) -> R
|
|
|
|
where
|
|
|
|
F: FnOnce(&mut [u8]) -> R,
|
|
|
|
{
|
2023-07-19 03:52:03 +02:00
|
|
|
// Only valid tx buffers should be put into the queue
|
|
|
|
let buf = self.tx_buf.try_recv().unwrap();
|
|
|
|
let r = f(&mut buf[..len]);
|
|
|
|
|
|
|
|
// The tx channel should always be of equal capacity to the tx_buf channel
|
2023-07-20 00:49:08 +02:00
|
|
|
self.tx.try_send((buf, len)).unwrap();
|
2023-07-19 03:52:03 +02:00
|
|
|
|
2023-07-18 02:26:58 +02:00
|
|
|
r
|
|
|
|
}
|
2023-07-16 02:15:01 +02:00
|
|
|
}
|