From bb09d253784639e6f783118ee1c5e3666bcd6468 Mon Sep 17 00:00:00 2001 From: pca006132 Date: Fri, 21 Aug 2020 13:31:08 +0800 Subject: [PATCH] libboard_zynq/ethernet: ethernet fix and config --- libboard_zynq/src/eth/mod.rs | 46 ++++++++++++++++++++---------------- libboard_zynq/src/eth/rx.rs | 18 ++++++++++---- 2 files changed, 39 insertions(+), 25 deletions(-) diff --git a/libboard_zynq/src/eth/mod.rs b/libboard_zynq/src/eth/mod.rs index 8dc6978..fc71346 100644 --- a/libboard_zynq/src/eth/mod.rs +++ b/libboard_zynq/src/eth/mod.rs @@ -27,7 +27,7 @@ const TX_1000: u32 = 125_000_000; pub struct Buffer(pub [u8; MTU]); impl Buffer { - pub fn new() -> Self { + pub const fn new() -> Self { Buffer([0; MTU]) } } @@ -224,48 +224,48 @@ impl Eth { // RX_CLK slcr.mio_pin_22.write( slcr::MioPin22::zeroed() - .tri_enable(true) .l0_sel(true) + .speed(true) .io_type(slcr::IoBufferType::Hstl) .pullup(true) ); // RX_CTRL slcr.mio_pin_27.write( slcr::MioPin27::zeroed() - .tri_enable(true) .l0_sel(true) + .speed(true) .io_type(slcr::IoBufferType::Hstl) .pullup(true) ); // RXD3 slcr.mio_pin_26.write( slcr::MioPin26::zeroed() - .tri_enable(true) .l0_sel(true) + .speed(true) .io_type(slcr::IoBufferType::Hstl) .pullup(true) ); // RXD2 slcr.mio_pin_25.write( slcr::MioPin25::zeroed() - .tri_enable(true) .l0_sel(true) + .speed(true) .io_type(slcr::IoBufferType::Hstl) .pullup(true) ); // RXD1 slcr.mio_pin_24.write( slcr::MioPin24::zeroed() - .tri_enable(true) .l0_sel(true) + .speed(true) .io_type(slcr::IoBufferType::Hstl) .pullup(true) ); // RXD0 slcr.mio_pin_23.write( slcr::MioPin23::zeroed() - .tri_enable(true) .l0_sel(true) + .speed(true) .io_type(slcr::IoBufferType::Hstl) .pullup(true) ); @@ -533,7 +533,10 @@ impl EthInner { fn configure(&mut self, macaddr: [u8; 6]) { let clocks = Clocks::get(); - let mdc_clk_div = (clocks.cpu_1x() / MAX_MDC) + 1; + let mut mdc_clk_div = clocks.cpu_1x() / MAX_MDC; + if clocks.cpu_1x() % MAX_MDC > 0 { + mdc_clk_div += 1; + } GEM::regs().net_cfg.write( regs::NetCfg::zeroed() @@ -542,10 +545,10 @@ impl EthInner { .speed(true) .no_broadcast(false) .multi_hash_en(true) - // Promiscuous mode (TODO?) - .copy_all(true) + .rx_1536_byte_frames(true) // Remove 4-byte Frame CheckSum .fcs_remove(true) + .dis_cp_pause_frame(true) // RX checksum offload .rx_chksum_offld_en(true) // One of the slower speeds @@ -553,22 +556,23 @@ impl EthInner { ); let macaddr_msbs = - (u16::from(macaddr[0]) << 8) | - u16::from(macaddr[1]); + (u16::from(macaddr[5]) << 8) | + u16::from(macaddr[4]); let macaddr_lsbs = - (u32::from(macaddr[2]) << 24) | - (u32::from(macaddr[3]) << 16) | - (u32::from(macaddr[4]) << 8) | - u32::from(macaddr[5]); - GEM::regs().spec_addr1_top.write( - regs::SpecAddrTop::zeroed() - .addr_msbs(macaddr_msbs) - ); + (u32::from(macaddr[3]) << 24) | + (u32::from(macaddr[2]) << 16) | + (u32::from(macaddr[1]) << 8) | + u32::from(macaddr[0]); + // writing to bot would disable the specific address GEM::regs().spec_addr1_bot.write( regs::SpecAddrBot::zeroed() .addr_lsbs(macaddr_lsbs) ); - + // writing to top would enable it again + GEM::regs().spec_addr1_top.write( + regs::SpecAddrTop::zeroed() + .addr_msbs(macaddr_msbs) + ); GEM::regs().dma_cfg.write( regs::DmaCfg::zeroed() diff --git a/libboard_zynq/src/eth/rx.rs b/libboard_zynq/src/eth/rx.rs index 01a10c3..3fea616 100644 --- a/libboard_zynq/src/eth/rx.rs +++ b/libboard_zynq/src/eth/rx.rs @@ -108,6 +108,20 @@ impl DescList { if entry.word0.read().used() { let word1 = entry.word1.read(); let len = word1.frame_length_lsbs().into(); + let padding = { + let diff = len % 0x20; + if diff == 0 { + 0 + } else { + 0x20 - diff + } + }; + unsafe { + // invalidate the buffer + // we cannot do it in the drop function, as L2 cache data prefetch would prefetch + // the data, and there is no way for us to prevent that unless changing MMU table. + dci_slice(&mut self.buffers[self.next][0..len + padding]); + } let buffer = &mut self.buffers[self.next][0..len]; self.next += 1; @@ -135,10 +149,6 @@ pub struct PktRef<'a> { impl<'a> Drop for PktRef<'a> { fn drop(&mut self) { - // Flush buffer from cache, to be filled by the peripheral - // before next read - dcci_slice(self.buffer); - self.entry.word0.modify(|_, w| w.used(false)); dmb(); }