| /////////////////////////////////////////////////////////////////////////////// |
| // Copyright (c) 2000-2019 Ericsson Telecom AB // |
| // // |
| // All rights reserved. This program and the accompanying materials // |
| // are made available under the terms of the Eclipse Public License v2.0 // |
| // which accompanies this distribution, and is available at // |
| // https://www.eclipse.org/org/documents/epl-2.0/EPL-2.0.html // |
| /////////////////////////////////////////////////////////////////////////////// |
| #include "EPTF_Transport_PerfTest_Testcases.hh" |
| |
| /* |
| UDP CHECKSUM CALCULATION |
| (see also short Description of Internet Checksum) |
| |
| To calculate UDP checksum a "pseudo header" is added to the UDP header. This includes: |
| |
| IP Source Address 4 bytes |
| IP Destination Address 4 bytes |
| Protocol 2 bytes |
| UDP Length 2 bytes |
| |
| The checksum is calculated over all the octets of the pseudo header, UDP header and data. |
| If the data contains an odd number of octets a pad, zero octet is added to the end of data. |
| The pseudo header and the pad are not transmitted with the packet. |
| |
| In the example code, |
| u16 buff[] is an array containing all the octets in the UDP header and data. |
| u16 len_udp is the length (number of octets) of the UDP header and data. |
| BOOL padding is 1 if data has an even number of octets and 0 for an odd number. |
| u16 src_addr[4] and u16 dest_addr[4] are the IP source and destination address octets |
| */ |
| |
| /* |
| ************************************************************************** |
| Function: udp_sum_calc() |
| Description: Calculate UDP checksum |
| *************************************************************************** |
| */ |
| typedef unsigned short u16; |
| typedef unsigned long u32; |
| typedef unsigned char u8; |
| |
| u16 udp_sum_calc(u16 len_udp, u8 src_addr[],u8 dest_addr[], bool padding, u8 buff[]) |
| { |
| u16 prot_udp=17; |
| u16 padd=0; |
| u16 word16; |
| u32 sum; |
| u32 i; |
| |
| // Find out if the length of data is even or odd number. If odd, |
| // add a padding byte = 0 at the end of packet |
| if ((padding&1)==1){ |
| padd=1; |
| buff[len_udp]=0; |
| } |
| |
| //initialize sum to zero |
| sum=0; |
| |
| // make 16 bit words out of every two adjacent 8 bit words and |
| // calculate the sum of all 16 vit words |
| for (i=0;i<len_udp+padd;i=i+2){ |
| word16 =((buff[i]<<8)&0xFF00)+(buff[i+1]&0xFF); |
| sum = sum + (unsigned long)word16; |
| } |
| // add the UDP pseudo header which contains the IP source and destinationn addresses |
| for (i=0;i<4;i=i+2){ |
| word16 =((src_addr[i]<<8)&0xFF00)+(src_addr[i+1]&0xFF); |
| sum=sum+word16; |
| } |
| for (i=0;i<4;i=i+2){ |
| word16 =((dest_addr[i]<<8)&0xFF00)+(dest_addr[i+1]&0xFF); |
| sum=sum+word16; |
| } |
| // the protocol number and the length of the UDP packet |
| sum = sum + prot_udp + len_udp; |
| |
| // keep only the last 16 bits of the 32 bit calculated sum and add the carries |
| while (sum>>16) |
| sum = (sum & 0xFFFF)+(sum >> 16); |
| |
| // Take the one's complement of sum |
| sum = ~sum; |
| |
| return ((u16) sum); |
| } |
| |
| INTEGER EPTF__Transport__PerfTest__Testcases::f__calc__internetChecksum(const INTEGER& len_udp, const OCTETSTRING& src_addr, const OCTETSTRING& dest_addr, const OCTETSTRING& buff) { |
| return udp_sum_calc((u16)(int)len_udp, (u8*)(const unsigned char*)src_addr, (u8*)(const unsigned char*)dest_addr, buff.lengthof()%2, (u8*)(const unsigned char*)buff); |
| |
| } |
| |
| |
| |
| |
| |
| |
| |
| //-------------------------------------------------------------- |
| |
| |
| // |
| // The following "C" code algorithm computes the checksum with an inner |
| // loop that sums 16-bits at a time in a 32-bit accumulator. |
| // |
| // in 6 |
| // { |
| // /* Compute Internet Checksum for "count" bytes |
| // * beginning at location "addr". |
| // */ |
| // register long sum = 0; |
| // |
| // while( count > 1 ) { |
| // /* This is the inner loop */ |
| // sum += * (unsigned short) addr++; |
| // count -= 2; |
| // } |
| // |
| // /* Add left-over byte, if any */ |
| // if( count > 0 ) |
| // sum += * (unsigned char *) addr; |
| // |
| // /* Fold 32-bit sum to 16 bits */ |
| // while (sum>>16) |
| // sum = (sum & 0xffff) + (sum >> 16); |
| // |
| // checksum = ~sum; |
| // } |
| // |