10G UDP协议栈 IP层设计-(6)IP TX模块

一、模块功能

1、上层数据封装IP报文头部

2、计算首部校验和

二、首部校验和计算方法 

在发送方,先把IP数据报首部划分为许多16位字的序列,并把检验和字段置零。用反码算术运算把所有16位字相加后,将得到的和的反码写入检验和字段。接收方收到数据报后,将首部的所有16位字再使用反码算术运算相加一次。将得到的和取反码,即得出接收方检验和的计算结果。若首部未发生任何变化,则此结果必为0,于是就保留这个数据报。否则即认为出差错。
原文链接:https://blog.csdn.net/weixin_44870077/article/details/118106364

 例如一包数据的首部:64‘h4500001400012000、64’h8017d0b9c0a86464、64‘hc0a8646300000000

版本号到片偏移:64‘h4500001400012000

生存时间:8’h80

协议号:8‘h17

计算出来的首部校验和:16’hd0b9

源IP地址:c0a86464

目的IP地址:c0a86463

划分为长度为16bit的字段:4500 0014 0001 2000 8017 首部校验和初始计算值0000 c0a8 6464 c0a8 6463

相加:4500 + 0014 +  0001 + 2000 + 8017 + 0000 + c0a8 + 6464 + c0a8 + 6463 = 3 2F43

进位的高位再次加到低16位:2F43 + 0003 = 2F46

按位取法之后得到:d0b9

三、程序设计

参考:奇哥FPGA

