From a1a211334f7fe8ebaec46e5d307238fbf37ab4fd Mon Sep 17 00:00:00 2001 From: Astro Date: Wed, 10 Jun 2020 23:20:43 +0200 Subject: [PATCH] eth: always just allocate desc list + buffers buffers are allocated vec anyway. this removes the lifetime hack and further prepares work on cache-line alignment to enable L1 writeback. --- experiments/src/main.rs | 20 +++----------------- libboard_zynq/src/eth/mod.rs | 16 ++++++++-------- libboard_zynq/src/eth/rx.rs | 18 +++++++++++------- libboard_zynq/src/eth/tx.rs | 24 ++++++++++++++---------- libboard_zynq/src/lib.rs | 2 ++ 5 files changed, 38 insertions(+), 42 deletions(-) diff --git a/experiments/src/main.rs b/experiments/src/main.rs index 8d1a01d..a9cb3e9 100644 --- a/experiments/src/main.rs +++ b/experiments/src/main.rs @@ -4,7 +4,7 @@ extern crate alloc; use alloc::{borrow::ToOwned, collections::BTreeMap, format}; -use core::{mem::transmute, task::Poll}; +use core::task::Poll; use libasync::{ delay, smoltcp::{Sockets, TcpStream}, @@ -30,7 +30,6 @@ use libcortex_a9::{ }; use libregister::RegisterR; use libsupport_zynq::{ - alloc::{vec, vec::Vec}, boot, ram, }; use log::info; @@ -181,24 +180,11 @@ pub fn main_core0() { println!("Eth on"); const RX_LEN: usize = 8; - let mut rx_descs = (0..RX_LEN) - .map(|_| zynq::eth::rx::DescEntry::zeroed()) - .collect::>(); - let mut rx_buffers = vec![zynq::eth::Buffer::new(); RX_LEN]; // Number of transmission buffers (minimum is two because with // one, duplicate packet transmission occurs) const TX_LEN: usize = 8; - let mut tx_descs = (0..TX_LEN) - .map(|_| zynq::eth::tx::DescEntry::zeroed()) - .collect::>(); - let mut tx_buffers = vec![zynq::eth::Buffer::new(); TX_LEN]; - let eth = eth.start_rx(&mut rx_descs, &mut rx_buffers); - // let mut eth = eth.start_tx(&mut tx_descs, &mut tx_buffers); - let mut eth = eth.start_tx( - // HACK - unsafe { transmute(tx_descs.as_mut_slice()) }, - unsafe { transmute(tx_buffers.as_mut_slice()) }, - ); + let eth = eth.start_rx(RX_LEN); + let mut eth = eth.start_tx(TX_LEN); let ethernet_addr = EthernetAddress(HWADDR); // IP stack diff --git a/libboard_zynq/src/eth/mod.rs b/libboard_zynq/src/eth/mod.rs index faee9cb..3dbb2d3 100644 --- a/libboard_zynq/src/eth/mod.rs +++ b/libboard_zynq/src/eth/mod.rs @@ -263,9 +263,9 @@ impl<'r, RX, TX> Eth<'r, RX, TX> { }); } - pub fn start_rx<'rx>(self, rx_list: &'rx mut [rx::DescEntry], rx_buffers: &'rx mut [Buffer]) -> Eth<'r, rx::DescList<'rx>, TX> { + pub fn start_rx(self, rx_size: usize) -> Eth<'r, rx::DescList, TX> { let new_self = Eth { - rx: rx::DescList::new(rx_list, rx_buffers), + rx: rx::DescList::new(rx_size), tx: self.tx, inner: self.inner, phy: self.phy, @@ -282,10 +282,10 @@ impl<'r, RX, TX> Eth<'r, RX, TX> { new_self } - pub fn start_tx<'tx>(self, tx_list: &'tx mut [tx::DescEntry], tx_buffers: &'tx mut [Buffer]) -> Eth<'r, RX, tx::DescList<'tx>> { + pub fn start_tx(self, tx_size: usize) -> Eth<'r, RX, tx::DescList> { let new_self = Eth { rx: self.rx, - tx: tx::DescList::new(tx_list, tx_buffers), + tx: tx::DescList::new(tx_size), inner: self.inner, phy: self.phy, }; @@ -302,7 +302,7 @@ impl<'r, RX, TX> Eth<'r, RX, TX> { } } -impl<'r, 'rx, TX> Eth<'r, rx::DescList<'rx>, TX> { +impl<'r, TX> Eth<'r, rx::DescList, TX> { pub fn recv_next<'s: 'p, 'p>(&'s mut self) -> Result>, rx::Error> { let status = self.inner.regs.rx_status.read(); if status.hresp_not_ok() { @@ -350,15 +350,15 @@ impl<'r, 'rx, TX> Eth<'r, rx::DescList<'rx>, TX> { } } -impl<'r, 'tx, RX> Eth<'r, RX, tx::DescList<'tx>> { +impl<'r, RX> Eth<'r, RX, tx::DescList> { pub fn send<'s: 'p, 'p>(&'s mut self, length: usize) -> Option> { self.tx.send(self.inner.regs, length) } } -impl<'r, 'rx, 'tx: 'a, 'a> smoltcp::phy::Device<'a> for &mut Eth<'r, rx::DescList<'rx>, tx::DescList<'tx>> { +impl<'r, 'a> smoltcp::phy::Device<'a> for &mut Eth<'r, rx::DescList, tx::DescList> { type RxToken = rx::PktRef<'a>; - type TxToken = tx::Token<'a, 'tx>; + type TxToken = tx::Token<'a>; fn capabilities(&self) -> smoltcp::phy::DeviceCapabilities { use smoltcp::phy::{DeviceCapabilities, ChecksumCapabilities, Checksum}; diff --git a/libboard_zynq/src/eth/rx.rs b/libboard_zynq/src/eth/rx.rs index 2a583cb..cc0847f 100644 --- a/libboard_zynq/src/eth/rx.rs +++ b/libboard_zynq/src/eth/rx.rs @@ -1,4 +1,5 @@ use core::ops::Deref; +use alloc::{vec, vec::Vec}; use libregister::*; use super::Buffer; @@ -53,14 +54,18 @@ register_bit!(desc_word1, multi_hash_match, 30); register_bit!(desc_word1, global_broadcast, 31); #[repr(C)] -pub struct DescList<'a> { - list: &'a mut [DescEntry], - buffers: &'a mut [Buffer], +pub struct DescList { + list: Vec, + buffers: Vec, next: usize, } -impl<'a> DescList<'a> { - pub fn new(list: &'a mut [DescEntry], buffers: &'a mut [Buffer]) -> Self { +impl DescList { + pub fn new(size: usize) -> Self { + let mut list: Vec<_> = (0..size).map(|_| DescEntry::zeroed()) + .collect(); + let mut buffers = vec![Buffer::new(); size]; + let last = list.len().min(buffers.len()) - 1; for (i, (entry, buffer)) in list.iter_mut().zip(buffers.iter_mut()).enumerate() { let is_last = i == last; @@ -78,8 +83,7 @@ impl<'a> DescList<'a> { } DescList { - // Shorten the list of descriptors to the required number. - list: &mut list[0..=last], + list, buffers, next: 0, } diff --git a/libboard_zynq/src/eth/tx.rs b/libboard_zynq/src/eth/tx.rs index 665a3c2..6261b3b 100644 --- a/libboard_zynq/src/eth/tx.rs +++ b/libboard_zynq/src/eth/tx.rs @@ -1,4 +1,5 @@ use core::ops::{Deref, DerefMut}; +use alloc::{vec, vec::Vec}; use libregister::*; use super::{Buffer, regs}; @@ -40,14 +41,18 @@ impl DescEntry { pub const DESCS: usize = 8; #[repr(C)] -pub struct DescList<'a> { - list: &'a mut [DescEntry], - buffers: &'a mut [Buffer], +pub struct DescList { + list: Vec, + buffers: Vec, next: usize, } -impl<'a> DescList<'a> { - pub fn new(list: &'a mut [DescEntry], buffers: &'a mut [Buffer]) -> Self { +impl DescList { + pub fn new(size: usize) -> Self { + let mut list: Vec<_> = (0..size).map(|_| DescEntry::zeroed()) + .collect(); + let mut buffers = vec![Buffer::new(); size]; + let last = list.len().min(buffers.len()) - 1; // Sending seems to not work properly with only one packet // buffer (two duplicates get send with every packet), so @@ -73,8 +78,7 @@ impl<'a> DescList<'a> { } DescList { - // Shorten the list of descriptors to the required number. - list: &mut list[0..=last], + list, buffers, next: 0, } @@ -142,12 +146,12 @@ impl<'a> DerefMut for PktRef<'a> { } /// TxToken for smoltcp support -pub struct Token<'a, 'tx: 'a> { +pub struct Token<'a> { pub regs: &'a mut regs::RegisterBlock, - pub desc_list: &'a mut DescList<'tx>, + pub desc_list: &'a mut DescList, } -impl<'a, 'tx: 'a> smoltcp::phy::TxToken for Token<'a, 'tx> { +impl<'a> smoltcp::phy::TxToken for Token<'a> { fn consume(self, _timestamp: smoltcp::time::Instant, len: usize, f: F) -> smoltcp::Result where F: FnOnce(&mut [u8]) -> smoltcp::Result { diff --git a/libboard_zynq/src/lib.rs b/libboard_zynq/src/lib.rs index b7316f0..5c043ab 100644 --- a/libboard_zynq/src/lib.rs +++ b/libboard_zynq/src/lib.rs @@ -1,5 +1,7 @@ #![no_std] +extern crate alloc; + /// Re-export so that dependents can always use the same version pub use smoltcp;