From 50978256b9773fe5c6d2fc177c9efcd4310893f6 Mon Sep 17 00:00:00 2001 From: Joshua Haberman Date: Fri, 5 Nov 2021 00:31:38 +0000 Subject: [PATCH] Properly byte-swap fixed packed fields. --- benchmarks/compare.py | 2 +- upb/decode.c | 27 +++++++++++++++++++++++++-- 2 files changed, 26 insertions(+), 3 deletions(-) diff --git a/benchmarks/compare.py b/benchmarks/compare.py index 6ce9e76019..55ed699582 100755 --- a/benchmarks/compare.py +++ b/benchmarks/compare.py @@ -85,7 +85,7 @@ def Benchmark(outbase, bench_cpu=True, runs=12, fasttable=False): Run("cp -f bazel-bin/tests/conformance_upb {}.bin".format(outbase)) -baseline = "master" +baseline = "main" bench_cpu = True fasttable = False diff --git a/upb/decode.c b/upb/decode.c index 822694fcb2..abc3ecb55b 100644 --- a/upb/decode.c +++ b/upb/decode.c @@ -449,8 +449,31 @@ static const char *decode_fixed_packed(upb_decstate *d, const char *ptr, arr->len += count; // Note: if/when the decoder supports multi-buffer input, we will need to // handle buffer seams here. - memcpy(mem, ptr, val->size); - return ptr + val->size; + if (_upb_isle()) { + memcpy(mem, ptr, val->size); + ptr += val->size; + } else { + const char *end = ptr + val->size; + char *dst = mem; + while (ptr < end) { + if (lg2 == 2) { + uint32_t val; + memcpy(&val, ptr, sizeof(val)); + val = _upb_be_swap32(val); + memcpy(dst, &val, sizeof(val)); + } else { + UPB_ASSERT(lg2 == 3); + uint64_t val; + memcpy(&val, ptr, sizeof(val)); + val = _upb_be_swap64(val); + memcpy(dst, &val, sizeof(val)); + } + ptr += 1 << lg2; + dst += 1 << lg2; + } + } + + return ptr; } UPB_FORCEINLINE