//将数据缓存到FIFO
FIFO_UDP_DATA_64X16 u_FIFO_UDP_DATA_64X16 (.clk          (i_clk              ), .srst         (i_rst              ), .din          (rs_axis_out_data   ), .wr_en        (rs_axis_out_valid  ), .rd_en        (r_fifo_rden        ), .dout         (w_fifo_data_out    ), .full         (), .empty        (w_fifo_empty       )  
);always@(posedge i_clk,posedge i_rst)beginif(i_rst)beginrs_axis_out_data    <= 'd0; rs_axis_out_user    <= 'd0;rs_axis_out_keep    <= 'd0;rs_axis_out_last    <= 'd0;rs_axis_out_valid   <= 'd0;endelse beginrs_axis_out_data    <= s_axis_out_data  ;rs_axis_out_user    <= s_axis_out_user  ;rs_axis_out_keep    <= s_axis_out_keep  ;rs_axis_out_last    <= s_axis_out_last  ;rs_axis_out_valid   <= s_axis_out_valid ;end
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)beginr_fifo_rden_ff1 <= 'd0;r_fifo_rden_ff2 <= 'd0;endelse beginr_fifo_rden_ff1 <= r_fifo_rden;r_fifo_rden_ff2 <= r_fifo_rden_ff1;end
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)r_fifo_data_out <= 'd0;elser_fifo_data_out <= w_fifo_data_out;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)r_last_user <= 'd0;elseif(s_axis_out_last)r_last_user <= s_axis_out_user;elser_last_user <= r_last_user;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)r_last_keep <= 'd0;elseif(s_axis_out_last)r_last_keep <= s_axis_out_keep;elser_last_keep <= r_last_keep;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)ri_set_source_ip <= P_SOURCE_IP;elseif(i_set_source_valid)ri_set_source_ip <= i_set_source_ip;elseri_set_source_ip <= ri_set_source_ip;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)ri_set_target_ip <= P_TARGET_IP;elseif(i_set_target_valid)ri_set_target_ip <= i_set_target_ip;elseri_set_target_ip <= ri_set_target_ip;
end
//当FIFO有数据时就开始读FIFO
always@(posedge i_clk,posedge i_rst)beginif(i_rst)r_fifo_rden <= 'd0;elseif(!w_fifo_empty && r_cnt == 0)r_fifo_rden <= 1'b1;else if(w_fifo_empty)r_fifo_rden <= 1'b0;elser_fifo_rden <= r_fifo_rden;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)r_cnt <= 'd0;elseif(rm_axis_mac_last)r_cnt <= 'd0;else if((!w_fifo_empty && r_cnt == 0 && m_axis_mac_ready)|| r_cnt)r_cnt <= r_cnt + 1;elser_cnt <= r_cnt;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)rs_axis_out_ready <= 'd1;elseif(s_axis_out_last || !m_axis_mac_ready)rs_axis_out_ready <= 'd0;else if(rm_axis_mac_last || (!rm_axis_mac_valid && !m_axis_mac_ready))rs_axis_out_ready <= 'd1;elsers_axis_out_ready <= rs_axis_out_ready ;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)rm_axis_mac_data <= 'd0;elseif(!w_fifo_empty && r_cnt == 0)rm_axis_mac_data <= {4'b0100,4'b0101,8'd0,(rs_axis_out_user[70:55] + 16'd20),rs_axis_out_user[15:0],{1'b0,rs_axis_out_user[54],~rs_axis_out_user[37]},rs_axis_out_user[28:16]};else if(r_cnt == 1)rm_axis_mac_data <= {8'd128,rs_axis_out_user[36:29],~r_header_check[15:0],ri_set_source_ip[31:0]};else if(r_cnt == 2)rm_axis_mac_data <= {ri_set_target_ip[31:0],w_fifo_data_out[63:32]};elserm_axis_mac_data <= {r_fifo_data_out[31:0],w_fifo_data_out[63:32]};
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)r_hd_check_cnt <= 'd0;elseif(s_axis_out_valid)r_hd_check_cnt <= r_hd_check_cnt + 1;elser_hd_check_cnt <= 'd0;
end//做首部校验和
always@(posedge i_clk,posedge i_rst)beginif(i_rst)r_header_check <= 'd0;elseif(r_hd_check_cnt == 1)r_header_check <= 16'h4500 + (rs_axis_out_user[70:55] + 16'd20) + rs_axis_out_user[15:0] + ({{1'b0,rs_axis_out_user[54],~rs_axis_out_user[37]},rs_axis_out_user[28:16]})+ {8'd128,rs_axis_out_user[36:29]} ++ ri_set_source_ip[31:16] + ri_set_source_ip[15:0] + ri_set_target_ip[31:16] + ri_set_target_ip[15:0];else if(r_hd_check_cnt == 1)r_header_check <= r_header_check[31:16] + r_header_check[15:0]; //可能会产生进位else if(r_hd_check_cnt == 2)r_header_check <= r_header_check[31:16] + r_header_check[15:0]; //加进位之后,可能还会产生进位,所以要再加一次elser_header_check <= r_header_check;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)rm_axis_mac_user <= 'd0;elserm_axis_mac_user <= {((rs_axis_out_user[70:55] + 16'd19) >> 3) + 1,48'hFFFFFFFF_FFFF,16'h0800};
end
//字节对齐
always@(posedge i_clk,posedge i_rst)beginif(i_rst)rm_axis_mac_keep <= 'd0;elseif(w_fifo_rden_neg && r_last_keep <= 8'b1111_0000)case(r_last_keep)// 8'b1111_1111: rm_axis_mac_keep <= 8'b1111_1111// 8'b1111_1110: rm_axis_mac_keep <= // 8'b1111_1100: rm_axis_mac_keep <=// 8'b1111_1000: rm_axis_mac_keep <=8'b1111_0000: rm_axis_mac_keep <= 8'b1111_1111;8'b1110_0000: rm_axis_mac_keep <= 8'b1111_1110;8'b1100_0000: rm_axis_mac_keep <= 8'b1111_1100;8'b1000_0000: rm_axis_mac_keep <= 8'b1111_1000;default     : rm_axis_mac_keep <= 8'b1111_1111;endcaseelse if(w_fifo_rden_neg_ff1 && r_last_keep >= 8'b1111_1000)case(r_last_keep)8'b1111_1111: rm_axis_mac_keep <= 8'b1111_0000;8'b1111_1110: rm_axis_mac_keep <= 8'b1110_0000;8'b1111_1100: rm_axis_mac_keep <= 8'b1100_0000;8'b1111_1000: rm_axis_mac_keep <= 8'b1000_0000;// 8'b1111_0000: rm_axis_mac_keep <= 8'b1111_1111;// 8'b1110_0000: rm_axis_mac_keep <= 8'b1111_1110;// 8'b1100_0000: rm_axis_mac_keep <= 8'b1111_1100;// 8'b1000_0000: rm_axis_mac_keep <= 8'b1111_1000;default     : rm_axis_mac_keep <= 8'b0000_0000;endcase   elserm_axis_mac_keep <= 8'b1111_1111;      
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)rm_axis_mac_last <= 'd0;elseif(w_fifo_rden_neg && r_last_keep <= 8'b1111_0000)rm_axis_mac_last <= 1'b1;else if(w_fifo_rden_neg_ff1 && r_last_keep >= 8'b1111_1000)rm_axis_mac_last <= 1'b1;elserm_axis_mac_last <= 'd0;
endalways@(posedge i_clk,posedge i_rst)beginif(i_rst)rm_axis_mac_valid <= 'd0;elseif(!w_fifo_empty && r_cnt == 0)rm_axis_mac_valid <= 1'b1;else if(rm_axis_mac_last)rm_axis_mac_valid <= 'd0;elserm_axis_mac_valid <= rm_axis_mac_valid ;end

