首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 开发语言 > C++ >

关于构造tcp报文出现的有关问题

2013-10-04 
关于构造tcp报文出现的问题主要代码如下://ip headerstruct iphdr{unsigned short h_ver:4//版本unsigned

关于构造tcp报文出现的问题
主要代码如下:
//ip header
struct iphdr
{
unsigned short h_ver:4;           //版本
unsigned short hl:4;//首部长度
unsigned short tos:8;               //服务类型
unsigned short total_len;          //总长度
unsigned short ident;             //标识
unsigned short frag_and_flags;     //标志和片偏移
unsigned short ttl:8;                //生存时间
unsigned short proto:8;             //协议
unsigned short checksum;         //校验和
unsigned int     sourceIP;        //源端IP地址
unsigned int destIP;              //目的地址
};

//TCP header
struct tcphdr
{
unsigned short source;
unsigned short dest;
unsigned int seq;
unsigned int ack_seq;
#  if __BYTE_ORDER == __LITTLE_ENDIAN
unsigned short res1:4;
unsigned short doff:4;
unsigned short fin:1;
unsigned short syn:1;
unsigned short rst:1;
unsigned short psh:1;
unsigned short ack:1;
unsigned short urg:1;
unsigned short res2:2;
#  elif __BYTE_ORDER == __BIG_ENDIAN
unsigned short doff:4;
unsigned short res1:4;
unsigned short res2:2;
unsigned short urg:1;
unsigned short ack:1;
unsigned short psh:1;
unsigned short rst:1;
unsigned short syn:1;
unsigned short fin:1;
#  else
#   error "Adjust your <bits/endian.h> defines"
#  endif
unsigned short window;
unsigned short check;
unsigned short urg_ptr;
};   

//TCP 伪首部
//伪首部
struct psehdr{                        //伪首部
unsigned long saddr;              //源IP地址
unsigned long daddr;              //目的IP地址
unsigned char reserved;         
unsigned char proto;              //协议号
unsigned short len;               //TCP长度
};
int SendTCPRequest(SOCKET s, LPSOCKADDR_IN lpstToAddr,unsigned short sport,unsigned short dport)
{
int nRet;
long PACKLEN;
char buf[50] = {0};
PACKLEN = sizeof(struct iphdr) + sizeof(struct tcphdr);
//填充IP
struct iphdr ipH;
  // ipH.h_verlen=(4<<4|sizeof(struct iphdr)/sizeof(unsigned long));
ipH.h_ver = 4;//版本号
ipH.hl = 5;
   ipH.tos = 0;
   ipH.total_len = htons(PACKLEN);//整个数据报总长度
   ipH.frag_and_flags = 0x40;//不分段
   ipH.ident = 13;
   ipH.ttl = 255;
   ipH.proto = IPPROTO_TCP;
   ipH.sourceIP = inet_addr(ip1);//这里IP只是一个代号
   ipH.destIP = inet_addr(ip2);
   ipH.checksum    = 0;
   //填充TCP伪首部
   struct psehdr pseuhdr;
   pseuhdr.saddr = ipH.sourceIP;
   pseuhdr.daddr = ipH.destIP;
   pseuhdr.reserved = 0 ;
   pseuhdr.proto = ipH.proto;
   pseuhdr.len     = htons( sizeof(struct tcphdr) );
//填充TCP数据。
struct tcphdr tcpH;
tcpH.dest = dport;
tcpH.source = sport;//发送端口号可以随便
tcpH.seq = 0;
tcpH.ack_seq = 0;
tcpH.doff = 5;
tcpH.res1 = 0;
tcpH.res2 = 0;
tcpH.ack = TRUE;
tcpH.fin = false;
tcpH.psh = false;
tcpH.rst = false;
tcpH.urg = false;
tcpH.syn = false;
tcpH.window = 1024;
tcpH.check = 0;
tcpH.urg_ptr = 0;
//
//memcpy(buf,&ipH,sizeof(struct iphdr));
memcpy(buf,&pseuhdr,sizeof(struct psehdr));
memcpy(buf + sizeof(struct psehdr),&tcpH,sizeof(struct tcphdr));

tcpH.check = in_cksum((u_short *)buf,sizeof(buf));

memset(buf,'\0',sizeof(buf));
memcpy(buf,&ipH,sizeof(struct iphdr));
memcpy(buf + sizeof(struct iphdr),&tcpH,sizeof(struct tcphdr));




nRet = sendto(s,
buf,
sizeof(buf),
0,
(LPSOCKADDR)lpstToAddr,
sizeof(SOCKADDR_IN));

if (nRet == SOCKET_ERROR)
{
printf("%d\n",errno);
printf("sendto()");0
}
return nRet;
}
//校验和代码
unsigned short in_cksum(unsigned short * addr,int len)
{
register int sum = 0;
u_short answer = 0;
register u_short * w = addr;
register int nleft = len;
while (nleft > 1)
{
sum += *w++;
nleft -= 2;
}
if (nleft == 1)
{
*(u_char *)(&answer) = *(u_char *)w;
sum += answer;
}
sum = (sum >> 16) + (sum & 0xffff);
sum += (sum >> 16);
answer = ~sum;
return answer;
}

程序一直出错在sendto。errno=0。我反复看了,我TCP,IP构造错了吗?还是怎么了?希望能有大侠指点一二。 TCP报文 C语言编程
[解决办法]
建议你sendto之前把报文打出来,你的ip头里写的长度是PACKLEN。但是实际发送的时候又用的sizeof(buff[50]),报文这样就不正确了。你的PACKLEN只有ip,tcp头的长度,,没有数据的长度加上,不知道你真实是想发送多少数据,还是就是想构造一个tcp的syn报文,或者啥的。

热点排行