/****************************************************************************** * * Name: checksum.c * * Description: Software checksum function * * Copyright: (c) 2005-2050 IC Plus Corp. * All rights reserved. By Chance * *******************************************************************************/ #include "checksum.h" /*-----------------------------------------------------------------------------------*/ /****************************************************************************** * * Function: uip_chksum * * Description: checksum function for protocol * * Parameters: sdata : the start address of data which user want to caculate the checksum * len : The length of the data * * Returns: checksum value * *******************************************************************************/ u16_t uip_chksum(u16_t *sdata, u16_t len) { u16_t acc; for(acc = 0; len > 1; len -= 2) { acc += *sdata; if(acc < *sdata) { /* Overflow, so we add the carry to acc (i.e., increase by one). */ ++acc; } ++sdata; } /* add up any odd byte */ if(len == 1) { acc += htons(((u16_t)(*(u8_t *)sdata)) << 8); if(acc < htons(((u16_t)(*(u8_t *)sdata)) << 8)) { ++acc; } } return acc; } /****************************************************************************** * * Function: uip_ipchksum * * Description: checksum function for IP protocol * * Parameters: None * * Returns: checksum value * *******************************************************************************/ /*-----------------------------------------------------------------------------------*/ u16_t uip_ipchksum(void) { return uip_chksum((u16_t *)&uip_fw_buf[UIP_LLH_LEN], 20); } /*-----------------------------------------------------------------------------------*/ #define UIP_PROTO_UDP 17 /****************************************************************************** * * Function: uip_udpchksum * * Description: checksum function for UDP protocol * * Parameters: None * * Returns: checksum value * *******************************************************************************/ u16_t uip_udpchksum(void) { u16_t hsum, sum; /* Compute the checksum of the UDP header. */ hsum = uip_chksum((u16_t *)&uip_fw_buf[20 + UIP_LLH_LEN], 8); /* Compute the checksum of the data in the TCP packet and add it to the TCP header checksum. */ sum = uip_chksum((u16_t *)(&uip_fw_buf[UIP_LLH_LEN+28]),//uip_appdata, //JC:change form uip_appdata to (&uip_buf[UIP_LLH_LEN+40]) (u16_t)(((((u16_t)(Checksum_BUF->len[0]) << 8) + Checksum_BUF->len[1]) - 28))); if((sum += hsum) < hsum) { ++sum; } if((sum += Checksum_BUF->srcipaddr[0]) < Checksum_BUF->srcipaddr[0]) { ++sum; } if((sum += Checksum_BUF->srcipaddr[1]) < Checksum_BUF->srcipaddr[1]) { ++sum; } if((sum += Checksum_BUF->destipaddr[0]) < Checksum_BUF->destipaddr[0]) { ++sum; } if((sum += Checksum_BUF->destipaddr[1]) < Checksum_BUF->destipaddr[1]) { ++sum; } if((sum += (u16_t)htons((u16_t)UIP_PROTO_UDP)) < (u16_t)htons((u16_t)UIP_PROTO_UDP)) { ++sum; } hsum = (u16_t)htons((((u16_t)(Checksum_BUF->len[0]) << 8) + Checksum_BUF->len[1]) - 20); if((sum += hsum) < hsum) { ++sum; } return sum; }