📄 tcp.bak
字号:
void tcp_handler(in_Header xdata *ip)
{
eth_Header xdata *peth;
tcp_Header xdata *tp;
tcp_PseudoHeader xdata *ph;
int xdata len;
int xdata diff;
uint flags;
long xdata diffticks;
long xdata ldiff; /* 注意必须有符号 */
if ( ip->destination !=local_ip)
return;
len =((ip.hd_ver)&0x0f)*4;
tp = (tcp_Header xdata *)((uchar xdata *)ip + len); /* TCP帧指针 */
ph=ETH_RECV_ADDR-sizeof(tcp_PseudoHeader);
len = ip->length - len; /* TCP数据长度 */
flags =tp->flags;
if ( s->hisaddr != 0 && tp->dstPort != s->myport )return;
if ( s->hisaddr != 0 && tp->srcPort != s->hisport)return;
if ( s->hisaddr != 0 && ip->source != s->hisaddr)return;
if( s->hisaddr==0 && tp->dstPort != s->myport && tp->dstPort != HTTPPORT)return;
ph.src = ip->source; /* 已经本地字节序(Intel) */
ph.dst = ip->destination;
ph.mbz = 0;
ph.protocol = TCP_PROTO;
ph.length = len ;
ph.checksum = checksum((uchar xdata *)tp, len);
if ( checksum((uchar xdata *)ph, sizeof(tcp_PseudoHeader)) != 0xffff )
{
return;
}
/* RESET code */
if ( flags & tcp_FlagRST )
{
s->rdatalen=0;
s->state = tcp_StateCLOSED;
s->safetysig=FALSE;
return;
}
curr_conf.type =TCP_PROTO;
curr_conf.dst_ip=ip.source;
curr_conf.timer =ARP_KEEP_TIME;
switch ( s->state )
{
case tcp_StateLISTEN: /* 接收SYN */
peth=((eth_Header xdata *)ip)-1;
curr_conf.dst_mac=peth.source;
if ( flags & tcp_FlagSYN )
{
s->acknum = tp->seqnum + 1;
s->myport = tp->dstPort;
s->hisport= tp->srcPort;
s->hisaddr = ip->source ;
s->flags = tcp_FlagSYN | tcp_FlagACK;
s->state = tcp_StateSYNREC;
s->unhappy = TRUE;
tcp_send(); /* 立即相应 */
s->timeout = set_timeout( tcp_TIMEOUT );
}
else
tcp_rst( ip , tp ); /* 是个错误RESET之 */
return;
case tcp_StateSYNSENT:
if ( flags & tcp_FlagSYN )
{
s->flags = tcp_FlagACK;
s->timeout = set_timeout( tcp_TIMEOUT );
/* FlagACK 意味着连接已经建立, 否则就是 SYNREC */
if ( flags & tcp_FlagACK)
{
/* 判断是不是当前对话的 */
if (tp->acknum == s->seqnum + 1)
{
s->state = tcp_StateESTAB;
s->seqnum++;
s->acknum = tp->seqnum + 1;
tcp_ProcessData( tp, len, ph);
s->unhappy = TRUE;
tcp_send( );
}
else
{
/* 错误的SEQNUM,RESET之,重发SYN */
s->flags = tcp_FlagRST;
s->unhappy = TRUE;
tcp_send( );
s->flags = tcp_FlagSYN;
tcp_send( );
}
}
else
{
s->acknum++;
s->state = tcp_StateSYNREC;
return;
}
}
else
tcp_rst( ip, tp );
break;
case tcp_StateSYNREC: /* recSYNSENT, sentACK, waiting EST */
if ( flags & tcp_FlagSYN )
{
s->flags = tcp_FlagSYN | tcp_FlagACK;
s->unhappy = TRUE;
tcp_send();
s->timeout = set_timeout( tcp_TIMEOUT );
return;
}
if ( (flags & tcp_FlagACK) && ( tp->acknum == s->seqnum + 1))
{
s->flags = tcp_FlagACK;
s->state = tcp_StateESTAB;
s->seqnum++;
s->timeout = set_timeout(0); /* never timeout 在我这里按说是不可能的 ,得要加上窗口探测
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -