标题:
UDP发送数据包,注意IP校验和
[打印本页]
作者:
xuwei
时间:
2015-6-13 16:54
标题:
UDP发送数据包,注意IP校验和
费了好大劲!本来很简单,一个校验擦!
注意,一定要注意
#include "ARP.h"
#include "IP.H"
#include "UDP.H"
#include "ENC28J60_SPI.h"
#include "ENC28J60_Send_Receive.h"
#include "ENC28J60_Buff_Operation.h"
#include "UART.H"
/*******************************8
发送UDP数据包
指定目标IP,本地IP,本地端口,目标端口
还有数据大小,什么数据,第几个包
uchar *MAC_Target_add,//MAC地址。一般情况下由ARP计算得出
uchar *IP_Source_add,//IP源地址
uchar *IP_Target_add,//IP目标地址
uint UDP_Source_Port,UDP源端口
uint UDP_Target_Port,UDP目标端口
uchar * UDP_Send_Data, UDP数据
uchar UDP_Send_Data_length UDP数据长度
**********************************/
//Send_UDP_packet( ); //应答
void Send_UDP_packet( uchar *MAC_Target_add,
uchar *IP_Target_add,
uchar *UDP_Source_Port,
uchar *UDP_Target_Port,
uchar *UDP_Send_Data,
uchar UDP_Send_Data_length
)
{
TypeDef_MAC_Frame_H xdata MAC_Frame_H;//MAC定义一个结构体头
TypeDef_IP_Frame_H xdata IP_Frame_H; //IP定义一个结构体头
TypeDef_UDP_Frame_H xdata UDP_Frame_H;//UDP定义数据结构
xdata unsigned long a,b;
xdata uchar i;
xdata uint tab[10];
xdata uint msb,lsb;
xdata uchar d;
xdata uint da1;
xdata uint da2;
xdata uchar MSB_SUM,LSB_SUM;
UDP_Frame_Set(&MAC_Frame_H,&IP_Frame_H,&UDP_Frame_H);//设置UDP相关参数
/*MAC目标地址*/
MAC_Frame_H.Destination_MAC[0]=MAC_Target_add[0];
MAC_Frame_H.Destination_MAC[1]=MAC_Target_add[1];
MAC_Frame_H.Destination_MAC[2]=MAC_Target_add[2];
MAC_Frame_H.Destination_MAC[3]=MAC_Target_add[3];
MAC_Frame_H.Destination_MAC[4]=MAC_Target_add[4];
MAC_Frame_H.Destination_MAC[5]=MAC_Target_add[5];
/*IP目标地址*/
IP_Frame_H.IP_Dstination[0]=IP_Target_add[0];
IP_Frame_H.IP_Dstination[1]=IP_Target_add[1];
IP_Frame_H.IP_Dstination[2]=IP_Target_add[2];
IP_Frame_H.IP_Dstination[3]=IP_Target_add[3];
//数据长度,
/*这个长度等于IP部首20字节+UDP部首8字节+UDP数据,这里是1字节*/
IP_Frame_H.IP_Total_Length[0]=0;//设置总长度
IP_Frame_H.IP_Total_Length[1]=0x1d;//设置总长度 //29字节
/*计算IP部首校验和**/
IP_Frame_H.IP_Check_sum[0]=0;
IP_Frame_H.IP_Check_sum[1]=0; //先设置为0
msb=IP_Frame_H.IP_Version_Head; //IP的版本号和IP的部首长度,默认为0X45,版本是4,部首是20字节
msb=msb<<8;
lsb=IP_Frame_H.IP_Tos; //ip的TOS据我抓包观察一般是00
tab[0]=msb+lsb;
msb=IP_Frame_H.IP_Total_Length[0];//总数据报文长度
msb=msb<<8;
lsb=IP_Frame_H.IP_Total_Length[1];//总数据报文长度
tab[1]=msb+lsb;
msb=IP_Frame_H.IP_Indentification[0];//IP标识字段,标识字段唯一地标识主机发送的每一份数据报。通常每发送一份报文它的值就会加1
msb=msb<<8;
lsb=IP_Frame_H.IP_Indentification[1];
tab[2]=msb+lsb;
msb=IP_Frame_H.IP_Flage_FRAGMENT_OFFSET[0];//标志位和片偏移
msb=msb<<8;
lsb=IP_Frame_H.IP_Flage_FRAGMENT_OFFSET[1];//标志位和片偏移
tab[3]=msb+lsb;
msb=IP_Frame_H.IP_TTL; //生存时间
msb=msb<<8;
lsb=IP_Frame_H.IP_Protocol; //协议类型
tab[4]=msb+lsb;
msb=IP_Frame_H.IP_Check_sum[0];//部首校验和
msb=msb<<8;
lsb=IP_Frame_H.IP_Check_sum[0];//部首校验和
tab[5]=msb+lsb;
msb=IP_Frame_H.IP_Source[0];//32IP位源地址
msb=msb<<8;
lsb=IP_Frame_H.IP_Source[1];//32IP位源地址
tab[6]=msb+lsb;
msb=IP_Frame_H.IP_Source[2];//32IP位源地址
msb=msb<<8;
lsb=IP_Frame_H.IP_Source[3];//32IP位源地址
tab[7]=msb+lsb;
msb=IP_Frame_H.IP_Dstination[0];//32位IP目标地址
msb=msb<<8;
lsb=IP_Frame_H.IP_Dstination[1];//32位IP目标地址
tab[8]=msb+lsb;
msb=IP_Frame_H.IP_Dstination[2];//32位IP目标地址
msb=msb<<8;
lsb=IP_Frame_H.IP_Dstination[3];//32位IP目标地址
tab[9]=msb+lsb;
/**我操原来是没有清空变量草,费了我一天时间,我说第一次运行正确,其后不对
没有清零!我擦我操!
2012年3月7日
日照高科园
王均伟*/
a=0;
b=0;
for(i=0;i<10;i++)
{
a=a+tab[i]; //变量加
b=a;//暂存A中
b+=(a>>16)&0x0000ffff; //取高位与地位相加,并且加完了清0高八位
}
b=~b; //取反
da1=b;
da2=da1;
da2=(da2>>8)&0x00ff;
//da=IP_Check_Sum_Verify(&IP_Frame_H); //计算IP部首校验和
LSB_SUM=da1;
MSB_SUM=da2;
IP_Frame_H.IP_Check_sum[0]=MSB_SUM;
IP_Frame_H.IP_Check_sum[1]=LSB_SUM; //写入IP部首校验和
UDP_Frame_H.UDP_Source_Port[0]=UDP_Source_Port[0];
UDP_Frame_H.UDP_Source_Port[1]=UDP_Source_Port[1];//源端口是8080
UDP_Frame_H.UDP_Dstination_Port[0]=UDP_Target_Port[0];
UDP_Frame_H.UDP_Dstination_Port[1]=UDP_Target_Port[1];//目标端口是8080
//for(i=0;i<UDP_Send_Data_length;i++) //等到多数据写入时采用的测试只发送一个字节
UDP_Frame_H.UDP_Data[0]=UDP_Send_Data[0];//数据写入
/* 物理操作 */
set_send_buffer_add(0x0200,0x023f);//缓冲区的大小设定,开始200结束1fff
write_buffer_add(0x0200,0x0e);//控制字节
// MAC
write_buffer_add(0x0201,MAC_Frame_H.Destination_MAC[0]);//
write_buffer_add(0x0202,MAC_Frame_H.Destination_MAC[1]);//
write_buffer_add(0x0203,MAC_Frame_H.Destination_MAC[2]);//
write_buffer_add(0x0204,MAC_Frame_H.Destination_MAC[3]);//
write_buffer_add(0x0205,MAC_Frame_H.Destination_MAC[4]);// MAC目的地址
write_buffer_add(0x0206,MAC_Frame_H.Destination_MAC[5]);//
write_buffer_add(0x0207, MAC_Frame_H.Source_add_MAC[0]);//
write_buffer_add(0x0208, MAC_Frame_H.Source_add_MAC[1]);//
write_buffer_add(0x0209, MAC_Frame_H.Source_add_MAC[2]);// MAC源地址
write_buffer_add(0x020A, MAC_Frame_H.Source_add_MAC[3]);//
write_buffer_add(0x020B, MAC_Frame_H.Source_add_MAC[4]);//
write_buffer_add(0x020C, MAC_Frame_H.Source_add_MAC[5]);//
write_buffer_add(0x020D, MAC_Frame_H.Type[0]);// MAC类型
write_buffer_add(0x020E, MAC_Frame_H.Type[1]);//
//IP
write_buffer_add(0x020F,IP_Frame_H.IP_Version_Head);//
write_buffer_add(0x0210,IP_Frame_H.IP_Tos);//
write_buffer_add(0x0211,IP_Frame_H.IP_Total_Length[0]);
write_buffer_add(0x0212,IP_Frame_H.IP_Total_Length[1]);
write_buffer_add(0x0213,IP_Frame_H.IP_Indentification[0]);
write_buffer_add(0x0214,IP_Frame_H.IP_Indentification[1]);
write_buffer_add(0x0215,IP_Frame_H.IP_Flage_FRAGMENT_OFFSET[0]);
write_buffer_add(0x0216,IP_Frame_H.IP_Flage_FRAGMENT_OFFSET[1]);
write_buffer_add(0x0217,IP_Frame_H.IP_TTL);
write_buffer_add(0x0218,IP_Frame_H.IP_Protocol);
write_buffer_add(0x0219,IP_Frame_H.IP_Check_sum[0]);
write_buffer_add(0x021A,IP_Frame_H.IP_Check_sum[1]);
write_buffer_add(0x021B,IP_Frame_H.IP_Source[0]);
write_buffer_add(0x021C,IP_Frame_H.IP_Source[1]);
write_buffer_add(0x021D,IP_Frame_H.IP_Source[2]);
write_buffer_add(0x021E,IP_Frame_H.IP_Source[3]);
write_buffer_add(0x021F,IP_Frame_H.IP_Dstination[0]);
write_buffer_add(0x0220,IP_Frame_H.IP_Dstination[1]);
write_buffer_add(0x0221,IP_Frame_H.IP_Dstination[2]);
write_buffer_add(0x0222,IP_Frame_H.IP_Dstination[3]);
//UDP
write_buffer_add(0x0223,UDP_Frame_H.UDP_Source_Port[0]);
write_buffer_add(0x0224,UDP_Frame_H.UDP_Source_Port[1]);
write_buffer_add(0x0225,UDP_Frame_H.UDP_Dstination_Port[0]);
write_buffer_add(0x0226,UDP_Frame_H.UDP_Dstination_Port[1]);
write_buffer_add(0x0227,UDP_Frame_H.UDP_Length[0]);
write_buffer_add(0x0228,UDP_Frame_H.UDP_Length[1]);
write_buffer_add(0x0229,UDP_Frame_H.UDP_check_sum[0]);
write_buffer_add(0x022A,UDP_Frame_H.UDP_check_sum[1]);
//数据
write_buffer_add(0x022B,UDP_Frame_H.UDP_Data[0]);
write_ENC28J60_REG_SPI(ECON1,0x0c);//允许发送,允许接收
for(;;)
{
d=read_ENC28J60_REG_SPI(EIR);//读取数据包接收标志位
if((d&0x08)==0x08)break; //发送完毕??OK退出ifNO死在里面
}
}
/*****************************
只有接收到一个请求后才会
发送一个arp应答数据包,
Receive_MAC_Source_add_MAC:源MAC,即本机MAC
Receive_ARP_Frame_sender_IP :本机IP
Receive_ARP_Frame_Target_IP:目标IP
******************************/
void Send_ARP_Answer_packet(uchar *Receive_MAC_Source_add_MAC,
uchar *Receive_ARP_Frame_sender_IP,
uchar *Receive_ARP_Frame_Target_IP
)
{
uchar xdata d;
TypeDef_ARP_Frame xdata ARP_Frame;
TypeDef_MAC_Frame_H xdata MAC_Frame_H; //定义两个类型结构变量
/*传递了两个结构传递过去,设置完了在回来用
也是我头回用结构做程序
*/
ARP_Frame_Set(&ARP_Frame,&MAC_Frame_H);//加载ARP数据包
/*mac目标地址*/
MAC_Frame_H.Destination_MAC[0]=*(Receive_MAC_Source_add_MAC);
MAC_Frame_H.Destination_MAC[1]=*(Receive_MAC_Source_add_MAC+1);
MAC_Frame_H.Destination_MAC[2]=*(Receive_MAC_Source_add_MAC+2);
MAC_Frame_H.Destination_MAC[3]=*(Receive_MAC_Source_add_MAC+3);
MAC_Frame_H.Destination_MAC[4]=*(Receive_MAC_Source_add_MAC+4);
MAC_Frame_H.Destination_MAC[5]=*(Receive_MAC_Source_add_MAC+5);
/*发送者IP*/
ARP_Frame.sender_IP[0]=Receive_ARP_Frame_Target_IP[0];
ARP_Frame.sender_IP[1]=Receive_ARP_Frame_Target_IP[1];
ARP_Frame.sender_IP[2]=Receive_ARP_Frame_Target_IP[2];
ARP_Frame.sender_IP[3]=Receive_ARP_Frame_Target_IP[3];
/*mac目标*/
ARP_Frame.Target_MAC[0]=*(Receive_MAC_Source_add_MAC);
ARP_Frame.Target_MAC[1]=*(Receive_MAC_Source_add_MAC+1);
ARP_Frame.Target_MAC[2]=*(Receive_MAC_Source_add_MAC+2);
ARP_Frame.Target_MAC[3]=*(Receive_MAC_Source_add_MAC+3);
ARP_Frame.Target_MAC[4]=*(Receive_MAC_Source_add_MAC+4);
ARP_Frame.Target_MAC[5]=*(Receive_MAC_Source_add_MAC+5);
/*目标IP*/
ARP_Frame.Target_IP[0]=Receive_ARP_Frame_sender_IP[0];
ARP_Frame.Target_IP[1]=Receive_ARP_Frame_sender_IP[1];
ARP_Frame.Target_IP[2]=Receive_ARP_Frame_sender_IP[2];
ARP_Frame.Target_IP[3]=Receive_ARP_Frame_sender_IP[3];
set_send_buffer_add(0x0200,0x023f);//缓冲区的大小设定,开始200结束1fff
write_buffer_add(0x0200,0x0e);//控制字节
write_buffer_add(0x0201,MAC_Frame_H.Destination_MAC[0]);//
write_buffer_add(0x0202,MAC_Frame_H.Destination_MAC[1]);//
write_buffer_add(0x0203,MAC_Frame_H.Destination_MAC[2]);//
write_buffer_add(0x0204,MAC_Frame_H.Destination_MAC[3]);//
write_buffer_add(0x0205,MAC_Frame_H.Destination_MAC[4]);// MAC目的地址
write_buffer_add(0x0206,MAC_Frame_H.Destination_MAC[5]);//
write_buffer_add(0x0207, MAC_Frame_H.Source_add_MAC[0]);//
write_buffer_add(0x0208, MAC_Frame_H.Source_add_MAC[1]);//
write_buffer_add(0x0209, MAC_Frame_H.Source_add_MAC[2]);// MAC源地址
write_buffer_add(0x020A, MAC_Frame_H.Source_add_MAC[3]);//
write_buffer_add(0x020B, MAC_Frame_H.Source_add_MAC[4]);//
write_buffer_add(0x020C, MAC_Frame_H.Source_add_MAC[5]);//
write_buffer_add(0x020D, MAC_Frame_H.Type[0]);// MAC类型
write_buffer_add(0x020E, MAC_Frame_H.Type[1]);//
write_buffer_add(0x020F,ARP_Frame.Hardware_type[0]);//
write_buffer_add(0x0210,ARP_Frame.Hardware_type[1]);//
write_buffer_add(0x0211,ARP_Frame.Protocol_type[0]);
write_buffer_add(0x0212,ARP_Frame.Protocol_type[1]);
write_buffer_add(0x0213,ARP_Frame.Hardware_address_length);
write_buffer_add(0x0214,ARP_Frame.Protocol_address_length);
write_buffer_add(0x0215,ARP_Frame.Operation_code[0]);
write_buffer_add(0x0216,ARP_Frame.Operation_code[1]);
write_buffer_add(0x0217,ARP_Frame.sender_MAC[0]);
write_buffer_add(0x0218,ARP_Frame.sender_MAC[1]);
write_buffer_add(0x0219,ARP_Frame.sender_MAC[2]);
write_buffer_add(0x021A,ARP_Frame.sender_MAC[3]);
write_buffer_add(0x021B,ARP_Frame.sender_MAC[4]);
write_buffer_add(0x021C,ARP_Frame.sender_MAC[5]);
write_buffer_add(0x021D,ARP_Frame.sender_IP[0]);
write_buffer_add(0x021E,ARP_Frame.sender_IP[1]);
write_buffer_add(0x021F,ARP_Frame.sender_IP[2]);
write_buffer_add(0x0220,ARP_Frame.sender_IP[3]);
write_buffer_add(0x0221,ARP_Frame.Target_MAC[0]);
write_buffer_add(0x0222,ARP_Frame.Target_MAC[1]);
write_buffer_add(0x0223,ARP_Frame.Target_MAC[2]);
write_buffer_add(0x0224,ARP_Frame.Target_MAC[3]);
write_buffer_add(0x0225,ARP_Frame.Target_MAC[4]);
write_buffer_add(0x0226,ARP_Frame.Target_MAC[5]);
write_buffer_add(0x0227,ARP_Frame.Target_IP[0]);
write_buffer_add(0x0228,ARP_Frame.Target_IP[1]);
write_buffer_add(0x0229,ARP_Frame.Target_IP[2]);
write_buffer_add(0x022A,ARP_Frame.Target_IP[3]);
write_ENC28J60_REG_SPI(ECON1,0x0c);//允许发送,允许接收
for(;;)
{
d=read_ENC28J60_REG_SPI(EIR);//读取数据包接收标志位
//SendOneByte(d);调试
if((d&0x08)==0x08)break; //发送完毕??OK退出ifNO死在里面
}
}
复制代码
欢迎光临 (http://www.51hei.com/bbs/)
Powered by Discuz! X3.1