summaryrefslogtreecommitdiffstats
path: root/pb_decode.c
diff options
context:
space:
mode:
authorPetteri Aimonen <jpa@git.mail.kapsi.fi>2013-02-05 22:39:32 +0200
committerPetteri Aimonen <jpa@git.mail.kapsi.fi>2013-02-05 22:39:32 +0200
commit39b8a5e2bbd5da85f23b48280e81a5ce6672b09d (patch)
tree616594521e30d4bbfd683122c1fdadc7233ac024 /pb_decode.c
parentc372ebc665540df2578e869e73405b3d309bfc48 (diff)
Make pb_decode_varint32 a separate implementation.
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.
Diffstat (limited to 'pb_decode.c')
-rw-r--r--pb_decode.c18
1 files changed, 14 insertions, 4 deletions
diff --git a/pb_decode.c b/pb_decode.c
index 6ddde77..9faceca 100644
--- a/pb_decode.c
+++ b/pb_decode.c
@@ -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)