[PATCH 4/5] checksum: optimize loop and get rid of add16()

Joakim Tjernlund Joakim.Tjernlund at transmode.se
Sun Apr 25 11:41:21 CEST 2010


Use some better vaiable names and get rid of add16 as
add32 will do just as well. Fold the 32 bit checkum
into 16 bits in the end.

Signed-off-by: Joakim Tjernlund <Joakim.Tjernlund at transmode.se>
---
 lib/checksum.c |   47 +++++++++++++++++++++++------------------------
 1 files changed, 23 insertions(+), 24 deletions(-)

diff --git a/lib/checksum.c b/lib/checksum.c
index 2e427a2..7b183d9 100644
--- a/lib/checksum.c
+++ b/lib/checksum.c
@@ -15,12 +15,6 @@
 #include "nest/bird.h"
 #include "checksum.h"
 
-static u16				/* One-complement addition */
-add16(u16 sum, u16 x)
-{
-  u16 z = sum + x;
-  return z + (z < sum);
-}
 #ifdef __powerpc__
 static
 u32
@@ -42,10 +36,10 @@ add32(u32 sum, u32 x)
 #endif
 
 static u16
-ipsum_calc_block(u16 *x, unsigned len, u16 sum)
+ipsum_calc_block(u16 *buf, unsigned len, u16 sum)
 {
   int rest;
-  u32 tmp, *xx;
+  u32 acc_sum, *buf_u32;
 
   /*
    *  A few simple facts about the IP checksum (see RFC 1071 for detailed
@@ -62,23 +56,28 @@ ipsum_calc_block(u16 *x, unsigned len, u16 sum)
   ASSERT(!(len % 2));
   if (!len)
     return sum;
-  len >>= 1;
-  if ((unsigned long) x & 2)		/* Align to 32-bit boundary */
-    {
-      sum = add16(sum, *x++);
-      len--;
-    }
+
+  acc_sum = sum;
+  if ((u32) buf & 2) {		/* Align to 32-bit boundary */
+      add32(acc_sum, *buf++);
+      len =- 2;
+  }
   rest = len & 1;
-  len >>= 1;
-  tmp = 0;
-  xx = (u32 *) x;
-  for (xx--; len; --len);
-      tmp = add32(tmp, *++xx);
-  xx++;
-  sum = add16(sum, add16(tmp & 0xffff, tmp >> 16U));
-  if (rest)
-    sum = add16(sum, *(u16 *) xx);
-  return sum;
+  len >>= 2;
+  buf_u32 =  (u32 *) buf;
+  for(buf_u32--; len; --len)
+      acc_sum = add32(acc_sum, *++buf_u32);
+
+  if (rest) {
+      buf = (u16 *)(buf_u32++);
+      add32(acc_sum, *buf);
+  }
+
+  /* Add back carry outs from top 16 bits to low 16 bits.
+   */
+  acc_sum = (acc_sum >> 16) + (acc_sum & 0xffff);    /* add high-16 to low-16 */
+  acc_sum += (acc_sum >> 16); /* add carry */
+  return acc_sum;
 }
 
 static u16
-- 
1.6.4.4




More information about the Bird-users mailing list