Make pb_decode_varint32 a separate implementation.
authorPetteri Aimonen <jpa@git.mail.kapsi.fi>
Tue, 5 Feb 2013 20:39:32 +0000 (22:39 +0200)
committerPetteri Aimonen <jpa@git.mail.kapsi.fi>
Tue, 5 Feb 2013 20:39:32 +0000 (22:39 +0200)
This avoids doing 64-bit arithmetic for 32-bit varint decodings.
It does increase the code size somewhat.

Results for ARM Cortex-M3: -10% execution time, +1% code size, -2% ram usage.

pb_decode.c

index 6ddde77..9faceca 100644 (file)
@@ -95,10 +95,20 @@ pb_istream_t pb_istream_from_buffer(uint8_t *buf, size_t bufsize)
 
 static bool checkreturn pb_decode_varint32(pb_istream_t *stream, uint32_t *dest)
 {
-    uint64_t temp;
-    bool status = pb_decode_varint(stream, &temp);
-    *dest = (uint32_t)temp;
-    return status;
+    uint8_t byte;
+    int bitpos = 0;
+    *dest = 0;
+    
+    while (bitpos < 32 && pb_read(stream, &byte, 1))
+    {
+        *dest |= (uint32_t)(byte & 0x7F) << bitpos;
+        bitpos += 7;
+        
+        if (!(byte & 0x80))
+            return true;
+    }
+    
+    PB_RETURN_ERROR(stream, "varint overflow");
 }
 
 bool checkreturn pb_decode_varint(pb_istream_t *stream, uint64_t *dest)