6.1810 Lab7 net: Network driver
本文最后更新于 218 天前,内容如有失效请评论区留言。

这个 Lab 又臭又长,我受不了,这破 intel 文档读不下去一点。因此这个 Lab 基本是抄作业,我也没有太细看 intel 文档,只针对关键部分看了下,但是我也想吐槽文档的图画得是真丑,也很不直观,受不了。

QEMU 环境问题

这个 Lab 直接编译运行失败,错误信息表明当前的 QEMU 二进制文件中没有编译进 user 模式的网络后端。需要重新编译 QEMU,并确保配置文件中包含 user 模式网络支持。

qemu-system-riscv64 -machine virt -bios none -kernel kernel/kernel -m 128M -smp 1 -nographic -global virtio-mmio.force-legacy=false -drive file=fs.img,if=none,format=raw,id=x0 -device virtio-blk-device,drive=x0,bus=virtio-mmio-bus.0 -netdev user,id=net0,hostfwd=udp::26999-:2000 -object filter-dump,id=net0,netdev=net0,file=packets.pcap -device e1000,netdev=net0,bus=pcie.0 -S -gdb tcp::26000
qemu-system-riscv64: -netdev user,id=net0,hostfwd=udp::26999-:2000: network backend 'user' is not compiled into this binary
make: *** [Makefile:309: qemu-gdb] Error 1

解决办法:network backend ‘user’ is not compiled into this binary

sudo apt install libslirp-dev
cd ~/qemu-8.0.5/
./configure --target-list=riscv64-softmmu --enable-slirp
make -j$(nproc)
sudo make install

Lab7

实验中用到的 e1000 描述与寄存器

struct rx_desc 结构:

image-20241110230727395

Receive Status 与实验中用到的部分:

image-20241110230843008

image-20241110230834167

Receive Descriptor Ring Structure,实际上 tail 指向的这个位置 software 是不能使用的,能用的位置是 (tail + 1) % RX_RING_SIZE,原因我也不知道,手册上似乎也没讲清楚。

image-20241110231029759

struct tx_desc结构,

image-20241110231404773

Transmit Command (TDESC.CMD) 与实验中用到的部分,

image-20241110231457583

image-20241110231509233

image-20241110231520105

Transmit Status 和用到的部分,

image-20241110231645972

image-20241110231701160

Transmit Descriptor Ring Structure,tail 指向 software 下一个发送的位置,

image-20241110192322509

TDT 寄存器,

image-20241110232115510

RDT 寄存器,

image-20241110232235094

代码

注意,锁只需要在 e1000_recv 中使用,e1000_recv 中不必使用锁。因为 e1000_recv 只被 e1000_intr 调用,而调用时不会发生嵌套中断,注释中有这样一句话:tell the e1000 we’ve seen this interrupt; without this the e1000 won’t raise any further interrupts.

剩余部分思路见代码注释,代码如下:

diff --git a/kernel/e1000.c b/kernel/e1000.c
index 70a2adf..82b446a 100644
--- a/kernel/e1000.c
+++ b/kernel/e1000.c
@@ -102,6 +102,27 @@ e1000_transmit(struct mbuf *m)
   // the TX descriptor ring so that the e1000 sends it. Stash
   // a pointer so that it can be freed after sending.
   //
+  acquire(&e1000_lock);
+  int idx = regs[E1000_TDT];
+
+  // check if the next descriptor has been sent
+  if (!(tx_ring[idx].status & E1000_TXD_STAT_DD)) {
+    release(&e1000_lock);
+    return -1;
+  }
+
+  // free the old mbuf
+  if (tx_mbufs[idx]) {
+    mbuffree(tx_mbufs[idx]);
+  }
+
+  tx_mbufs[idx] = m;
+  tx_ring[idx].addr = (uint64)m->head;
+  tx_ring[idx].length = m->len;
+  tx_ring[idx].cmd = E1000_TXD_CMD_RS | E1000_TXD_CMD_EOP; // Report Status, End of Packet
+
+  regs[E1000_TDT] = (idx + 1) % TX_RING_SIZE;
+  release(&e1000_lock);

   return 0;
 }
@@ -115,6 +136,25 @@ e1000_recv(void)
   // Check for packets that have arrived from the e1000
   // Create and deliver an mbuf for each packet (using net_rx()).
   //
+  while (1) {
+    int idx = (regs[E1000_RDT] + 1) % RX_RING_SIZE;
+
+    if (!(rx_ring[idx].status & E1000_RXD_STAT_DD)) {
+      break;
+    }
+
+    // update the mbuf's m->len and deliver it to the network stack
+    rx_mbufs[idx]->len = rx_ring[idx].length;
+    net_rx(rx_mbufs[idx]);
+
+    // allocate a new mbuf for the descriptor
+    rx_mbufs[idx] = mbufalloc(0);
+    // update the descriptor's address
+    rx_ring[idx].addr = (uint64)rx_mbufs[idx]->head;
+    rx_ring[idx].status = 0;
+
+    regs[E1000_RDT] = idx;
+  }
 }

 void

测试

image-20241110192410390
image-20241110192552376

References

YEWPO’s blog – Lab net

[MIT 6.s081] Xv6 Lab8 Networking 实验记录

XV6学习(16)Lab net: Network stack

[mit6.s081] 笔记 Lab11: Networking | 网络

Intel E1000 Software Developer’s Manual

暂无评论

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