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

📄 uip.c

📁 58enc28j06protuesuip09.rar
💻 C
📖 第 1 页 / 共 4 页
字号:
       reassembly buffer, we discard the entire packet. */    if(offset > UIP_REASS_BUFSIZE ||       offset + len > UIP_REASS_BUFSIZE) {      uip_reasstmr = 0;      goto nullreturn;    }    /* Copy the fragment into the reassembly buffer, at the right       offset. */    memcpy(&uip_reassbuf[IP_HLEN + offset],	   (char *)BUF + (int)((BUF->vhl & 0x0f) * 4),	   len);          /* Update the bitmap. */    if(offset / (8 * 8) == (offset + len) / (8 * 8)) {      /* If the two endpoints are in the same byte, we only update	 that byte. */	           uip_reassbitmap[offset / (8 * 8)] |=	     bitmap_bits[(offset / 8 ) & 7] &	     ~bitmap_bits[((offset + len) / 8 ) & 7];    } else {      /* If the two endpoints are in different bytes, we update the	 bytes in the endpoints and fill the stuff inbetween with	 0xff. */      uip_reassbitmap[offset / (8 * 8)] |=	bitmap_bits[(offset / 8 ) & 7];      for(i = 1 + offset / (8 * 8); i < (offset + len) / (8 * 8); ++i) {	uip_reassbitmap[i] = 0xff;      }            uip_reassbitmap[(offset + len) / (8 * 8)] |=	~bitmap_bits[((offset + len) / 8 ) & 7];    }        /* If this fragment has the More Fragments flag set to zero, we       know that this is the last fragment, so we can calculate the       size of the entire packet. We also set the       IP_REASS_FLAG_LASTFRAG flag to indicate that we have received       the final fragment. */    if((BUF->ipoffset[0] & IP_MF) == 0) {      uip_reassflags |= UIP_REASS_FLAG_LASTFRAG;      uip_reasslen = offset + len;    }        /* Finally, we check if we have a full packet in the buffer. We do       this by checking if we have the last fragment and if all bits       in the bitmap are set. */    if(uip_reassflags & UIP_REASS_FLAG_LASTFRAG) {      /* Check all bytes up to and including all but the last byte in	 the bitmap. */      for(i = 0; i < uip_reasslen / (8 * 8) - 1; ++i) {	if(uip_reassbitmap[i] != 0xff) {	  goto nullreturn;	}      }      /* Check the last byte in the bitmap. It should contain just the	 right amount of bits. */      if(uip_reassbitmap[uip_reasslen / (8 * 8)] !=	 (u8_t)~bitmap_bits[uip_reasslen / 8 & 7]) {	goto nullreturn;      }      /* If we have come this far, we have a full packet in the	 buffer, so we allocate a pbuf and copy the packet into it. We	 also reset the timer. */      uip_reasstmr = 0;      memcpy(BUF, FBUF, uip_reasslen);      /* Pretend to be a "normal" (i.e., not fragmented) IP packet	 from now on. */      BUF->ipoffset[0] = BUF->ipoffset[1] = 0;      BUF->len[0] = uip_reasslen >> 8;      BUF->len[1] = uip_reasslen & 0xff;      BUF->ipchksum = 0;      BUF->ipchksum = ~(uip_ipchksum());      return uip_reasslen;    }  } nullreturn:  return 0;}#endif /* UIP_REASSEMBL *//*-----------------------------------------------------------------------------------*/static voiduip_add_rcv_nxt(u16_t n){  uip_add32(uip_conn->rcv_nxt, n);  uip_conn->rcv_nxt[0] = uip_acc32[0];  uip_conn->rcv_nxt[1] = uip_acc32[1];  uip_conn->rcv_nxt[2] = uip_acc32[2];  uip_conn->rcv_nxt[3] = uip_acc32[3];}/*-----------------------------------------------------------------------------------*/voiduip_process(u8_t flag){
  u8_t gjk_iptemp;  register struct uip_conn *uip_connr = uip_conn;    uip_appdata = &uip_buf[40 + UIP_LLH_LEN];    /* Check if we were invoked because of the perodic timer fireing. */  if(flag == UIP_TIMER) {#if UIP_REASSEMBLY    if(uip_reasstmr != 0) {      --uip_reasstmr;    }#endif /* UIP_REASSEMBLY */    /* Increase the initial sequence number. */    if(++iss[3] == 0) {      if(++iss[2] == 0) {	if(++iss[1] == 0) {	  ++iss[0];	}      }    }        uip_len = 0;    if(uip_connr->tcpstateflags == TIME_WAIT ||       uip_connr->tcpstateflags == FIN_WAIT_2) {      ++(uip_connr->timer);      if(uip_connr->timer == UIP_TIME_WAIT_TIMEOUT) {	uip_connr->tcpstateflags = CLOSED;      }    } else if(uip_connr->tcpstateflags != CLOSED) {      /* If the connection has outstanding data, we increase the	 connection's timer and see if it has reached the RTO value	 in which case we retransmit. */      if(uip_outstanding(uip_connr)) {	if(uip_connr->timer-- == 0) {	  if(uip_connr->nrtx == UIP_MAXRTX ||	     ((uip_connr->tcpstateflags == SYN_SENT ||	       uip_connr->tcpstateflags == SYN_RCVD) &&	      uip_connr->nrtx == UIP_MAXSYNRTX)) {	    uip_connr->tcpstateflags = CLOSED;	    /* We call UIP_APPCALL() with uip_flags set to	       UIP_TIMEDOUT to inform the application that the	       connection has timed out. */	    uip_flags = UIP_TIMEDOUT;	    UIP_APPCALL();	    /* We also send a reset packet to the remote host. */	    BUF->flags = TCP_RST | TCP_ACK;	    goto tcp_send_nodata;	  }	  /* Exponential backoff. */	  uip_connr->timer = UIP_RTO << (uip_connr->nrtx > 4?					 4:					 uip_connr->nrtx);	  ++(uip_connr->nrtx);	  	  /* Ok, so we need to retransmit. We do this differently	     depending on which state we are in. In ESTABLISHED, we	     call upon the application so that it may prepare the	     data for the retransmit. In SYN_RCVD, we resend the	     SYNACK that we sent earlier and in LAST_ACK we have to	     retransmit our FINACK. */	  UIP_STAT(++uip_stat.tcp.rexmit);	  switch(uip_connr->tcpstateflags & TS_MASK) {	  case SYN_RCVD:	    /* In the SYN_RCVD state, we should retransmit our               SYNACK. */	    goto tcp_send_synack;	    #if UIP_ACTIVE_OPEN	  case SYN_SENT:	    /* In the SYN_SENT state, we retransmit out SYN. */	    BUF->flags = 0;	    goto tcp_send_syn;#endif /* UIP_ACTIVE_OPEN */	    	  case ESTABLISHED:	    /* In the ESTABLISHED state, we call upon the application               to do the actual retransmit after which we jump into               the code for sending out the packet (the apprexmit               label). */	    uip_len = 0;	    uip_slen = 0;	    uip_flags = UIP_REXMIT;	    UIP_APPCALL();	    goto apprexmit;	    	  case FIN_WAIT_1:	  case CLOSING:	  case LAST_ACK:	    /* In all these states we should retransmit a FINACK. */	    goto tcp_send_finack;	    	  }	}      } else if((uip_connr->tcpstateflags & TS_MASK) == ESTABLISHED) {	/* If there was no need for a retransmission, we poll the           application for new data. */	uip_len = 0;	uip_slen = 0;	uip_flags = UIP_POLL;	UIP_APPCALL();	goto appsend;      }    }    goto drop;  }#if UIP_UDP   if(flag == UIP_UDP_TIMER) {    if(uip_udp_conn->lport != 0) {      uip_appdata = &uip_buf[UIP_LLH_LEN + 28];      uip_len = uip_slen = 0;      uip_flags = UIP_POLL;      UIP_UDP_APPCALL();      goto udp_send;    } else {      goto drop;    }  }#endif  /* This is where the input processing starts. */  UIP_STAT(++uip_stat.ip.recv);  /* Start of IPv4 input header processing code. */    /* Check validity of the IP header. */    if(BUF->vhl != 0x45)  { /* IP version and header length. */    UIP_STAT(++uip_stat.ip.drop);    UIP_STAT(++uip_stat.ip.vhlerr);    Printf_String("\r\n[MSG:] ip: invalid version or header length.");    goto drop;  }    /* Check the size of the packet. If the size reported to us in     uip_len doesn't match the size reported in the IP header, there     has been a transmission error and we drop the packet. */    if(BUF->len[0] != (uip_len >> 8)) { /* IP length, high byte. */    uip_len = (uip_len & 0xff) | (BUF->len[0] << 8);  }  if(BUF->len[1] != (uip_len & 0xff)) { /* IP length, low byte. */    uip_len = (uip_len & 0xff00) | BUF->len[1];  }  /* Check the fragment flag. */  if((BUF->ipoffset[0] & 0x3f) != 0 ||     BUF->ipoffset[1] != 0) { #if UIP_REASSEMBLY    uip_len = uip_reass();    if(uip_len == 0) {      goto drop;    }#else    UIP_STAT(++uip_stat.ip.drop);    UIP_STAT(++uip_stat.ip.fragerr);    Printf_String("\r\n[MSG:] ip: fragment dropped.");        goto drop;#endif /* UIP_REASSEMBLY */  }  /* If we are configured to use ping IP address configuration and     hasn't been assigned an IP address yet, we accept all ICMP     packets. */#if UIP_PINGADDRCONF  if((uip_hostaddr[0] | uip_hostaddr[1]) == 0) {    if(BUF->proto == UIP_PROTO_ICMP) {      Printf_String("\r\n[MSG:] ip: possible ping config packet received.");      goto icmp_input;    } else {      Printf_String("\r\n[MSG:] ip: packet dropped since no address assigned.");      goto drop;    }  }#endif /* UIP_PINGADDRCONF */    /* Check if the packet is destined for our IP address. */    if(BUF->destipaddr[0] != uip_hostaddr[0]) {    UIP_STAT(++uip_stat.ip.drop);   // Printf_String("\r\n ->ip: packet not for us.");            goto drop;  }  if(BUF->destipaddr[1] != uip_hostaddr[1]) {    UIP_STAT(++uip_stat.ip.drop);   // Printf_String("\r\n ->ip: packet not for us.");            goto drop;  }  if(uip_ipchksum() != 0xffff) { /* Compute and check the IP header				    checksum. */    UIP_STAT(++uip_stat.ip.drop);    UIP_STAT(++uip_stat.ip.chkerr);    Printf_String("\r\n[MSG:] ip: bad checksum.");        goto drop;  }  if(BUF->proto == UIP_PROTO_TCP)  /* Check for TCP packet. If so, jump                                     to the tcp_input label. */    goto tcp_input;#if UIP_UDP  if(BUF->proto == UIP_PROTO_UDP)    goto udp_input;#endif /* UIP_UDP */  if(BUF->proto != UIP_PROTO_ICMP) { /* We only allow ICMP packets from					here. */    UIP_STAT(++uip_stat.ip.drop);    UIP_STAT(++uip_stat.ip.protoerr);    Printf_String("\r\n[MSG:] ip: neither tcp nor icmp.");            goto drop;  }   icmp_input:  UIP_STAT(++uip_stat.icmp.recv);    /* ICMP echo (i.e., ping) processing. This is simple, we only change     the ICMP type from ECHO to ECHO_REPLY and adjust the ICMP     checksum before we return the packet. */  if(ICMPBUF->type != ICMP_ECHO) {    UIP_STAT(++uip_stat.icmp.drop);    UIP_STAT(++uip_stat.icmp.typeerr);    Printf_String("\r\n[MSG:] icmp: not icmp echo.");    goto drop;  }  /* If we are configured to use ping IP address assignment, we use     the destination IP address of this ping packet and assign it to     ourself. */#if UIP_PINGADDRCONF  if((uip_hostaddr[0] | uip_hostaddr[1]) == 0) {    uip_hostaddr[0] = BUF->destipaddr[0];    uip_hostaddr[1] = BUF->destipaddr[1];  }#endif /* UIP_PINGADDRCONF */      ICMPBUF->type = ICMP_ECHO_REPLY;    if(ICMPBUF->icmpchksum >= HTONS(0xffff - (ICMP_ECHO << 8))) {    ICMPBUF->icmpchksum += HTONS(ICMP_ECHO << 8) + 1;  } else {    ICMPBUF->icmpchksum += HTONS(ICMP_ECHO << 8);  }    /* Swap IP addresses. */  tmp16 = BUF->destipaddr[0];  BUF->destipaddr[0] = BUF->srcipaddr[0];  BUF->srcipaddr[0] = tmp16;  tmp16 = BUF->destipaddr[1];  BUF->destipaddr[1] = BUF->srcipaddr[1];  BUF->srcipaddr[1] = tmp16;  UIP_STAT(++uip_stat.icmp.sent);


   /*@test by jerkoh  ping debug@*/
   gjk_iptemp=BUF->srcipaddr[0]>>8;

   Printf_String("\r\n[MSG:] Reply from ");

   Printf_Str(gjk_iptemp);
   Printf_String(".");
   Printf_Str(BUF->srcipaddr[0]);
   Printf_String(".");
   gjk_iptemp=BUF->srcipaddr[1]>>8;

   Printf_Str(gjk_iptemp);
   Printf_String(".");
   Printf_Str(BUF->srcipaddr[1]);

   Printf_String(": byte=32 time<37ms TTL=64 ");

   /*@test by jerkoh  ping debug@*/


  goto send;  /* End of IPv4 input header processing code. */  #if UIP_UDP

⌨️ 快捷键说明

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