1 // Protocol Buffers - Google's data interchange format
2 // Copyright 2023 Google LLC. All rights reserved.
3 //
4 // Use of this source code is governed by a BSD-style
5 // license that can be found in the LICENSE file or at
6 // https://developers.google.com/open-source/licenses/bsd
7
8 #include "upb/wire/decode.h"
9
10 #include <assert.h>
11 #include <stdbool.h>
12 #include <stddef.h>
13 #include <stdint.h>
14 #include <string.h>
15
16 #include "upb/base/descriptor_constants.h"
17 #include "upb/base/internal/endian.h"
18 #include "upb/base/string_view.h"
19 #include "upb/hash/common.h"
20 #include "upb/mem/arena.h"
21 #include "upb/message/array.h"
22 #include "upb/message/internal/accessors.h"
23 #include "upb/message/internal/array.h"
24 #include "upb/message/internal/extension.h"
25 #include "upb/message/internal/map.h"
26 #include "upb/message/internal/map_entry.h"
27 #include "upb/message/internal/message.h"
28 #include "upb/message/internal/tagged_ptr.h"
29 #include "upb/message/map.h"
30 #include "upb/message/message.h"
31 #include "upb/message/tagged_ptr.h"
32 #include "upb/mini_table/enum.h"
33 #include "upb/mini_table/extension.h"
34 #include "upb/mini_table/extension_registry.h"
35 #include "upb/mini_table/field.h"
36 #include "upb/mini_table/internal/field.h"
37 #include "upb/mini_table/internal/message.h"
38 #include "upb/mini_table/internal/sub.h"
39 #include "upb/mini_table/message.h"
40 #include "upb/mini_table/sub.h"
41 #include "upb/port/atomic.h"
42 #include "upb/wire/encode.h"
43 #include "upb/wire/eps_copy_input_stream.h"
44 #include "upb/wire/internal/constants.h"
45 #include "upb/wire/internal/decoder.h"
46 #include "upb/wire/reader.h"
47
48 // Must be last.
49 #include "upb/port/def.inc"
50
51 // A few fake field types for our tables.
52 enum {
53 kUpb_FakeFieldType_FieldNotFound = 0,
54 kUpb_FakeFieldType_MessageSetItem = 19,
55 };
56
57 // DecodeOp: an action to be performed for a wire-type/field-type combination.
58 enum {
59 // Special ops: we don't write data to regular fields for these.
60 kUpb_DecodeOp_UnknownField = -1,
61 kUpb_DecodeOp_MessageSetItem = -2,
62
63 // Scalar-only ops.
64 kUpb_DecodeOp_Scalar1Byte = 0,
65 kUpb_DecodeOp_Scalar4Byte = 2,
66 kUpb_DecodeOp_Scalar8Byte = 3,
67 kUpb_DecodeOp_Enum = 1,
68
69 // Scalar/repeated ops.
70 kUpb_DecodeOp_String = 4,
71 kUpb_DecodeOp_Bytes = 5,
72 kUpb_DecodeOp_SubMessage = 6,
73
74 // Repeated-only ops (also see macros below).
75 kUpb_DecodeOp_PackedEnum = 13,
76 };
77
78 // For packed fields it is helpful to be able to recover the lg2 of the data
79 // size from the op.
80 #define OP_FIXPCK_LG2(n) (n + 5) /* n in [2, 3] => op in [7, 8] */
81 #define OP_VARPCK_LG2(n) (n + 9) /* n in [0, 2, 3] => op in [9, 11, 12] */
82
83 typedef union {
84 bool bool_val;
85 uint32_t uint32_val;
86 uint64_t uint64_val;
87 uint32_t size;
88 } wireval;
89
90 // Ideally these two functions should take the owning MiniTable pointer as a
91 // first argument, then we could just put them in mini_table/message.h as nice
92 // clean getters. But we don't have that so instead we gotta write these
93 // Frankenfunctions that take an array of subtables.
94 // TODO: Move these to mini_table/ anyway since there are other places
95 // that could use them.
96
97 // Returns the MiniTable corresponding to a given MiniTableField
98 // from an array of MiniTableSubs.
_upb_MiniTableSubs_MessageByField(const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field)99 static const upb_MiniTable* _upb_MiniTableSubs_MessageByField(
100 const upb_MiniTableSubInternal* subs, const upb_MiniTableField* field) {
101 return *subs[field->UPB_PRIVATE(submsg_index)].UPB_PRIVATE(submsg);
102 }
103
104 // Returns the MiniTableEnum corresponding to a given MiniTableField
105 // from an array of MiniTableSub.
_upb_MiniTableSubs_EnumByField(const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field)106 static const upb_MiniTableEnum* _upb_MiniTableSubs_EnumByField(
107 const upb_MiniTableSubInternal* subs, const upb_MiniTableField* field) {
108 return subs[field->UPB_PRIVATE(submsg_index)].UPB_PRIVATE(subenum);
109 }
110
111 static const char* _upb_Decoder_DecodeMessage(upb_Decoder* d, const char* ptr,
112 upb_Message* msg,
113 const upb_MiniTable* layout);
114
_upb_Decoder_ErrorJmp(upb_Decoder * d,upb_DecodeStatus status)115 UPB_NORETURN static void* _upb_Decoder_ErrorJmp(upb_Decoder* d,
116 upb_DecodeStatus status) {
117 UPB_ASSERT(status != kUpb_DecodeStatus_Ok);
118 d->status = status;
119 UPB_LONGJMP(d->err, 1);
120 }
121
_upb_FastDecoder_ErrorJmp(upb_Decoder * d,int status)122 const char* _upb_FastDecoder_ErrorJmp(upb_Decoder* d, int status) {
123 UPB_ASSERT(status != kUpb_DecodeStatus_Ok);
124 d->status = status;
125 UPB_LONGJMP(d->err, 1);
126 return NULL;
127 }
128
_upb_Decoder_VerifyUtf8(upb_Decoder * d,const char * buf,int len)129 static void _upb_Decoder_VerifyUtf8(upb_Decoder* d, const char* buf, int len) {
130 if (!_upb_Decoder_VerifyUtf8Inline(buf, len)) {
131 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_BadUtf8);
132 }
133 }
134
_upb_Decoder_Reserve(upb_Decoder * d,upb_Array * arr,size_t elem)135 static bool _upb_Decoder_Reserve(upb_Decoder* d, upb_Array* arr, size_t elem) {
136 bool need_realloc =
137 arr->UPB_PRIVATE(capacity) - arr->UPB_PRIVATE(size) < elem;
138 if (need_realloc && !UPB_PRIVATE(_upb_Array_Realloc)(
139 arr, arr->UPB_PRIVATE(size) + elem, &d->arena)) {
140 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
141 }
142 return need_realloc;
143 }
144
145 typedef struct {
146 const char* ptr;
147 uint64_t val;
148 } _upb_DecodeLongVarintReturn;
149
150 UPB_NOINLINE
_upb_Decoder_DecodeLongVarint(const char * ptr,uint64_t val)151 static _upb_DecodeLongVarintReturn _upb_Decoder_DecodeLongVarint(
152 const char* ptr, uint64_t val) {
153 _upb_DecodeLongVarintReturn ret = {NULL, 0};
154 uint64_t byte;
155 for (int i = 1; i < 10; i++) {
156 byte = (uint8_t)ptr[i];
157 val += (byte - 1) << (i * 7);
158 if (!(byte & 0x80)) {
159 ret.ptr = ptr + i + 1;
160 ret.val = val;
161 return ret;
162 }
163 }
164 return ret;
165 }
166
167 UPB_FORCEINLINE
_upb_Decoder_DecodeVarint(upb_Decoder * d,const char * ptr,uint64_t * val)168 const char* _upb_Decoder_DecodeVarint(upb_Decoder* d, const char* ptr,
169 uint64_t* val) {
170 uint64_t byte = (uint8_t)*ptr;
171 if (UPB_LIKELY((byte & 0x80) == 0)) {
172 *val = byte;
173 return ptr + 1;
174 } else {
175 _upb_DecodeLongVarintReturn res = _upb_Decoder_DecodeLongVarint(ptr, byte);
176 if (!res.ptr) _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
177 *val = res.val;
178 return res.ptr;
179 }
180 }
181
182 UPB_FORCEINLINE
_upb_Decoder_DecodeTag(upb_Decoder * d,const char * ptr,uint32_t * val)183 const char* _upb_Decoder_DecodeTag(upb_Decoder* d, const char* ptr,
184 uint32_t* val) {
185 uint64_t byte = (uint8_t)*ptr;
186 if (UPB_LIKELY((byte & 0x80) == 0)) {
187 *val = byte;
188 return ptr + 1;
189 } else {
190 const char* start = ptr;
191 _upb_DecodeLongVarintReturn res = _upb_Decoder_DecodeLongVarint(ptr, byte);
192 if (!res.ptr || res.ptr - start > 5 || res.val > UINT32_MAX) {
193 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
194 }
195 *val = res.val;
196 return res.ptr;
197 }
198 }
199
200 UPB_FORCEINLINE
upb_Decoder_DecodeSize(upb_Decoder * d,const char * ptr,uint32_t * size)201 const char* upb_Decoder_DecodeSize(upb_Decoder* d, const char* ptr,
202 uint32_t* size) {
203 uint64_t size64;
204 ptr = _upb_Decoder_DecodeVarint(d, ptr, &size64);
205 if (size64 >= INT32_MAX ||
206 !upb_EpsCopyInputStream_CheckSize(&d->input, ptr, (int)size64)) {
207 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
208 }
209 *size = size64;
210 return ptr;
211 }
212
_upb_Decoder_MungeInt32(wireval * val)213 static void _upb_Decoder_MungeInt32(wireval* val) {
214 if (!upb_IsLittleEndian()) {
215 /* The next stage will memcpy(dst, &val, 4) */
216 val->uint32_val = val->uint64_val;
217 }
218 }
219
_upb_Decoder_Munge(int type,wireval * val)220 static void _upb_Decoder_Munge(int type, wireval* val) {
221 switch (type) {
222 case kUpb_FieldType_Bool:
223 val->bool_val = val->uint64_val != 0;
224 break;
225 case kUpb_FieldType_SInt32: {
226 uint32_t n = val->uint64_val;
227 val->uint32_val = (n >> 1) ^ -(int32_t)(n & 1);
228 break;
229 }
230 case kUpb_FieldType_SInt64: {
231 uint64_t n = val->uint64_val;
232 val->uint64_val = (n >> 1) ^ -(int64_t)(n & 1);
233 break;
234 }
235 case kUpb_FieldType_Int32:
236 case kUpb_FieldType_UInt32:
237 case kUpb_FieldType_Enum:
238 _upb_Decoder_MungeInt32(val);
239 break;
240 }
241 }
242
_upb_Decoder_NewSubMessage2(upb_Decoder * d,const upb_MiniTable * subl,const upb_MiniTableField * field,upb_TaggedMessagePtr * target)243 static upb_Message* _upb_Decoder_NewSubMessage2(upb_Decoder* d,
244 const upb_MiniTable* subl,
245 const upb_MiniTableField* field,
246 upb_TaggedMessagePtr* target) {
247 UPB_ASSERT(subl);
248 upb_Message* msg = _upb_Message_New(subl, &d->arena);
249 if (!msg) _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
250
251 // Extensions should not be unlinked. A message extension should not be
252 // registered until its sub-message type is available to be linked.
253 bool is_empty = UPB_PRIVATE(_upb_MiniTable_IsEmpty)(subl);
254 bool is_extension = field->UPB_PRIVATE(mode) & kUpb_LabelFlags_IsExtension;
255 UPB_ASSERT(!(is_empty && is_extension));
256
257 if (is_empty && !(d->options & kUpb_DecodeOption_ExperimentalAllowUnlinked)) {
258 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_UnlinkedSubMessage);
259 }
260
261 upb_TaggedMessagePtr tagged =
262 UPB_PRIVATE(_upb_TaggedMessagePtr_Pack)(msg, is_empty);
263 memcpy(target, &tagged, sizeof(tagged));
264 return msg;
265 }
266
_upb_Decoder_NewSubMessage(upb_Decoder * d,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field,upb_TaggedMessagePtr * target)267 static upb_Message* _upb_Decoder_NewSubMessage(
268 upb_Decoder* d, const upb_MiniTableSubInternal* subs,
269 const upb_MiniTableField* field, upb_TaggedMessagePtr* target) {
270 const upb_MiniTable* subl = _upb_MiniTableSubs_MessageByField(subs, field);
271 return _upb_Decoder_NewSubMessage2(d, subl, field, target);
272 }
273
_upb_Decoder_ReuseSubMessage(upb_Decoder * d,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field,upb_TaggedMessagePtr * target)274 static upb_Message* _upb_Decoder_ReuseSubMessage(
275 upb_Decoder* d, const upb_MiniTableSubInternal* subs,
276 const upb_MiniTableField* field, upb_TaggedMessagePtr* target) {
277 upb_TaggedMessagePtr tagged = *target;
278 const upb_MiniTable* subl = _upb_MiniTableSubs_MessageByField(subs, field);
279 UPB_ASSERT(subl);
280 if (!upb_TaggedMessagePtr_IsEmpty(tagged) ||
281 UPB_PRIVATE(_upb_MiniTable_IsEmpty)(subl)) {
282 return UPB_PRIVATE(_upb_TaggedMessagePtr_GetMessage)(tagged);
283 }
284
285 // We found an empty message from a previous parse that was performed before
286 // this field was linked. But it is linked now, so we want to allocate a new
287 // message of the correct type and promote data into it before continuing.
288 upb_Message* existing =
289 UPB_PRIVATE(_upb_TaggedMessagePtr_GetEmptyMessage)(tagged);
290 upb_Message* promoted = _upb_Decoder_NewSubMessage(d, subs, field, target);
291 size_t size;
292 const char* unknown = upb_Message_GetUnknown(existing, &size);
293 upb_DecodeStatus status = upb_Decode(unknown, size, promoted, subl, d->extreg,
294 d->options, &d->arena);
295 if (status != kUpb_DecodeStatus_Ok) _upb_Decoder_ErrorJmp(d, status);
296 return promoted;
297 }
298
_upb_Decoder_ReadString(upb_Decoder * d,const char * ptr,int size,upb_StringView * str)299 static const char* _upb_Decoder_ReadString(upb_Decoder* d, const char* ptr,
300 int size, upb_StringView* str) {
301 const char* str_ptr = ptr;
302 ptr = upb_EpsCopyInputStream_ReadString(&d->input, &str_ptr, size, &d->arena);
303 if (!ptr) _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
304 str->data = str_ptr;
305 str->size = size;
306 return ptr;
307 }
308
309 UPB_FORCEINLINE
_upb_Decoder_RecurseSubMessage(upb_Decoder * d,const char * ptr,upb_Message * submsg,const upb_MiniTable * subl,uint32_t expected_end_group)310 const char* _upb_Decoder_RecurseSubMessage(upb_Decoder* d, const char* ptr,
311 upb_Message* submsg,
312 const upb_MiniTable* subl,
313 uint32_t expected_end_group) {
314 if (--d->depth < 0) {
315 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_MaxDepthExceeded);
316 }
317 ptr = _upb_Decoder_DecodeMessage(d, ptr, submsg, subl);
318 d->depth++;
319 if (d->end_group != expected_end_group) {
320 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
321 }
322 return ptr;
323 }
324
325 UPB_FORCEINLINE
_upb_Decoder_DecodeSubMessage(upb_Decoder * d,const char * ptr,upb_Message * submsg,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field,int size)326 const char* _upb_Decoder_DecodeSubMessage(upb_Decoder* d, const char* ptr,
327 upb_Message* submsg,
328 const upb_MiniTableSubInternal* subs,
329 const upb_MiniTableField* field,
330 int size) {
331 int saved_delta = upb_EpsCopyInputStream_PushLimit(&d->input, ptr, size);
332 const upb_MiniTable* subl = _upb_MiniTableSubs_MessageByField(subs, field);
333 UPB_ASSERT(subl);
334 ptr = _upb_Decoder_RecurseSubMessage(d, ptr, submsg, subl, DECODE_NOGROUP);
335 upb_EpsCopyInputStream_PopLimit(&d->input, ptr, saved_delta);
336 return ptr;
337 }
338
339 UPB_FORCEINLINE
_upb_Decoder_DecodeGroup(upb_Decoder * d,const char * ptr,upb_Message * submsg,const upb_MiniTable * subl,uint32_t number)340 const char* _upb_Decoder_DecodeGroup(upb_Decoder* d, const char* ptr,
341 upb_Message* submsg,
342 const upb_MiniTable* subl,
343 uint32_t number) {
344 if (_upb_Decoder_IsDone(d, &ptr)) {
345 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
346 }
347 ptr = _upb_Decoder_RecurseSubMessage(d, ptr, submsg, subl, number);
348 d->end_group = DECODE_NOGROUP;
349 return ptr;
350 }
351
352 UPB_FORCEINLINE
_upb_Decoder_DecodeUnknownGroup(upb_Decoder * d,const char * ptr,uint32_t number)353 const char* _upb_Decoder_DecodeUnknownGroup(upb_Decoder* d, const char* ptr,
354 uint32_t number) {
355 return _upb_Decoder_DecodeGroup(d, ptr, NULL, NULL, number);
356 }
357
358 UPB_FORCEINLINE
_upb_Decoder_DecodeKnownGroup(upb_Decoder * d,const char * ptr,upb_Message * submsg,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field)359 const char* _upb_Decoder_DecodeKnownGroup(upb_Decoder* d, const char* ptr,
360 upb_Message* submsg,
361 const upb_MiniTableSubInternal* subs,
362 const upb_MiniTableField* field) {
363 const upb_MiniTable* subl = _upb_MiniTableSubs_MessageByField(subs, field);
364 UPB_ASSERT(subl);
365 return _upb_Decoder_DecodeGroup(d, ptr, submsg, subl,
366 field->UPB_PRIVATE(number));
367 }
368
upb_Decoder_EncodeVarint32(uint32_t val,char * ptr)369 static char* upb_Decoder_EncodeVarint32(uint32_t val, char* ptr) {
370 do {
371 uint8_t byte = val & 0x7fU;
372 val >>= 7;
373 if (val) byte |= 0x80U;
374 *(ptr++) = byte;
375 } while (val);
376 return ptr;
377 }
378
_upb_Decoder_AddUnknownVarints(upb_Decoder * d,upb_Message * msg,uint32_t val1,uint32_t val2)379 static void _upb_Decoder_AddUnknownVarints(upb_Decoder* d, upb_Message* msg,
380 uint32_t val1, uint32_t val2) {
381 char buf[20];
382 char* end = buf;
383 end = upb_Decoder_EncodeVarint32(val1, end);
384 end = upb_Decoder_EncodeVarint32(val2, end);
385
386 if (!UPB_PRIVATE(_upb_Message_AddUnknown)(msg, buf, end - buf, &d->arena)) {
387 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
388 }
389 }
390
391 UPB_FORCEINLINE
_upb_Decoder_CheckEnum(upb_Decoder * d,const char * ptr,upb_Message * msg,const upb_MiniTableEnum * e,const upb_MiniTableField * field,wireval * val)392 bool _upb_Decoder_CheckEnum(upb_Decoder* d, const char* ptr, upb_Message* msg,
393 const upb_MiniTableEnum* e,
394 const upb_MiniTableField* field, wireval* val) {
395 const uint32_t v = val->uint32_val;
396
397 if (UPB_LIKELY(upb_MiniTableEnum_CheckValue(e, v))) return true;
398
399 // Unrecognized enum goes into unknown fields.
400 // For packed fields the tag could be arbitrarily far in the past,
401 // so we just re-encode the tag and value here.
402 const uint32_t tag =
403 ((uint32_t)field->UPB_PRIVATE(number) << 3) | kUpb_WireType_Varint;
404 upb_Message* unknown_msg =
405 field->UPB_PRIVATE(mode) & kUpb_LabelFlags_IsExtension ? d->unknown_msg
406 : msg;
407 _upb_Decoder_AddUnknownVarints(d, unknown_msg, tag, v);
408 return false;
409 }
410
411 UPB_NOINLINE
_upb_Decoder_DecodeEnumArray(upb_Decoder * d,const char * ptr,upb_Message * msg,upb_Array * arr,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field,wireval * val)412 static const char* _upb_Decoder_DecodeEnumArray(
413 upb_Decoder* d, const char* ptr, upb_Message* msg, upb_Array* arr,
414 const upb_MiniTableSubInternal* subs, const upb_MiniTableField* field,
415 wireval* val) {
416 const upb_MiniTableEnum* e = _upb_MiniTableSubs_EnumByField(subs, field);
417 if (!_upb_Decoder_CheckEnum(d, ptr, msg, e, field, val)) return ptr;
418 void* mem = UPB_PTR_AT(upb_Array_MutableDataPtr(arr),
419 arr->UPB_PRIVATE(size) * 4, void);
420 arr->UPB_PRIVATE(size)++;
421 memcpy(mem, val, 4);
422 return ptr;
423 }
424
425 UPB_FORCEINLINE
_upb_Decoder_DecodeFixedPacked(upb_Decoder * d,const char * ptr,upb_Array * arr,wireval * val,const upb_MiniTableField * field,int lg2)426 const char* _upb_Decoder_DecodeFixedPacked(upb_Decoder* d, const char* ptr,
427 upb_Array* arr, wireval* val,
428 const upb_MiniTableField* field,
429 int lg2) {
430 int mask = (1 << lg2) - 1;
431 size_t count = val->size >> lg2;
432 if ((val->size & mask) != 0) {
433 // Length isn't a round multiple of elem size.
434 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
435 }
436 _upb_Decoder_Reserve(d, arr, count);
437 void* mem = UPB_PTR_AT(upb_Array_MutableDataPtr(arr),
438 arr->UPB_PRIVATE(size) << lg2, void);
439 arr->UPB_PRIVATE(size) += count;
440 // Note: if/when the decoder supports multi-buffer input, we will need to
441 // handle buffer seams here.
442 if (upb_IsLittleEndian()) {
443 ptr = upb_EpsCopyInputStream_Copy(&d->input, ptr, mem, val->size);
444 } else {
445 int delta = upb_EpsCopyInputStream_PushLimit(&d->input, ptr, val->size);
446 char* dst = mem;
447 while (!_upb_Decoder_IsDone(d, &ptr)) {
448 if (lg2 == 2) {
449 ptr = upb_WireReader_ReadFixed32(ptr, dst);
450 dst += 4;
451 } else {
452 UPB_ASSERT(lg2 == 3);
453 ptr = upb_WireReader_ReadFixed64(ptr, dst);
454 dst += 8;
455 }
456 }
457 upb_EpsCopyInputStream_PopLimit(&d->input, ptr, delta);
458 }
459
460 return ptr;
461 }
462
463 UPB_FORCEINLINE
_upb_Decoder_DecodeVarintPacked(upb_Decoder * d,const char * ptr,upb_Array * arr,wireval * val,const upb_MiniTableField * field,int lg2)464 const char* _upb_Decoder_DecodeVarintPacked(upb_Decoder* d, const char* ptr,
465 upb_Array* arr, wireval* val,
466 const upb_MiniTableField* field,
467 int lg2) {
468 int scale = 1 << lg2;
469 int saved_limit = upb_EpsCopyInputStream_PushLimit(&d->input, ptr, val->size);
470 char* out = UPB_PTR_AT(upb_Array_MutableDataPtr(arr),
471 arr->UPB_PRIVATE(size) << lg2, void);
472 while (!_upb_Decoder_IsDone(d, &ptr)) {
473 wireval elem;
474 ptr = _upb_Decoder_DecodeVarint(d, ptr, &elem.uint64_val);
475 _upb_Decoder_Munge(field->UPB_PRIVATE(descriptortype), &elem);
476 if (_upb_Decoder_Reserve(d, arr, 1)) {
477 out = UPB_PTR_AT(upb_Array_MutableDataPtr(arr),
478 arr->UPB_PRIVATE(size) << lg2, void);
479 }
480 arr->UPB_PRIVATE(size)++;
481 memcpy(out, &elem, scale);
482 out += scale;
483 }
484 upb_EpsCopyInputStream_PopLimit(&d->input, ptr, saved_limit);
485 return ptr;
486 }
487
488 UPB_NOINLINE
_upb_Decoder_DecodeEnumPacked(upb_Decoder * d,const char * ptr,upb_Message * msg,upb_Array * arr,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field,wireval * val)489 static const char* _upb_Decoder_DecodeEnumPacked(
490 upb_Decoder* d, const char* ptr, upb_Message* msg, upb_Array* arr,
491 const upb_MiniTableSubInternal* subs, const upb_MiniTableField* field,
492 wireval* val) {
493 const upb_MiniTableEnum* e = _upb_MiniTableSubs_EnumByField(subs, field);
494 int saved_limit = upb_EpsCopyInputStream_PushLimit(&d->input, ptr, val->size);
495 char* out = UPB_PTR_AT(upb_Array_MutableDataPtr(arr),
496 arr->UPB_PRIVATE(size) * 4, void);
497 while (!_upb_Decoder_IsDone(d, &ptr)) {
498 wireval elem;
499 ptr = _upb_Decoder_DecodeVarint(d, ptr, &elem.uint64_val);
500 _upb_Decoder_MungeInt32(&elem);
501 if (!_upb_Decoder_CheckEnum(d, ptr, msg, e, field, &elem)) {
502 continue;
503 }
504 if (_upb_Decoder_Reserve(d, arr, 1)) {
505 out = UPB_PTR_AT(upb_Array_MutableDataPtr(arr),
506 arr->UPB_PRIVATE(size) * 4, void);
507 }
508 arr->UPB_PRIVATE(size)++;
509 memcpy(out, &elem, 4);
510 out += 4;
511 }
512 upb_EpsCopyInputStream_PopLimit(&d->input, ptr, saved_limit);
513 return ptr;
514 }
515
_upb_Decoder_CreateArray(upb_Decoder * d,const upb_MiniTableField * field)516 static upb_Array* _upb_Decoder_CreateArray(upb_Decoder* d,
517 const upb_MiniTableField* field) {
518 const upb_FieldType field_type = field->UPB_PRIVATE(descriptortype);
519 const size_t lg2 = UPB_PRIVATE(_upb_FieldType_SizeLg2)(field_type);
520 upb_Array* ret = UPB_PRIVATE(_upb_Array_New)(&d->arena, 4, lg2);
521 if (!ret) _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
522 return ret;
523 }
524
_upb_Decoder_DecodeToArray(upb_Decoder * d,const char * ptr,upb_Message * msg,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field,wireval * val,int op)525 static const char* _upb_Decoder_DecodeToArray(
526 upb_Decoder* d, const char* ptr, upb_Message* msg,
527 const upb_MiniTableSubInternal* subs, const upb_MiniTableField* field,
528 wireval* val, int op) {
529 upb_Array** arrp = UPB_PTR_AT(msg, field->UPB_PRIVATE(offset), void);
530 upb_Array* arr = *arrp;
531 void* mem;
532
533 if (arr) {
534 _upb_Decoder_Reserve(d, arr, 1);
535 } else {
536 arr = _upb_Decoder_CreateArray(d, field);
537 *arrp = arr;
538 }
539
540 switch (op) {
541 case kUpb_DecodeOp_Scalar1Byte:
542 case kUpb_DecodeOp_Scalar4Byte:
543 case kUpb_DecodeOp_Scalar8Byte:
544 /* Append scalar value. */
545 mem = UPB_PTR_AT(upb_Array_MutableDataPtr(arr),
546 arr->UPB_PRIVATE(size) << op, void);
547 arr->UPB_PRIVATE(size)++;
548 memcpy(mem, val, 1 << op);
549 return ptr;
550 case kUpb_DecodeOp_String:
551 _upb_Decoder_VerifyUtf8(d, ptr, val->size);
552 /* Fallthrough. */
553 case kUpb_DecodeOp_Bytes: {
554 /* Append bytes. */
555 upb_StringView* str = (upb_StringView*)upb_Array_MutableDataPtr(arr) +
556 arr->UPB_PRIVATE(size);
557 arr->UPB_PRIVATE(size)++;
558 return _upb_Decoder_ReadString(d, ptr, val->size, str);
559 }
560 case kUpb_DecodeOp_SubMessage: {
561 /* Append submessage / group. */
562 upb_TaggedMessagePtr* target = UPB_PTR_AT(
563 upb_Array_MutableDataPtr(arr), arr->UPB_PRIVATE(size) * sizeof(void*),
564 upb_TaggedMessagePtr);
565 upb_Message* submsg = _upb_Decoder_NewSubMessage(d, subs, field, target);
566 arr->UPB_PRIVATE(size)++;
567 if (UPB_UNLIKELY(field->UPB_PRIVATE(descriptortype) ==
568 kUpb_FieldType_Group)) {
569 return _upb_Decoder_DecodeKnownGroup(d, ptr, submsg, subs, field);
570 } else {
571 return _upb_Decoder_DecodeSubMessage(d, ptr, submsg, subs, field,
572 val->size);
573 }
574 }
575 case OP_FIXPCK_LG2(2):
576 case OP_FIXPCK_LG2(3):
577 return _upb_Decoder_DecodeFixedPacked(d, ptr, arr, val, field,
578 op - OP_FIXPCK_LG2(0));
579 case OP_VARPCK_LG2(0):
580 case OP_VARPCK_LG2(2):
581 case OP_VARPCK_LG2(3):
582 return _upb_Decoder_DecodeVarintPacked(d, ptr, arr, val, field,
583 op - OP_VARPCK_LG2(0));
584 case kUpb_DecodeOp_Enum:
585 return _upb_Decoder_DecodeEnumArray(d, ptr, msg, arr, subs, field, val);
586 case kUpb_DecodeOp_PackedEnum:
587 return _upb_Decoder_DecodeEnumPacked(d, ptr, msg, arr, subs, field, val);
588 default:
589 UPB_UNREACHABLE();
590 }
591 }
592
_upb_Decoder_CreateMap(upb_Decoder * d,const upb_MiniTable * entry)593 static upb_Map* _upb_Decoder_CreateMap(upb_Decoder* d,
594 const upb_MiniTable* entry) {
595 // Maps descriptor type -> upb map size
596 static const uint8_t kSizeInMap[] = {
597 [0] = -1, // invalid descriptor type
598 [kUpb_FieldType_Double] = 8,
599 [kUpb_FieldType_Float] = 4,
600 [kUpb_FieldType_Int64] = 8,
601 [kUpb_FieldType_UInt64] = 8,
602 [kUpb_FieldType_Int32] = 4,
603 [kUpb_FieldType_Fixed64] = 8,
604 [kUpb_FieldType_Fixed32] = 4,
605 [kUpb_FieldType_Bool] = 1,
606 [kUpb_FieldType_String] = UPB_MAPTYPE_STRING,
607 [kUpb_FieldType_Group] = sizeof(void*),
608 [kUpb_FieldType_Message] = sizeof(void*),
609 [kUpb_FieldType_Bytes] = UPB_MAPTYPE_STRING,
610 [kUpb_FieldType_UInt32] = 4,
611 [kUpb_FieldType_Enum] = 4,
612 [kUpb_FieldType_SFixed32] = 4,
613 [kUpb_FieldType_SFixed64] = 8,
614 [kUpb_FieldType_SInt32] = 4,
615 [kUpb_FieldType_SInt64] = 8,
616 };
617
618 const upb_MiniTableField* key_field = &entry->UPB_PRIVATE(fields)[0];
619 const upb_MiniTableField* val_field = &entry->UPB_PRIVATE(fields)[1];
620 char key_size = kSizeInMap[key_field->UPB_PRIVATE(descriptortype)];
621 char val_size = kSizeInMap[val_field->UPB_PRIVATE(descriptortype)];
622 UPB_ASSERT(key_field->UPB_PRIVATE(offset) == offsetof(upb_MapEntry, k));
623 UPB_ASSERT(val_field->UPB_PRIVATE(offset) == offsetof(upb_MapEntry, v));
624 upb_Map* ret = _upb_Map_New(&d->arena, key_size, val_size);
625 if (!ret) _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
626 return ret;
627 }
628
_upb_Decoder_DecodeToMap(upb_Decoder * d,const char * ptr,upb_Message * msg,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field,wireval * val)629 static const char* _upb_Decoder_DecodeToMap(
630 upb_Decoder* d, const char* ptr, upb_Message* msg,
631 const upb_MiniTableSubInternal* subs, const upb_MiniTableField* field,
632 wireval* val) {
633 upb_Map** map_p = UPB_PTR_AT(msg, field->UPB_PRIVATE(offset), upb_Map*);
634 upb_Map* map = *map_p;
635 upb_MapEntry ent;
636 UPB_ASSERT(upb_MiniTableField_Type(field) == kUpb_FieldType_Message);
637 const upb_MiniTable* entry = _upb_MiniTableSubs_MessageByField(subs, field);
638
639 UPB_ASSERT(entry);
640 UPB_ASSERT(entry->UPB_PRIVATE(field_count) == 2);
641 UPB_ASSERT(upb_MiniTableField_IsScalar(&entry->UPB_PRIVATE(fields)[0]));
642 UPB_ASSERT(upb_MiniTableField_IsScalar(&entry->UPB_PRIVATE(fields)[1]));
643
644 if (!map) {
645 map = _upb_Decoder_CreateMap(d, entry);
646 *map_p = map;
647 }
648
649 // Parse map entry.
650 memset(&ent, 0, sizeof(ent));
651
652 if (entry->UPB_PRIVATE(fields)[1].UPB_PRIVATE(descriptortype) ==
653 kUpb_FieldType_Message ||
654 entry->UPB_PRIVATE(fields)[1].UPB_PRIVATE(descriptortype) ==
655 kUpb_FieldType_Group) {
656 // Create proactively to handle the case where it doesn't appear.
657 upb_TaggedMessagePtr msg;
658 _upb_Decoder_NewSubMessage(d, entry->UPB_PRIVATE(subs),
659 &entry->UPB_PRIVATE(fields)[1], &msg);
660 ent.v.val = upb_value_uintptr(msg);
661 }
662
663 ptr = _upb_Decoder_DecodeSubMessage(d, ptr, &ent.message, subs, field,
664 val->size);
665 // check if ent had any unknown fields
666 size_t size;
667 upb_Message_GetUnknown(&ent.message, &size);
668 if (size != 0) {
669 char* buf;
670 size_t size;
671 uint32_t tag =
672 ((uint32_t)field->UPB_PRIVATE(number) << 3) | kUpb_WireType_Delimited;
673 upb_EncodeStatus status =
674 upb_Encode(&ent.message, entry, 0, &d->arena, &buf, &size);
675 if (status != kUpb_EncodeStatus_Ok) {
676 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
677 }
678 _upb_Decoder_AddUnknownVarints(d, msg, tag, size);
679 if (!UPB_PRIVATE(_upb_Message_AddUnknown)(msg, buf, size, &d->arena)) {
680 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
681 }
682 } else {
683 if (_upb_Map_Insert(map, &ent.k, map->key_size, &ent.v, map->val_size,
684 &d->arena) == kUpb_MapInsertStatus_OutOfMemory) {
685 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
686 }
687 }
688 return ptr;
689 }
690
_upb_Decoder_DecodeToSubMessage(upb_Decoder * d,const char * ptr,upb_Message * msg,const upb_MiniTableSubInternal * subs,const upb_MiniTableField * field,wireval * val,int op)691 static const char* _upb_Decoder_DecodeToSubMessage(
692 upb_Decoder* d, const char* ptr, upb_Message* msg,
693 const upb_MiniTableSubInternal* subs, const upb_MiniTableField* field,
694 wireval* val, int op) {
695 void* mem = UPB_PTR_AT(msg, field->UPB_PRIVATE(offset), void);
696 int type = field->UPB_PRIVATE(descriptortype);
697
698 if (UPB_UNLIKELY(op == kUpb_DecodeOp_Enum) &&
699 !_upb_Decoder_CheckEnum(d, ptr, msg,
700 _upb_MiniTableSubs_EnumByField(subs, field),
701 field, val)) {
702 return ptr;
703 }
704
705 // Set presence if necessary.
706 if (UPB_PRIVATE(_upb_MiniTableField_HasHasbit)(field)) {
707 UPB_PRIVATE(_upb_Message_SetHasbit)(msg, field);
708 } else if (upb_MiniTableField_IsInOneof(field)) {
709 // Oneof case
710 uint32_t* oneof_case = UPB_PRIVATE(_upb_Message_OneofCasePtr)(msg, field);
711 if (op == kUpb_DecodeOp_SubMessage &&
712 *oneof_case != field->UPB_PRIVATE(number)) {
713 memset(mem, 0, sizeof(void*));
714 }
715 *oneof_case = field->UPB_PRIVATE(number);
716 }
717
718 // Store into message.
719 switch (op) {
720 case kUpb_DecodeOp_SubMessage: {
721 upb_TaggedMessagePtr* submsgp = mem;
722 upb_Message* submsg;
723 if (*submsgp) {
724 submsg = _upb_Decoder_ReuseSubMessage(d, subs, field, submsgp);
725 } else {
726 submsg = _upb_Decoder_NewSubMessage(d, subs, field, submsgp);
727 }
728 if (UPB_UNLIKELY(type == kUpb_FieldType_Group)) {
729 ptr = _upb_Decoder_DecodeKnownGroup(d, ptr, submsg, subs, field);
730 } else {
731 ptr = _upb_Decoder_DecodeSubMessage(d, ptr, submsg, subs, field,
732 val->size);
733 }
734 break;
735 }
736 case kUpb_DecodeOp_String:
737 _upb_Decoder_VerifyUtf8(d, ptr, val->size);
738 /* Fallthrough. */
739 case kUpb_DecodeOp_Bytes:
740 return _upb_Decoder_ReadString(d, ptr, val->size, mem);
741 case kUpb_DecodeOp_Scalar8Byte:
742 memcpy(mem, val, 8);
743 break;
744 case kUpb_DecodeOp_Enum:
745 case kUpb_DecodeOp_Scalar4Byte:
746 memcpy(mem, val, 4);
747 break;
748 case kUpb_DecodeOp_Scalar1Byte:
749 memcpy(mem, val, 1);
750 break;
751 default:
752 UPB_UNREACHABLE();
753 }
754
755 return ptr;
756 }
757
758 UPB_NOINLINE
_upb_Decoder_CheckRequired(upb_Decoder * d,const char * ptr,const upb_Message * msg,const upb_MiniTable * m)759 const char* _upb_Decoder_CheckRequired(upb_Decoder* d, const char* ptr,
760 const upb_Message* msg,
761 const upb_MiniTable* m) {
762 UPB_ASSERT(m->UPB_PRIVATE(required_count));
763 if (UPB_UNLIKELY(d->options & kUpb_DecodeOption_CheckRequired)) {
764 d->missing_required =
765 !UPB_PRIVATE(_upb_Message_IsInitializedShallow)(msg, m);
766 }
767 return ptr;
768 }
769
770 UPB_FORCEINLINE
_upb_Decoder_TryFastDispatch(upb_Decoder * d,const char ** ptr,upb_Message * msg,const upb_MiniTable * m)771 bool _upb_Decoder_TryFastDispatch(upb_Decoder* d, const char** ptr,
772 upb_Message* msg, const upb_MiniTable* m) {
773 #if UPB_FASTTABLE
774 if (m && m->UPB_PRIVATE(table_mask) != (unsigned char)-1) {
775 uint16_t tag = _upb_FastDecoder_LoadTag(*ptr);
776 intptr_t table = decode_totable(m);
777 *ptr = _upb_FastDecoder_TagDispatch(d, *ptr, msg, table, 0, tag);
778 return true;
779 }
780 #endif
781 return false;
782 }
783
upb_Decoder_SkipField(upb_Decoder * d,const char * ptr,uint32_t tag)784 static const char* upb_Decoder_SkipField(upb_Decoder* d, const char* ptr,
785 uint32_t tag) {
786 int field_number = tag >> 3;
787 int wire_type = tag & 7;
788 switch (wire_type) {
789 case kUpb_WireType_Varint: {
790 uint64_t val;
791 return _upb_Decoder_DecodeVarint(d, ptr, &val);
792 }
793 case kUpb_WireType_64Bit:
794 return ptr + 8;
795 case kUpb_WireType_32Bit:
796 return ptr + 4;
797 case kUpb_WireType_Delimited: {
798 uint32_t size;
799 ptr = upb_Decoder_DecodeSize(d, ptr, &size);
800 return ptr + size;
801 }
802 case kUpb_WireType_StartGroup:
803 return _upb_Decoder_DecodeUnknownGroup(d, ptr, field_number);
804 default:
805 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
806 }
807 }
808
809 enum {
810 kStartItemTag = ((kUpb_MsgSet_Item << 3) | kUpb_WireType_StartGroup),
811 kEndItemTag = ((kUpb_MsgSet_Item << 3) | kUpb_WireType_EndGroup),
812 kTypeIdTag = ((kUpb_MsgSet_TypeId << 3) | kUpb_WireType_Varint),
813 kMessageTag = ((kUpb_MsgSet_Message << 3) | kUpb_WireType_Delimited),
814 };
815
upb_Decoder_AddKnownMessageSetItem(upb_Decoder * d,upb_Message * msg,const upb_MiniTableExtension * item_mt,const char * data,uint32_t size)816 static void upb_Decoder_AddKnownMessageSetItem(
817 upb_Decoder* d, upb_Message* msg, const upb_MiniTableExtension* item_mt,
818 const char* data, uint32_t size) {
819 upb_Extension* ext =
820 UPB_PRIVATE(_upb_Message_GetOrCreateExtension)(msg, item_mt, &d->arena);
821 if (UPB_UNLIKELY(!ext)) {
822 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
823 }
824 upb_Message* submsg = _upb_Decoder_NewSubMessage2(
825 d, ext->ext->UPB_PRIVATE(sub).UPB_PRIVATE(submsg),
826 &ext->ext->UPB_PRIVATE(field), (upb_TaggedMessagePtr*)&ext->data);
827 upb_DecodeStatus status = upb_Decode(
828 data, size, submsg, upb_MiniTableExtension_GetSubMessage(item_mt),
829 d->extreg, d->options, &d->arena);
830 if (status != kUpb_DecodeStatus_Ok) _upb_Decoder_ErrorJmp(d, status);
831 }
832
upb_Decoder_AddUnknownMessageSetItem(upb_Decoder * d,upb_Message * msg,uint32_t type_id,const char * message_data,uint32_t message_size)833 static void upb_Decoder_AddUnknownMessageSetItem(upb_Decoder* d,
834 upb_Message* msg,
835 uint32_t type_id,
836 const char* message_data,
837 uint32_t message_size) {
838 char buf[60];
839 char* ptr = buf;
840 ptr = upb_Decoder_EncodeVarint32(kStartItemTag, ptr);
841 ptr = upb_Decoder_EncodeVarint32(kTypeIdTag, ptr);
842 ptr = upb_Decoder_EncodeVarint32(type_id, ptr);
843 ptr = upb_Decoder_EncodeVarint32(kMessageTag, ptr);
844 ptr = upb_Decoder_EncodeVarint32(message_size, ptr);
845 char* split = ptr;
846
847 ptr = upb_Decoder_EncodeVarint32(kEndItemTag, ptr);
848 char* end = ptr;
849
850 if (!UPB_PRIVATE(_upb_Message_AddUnknown)(msg, buf, split - buf, &d->arena) ||
851 !UPB_PRIVATE(_upb_Message_AddUnknown)(msg, message_data, message_size,
852 &d->arena) ||
853 !UPB_PRIVATE(_upb_Message_AddUnknown)(msg, split, end - split,
854 &d->arena)) {
855 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
856 }
857 }
858
upb_Decoder_AddMessageSetItem(upb_Decoder * d,upb_Message * msg,const upb_MiniTable * t,uint32_t type_id,const char * data,uint32_t size)859 static void upb_Decoder_AddMessageSetItem(upb_Decoder* d, upb_Message* msg,
860 const upb_MiniTable* t,
861 uint32_t type_id, const char* data,
862 uint32_t size) {
863 const upb_MiniTableExtension* item_mt =
864 upb_ExtensionRegistry_Lookup(d->extreg, t, type_id);
865 if (item_mt) {
866 upb_Decoder_AddKnownMessageSetItem(d, msg, item_mt, data, size);
867 } else {
868 upb_Decoder_AddUnknownMessageSetItem(d, msg, type_id, data, size);
869 }
870 }
871
upb_Decoder_DecodeMessageSetItem(upb_Decoder * d,const char * ptr,upb_Message * msg,const upb_MiniTable * layout)872 static const char* upb_Decoder_DecodeMessageSetItem(
873 upb_Decoder* d, const char* ptr, upb_Message* msg,
874 const upb_MiniTable* layout) {
875 uint32_t type_id = 0;
876 upb_StringView preserved = {NULL, 0};
877 typedef enum {
878 kUpb_HaveId = 1 << 0,
879 kUpb_HavePayload = 1 << 1,
880 } StateMask;
881 StateMask state_mask = 0;
882 while (!_upb_Decoder_IsDone(d, &ptr)) {
883 uint32_t tag;
884 ptr = _upb_Decoder_DecodeTag(d, ptr, &tag);
885 switch (tag) {
886 case kEndItemTag:
887 return ptr;
888 case kTypeIdTag: {
889 uint64_t tmp;
890 ptr = _upb_Decoder_DecodeVarint(d, ptr, &tmp);
891 if (state_mask & kUpb_HaveId) break; // Ignore dup.
892 state_mask |= kUpb_HaveId;
893 type_id = tmp;
894 if (state_mask & kUpb_HavePayload) {
895 upb_Decoder_AddMessageSetItem(d, msg, layout, type_id, preserved.data,
896 preserved.size);
897 }
898 break;
899 }
900 case kMessageTag: {
901 uint32_t size;
902 ptr = upb_Decoder_DecodeSize(d, ptr, &size);
903 const char* data = ptr;
904 ptr += size;
905 if (state_mask & kUpb_HavePayload) break; // Ignore dup.
906 state_mask |= kUpb_HavePayload;
907 if (state_mask & kUpb_HaveId) {
908 upb_Decoder_AddMessageSetItem(d, msg, layout, type_id, data, size);
909 } else {
910 // Out of order, we must preserve the payload.
911 preserved.data = data;
912 preserved.size = size;
913 }
914 break;
915 }
916 default:
917 // We do not preserve unexpected fields inside a message set item.
918 ptr = upb_Decoder_SkipField(d, ptr, tag);
919 break;
920 }
921 }
922 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
923 }
924
_upb_Decoder_FindField(upb_Decoder * d,const upb_MiniTable * t,uint32_t field_number,int * last_field_index)925 static const upb_MiniTableField* _upb_Decoder_FindField(upb_Decoder* d,
926 const upb_MiniTable* t,
927 uint32_t field_number,
928 int* last_field_index) {
929 static upb_MiniTableField none = {
930 0, 0, 0, 0, kUpb_FakeFieldType_FieldNotFound, 0};
931 if (t == NULL) return &none;
932
933 size_t idx = ((size_t)field_number) - 1; // 0 wraps to SIZE_MAX
934 if (idx < t->UPB_PRIVATE(dense_below)) {
935 // Fastest case: index into dense fields.
936 goto found;
937 }
938
939 if (t->UPB_PRIVATE(dense_below) < t->UPB_PRIVATE(field_count)) {
940 // Linear search non-dense fields. Resume scanning from last_field_index
941 // since fields are usually in order.
942 size_t last = *last_field_index;
943 for (idx = last; idx < t->UPB_PRIVATE(field_count); idx++) {
944 if (t->UPB_PRIVATE(fields)[idx].UPB_PRIVATE(number) == field_number) {
945 goto found;
946 }
947 }
948
949 for (idx = t->UPB_PRIVATE(dense_below); idx < last; idx++) {
950 if (t->UPB_PRIVATE(fields)[idx].UPB_PRIVATE(number) == field_number) {
951 goto found;
952 }
953 }
954 }
955
956 if (d->extreg) {
957 switch (t->UPB_PRIVATE(ext)) {
958 case kUpb_ExtMode_Extendable: {
959 const upb_MiniTableExtension* ext =
960 upb_ExtensionRegistry_Lookup(d->extreg, t, field_number);
961 if (ext) return &ext->UPB_PRIVATE(field);
962 break;
963 }
964 case kUpb_ExtMode_IsMessageSet:
965 if (field_number == kUpb_MsgSet_Item) {
966 static upb_MiniTableField item = {
967 0, 0, 0, 0, kUpb_FakeFieldType_MessageSetItem, 0};
968 return &item;
969 }
970 break;
971 }
972 }
973
974 return &none; // Unknown field.
975
976 found:
977 UPB_ASSERT(t->UPB_PRIVATE(fields)[idx].UPB_PRIVATE(number) == field_number);
978 *last_field_index = idx;
979 return &t->UPB_PRIVATE(fields)[idx];
980 }
981
_upb_Decoder_GetVarintOp(const upb_MiniTableField * field)982 static int _upb_Decoder_GetVarintOp(const upb_MiniTableField* field) {
983 static const int8_t kVarintOps[] = {
984 [kUpb_FakeFieldType_FieldNotFound] = kUpb_DecodeOp_UnknownField,
985 [kUpb_FieldType_Double] = kUpb_DecodeOp_UnknownField,
986 [kUpb_FieldType_Float] = kUpb_DecodeOp_UnknownField,
987 [kUpb_FieldType_Int64] = kUpb_DecodeOp_Scalar8Byte,
988 [kUpb_FieldType_UInt64] = kUpb_DecodeOp_Scalar8Byte,
989 [kUpb_FieldType_Int32] = kUpb_DecodeOp_Scalar4Byte,
990 [kUpb_FieldType_Fixed64] = kUpb_DecodeOp_UnknownField,
991 [kUpb_FieldType_Fixed32] = kUpb_DecodeOp_UnknownField,
992 [kUpb_FieldType_Bool] = kUpb_DecodeOp_Scalar1Byte,
993 [kUpb_FieldType_String] = kUpb_DecodeOp_UnknownField,
994 [kUpb_FieldType_Group] = kUpb_DecodeOp_UnknownField,
995 [kUpb_FieldType_Message] = kUpb_DecodeOp_UnknownField,
996 [kUpb_FieldType_Bytes] = kUpb_DecodeOp_UnknownField,
997 [kUpb_FieldType_UInt32] = kUpb_DecodeOp_Scalar4Byte,
998 [kUpb_FieldType_Enum] = kUpb_DecodeOp_Enum,
999 [kUpb_FieldType_SFixed32] = kUpb_DecodeOp_UnknownField,
1000 [kUpb_FieldType_SFixed64] = kUpb_DecodeOp_UnknownField,
1001 [kUpb_FieldType_SInt32] = kUpb_DecodeOp_Scalar4Byte,
1002 [kUpb_FieldType_SInt64] = kUpb_DecodeOp_Scalar8Byte,
1003 [kUpb_FakeFieldType_MessageSetItem] = kUpb_DecodeOp_UnknownField,
1004 };
1005
1006 return kVarintOps[field->UPB_PRIVATE(descriptortype)];
1007 }
1008
1009 UPB_FORCEINLINE
_upb_Decoder_CheckUnlinked(upb_Decoder * d,const upb_MiniTable * mt,const upb_MiniTableField * field,int * op)1010 void _upb_Decoder_CheckUnlinked(upb_Decoder* d, const upb_MiniTable* mt,
1011 const upb_MiniTableField* field, int* op) {
1012 // If sub-message is not linked, treat as unknown.
1013 if (field->UPB_PRIVATE(mode) & kUpb_LabelFlags_IsExtension) return;
1014 const upb_MiniTable* mt_sub =
1015 _upb_MiniTableSubs_MessageByField(mt->UPB_PRIVATE(subs), field);
1016 if ((d->options & kUpb_DecodeOption_ExperimentalAllowUnlinked) ||
1017 !UPB_PRIVATE(_upb_MiniTable_IsEmpty)(mt_sub)) {
1018 return;
1019 }
1020 #ifndef NDEBUG
1021 const upb_MiniTableField* oneof = upb_MiniTable_GetOneof(mt, field);
1022 if (oneof) {
1023 // All other members of the oneof must be message fields that are also
1024 // unlinked.
1025 do {
1026 UPB_ASSERT(upb_MiniTableField_CType(oneof) == kUpb_CType_Message);
1027 const upb_MiniTable* oneof_sub =
1028 *mt->UPB_PRIVATE(subs)[oneof->UPB_PRIVATE(submsg_index)].UPB_PRIVATE(
1029 submsg);
1030 UPB_ASSERT(!oneof_sub);
1031 } while (upb_MiniTable_NextOneofField(mt, &oneof));
1032 }
1033 #endif // NDEBUG
1034 *op = kUpb_DecodeOp_UnknownField;
1035 }
1036
1037 UPB_FORCEINLINE
_upb_Decoder_MaybeVerifyUtf8(upb_Decoder * d,const upb_MiniTableField * field,int * op)1038 void _upb_Decoder_MaybeVerifyUtf8(upb_Decoder* d,
1039 const upb_MiniTableField* field, int* op) {
1040 if ((field->UPB_ONLYBITS(mode) & kUpb_LabelFlags_IsAlternate) &&
1041 UPB_UNLIKELY(d->options & kUpb_DecodeOption_AlwaysValidateUtf8))
1042 *op = kUpb_DecodeOp_String;
1043 }
1044
_upb_Decoder_GetDelimitedOp(upb_Decoder * d,const upb_MiniTable * mt,const upb_MiniTableField * field)1045 static int _upb_Decoder_GetDelimitedOp(upb_Decoder* d, const upb_MiniTable* mt,
1046 const upb_MiniTableField* field) {
1047 enum { kRepeatedBase = 19 };
1048
1049 static const int8_t kDelimitedOps[] = {
1050 // For non-repeated field type.
1051 [kUpb_FakeFieldType_FieldNotFound] =
1052 kUpb_DecodeOp_UnknownField, // Field not found.
1053 [kUpb_FieldType_Double] = kUpb_DecodeOp_UnknownField,
1054 [kUpb_FieldType_Float] = kUpb_DecodeOp_UnknownField,
1055 [kUpb_FieldType_Int64] = kUpb_DecodeOp_UnknownField,
1056 [kUpb_FieldType_UInt64] = kUpb_DecodeOp_UnknownField,
1057 [kUpb_FieldType_Int32] = kUpb_DecodeOp_UnknownField,
1058 [kUpb_FieldType_Fixed64] = kUpb_DecodeOp_UnknownField,
1059 [kUpb_FieldType_Fixed32] = kUpb_DecodeOp_UnknownField,
1060 [kUpb_FieldType_Bool] = kUpb_DecodeOp_UnknownField,
1061 [kUpb_FieldType_String] = kUpb_DecodeOp_String,
1062 [kUpb_FieldType_Group] = kUpb_DecodeOp_UnknownField,
1063 [kUpb_FieldType_Message] = kUpb_DecodeOp_SubMessage,
1064 [kUpb_FieldType_Bytes] = kUpb_DecodeOp_Bytes,
1065 [kUpb_FieldType_UInt32] = kUpb_DecodeOp_UnknownField,
1066 [kUpb_FieldType_Enum] = kUpb_DecodeOp_UnknownField,
1067 [kUpb_FieldType_SFixed32] = kUpb_DecodeOp_UnknownField,
1068 [kUpb_FieldType_SFixed64] = kUpb_DecodeOp_UnknownField,
1069 [kUpb_FieldType_SInt32] = kUpb_DecodeOp_UnknownField,
1070 [kUpb_FieldType_SInt64] = kUpb_DecodeOp_UnknownField,
1071 [kUpb_FakeFieldType_MessageSetItem] = kUpb_DecodeOp_UnknownField,
1072 // For repeated field type.
1073 [kRepeatedBase + kUpb_FieldType_Double] = OP_FIXPCK_LG2(3),
1074 [kRepeatedBase + kUpb_FieldType_Float] = OP_FIXPCK_LG2(2),
1075 [kRepeatedBase + kUpb_FieldType_Int64] = OP_VARPCK_LG2(3),
1076 [kRepeatedBase + kUpb_FieldType_UInt64] = OP_VARPCK_LG2(3),
1077 [kRepeatedBase + kUpb_FieldType_Int32] = OP_VARPCK_LG2(2),
1078 [kRepeatedBase + kUpb_FieldType_Fixed64] = OP_FIXPCK_LG2(3),
1079 [kRepeatedBase + kUpb_FieldType_Fixed32] = OP_FIXPCK_LG2(2),
1080 [kRepeatedBase + kUpb_FieldType_Bool] = OP_VARPCK_LG2(0),
1081 [kRepeatedBase + kUpb_FieldType_String] = kUpb_DecodeOp_String,
1082 [kRepeatedBase + kUpb_FieldType_Group] = kUpb_DecodeOp_SubMessage,
1083 [kRepeatedBase + kUpb_FieldType_Message] = kUpb_DecodeOp_SubMessage,
1084 [kRepeatedBase + kUpb_FieldType_Bytes] = kUpb_DecodeOp_Bytes,
1085 [kRepeatedBase + kUpb_FieldType_UInt32] = OP_VARPCK_LG2(2),
1086 [kRepeatedBase + kUpb_FieldType_Enum] = kUpb_DecodeOp_PackedEnum,
1087 [kRepeatedBase + kUpb_FieldType_SFixed32] = OP_FIXPCK_LG2(2),
1088 [kRepeatedBase + kUpb_FieldType_SFixed64] = OP_FIXPCK_LG2(3),
1089 [kRepeatedBase + kUpb_FieldType_SInt32] = OP_VARPCK_LG2(2),
1090 [kRepeatedBase + kUpb_FieldType_SInt64] = OP_VARPCK_LG2(3),
1091 // Omitting kUpb_FakeFieldType_MessageSetItem, because we never emit a
1092 // repeated msgset type
1093 };
1094
1095 int ndx = field->UPB_PRIVATE(descriptortype);
1096 if (upb_MiniTableField_IsArray(field)) ndx += kRepeatedBase;
1097 int op = kDelimitedOps[ndx];
1098
1099 if (op == kUpb_DecodeOp_SubMessage) {
1100 _upb_Decoder_CheckUnlinked(d, mt, field, &op);
1101 } else if (op == kUpb_DecodeOp_Bytes) {
1102 _upb_Decoder_MaybeVerifyUtf8(d, field, &op);
1103 }
1104
1105 return op;
1106 }
1107
1108 UPB_FORCEINLINE
_upb_Decoder_DecodeWireValue(upb_Decoder * d,const char * ptr,const upb_MiniTable * mt,const upb_MiniTableField * field,int wire_type,wireval * val,int * op)1109 const char* _upb_Decoder_DecodeWireValue(upb_Decoder* d, const char* ptr,
1110 const upb_MiniTable* mt,
1111 const upb_MiniTableField* field,
1112 int wire_type, wireval* val, int* op) {
1113 static const unsigned kFixed32OkMask = (1 << kUpb_FieldType_Float) |
1114 (1 << kUpb_FieldType_Fixed32) |
1115 (1 << kUpb_FieldType_SFixed32);
1116
1117 static const unsigned kFixed64OkMask = (1 << kUpb_FieldType_Double) |
1118 (1 << kUpb_FieldType_Fixed64) |
1119 (1 << kUpb_FieldType_SFixed64);
1120
1121 switch (wire_type) {
1122 case kUpb_WireType_Varint:
1123 ptr = _upb_Decoder_DecodeVarint(d, ptr, &val->uint64_val);
1124 *op = _upb_Decoder_GetVarintOp(field);
1125 _upb_Decoder_Munge(field->UPB_PRIVATE(descriptortype), val);
1126 return ptr;
1127 case kUpb_WireType_32Bit:
1128 *op = kUpb_DecodeOp_Scalar4Byte;
1129 if (((1 << field->UPB_PRIVATE(descriptortype)) & kFixed32OkMask) == 0) {
1130 *op = kUpb_DecodeOp_UnknownField;
1131 }
1132 return upb_WireReader_ReadFixed32(ptr, &val->uint32_val);
1133 case kUpb_WireType_64Bit:
1134 *op = kUpb_DecodeOp_Scalar8Byte;
1135 if (((1 << field->UPB_PRIVATE(descriptortype)) & kFixed64OkMask) == 0) {
1136 *op = kUpb_DecodeOp_UnknownField;
1137 }
1138 return upb_WireReader_ReadFixed64(ptr, &val->uint64_val);
1139 case kUpb_WireType_Delimited:
1140 ptr = upb_Decoder_DecodeSize(d, ptr, &val->size);
1141 *op = _upb_Decoder_GetDelimitedOp(d, mt, field);
1142 return ptr;
1143 case kUpb_WireType_StartGroup:
1144 val->uint32_val = field->UPB_PRIVATE(number);
1145 if (field->UPB_PRIVATE(descriptortype) == kUpb_FieldType_Group) {
1146 *op = kUpb_DecodeOp_SubMessage;
1147 _upb_Decoder_CheckUnlinked(d, mt, field, op);
1148 } else if (field->UPB_PRIVATE(descriptortype) ==
1149 kUpb_FakeFieldType_MessageSetItem) {
1150 *op = kUpb_DecodeOp_MessageSetItem;
1151 } else {
1152 *op = kUpb_DecodeOp_UnknownField;
1153 }
1154 return ptr;
1155 default:
1156 break;
1157 }
1158 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
1159 }
1160
1161 UPB_FORCEINLINE
_upb_Decoder_DecodeKnownField(upb_Decoder * d,const char * ptr,upb_Message * msg,const upb_MiniTable * layout,const upb_MiniTableField * field,int op,wireval * val)1162 const char* _upb_Decoder_DecodeKnownField(upb_Decoder* d, const char* ptr,
1163 upb_Message* msg,
1164 const upb_MiniTable* layout,
1165 const upb_MiniTableField* field,
1166 int op, wireval* val) {
1167 const upb_MiniTableSubInternal* subs = layout->UPB_PRIVATE(subs);
1168 uint8_t mode = field->UPB_PRIVATE(mode);
1169 upb_MiniTableSubInternal ext_sub;
1170
1171 if (UPB_UNLIKELY(mode & kUpb_LabelFlags_IsExtension)) {
1172 const upb_MiniTableExtension* ext_layout =
1173 (const upb_MiniTableExtension*)field;
1174 upb_Extension* ext = UPB_PRIVATE(_upb_Message_GetOrCreateExtension)(
1175 msg, ext_layout, &d->arena);
1176 if (UPB_UNLIKELY(!ext)) {
1177 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
1178 }
1179 d->unknown_msg = msg;
1180 msg = (upb_Message*)&ext->data;
1181 if (upb_MiniTableField_IsSubMessage(&ext->ext->UPB_PRIVATE(field))) {
1182 ext_sub.UPB_PRIVATE(submsg) =
1183 &ext->ext->UPB_PRIVATE(sub).UPB_PRIVATE(submsg);
1184 } else {
1185 ext_sub.UPB_PRIVATE(subenum) =
1186 ext->ext->UPB_PRIVATE(sub).UPB_PRIVATE(subenum);
1187 }
1188 subs = &ext_sub;
1189 }
1190
1191 switch (mode & kUpb_FieldMode_Mask) {
1192 case kUpb_FieldMode_Array:
1193 return _upb_Decoder_DecodeToArray(d, ptr, msg, subs, field, val, op);
1194 case kUpb_FieldMode_Map:
1195 return _upb_Decoder_DecodeToMap(d, ptr, msg, subs, field, val);
1196 case kUpb_FieldMode_Scalar:
1197 return _upb_Decoder_DecodeToSubMessage(d, ptr, msg, subs, field, val, op);
1198 default:
1199 UPB_UNREACHABLE();
1200 }
1201 }
1202
_upb_Decoder_ReverseSkipVarint(const char * ptr,uint32_t val)1203 static const char* _upb_Decoder_ReverseSkipVarint(const char* ptr,
1204 uint32_t val) {
1205 uint32_t seen = 0;
1206 do {
1207 ptr--;
1208 seen <<= 7;
1209 seen |= *ptr & 0x7f;
1210 } while (seen != val);
1211 return ptr;
1212 }
1213
_upb_Decoder_DecodeUnknownField(upb_Decoder * d,const char * ptr,upb_Message * msg,int field_number,int wire_type,wireval val)1214 static const char* _upb_Decoder_DecodeUnknownField(upb_Decoder* d,
1215 const char* ptr,
1216 upb_Message* msg,
1217 int field_number,
1218 int wire_type, wireval val) {
1219 if (field_number == 0) _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_Malformed);
1220
1221 // Since unknown fields are the uncommon case, we do a little extra work here
1222 // to walk backwards through the buffer to find the field start. This frees
1223 // up a register in the fast paths (when the field is known), which leads to
1224 // significant speedups in benchmarks.
1225 const char* start = ptr;
1226
1227 if (wire_type == kUpb_WireType_Delimited) ptr += val.size;
1228 if (msg) {
1229 switch (wire_type) {
1230 case kUpb_WireType_Varint:
1231 case kUpb_WireType_Delimited:
1232 start--;
1233 while (start[-1] & 0x80) start--;
1234 break;
1235 case kUpb_WireType_32Bit:
1236 start -= 4;
1237 break;
1238 case kUpb_WireType_64Bit:
1239 start -= 8;
1240 break;
1241 default:
1242 break;
1243 }
1244
1245 assert(start == d->debug_valstart);
1246 uint32_t tag = ((uint32_t)field_number << 3) | wire_type;
1247 start = _upb_Decoder_ReverseSkipVarint(start, tag);
1248 assert(start == d->debug_tagstart);
1249
1250 if (wire_type == kUpb_WireType_StartGroup) {
1251 d->unknown = start;
1252 d->unknown_msg = msg;
1253 ptr = _upb_Decoder_DecodeUnknownGroup(d, ptr, field_number);
1254 start = d->unknown;
1255 d->unknown = NULL;
1256 }
1257 if (!UPB_PRIVATE(_upb_Message_AddUnknown)(msg, start, ptr - start,
1258 &d->arena)) {
1259 _upb_Decoder_ErrorJmp(d, kUpb_DecodeStatus_OutOfMemory);
1260 }
1261 } else if (wire_type == kUpb_WireType_StartGroup) {
1262 ptr = _upb_Decoder_DecodeUnknownGroup(d, ptr, field_number);
1263 }
1264 return ptr;
1265 }
1266
1267 UPB_NOINLINE
_upb_Decoder_DecodeMessage(upb_Decoder * d,const char * ptr,upb_Message * msg,const upb_MiniTable * layout)1268 static const char* _upb_Decoder_DecodeMessage(upb_Decoder* d, const char* ptr,
1269 upb_Message* msg,
1270 const upb_MiniTable* layout) {
1271 int last_field_index = 0;
1272
1273 #if UPB_FASTTABLE
1274 // The first time we want to skip fast dispatch, because we may have just been
1275 // invoked by the fast parser to handle a case that it bailed on.
1276 if (!_upb_Decoder_IsDone(d, &ptr)) goto nofast;
1277 #endif
1278
1279 while (!_upb_Decoder_IsDone(d, &ptr)) {
1280 uint32_t tag;
1281 const upb_MiniTableField* field;
1282 int field_number;
1283 int wire_type;
1284 wireval val;
1285 int op;
1286
1287 if (_upb_Decoder_TryFastDispatch(d, &ptr, msg, layout)) break;
1288
1289 #if UPB_FASTTABLE
1290 nofast:
1291 #endif
1292
1293 #ifndef NDEBUG
1294 d->debug_tagstart = ptr;
1295 #endif
1296
1297 UPB_ASSERT(ptr < d->input.limit_ptr);
1298 ptr = _upb_Decoder_DecodeTag(d, ptr, &tag);
1299 field_number = tag >> 3;
1300 wire_type = tag & 7;
1301
1302 #ifndef NDEBUG
1303 d->debug_valstart = ptr;
1304 #endif
1305
1306 if (wire_type == kUpb_WireType_EndGroup) {
1307 d->end_group = field_number;
1308 return ptr;
1309 }
1310
1311 field = _upb_Decoder_FindField(d, layout, field_number, &last_field_index);
1312 ptr = _upb_Decoder_DecodeWireValue(d, ptr, layout, field, wire_type, &val,
1313 &op);
1314
1315 if (op >= 0) {
1316 ptr = _upb_Decoder_DecodeKnownField(d, ptr, msg, layout, field, op, &val);
1317 } else {
1318 switch (op) {
1319 case kUpb_DecodeOp_UnknownField:
1320 ptr = _upb_Decoder_DecodeUnknownField(d, ptr, msg, field_number,
1321 wire_type, val);
1322 break;
1323 case kUpb_DecodeOp_MessageSetItem:
1324 ptr = upb_Decoder_DecodeMessageSetItem(d, ptr, msg, layout);
1325 break;
1326 }
1327 }
1328 }
1329
1330 return UPB_UNLIKELY(layout && layout->UPB_PRIVATE(required_count))
1331 ? _upb_Decoder_CheckRequired(d, ptr, msg, layout)
1332 : ptr;
1333 }
1334
_upb_FastDecoder_DecodeGeneric(struct upb_Decoder * d,const char * ptr,upb_Message * msg,intptr_t table,uint64_t hasbits,uint64_t data)1335 const char* _upb_FastDecoder_DecodeGeneric(struct upb_Decoder* d,
1336 const char* ptr, upb_Message* msg,
1337 intptr_t table, uint64_t hasbits,
1338 uint64_t data) {
1339 (void)data;
1340 *(uint32_t*)msg |= hasbits;
1341 return _upb_Decoder_DecodeMessage(d, ptr, msg, decode_totablep(table));
1342 }
1343
_upb_Decoder_DecodeTop(struct upb_Decoder * d,const char * buf,upb_Message * msg,const upb_MiniTable * m)1344 static upb_DecodeStatus _upb_Decoder_DecodeTop(struct upb_Decoder* d,
1345 const char* buf,
1346 upb_Message* msg,
1347 const upb_MiniTable* m) {
1348 if (!_upb_Decoder_TryFastDispatch(d, &buf, msg, m)) {
1349 _upb_Decoder_DecodeMessage(d, buf, msg, m);
1350 }
1351 if (d->end_group != DECODE_NOGROUP) return kUpb_DecodeStatus_Malformed;
1352 if (d->missing_required) return kUpb_DecodeStatus_MissingRequired;
1353 return kUpb_DecodeStatus_Ok;
1354 }
1355
1356 UPB_NOINLINE
_upb_Decoder_IsDoneFallback(upb_EpsCopyInputStream * e,const char * ptr,int overrun)1357 const char* _upb_Decoder_IsDoneFallback(upb_EpsCopyInputStream* e,
1358 const char* ptr, int overrun) {
1359 return _upb_EpsCopyInputStream_IsDoneFallbackInline(
1360 e, ptr, overrun, _upb_Decoder_BufferFlipCallback);
1361 }
1362
upb_Decoder_Decode(upb_Decoder * const decoder,const char * const buf,upb_Message * const msg,const upb_MiniTable * const m,upb_Arena * const arena)1363 static upb_DecodeStatus upb_Decoder_Decode(upb_Decoder* const decoder,
1364 const char* const buf,
1365 upb_Message* const msg,
1366 const upb_MiniTable* const m,
1367 upb_Arena* const arena) {
1368 if (UPB_SETJMP(decoder->err) == 0) {
1369 decoder->status = _upb_Decoder_DecodeTop(decoder, buf, msg, m);
1370 } else {
1371 UPB_ASSERT(decoder->status != kUpb_DecodeStatus_Ok);
1372 }
1373
1374 UPB_PRIVATE(_upb_Arena_SwapOut)(arena, &decoder->arena);
1375
1376 return decoder->status;
1377 }
1378
upb_Decode(const char * buf,size_t size,upb_Message * msg,const upb_MiniTable * mt,const upb_ExtensionRegistry * extreg,int options,upb_Arena * arena)1379 upb_DecodeStatus upb_Decode(const char* buf, size_t size, upb_Message* msg,
1380 const upb_MiniTable* mt,
1381 const upb_ExtensionRegistry* extreg, int options,
1382 upb_Arena* arena) {
1383 UPB_ASSERT(!upb_Message_IsFrozen(msg));
1384 upb_Decoder decoder;
1385 unsigned depth = (unsigned)options >> 16;
1386
1387 upb_EpsCopyInputStream_Init(&decoder.input, &buf, size,
1388 options & kUpb_DecodeOption_AliasString);
1389
1390 decoder.extreg = extreg;
1391 decoder.unknown = NULL;
1392 decoder.depth = depth ? depth : kUpb_WireFormat_DefaultDepthLimit;
1393 decoder.end_group = DECODE_NOGROUP;
1394 decoder.options = (uint16_t)options;
1395 decoder.missing_required = false;
1396 decoder.status = kUpb_DecodeStatus_Ok;
1397
1398 // Violating the encapsulation of the arena for performance reasons.
1399 // This is a temporary arena that we swap into and swap out of when we are
1400 // done. The temporary arena only needs to be able to handle allocation,
1401 // not fuse or free, so it does not need many of the members to be initialized
1402 // (particularly parent_or_count).
1403 UPB_PRIVATE(_upb_Arena_SwapIn)(&decoder.arena, arena);
1404
1405 return upb_Decoder_Decode(&decoder, buf, msg, mt, arena);
1406 }
1407
upb_DecodeLengthPrefixed(const char * buf,size_t size,upb_Message * msg,size_t * num_bytes_read,const upb_MiniTable * mt,const upb_ExtensionRegistry * extreg,int options,upb_Arena * arena)1408 upb_DecodeStatus upb_DecodeLengthPrefixed(const char* buf, size_t size,
1409 upb_Message* msg,
1410 size_t* num_bytes_read,
1411 const upb_MiniTable* mt,
1412 const upb_ExtensionRegistry* extreg,
1413 int options, upb_Arena* arena) {
1414 // To avoid needing to make a Decoder just to decode the initial length,
1415 // hand-decode the leading varint for the message length here.
1416 uint64_t msg_len = 0;
1417 for (size_t i = 0;; ++i) {
1418 if (i >= size || i > 9) {
1419 return kUpb_DecodeStatus_Malformed;
1420 }
1421 uint64_t b = *buf;
1422 buf++;
1423 msg_len += (b & 0x7f) << (i * 7);
1424 if ((b & 0x80) == 0) {
1425 *num_bytes_read = i + 1 + msg_len;
1426 break;
1427 }
1428 }
1429
1430 // If the total number of bytes we would read (= the bytes from the varint
1431 // plus however many bytes that varint says we should read) is larger then the
1432 // input buffer then error as malformed.
1433 if (*num_bytes_read > size) {
1434 return kUpb_DecodeStatus_Malformed;
1435 }
1436 if (msg_len > INT32_MAX) {
1437 return kUpb_DecodeStatus_Malformed;
1438 }
1439
1440 return upb_Decode(buf, msg_len, msg, mt, extreg, options, arena);
1441 }
1442
upb_DecodeStatus_String(upb_DecodeStatus status)1443 const char* upb_DecodeStatus_String(upb_DecodeStatus status) {
1444 switch (status) {
1445 case kUpb_DecodeStatus_Ok:
1446 return "Ok";
1447 case kUpb_DecodeStatus_Malformed:
1448 return "Wire format was corrupt";
1449 case kUpb_DecodeStatus_OutOfMemory:
1450 return "Arena alloc failed";
1451 case kUpb_DecodeStatus_BadUtf8:
1452 return "String field had bad UTF-8";
1453 case kUpb_DecodeStatus_MaxDepthExceeded:
1454 return "Exceeded upb_DecodeOptions_MaxDepth";
1455 case kUpb_DecodeStatus_MissingRequired:
1456 return "Missing required field";
1457 case kUpb_DecodeStatus_UnlinkedSubMessage:
1458 return "Unlinked sub-message field was present";
1459 default:
1460 return "Unknown decode status";
1461 }
1462 }
1463
1464 #undef OP_FIXPCK_LG2
1465 #undef OP_VARPCK_LG2
1466