summaryrefslogtreecommitdiffstats
path: root/src/tests
diff options
context:
space:
mode:
Diffstat (limited to 'src/tests')
-rw-r--r--src/tests/tcpip_test.c19
1 files changed, 18 insertions, 1 deletions
diff --git a/src/tests/tcpip_test.c b/src/tests/tcpip_test.c
index 759f886b..fac0ec26 100644
--- a/src/tests/tcpip_test.c
+++ b/src/tests/tcpip_test.c
@@ -94,6 +94,12 @@ TCPIP_TEST ( one_byte, DATA ( 0xeb ) );
/** Double byte */
TCPIP_TEST ( two_bytes, DATA ( 0xba, 0xbe ) );
+/** Positive zero data */
+TCPIP_TEST ( positive_zero, DATA ( 0x00, 0x00 ) );
+
+/** Negative zero data */
+TCPIP_TEST ( negative_zero, DATA ( 0xff, 0xff ) );
+
/** Final wrap-around carry (big-endian) */
TCPIP_TEST ( final_carry_big,
DATA ( 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 ) );
@@ -126,9 +132,17 @@ TCPIP_RANDOM_TEST ( partial, 0xcafebabe, 121, 5 );
*
* This is a reference implementation taken from RFC1071 (and modified
* to fix compilation without warnings under gcc).
+ *
+ * The initial value of the one's complement @c sum is changed from
+ * positive zero (0x0000) to negative zero (0xffff). This ensures
+ * that the return value will always use the positive representation
+ * of zero (0x0000). Without this change, the return value would use
+ * negative zero (0xffff) if the input data is zero length (or all
+ * zeros) but positive zero (0x0000) for any other data which sums to
+ * zero.
*/
static uint16_t rfc_tcpip_chksum ( const void *data, size_t len ) {
- unsigned long sum = 0;
+ unsigned long sum = 0xffff;
while ( len > 1 ) {
sum += *( ( uint16_t * ) data );
@@ -142,6 +156,7 @@ static uint16_t rfc_tcpip_chksum ( const void *data, size_t len ) {
while ( sum >> 16 )
sum = ( ( sum & 0xffff ) + ( sum >> 16 ) );
+ assert ( sum != 0x0000 );
return ~sum;
}
@@ -227,6 +242,8 @@ static void tcpip_test_exec ( void ) {
tcpip_ok ( &empty );
tcpip_ok ( &one_byte );
tcpip_ok ( &two_bytes );
+ tcpip_ok ( &positive_zero );
+ tcpip_ok ( &negative_zero );
tcpip_ok ( &final_carry_big );
tcpip_ok ( &final_carry_little );
tcpip_random_ok ( &random_aligned );