⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tcp.c.bak

📁 一种操作系统源码核
💻 BAK
📖 第 1 页 / 共 2 页
字号:
#include "p_tcpip.h"
static struct tcb *TcbTable[MAX_TCB_NUM];
static struct tcb * pCurrentTcb;  //TCB STATE //48  当前的TCB 控制块
//static	DCHAR	Tcp_RcvHeadLen;
static  INT8U	TcpRcvHLen;
static INT8U  Tcp_Packet_Buffer[EP_MIN_LEN];   //POINTER  TCP PACKET START MAC HEADER //58  无数据TCP包缓冲区
static INT8U * pTcp_RcvSeq;
static INT8U * pTcp_RcvAck;

static INT8U * pTcb_RcvNext;  //4a
static INT8U * pTcb_SndNext;  //4c
static INT8U * pTcb_SndUnAck; //4e
static INT8U * pTcb_PeerIP;    //50
static ULONG   pTcp_cksum;  //52

static INT8U * pIp_PeerIp;
static INT8U * pTcp_EpData;
static INT8U * pTcp_SndSeq;
static INT8U * pTcp_SndAck;

static INT8U *   pTcpSndPacket;// 0x630f //pCurrentTcb-739   point TCP SEND PACKET begin mac header
static BOOLEAN  bDataAcked;
 BOOLEAN    Tcp_bDataEvent;
 BOOLEAN    Tcp_bCloseEvent ;
BOOLEAN    Tcp_bAcceptEvent;
BOOLEAN    Tcp_bConnectEvent;
 //BOOLEAN     Tcp_bFreeEvent;
static BOOLEAN     bReceiveRstFlag;
static BOOLEAN     bReceiveAckFlag;
static BOOLEAN     bReceiveSynFlag;
static BOOLEAN     bReceiveFinFlag;
 
