博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
利用libpcap抓包(二)----------网络数据包头结构定义
阅读量:4126 次
发布时间:2019-05-25

本文共 3456 字,大约阅读时间需要 11 分钟。

这里在head.h的头文件中定义了以太网,IP, PPPOE, ARP, TCP, UDP 等数据包头部的结构体,以便于对数据包进行解析,其实在库中有已经定义好的各个数据包头部,像ethhdr,iphdr,tcphdr等,这里自己写一遍可以加深对网络数据包的理解。

/******************************************************************************  文 件 名   : head.h  版 本 号   : V1.1  负 责 人   : Sophisticated  生成日期   : 2018年9月27日  最近修改   :  文件描述   : 报文头部结构体  函数列表   :  修改历史   :  1.日    期   : 2018年9月27日    作    者   : Sophisticated    修改内容   : 创建文件******************************************************************************/#ifndef _HEAD_H_#define _HEAD_H_#include
#include
/*最大抓包长度 :Ethernet 1500字节 + 以太网帧头部14字节 + 以太网帧尾部4字节*/#define SNAP_LEN 1518/*ethernet head are exactly 14 bytes*/#define ETHERNET_HEAD_SIZE 14/*ip头部字节数宏 取hlv低四位即头部长度*单位4bytes 然后强转为ip结构体*///#define IP_HEAD_SIZE(ipheader) ((ipheader->ip_hlv & 0x0f) * 4)#define IP_HEAD_SIZE(packet) ((((struct ip *)(packet + ETHERNET_HEAD_SIZE))->ip_hlv & 0x0f) * 4)/*ethernet address are 6 bytes*/#define ETHERNET_ADDR_LEN 6/*ip address are 4 bytes*/#define IP_ADDR_LEN 4#define ARP_REQUEST 1#define ARP_REPLY 2/*TCP flag*/#define TCP_FIN 0x01#define TCP_SYN 0x02#define TCP_RST 0x04#define TCP_PUSH 0x08#define TCP_ACK 0x10#define TCP_URG 0x20#define TCP_ECE 0x40#define TCP_CWR 0x80/*Ethernet HEADER*/struct ethernet{
u_char ether_dhost[ETHERNET_ADDR_LEN]; u_char ether_shost[ETHERNET_ADDR_LEN]; u_short ether_type; //IP?ARP?etc};/*IP HEADER*/struct ip{
//unsigned int ip_version:4; //unsigned int ip_hlen:4; u_char ip_hlv; /*version + headlength 如果分开定义会有大小端问题,会增加额外的判断*/ u_char ip_tos; u_short ip_len; u_short ip_id; u_short ip_off; u_char ip_ttl; u_char ip_protocol; u_short ip_sum; u_char ip_src[IP_ADDR_LEN]; u_char ip_dst[IP_ADDR_LEN];};/*TCP HEADER*/struct tcp{
u_short tcp_sport; u_short tcp_dport; u_int tcp_seqe; u_int tcp_ack; //u_char tcp_off:4; //u_char tcp_unused:4; //保留位 u_char tcp_hre; //header(4bits) + reserved(4bits) u_char tcp_flag; u_short tcp_win; u_short tcp_sum; u_short tcp_urp;};/*UDP HEADER*/struct udp{
u_short udp_sport; u_short udp_dport; u_short udp_len; u_short udp_sum;};/*ARP HEADER 8+6+4+6+4*/struct arp{
u_short arp_hrd; //hardware u_short arp_pro; //protocol u_char arp_hdlen; //hardware address length u_char arp_prolen; //protocol length u_short arp_op; //arp operations u_char arp_shost[ETHERNET_ADDR_LEN]; u_char arp_sip[IP_ADDR_LEN]; u_char arp_dhost[ETHERNET_ADDR_LEN]; u_char arp_dip[IP_ADDR_LEN];};/*ICMP HEADER*/struct icmp{
u_char icmp_type; u_char icmp_code; u_short icmp_sum; u_short icmp_id; u_short icmp_seq; u_int icmp_time;};/*PPPOE HEADER*/struct pppoe{
u_char pppoe_vtype; //version(0x1) + type(0x1) u_char pppoe_code; u_short pppoe_s_id; u_short pppoe_len;}#endif

说明

在定义IP数据包头结构的第一个字节时,即IP版本号和数据报头长度,我和源码中的做法不太一样,源码中是这样:

#if defined(__LITTLE_ENDIAN_BITFIELD)	__u8	ihl:4,		version:4;#elif defined (__BIG_ENDIAN_BITFIELD)	__u8	version:4,  		ihl:4;#else#error	"Please fix 
"#endif......

而我是把版本号和报文头长度一起定义在了一个字节里,这样不用区分大小端问题,只是解析起来会麻烦些。

解析方法:

ipheader->ip_hlv & 0xf0) >> 4取这个字节高四位即为版本号
ipheader->ip_hlv & 0x0f取这个字节低四位即为报文头长度

在定义tcp数据包头结构体时也是如此,我把标志位flag定义到一个字节里了,源码中是这样的:

#if defined(__LITTLE_ENDIAN_BITFIELD)	__u16	res1:4,		doff:4,		fin:1,		syn:1,		rst:1,		psh:1,		ack:1,		urg:1,		ece:1,		cwr:1;#elif defined(__BIG_ENDIAN_BITFIELD)	__u16	doff:4,		res1:4,		cwr:1,		ece:1,		urg:1,		ack:1,		psh:1,		rst:1,		syn:1,		fin:1;#else#error	"Adjust your 
defines"#endif

解析方法见后面的tcp报文头部解析函数,同样是使用的&运算

转载地址:http://yuhpi.baihongyu.com/

你可能感兴趣的文章
C# 发HTTP请求
查看>>
启动 LocalDB 和连接到 LocalDB
查看>>
Palindrome Number --回文整数
查看>>
Reverse Integer--反转整数
查看>>
Container With Most Water --装最多水的容器(重)
查看>>
Longest Common Prefix -最长公共前缀
查看>>
Letter Combinations of a Phone Number
查看>>
Single Number II --出现一次的数(重)
查看>>
Valid Parentheses --括号匹配
查看>>
Remove Element--原地移除重复元素
查看>>
Remove Duplicates from Sorted Array--从有序数组中移除重复元素
查看>>
Count and Say
查看>>
Gas Station
查看>>
Palindrome Partitioning --回文切割 深搜(重重)
查看>>
Valid Palindrome 简单的回文判断
查看>>
Pascal's Triangle -- 生成杨辉三角
查看>>
Pascal's Triangle II 生成杨辉三角中的某行
查看>>
Minimum Depth of Binary Tree -- 二叉树的最小深度 DFS 加剪枝
查看>>
Climbing Stairs 爬楼梯方法 动态规划
查看>>
Merge Two Sorted Lists 合并两个有序链表
查看>>