14 Star 9 Fork 0

zhangruoxu/demo

加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
文件
该仓库未声明开源许可证文件(LICENSE),使用请关注具体项目描述及其代码上游依赖。
克隆/下载
ipv4_lib.c 4.03 KB
一键复制 编辑 原始数据 按行查看 历史
fishobone 提交于 2023-07-24 17:01 . vlan功能完成
#include "basetype.h"
#include "common.h"
#include "ethernet_lib.h"
#include "packet_lib.h"
/*
* description: 封装报文的IP头部分(固定的20字节)
*
* input:
* ucTTL ttl
* ucProtocol ucProtocol
* uiSrcIPv4Addr 源ip地址
*uiDstIPv4Addr 目的ip地址
*
* output:
* pucBuffer 报文
* return: 固定的20字节ipv4头
* tip: IN是空宏,表示改参数是输入
*/
UINT32 Ipv4Lib_EncodeIPv4Header(UINT8 ucTTL, UINT8 ucProtocol,
UINT32 uiSrcIPv4Addr, UINT32 uiDstIPv4Addr, UINT8* pucBuffer) // , UINT16 TotalLength
{
// UINT16 Head_check,自己算
UINT8 *pucPointer = pucBuffer;
pucPointer += MAC_BYTE + MAC_BYTE + 2;
*pucPointer = (UINT8)((4 & 0x0F) << 4); // 4位的版本号
*pucPointer = *pucPointer + (UINT8)(5 & 0x0F); // 4位的首部长度
pucPointer++;
*pucPointer = 0X00; // 服务类型
pucPointer++;
// 总长度,封装的时候不知道 ,需要调用PacketLib_UpdateTollength设置
pucPointer += 2;
// 标识
UINT16 id = 0X0000;
*pucPointer = (UINT8)((id & 0xFF00) >> 8);
pucPointer++;
*pucPointer = (UINT8)(id & 0x00FF);
pucPointer++;
// 标志和片位移
UINT16 flag_offset = 0X0000;
*pucPointer = (UINT8)((flag_offset & 0xFF00) >> 8);
pucPointer++;
*pucPointer = (UINT8)(flag_offset & 0x00FF);
pucPointer++;
// TTL
*pucPointer = ucTTL;
pucPointer++;
// 协议
*pucPointer = ucProtocol;
pucPointer++;
// 计算校验和
UINT16 Head_check = PacketLib_CRCCheak(pucBuffer, 5 * 4);
*pucPointer = (Head_check & 0XFF00) >> 8;
pucPointer++;
*pucPointer = (Head_check & 0X00FF);
pucPointer++;
// IPV4地址
memcpy(pucPointer, PacketLib_Displacement(uiSrcIPv4Addr), 4);
pucPointer += 4;
// IPV4地址
memcpy(pucPointer, PacketLib_Displacement(uiDstIPv4Addr), 4);
pucPointer += 4;
// todo:
return 20; // 固定部分
}
/*
* description: 解封装报文的ipv4部分
*
* input:
* pucBuffer 报文
* usPacketLen 报文长度
*
* output:
* pstIpv4Header 报文的Ipv4部分
* return: icmp部分长度
* tip: IN是空宏,表示改参数是输入
*/
VOID Ipv4Lib_DecodeIPv4Header(UINT8 *pucBuffer, UINT16 usPacketLen,
IPV4HEAD_S *pstIpv4Header)
{
if (usPacketLen < 34)
{
printf("Ip header message length error\n");
exit(-1);
}
UINT8* pucPointer = pucBuffer;
ETHERNET_VLAN_S ustEthernetVlanHeader;
UINT16 usVlanFlag;
usVlanFlag = 0x8100;
pucPointer = pucBuffer;
// 得到以太头中是否有vlan
EthernetLib_DecodeEthernetVlanHeader(pucBuffer, usPacketLen, &ustEthernetVlanHeader);
if (usVlanFlag == ustEthernetVlanHeader.usEtype)
{
// 偏移18字节以太头
pucPointer += ETHERHEAD_OFFSET_LENGTH + VLAN_ETYPE + VLAN_ID;
}
else
{
// 偏移14字节以太头
pucPointer += ETHERHEAD_OFFSET_LENGTH;
}
// 版本
pstIpv4Header->ucVersion = ((*pucPointer) & 0xF0);
// 首部长度
pstIpv4Header->ucHeadlen = ((*pucPointer) & 0x0F);
pucPointer++;
pstIpv4Header->ucTos = *pucPointer;
pucPointer++;
pstIpv4Header->usTotal_len = ((UINT16)(*pucPointer) << 8);
pucPointer++;
pstIpv4Header->usTotal_len += (UINT16)(*pucPointer);
pucPointer++;
pstIpv4Header->usId = ((UINT16)(*pucPointer) << 8);
pucPointer++;
pstIpv4Header->usId += (UINT16)(*pucPointer);
pucPointer++;
UINT16 flag_offset = 0;
flag_offset = ((UINT16)(*pucPointer) << 8);
pucPointer++;
flag_offset += (UINT16)(*pucPointer);
pucPointer++;
pstIpv4Header->usFlag = (flag_offset & 0b1110000000000000) >> 13;
pstIpv4Header->usOffset = (flag_offset & 0b0001111111111111);
pstIpv4Header->ucTTL = *pucPointer;
pucPointer++;
pstIpv4Header->ucProtocol = *pucPointer;
pucPointer++;
UINT16 Head_check = PacketLib_CRCCheak(pucBuffer, 5 * 4);
pstIpv4Header->usHead_check = Head_check;
pucPointer += 2;
pstIpv4Header->uiSrcIPv4Addr = PacketLib_Undisplacement(pucPointer);
pucPointer += IPV4_BYTE;
pstIpv4Header->uiDstIPv4Addr = PacketLib_Undisplacement(pucPointer);
pucPointer += IPV4_BYTE;
}
Loading...
马建仓 AI 助手
尝试更多
代码解读
代码找茬
代码优化
1
https://gitee.com/zhangruoxudada/demo.git
git@gitee.com:zhangruoxudada/demo.git
zhangruoxudada
demo
demo
master

搜索帮助

0d507c66 1850385 C8b1a773 1850385