四、仿真

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/837614.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

C++(week2):C语言中高级

文章目录 (八) 指针0.概念1.指针基础(1)指针的声明(2)指针的两个基本操作①取地址运算符 &②解引用运算符 * (3)野指针①野指针②空指针③指针变量的赋值 vs 指针变量指向对象的赋值 (4)指针的应用①指针作为参数进行传递②指针作为返回值③拓展&#xff1a;栈帧 (5)常量指…

手撸XXL-JOB(一)——定时任务的执行

SpringBoot执行定时任务 对于定时任务的执行&#xff0c;SpringBoot提供了三种创建方式&#xff1a; 1&#xff09;基于注解(Scheduled) 2&#xff09;基于接口&#xff08;SchedulingConfigurer&#xff09; 3&#xff09;基于注解设定多线程定时任务 基于Scheduled注解 首…

基于51单片机的冰箱控制系统设计( proteus仿真+程序+设计报告+原理图+讲解视频)

基于51单片机冰箱控制系统设计( proteus仿真程序设计报告原理图讲解视频&#xff09; 基于51单片机冰箱控制系统设计 1. 主要功能&#xff1a;2. 讲解视频&#xff1a;3. 仿真4. 程序代码5. 设计报告6. 原理图7. 设计资料内容清单&&下载链接资料下载链接&#xff1a; …

【C++】学习笔记——继承_2

文章目录 十二、继承5. 继承与友元6. 继承与静态成员7. 复杂的菱形继承及菱形虚拟继承 未完待续 十二、继承 5. 继承与友元 友元关系不能继承&#xff0c;也就是说父类友元不能访问子类私有和保护成员 。除非子类也设置成友元。 6. 继承与静态成员 父类定义了 static 静态成…

pnpm:无法加载文件 C:\Users\PC\AppData\Roaming\npm\pnpm.ps1,因为在此系统上禁止运行脚本。

使用pnpm命令启动vue时报了个错&#xff1a; 解决起来也简单&#xff0c;右击开始菜单&#xff0c;用管理员身份打开终端。win11的如下图&#xff1a; win10我记得应该是PowerShell&#xff08;管理员&#xff09;&#xff0c;这样的。 打开之后执行命令&#xff1a; set-…

物联网平台之单体架构

介绍本文主要介绍平台的单体架构&#xff0c;包括各个组件之间的数据流描述以及所做的一些架构选择。在单体架构模式下&#xff0c;所有 ThingsKit 组件都在单个 Java 虚拟机 (JVM) 中启动&#xff0c;并共享相同的操作系统资源。由于 ThingsKit 是用 Java 编写的&#xff0c;因…

dnf手游攻略,新手入坑必备!

一、角色创建策略 在DNF手游中&#xff0c;角色创建是玩家初入游戏的首要步骤。为最大化游戏体验和收益&#xff0c;新手玩家通常建议创建三个角色&#xff1a;一个主账号和两个副账号。 主账号选择 主账号的选择应基于玩家个人的喜好和对职业的熟悉程度。无论选择哪个职业&a…

番外篇 | 手把手教你利用YOLOv8进行热力图可视化 | 针对视频

前言:Hello大家好,我是小哥谈。YOLOv8的热力图可视化可以帮助我们更加直观地了解模型在图像中的检测情况,同时也可以帮助我们进行模型的调试和优化。热力图是一种颜色渐变的图像,不同颜色的区域表示不同程度的关注度或者置信度。在YOLOv8中,可以通过设置阈值来控制热力图的…

电机控制杂谈——“双采样双更新模式”对模型预测控制/PI控制的提升有多大?

1.采样频率与PWM开关频率的关系 一般有以下两种采样模式。 如下图&#xff08;a&#xff09;所示&#xff0c;这种方式称之为单采单更模式&#xff0c;即在一个PWM周期内&#xff0c;采样一次&#xff0c;更新一次PWM占空比&#xff0c;在这种情况下&#xff0c;采样频率&…

小红书自动私信获客,打造个人品牌

在当今这个内容为王、社交至上的时代&#xff0c;小红书作为新兴的社交电商平台&#xff0c;凭借其独特的社区氛围和强大的种草能力&#xff0c;成为了众多KOL、商家以及个人品牌打造的首选平台。想要在小红书上脱颖而出&#xff0c;精准引流获客&#xff0c;利用自动私信功能不…

【MyBatis】 MyBatis框架下的高效数据操作:深入理解增删查改(CRUD)

文章目录 1. 环境准备2. 增加数据&#xff08;Create&#xff09;3. 查询数据&#xff08;Retrieve&#xff09;4. 更新数据&#xff08;Update&#xff09;5. 删除数据&#xff08;Delete&#xff09;6. 总结 &#x1f389;欢迎来到Java学习路线专栏~探索Java中的静态变量与实…

强化训练:day8(求最小公倍数、数组中的最⻓连续⼦序列、字⺟收集)

文章目录 前言1. 最小公倍数1.1 题目描述1.2 解题思路1.3 代码实现 2. 数组中的最⻓连续⼦序列2.1 题目描述2.2 解题思路2.3 代码实现 3. 字母收集3.1 题目描述3.2 解题思路3.3 代码实现 总结 前言 1. 最小公倍数   2. 数组中的最⻓连续⼦序列   3. 字⺟收集 1. 最小公倍数…

JavaEE之线程(5)——Java内存模型、内存可见性、volatile关键字

前言 volatile可以理解成轻量级的 synchronized&#xff0c; 它在多CPU开发中保证了共享变量的“可见性”&#xff0c;可见性我们可以理解成是&#xff1a;当一个线程修改一个共享变量时&#xff0c;另一个线程可以读到这个修改的值。由于它不会引起线程的上下文切换和调度&am…

HTML的使用(中)

文章目录 前言一、HTML表单是什么&#xff1f;二、HTML表单的使用 &#xff08;1&#xff09;<form>...</form>表单标记&#xff08;2&#xff09;<input>表单输入标记总结 前言 在许多网页平台上浏览&#xff0c;大多逃不了登录账号。此时在网页中填写的用户…

Centos 7.9 安装 tigervnc-server

环境&#xff1a;当前使用的 Centos 7.9 的光盘作为的本地源&#xff0c;或使用离线rpm包。 1 检查是否已安装 tigervnc [rootlocalhost /]# rpm -q tigervnc tigervnc-server 未安装软件包 tigervnc tigervnc-server-1.8.0-21.el7.x86_64 如果安装过卸掉 卸载: rpm -e [ro…

MYSQL DBA运维实战 SQL2

1.DML:通过SQL语句中的DML语言来实现数据的操作。 insert实现数据的插入。 update实现数据的更新。delete实现数据的删除。 插入&#xff0c;完全插入insert into 表名 values(值) 非完全插入:insert into 表名(列名&#xff0c;列名) values(值) 更新&#xff0…

RustGUI学习(iced)之小部件(十二):如何使用rule分割线部件来分割UI?

前言 本专栏是学习Rust的GUI库iced的合集,将介绍iced涉及的各个小部件分别介绍,最后会汇总为一个总的程序。 iced是RustGUI中比较强大的一个,目前处于发展中(即版本可能会改变),本专栏基于版本0.12.1. 概述 这是本专栏的第十二篇,主要讲述rule分割线部件的使用,会结合…

【计算机网络】http协议的原理与应用,以及https是如何保证安全传输的

HTTP 超文本传输协议&#xff08;英文&#xff1a;HyperText Transfer Protocol&#xff0c;缩写&#xff1a;HTTP&#xff09;是一种用于分布式、协作式和超媒体信息系统的应用层协议。HTTP是万维网的数据通信的基础。 HTTP的发展是由蒂姆伯纳斯-李于1989年在欧洲核子研究组织…

React useEffect Hook: 理解和解决组件双重渲染问题

在React中&#xff0c;useEffect可能会在组件的每次渲染后运行&#xff0c;这取决于它的依赖项。如果你发现useEffect运行了两次&#xff0c;并且你正在使用React 18或更高版本的严格模式&#xff08;Strict Mode&#xff09;&#xff0c;这可能是因为在开发模式下&#xff0c;…

轻松掌握抖音自动点赞技巧,快速吸粉

在当今这个信息爆炸的时代&#xff0c;抖音作为短视频领域的领头羊&#xff0c;不仅汇聚了庞大的用户群体&#xff0c;也成为了品牌和个人展示自我、吸引粉丝的重要平台。如何在众多内容创作者中脱颖而出&#xff0c;实现高效引流获客&#xff0c;精准推广自己的内容&#xff0…