千兆以太网(5):发送——ODDR原语和Wireshark抓包工具
一、ODDR原语
FPGA 传输的数据为单沿数据,而 PHY 传输的数据为双沿数据,所以FPGA 发送心跳包的最后需要使用 ODDR 原语将单沿数据转换为双沿数据。通常情况下 FPGA 处理数据使用的时钟为晶振产生的时钟(FPGA 时钟),而 FPGA 传输来的数据经过ODDR 原语后转换为双沿的数据都是和 PHY 的时钟同步,所以我们如果想把 FPGA 时钟的数据传给 PHY 芯片则需要进行跨时钟域,将 FPGA 时钟同步的数据转换为 PHY 时钟同步的数据。此处单沿转双沿数据采用 Output DDR 原语,简称 ODDR,将单沿 8bit 数据转换为双沿 4bit 数据。
ODDR原语参考 7 Series FPGAs SelectIO Resources 文档和 Xilinx 7 Series FPGA Libraries Guide for HDL Designs 。
1、ODDR原语获取途径
2、ODDR原语接口和属性
D1 和 D2 为数据输入,CE 为 ODDR 工作使能,C 为时钟,S 和 R 分别为置位和复位,Q为输出。
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106185845177-1179461754.png)
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106185851983-1628515970.png)
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106185927516-510125402.png)
3、ODDR原语工作模式
ODDR 有两种工作模式,模式配置如下图所示,分别为:OPPOSITE_EDGE、SAME_EDGE。
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106190108210-942475615.png)
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106190116378-1251283589.png)
OPPOSITE_EDGE 模式下,双沿都用来捕捉数据,其中上升沿捕捉低位数据 D1,下降沿捕捉高位数据D2,输出 Q 在上升沿传输 D1,下降沿传输D2。SAME_EDGE 模式下,只采用上升沿来捕捉低位数据 D1 和高位数据 D2,然后在输出 Q 的下降传输 D1,上升沿传输 D2。此次传输我们采用 SAME_EDGE 模式。
4、ODDR双沿数据转单沿数据使用方式
根据硬件电路图,PHY 传输给 FPGA 有一条时钟线、一条使能线和四条数据线,其中使能线和数据线都为双沿数据。一条使能线包含了 DV 和 ERR,其中上升沿传输的是 DV 信号(即数据有效信号),下降沿传输的为 ERR 信号(即数据出错信号,通常情况下不考虑 ERR,ERR 是由硬件引起,和软件无关);四条数据线包含了一个始终 8bit 数据,其中上升沿传输的是 8bit 数据中的[3:0],下降沿传输的是 8bit 数据中的[7:4]。 我们采用 ODDR 原语将单沿 8bit 数据转换为双沿 4bit 数据,同时将 4bit 数据对应有效 DV 信号提取。那么可以建立实现单沿转双沿功能的模块:oddr_ctrl,其中输入与输出关系图如下所示。 最后 PHY 芯片传输出去的 phy_txd 和 phy_tx_ctl 都和 PHY 的时钟 phy_tx_clk 同步。图中 sclk_90 为输入的时钟信号是 FPGA 时钟相移90度后形成的,目的是转换 phy_tx_rxd 和 phy_tx_ctl 更稳定,tx_dat 和 tx_en 为该模块输入的单沿 8bit 数据和对应的数据有效使能。
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106190952674-1389158993.png)
二、以太网复位信号
前面博客《千兆以太网(1)》中说过 PHY 芯片初始化必须满足当上电后至少经过 4ms 以上才可以将 PHY 芯片复位引脚置高,因此输出端口不要忘记了 PHY 芯片的复位信号 phy_rst_n,该信号通过延时 4ms 即可产生,有了这个信号,PHY 芯片才能工作起来。
//延时 4ms 后启动 phy_rst_n always @(posedge clk50) begin if(rst) begin phy_rst_cnt <= 'd0; end else if(phy_rst_cnt[18]==1'b0) begin phy_rst_cnt <= phy_rst_cnt + 1'b1; end end assign phy_rst_n = phy_rst_cnt[18];
三、Wireshark 抓包
上板后打开点击电脑中的以太网设置 --- 更改适配器选项,即可看到网卡正常工作起来。
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106192212356-430304220.png)
打开 Wireshark 软件,可以看到 以太网 的波形正在变化。
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106192300939-1631285707.png)
双击进去,点击 编辑 --- 首选项,点击 NTP 即可看到我们的端口编号,本次设计的是 UDP,为什么看 NTP ?因为 NTP 其实包含了 UDP,可以看成是 UDP 的一种。
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106192327885-1609488878.png)
点击 UDP 和 IPv4,将 UDP校验和 IP校验 打勾,待会就看得到是否校验成功了。
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106192335318-1044734874.png)
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106192342225-865856095.png)
接着我们重新捕获以太网,可以看到很多蓝色的部分表示我们传输的心跳包,黑色则的不是我们的,它的 Source 和 Destination 都和我们设置的不同,那就不管它了。点击某个蓝色条纹,下方就出现了相关信息,这些信息是去除了包头(7个55、1个d5)后的,因此字节显示 106 ,和我们设计相吻合。此外可以看到头部校验分别显示 [correct] 和 [Good],表明我们这次的校验也是正确的。
![](https://img2018.cnblogs.com/common/1536533/202001/1536533-20200106192352827-1717836097.png)
上面的现象表明我们此次的千兆以太网发送项目成功实现。
四、千兆网络摄像头
将摄像头的数据组建成千兆网帧,即可实现基于 UDP 的千兆网络摄像头。由于摄像头速率慢,千兆网速率快,中间不需要通过 SDRAM、DDR3 等缓存。只需要利用 FIFO,在数据段时发出读数据请求即可。该FIFO还可以起到跨时钟域的作用。可以在电脑端设置巨型帧,也可以每次发一行图像数据。上位机编写时为避免图像错位,可以设置图像的行号或图像的帧开始标志,FPGA发送时加上这个标志即可。如果上位机软件来不及解析,可以每次发送一行或一帧时,延时若干时间,强行降低图像帧率。这个工程的具体实现就不记录了。
参考资料:威三学院FPGA教程