INT8U SeqCmp(INT8U * pData1,INT8U * pData2);
void  TcbListen();
BOOLEAN CheckRstFlag();
void TcbAckit();
INT8U TcbAcked();
void TcbData();
void  TcbFin1();
void TcbFin2();
void TcbSynSent();
void 	TcbSynRcvd();
void TcbEstablished();
void TcbCloseWait();
void  TcbLastAck();
void TcbClosing();
void TcbSendPacket(;
void  TcbSetCurrent(struct tcb *ptcb);
void TcpInitialize()
{
   DLONG iSum;
   struct tcp_packet *ptcp;
   struct tcp *pin_tcp;
   pTcpSndData=&(pTcpSndPacket->tcp_data);
   ptcp=(struct tcp_packet *)Tcp_Packet_Buffer;
   
   pin_tcp=(sruct tcp *)Adapter_pRcvPacket;

   iSum=IpPrepareData(IPT_TCP,Tcp_Packet_Buffer);//from mac header begin
   pTcp_IpCheckSum=iSum;
   ptcp->tcp_window[0]=0;//tcp_window
   ptcp->tcp_urgptr[0]=0;  //tcp_urgptr
   ptcp->tcp_urgptr[1]=0; //tcp_option
   pTcp_EpData=&(ptcp->tcp_verlen);
   pIp_PeerIp=&(ptcp->ip_dst);
   pTcp_SndSeq=&(ptcp->tcp_seq);
   pTcp_SndAck=&(ptcp->tcp_ack);
   pTcp_RcvSeq=&(pin_tcp->seq);
   pTcp_RcvAck=&(pin_tcp->ack);
   Tcp_bDataEvent=0;
   Tcp_bCloseEvent =0;
   Tcp_bAcceptEvent=0;
   Tcp_bConnectEvent=0;
}
void TcpPrepareData()
{
  struct tcp_packet *ptcp;

   ptcp=(sruct tcp_packet *)pTcpSndPacket;
  
   p_memcpy_x2x(ptcp->ep_dst,pPeerMacAddress,EP_ALEN);//copy dst mac address
   IpPrepareData(IPT_TCP,pTcpSndPacket); //prepare ip packet
   p_memcpy_x2x(ptcp->ip_dst,pPeerIPAddress,IP_ALEN); //copy dst ip address
   p_memcpy_x2x(pTcb_PeerIP,pPeerIPAddress,IP_ALEN);

   ptcp->tcp_urgptr[0]=0; //tcp udp point
   ptcp->tcp_urgptr[1]=0;
   ptcp->local_port[0]= pCurrentTcb->local_port[0];
   ptcp->local_port[1]= pCurrentTcb->local_port[1];//tcp local port
   ptcp->peer_port[0]= pCurrentTcb->peer_port[0];
   ptcp->peer_port[1]= pCurrentTcb->peer_port[1];//tcp local port
   ptcp->tcp_window[0]=0;  //tcp window
   ptcp->tcp_window_low=TCPMAXPACKETLEN; //window size=197
}
BOOLEAN TcbAlloc(INT8U * ptcb)  //init syn packet and state
{
static INT8 Next_ID;
for (i=0 ; i<MAX_TCB_NUM ; i++) {	/* check all NPROC slots	*/
		if ( (Next_ID++) == MAX_TCB_NUM)
			Next_ID = 0;
		if (TcbTable[Next_ID] == NULL)
			break;
	}
  if(i<MAX_TCB_NUM){
   ptcb->id=Next_ID;		
   TcbTable[Next_ID]=ptcb;
   return TRUE;
  }
  else 
    return FALSE; 	

}

void TcbDeAlloc()
{
pCurrentTcb->state=TCPS_FREE; //receive status=0 closed
pCurrentTcb->acked=TRUE; //tcps_free  =1 ff=use
TcbTable[pCurrentTcb->id]=NULL;
Tcp_bCloseEvent=TRUE;
}

//check receive packet if is  Local port

/*------------------------------------------------------------------------
 *  _TcpDemux -  do TCP port demultiplexing
 *------------------------------------------------------------------------
 */
INT8 _TcpDemux()
{
	struct	tcp	*ptcp = (struct tcp *)Adapter_pRcvPacket;
	struct	tcb	*ptcb;
	int		tcbn;
	for (tcbn=0,; tcbn<MAX_TCB_NUM; ++tcbn) {
		if (TcbTable[tcbn]== NULL)
			continue;
		  if(ptcp->remote_port[0] == TcbTable[tcbn]->local_port[0] && ptcp->remote_port[1] == TcbTable[tcbn]->local_port[1]){
		  	break;
		   }
		 	
	}
	if (tcbn >= MAX_TCB_NUM)
	       return 0;
	if (TcbTable[tcbn]->state == TCPS_CLOSED)	
	      TcbSetCurrent(TcbTable[tcbn]);
	return TRUE;
}
void TcpInput()
{
if (!_TcpDemux())//0x6352  _pTcbData enscap Tcb connect info
   TcpReset();
TcbRun();	

	
}
void TcpOpen(INT8U * ptcb,INT8U  ServerPortHi, INT8U  ServerPortLo,INT8U type)
{
  struct tcb *tcb_ptr=(struct tcb *)ptcb;
  
  if(!TcbAlloc(ptcb))
       return ;  //aclloc tcb
  
  if(type==TCP_CLIENT){
     TcbSetCurrent(ptcb); //init  ptcb pCurrentTcb=pData
     p_memset_x(pTcb_RcvNext,0,4);
     pCurrentTcb->state=TCPS_SYNSENT;//   client state  initiative connect entry syn sent state
     pCurrentTcb->flag=TCBF_NEED_OUT; //server state transmit
     pCurrentTcb->local_port[0]=ServerPortHi;
     pCurrentTcb->local_port[1]=ServerPortLo;
     pCurrentTcb->code=TCPF_SYN; //flag=syn
     RandSting(pTcb_SndNext,4);
     p_memcpy_x2x(pTcb_SndUnAck,pTcb_SndNext,4);
     TcpPrepareData();//prepare tcp packet
     TcpSend(0); //send syn packet
   }
 else{
    tcb_ptr->local_port[0]=ServerPortHi;
    tcb_ptr->local_port[1]=ServerPortLo;
    tcb_ptr->state=TCPS_CLOSED;  //close
    tcb_ptr->flag=TCPS_FREE; //server state free
    tcb_ptr->acked=TRUE; //tcps_free  =1 ff=use
    tcb_ptr->snd_bytes=0;  //send size
   }

}
void TcpClose(INT8U * ptcb)
{
bdata INT8U  flag;
  TcbSetCurrent(ptcb);
  flag=pCurrentTcb->flag;
  if (flag&0x10)
    return;

    if ((pCurrentTcb->state!= TCPS_ESTABLISHED)&&(pCurrentTcb->state!=TCPS_CLOSEWAIT))  //not established and close wait state
       return;
     if (pCurrentTcb->state == TCPS_ESTABLISHED)
	pCurrentTcb->state = TCPS_FINWAIT1;
    else	/* CLOSE_WAIT */
	pCurrentTcb->state = TCPS_LASTACK;
     pCurrentTcb->flag |= TCBF_NEED_OUT;
     TcpSend(0);

 }
//读写应与TCP处理属于不同的进程
INT8U TcpWrite(INT8U *pch, INT8U len)
{
    INT8U i;	
    
  
    if (pCurrentTcb->state==TCPS_ESTABLISHED)
    {	
      for(i=0;i<len;i++) 
	 pTcpSndData[i] = *pch++;
     	 	
     bDataAcked=TcpSend(len);		
    return len;
      
    }
    else 
      return 0;			
		
}

INT16 TcpRead(INT8U *pch, INT16U len)
{
     INT8U pData;
     pData=Adapter_pRcvTcpData;//point receive tcp packet
    while (Tcp_bDataEvent){//等待数据到达
    	  for(i=0;i<Adapter_RcvLen && i < len;i++) 
	    *pch++ = pData[i];	
	Tcp_bDataEvent= = FALSE;   //表示当前TCB到达的数据已读过 	
	TcpSend(0);//发送应答
	
    }	
    return i;
}

BOOLEAN TcpSend(INT8U  len)
{
 DCHAR datalen,acked;
 ULONG ip_cksum;
 DSHORT cksum;
 bdata INT8U  flag;
 struct tcp_packet *ptcp;
 ptcp=(sruct tcp_packet *)pTcpSndPacket;

   if (len==0)  //len is tcp data size
   {
     acked=pCurrentTcb->flags;
     if(!(acked &TCBF_NEEDOUT))  // in transmit
     {
     	  acked=pCurrentTcb->acked;
	    return(acked+0xff);

     }
   }

   p_memcpy_x2x(ptcp->seq,pTcb_SndNext,4); //seq
   p_memcpy_x2x(ptcp->ack,pTcb_RcvNext,4);//ack seq
    acked=pCurrentTcb->flags;
   if(acked & TCBF_SNDFIN) // tcb_flags
      pCurrentTcb->tcb_code |=TCPF_FIN;//fin=1
    ptcp->tcp_code=pCurrentTcb->code; //flag
    flag=tcp->ptcp->tcp_code;
   if (flag & TCPF_SYN)  //syn=1
   {
          olen = 2 + sizeof(INT16);
	 ptcp->tcp_data[0]=0x02;
         ptcp->tcp_data[1]=olen;
    	 ptcp->tcp_data[2]=0x02;
	 ptcp->tcp_data[3]=0x18;//option max seg size=536
	  ptcp->tcp_offset = 0x60;
	}
	else
	    ptcp->tcp_offset =TCP_MIN_OFFSET;  //lword=5

    if (len)
       ptcp->tcp_code |=TCPF_PSH; //set psh=1
    datalen=len;
    flag=ptcp->tcp_code;
    if(flag& TCPF_SYN) //syn=1
       datalen++;

    if(flag & TCPF_FIN) //fin=1
       datalen++;
	 if  (datalen)
	 {
	 pCurrentTcb->snd_next +=datalen;
         pCurrentTcb->acked=0;
	  pCurrentTcb->retry=3;
          pCurrentTcb->rexmt=0;
	 }
     datalen=TCP_HLEN(ptcp);//tcp header oct length  20 or 24 octs
     if (len)
        datalen+=len; //tcp header+tcp data

     ptcp->ip_len=datalen+IPMHLEN;//ip_len pTcpSndPacket begin Mac header
     ip_cksum=pTcp_IpCheckSum;
     ip_cksum=IpModifycksum(pTcb_PeerIP,ip_cksum);
     IpCheckSum(&(pTcpSndPacket->ip_verlen),ip_cksum); //ip cksum
     ptcp->tcp_cksum=0;
     ptcp->tcp_cksum_low=0;
     cksum=TcpCheckSum(pTcpSndPacket,datalen);
     ptcp->tcp_cksum=P_HIBYTE(cksum);
     ptcp->tcp_cksum_low=P_LOBYTE(cksum);
     datalen+=IPMHLEN+EP_HLEN; //add ip header +mac header
     Ne2000Send(pTcpSndPacket,datalen);
     pCurrentTcb->snd_bytes=datalen;//sbcount
     pCurrentTcb->flags &=~TCBF_NEEDOUT;  // sended
      acked=pCurrentTcb->acked;
      return(acked+0xff);


 }


void TcpReset()
{
 DCHAR datalen;
 struct tcp_packet *ptcpout;
 struct tcp_packet *ptcpin;
 ptcpout=(sruct tcp_packet *)Tcp_Packet_Buffer;
 ptcpin=(sruct tcp *)Adapter_pRcvPacket;
  if(bReceiveRstFlag)
     return;
   ptcpout->local_port[0] = ptcpin->peer_port[0];
     ptcpout->local_port[1] = ptcpin->peer_port[1];
   ptcpout->peer_port[0] = ptcpin->local_port[0];
   ptcpout->peer_port[1] = ptcpin->local_port[1];


  if(bReceiveAckFlag)
  {
     p_memcpy_x2x(pTcp_SndSeq,pTcp_RcvAck,4);
	 ptcpout->tcp_code = TCPF_RST;
  }
  else
  {
     p_memset_x(pTcp_SndSeq,0,4);//pTcp_Seq=0
     ptcpout->tcp_code = TCPF_RST|TCPF_ACK;
  }
  datalen=iReceiveLen;
  if (bReceiveSynFlag)
     datalen++;
  if (bReceiveFinFlag)
     datalen++;
  p_memcpy_x2x(pTcp_SndAck,pTcp_RcvSeq,4);//ack seq=receive seq
  SeqAdd(pTcp_SndAck,datalen);
   ptcpout->tcp_offset = TCP_MIN_OFFSET; //data offset lword=5
    ptcpout->tcp_window = 0;  //window size =0
   TcbSendPacket(); //send rst packet
}







BOOLEAN TcbHandleTimer(INT8U * ptcb)
{
 DCHAR i;
 DCHAR iPeerPortHigh,iPeerPortLow;
 INT8U * iPeerIp;
 TcbSetCurrent(ptcb);
 i=pCurrentTcb->retry);//rexmitcount
 i--;
 if(!i)
 {
       i=3;
        if(pCurrentTcb->rexmt<5)
        {
          iPeerIp=TcbGetPeerIP(pCurrentTcb);
          iPeerPortHigh=TcbGetPeerPortHi(pCurrentTcb);
          iPeerPortLow=TcbGetPeerPortLo(pCurrentTcb);
       //   DebugString1(iPeerIp,iPeerPortHigh,0x1022);
          pCurrentTcb->rexmt+=+1;
	   	  Ne2000WaitPacket();
		  Ne2000Send(pCurrentTcb->snd_bytes,pTcpSndPacket);
		}
		else
		  return FALSE;
  }

    pCurrentTcb->retry=i;
     return TRUE;
}
 

void  TcbRun()// tcb input module
{
     DCHAR TcpRcvHLen;
     DCHAR state;
    struct tcp *ptcp;
    ptcp  =(struct tcp *)Adapter_pRcvPacket;
    TcpRcvHLen=(ptcp->offset & 0xf0)>>2;//get tcp header size
    Adapter_pRcvTcpData=Adapter_pRcvPacket+TcpRcvHLen;//tcp data
    if(Adapter_iRcvLen<TcpRcvHLen) //receive data size<tcp header size
	    TcpReset();
     Adapter_iRcvLen-=TcpRcvHLen;
    if(ptcp->code & TCPF_ACK) //ack=1
	    bReceiveAckFlag=1;
	else
	    bReceiveAckFlag=0;
    if(ptcp->code & TCPF_RST) //rst=1
	     bReceiveRstFlag=1;
    else
	    bReceiveRstFlag=0;
    if(ptcp->code & TCPF_SYN) //syn=1
	     bReceiveSynFlag=1;
    else

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -