google-protobuf 4.35.0-x86_64-linux-gnu → 4.36.0.rc.1-x86_64-linux-gnu

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -46,6 +46,12 @@
46
46
  #define UPB_HAS_ATTRIBUTE(x) 0
47
47
  #endif
48
48
 
49
+ #ifdef __has_c_attribute
50
+ #define UPB_HAS_C_ATTRIBUTE(x) __has_c_attribute(x)
51
+ #else
52
+ #define UPB_HAS_C_ATTRIBUTE(x) 0
53
+ #endif
54
+
49
55
  #if defined(__cplusplus) && defined(__has_cpp_attribute)
50
56
  // NOTE: requiring __cplusplus above should not be necessary, but
51
57
  // works around https://bugs.llvm.org/show_bug.cgi?id=23435.
@@ -284,12 +290,23 @@ Error, UINTPTR_MAX is undefined
284
290
  #define UPB_PRINTF(str, first_vararg)
285
291
  #endif
286
292
 
287
- #if defined(__clang__)
293
+ #if UPB_HAS_ATTRIBUTE(noderef)
288
294
  #define UPB_NODEREF __attribute__((noderef))
289
295
  #else
290
296
  #define UPB_NODEREF
291
297
  #endif
292
298
 
299
+ // Will be defined properly once call sites are updated
300
+ #if false && UPB_HAS_C_ATTRIBUTE(nodiscard)
301
+ #define UPB_NODISCARD [[nodiscard]]
302
+ #elif false && UPB_HAS_ATTRIBUTE(warn_unused_result)
303
+ #define UPB_NODISCARD __attribute__((warn_unused_result))
304
+ #elif false && UPB_HAS_CPP_ATTRIBUTE(nodiscard)
305
+ #define UPB_NODISCARD [[nodiscard]]
306
+ #else
307
+ #define UPB_NODISCARD
308
+ #endif
309
+
293
310
  #define UPB_MAX(x, y) ((x) > (y) ? (x) : (y))
294
311
  #define UPB_MIN(x, y) ((x) < (y) ? (x) : (y))
295
312
 
@@ -338,21 +355,42 @@ Error, UINTPTR_MAX is undefined
338
355
  #endif
339
356
 
340
357
  #if defined(__GNUC__) || defined(__clang__)
341
- #define UPB_UNREACHABLE() \
342
- do { \
343
- assert(0); \
344
- __builtin_unreachable(); \
358
+ #define UPB_PRETTY_FUNCTION __PRETTY_FUNCTION__
359
+ #else
360
+ #define UPB_PRETTY_FUNCTION NULL
361
+ #endif
362
+
363
+ #ifdef __cplusplus
364
+ extern "C" {
365
+ #endif
366
+ UPB_NORETURN void _upb_UnreachableFailure(const char* file, int line,
367
+ const char* function_name);
368
+ #if !defined(NDEBUG)
369
+ #define UPB_UNREACHABLE_FAILURE() \
370
+ _upb_UnreachableFailure(__FILE__, __LINE__, UPB_PRETTY_FUNCTION);
371
+ #else
372
+ #define UPB_UNREACHABLE_FAILURE()
373
+ #endif
374
+ #ifdef __cplusplus
375
+ } /* extern "C" */
376
+ #endif
377
+
378
+ #if defined(__GNUC__) || defined(__clang__)
379
+ #define UPB_UNREACHABLE() \
380
+ do { \
381
+ UPB_UNREACHABLE_FAILURE(); \
382
+ __builtin_unreachable(); \
345
383
  } while (0)
346
384
  #elif defined(_MSC_VER)
347
- #define UPB_UNREACHABLE() \
348
- do { \
349
- assert(0); \
350
- __assume(0); \
385
+ #define UPB_UNREACHABLE() \
386
+ do { \
387
+ UPB_UNREACHABLE_FAILURE(); \
388
+ __assume(0); \
351
389
  } while (0)
352
390
  #else
353
- #define UPB_UNREACHABLE() \
354
- do { \
355
- assert(0); \
391
+ #define UPB_UNREACHABLE() \
392
+ do { \
393
+ UPB_UNREACHABLE_FAILURE(); \
356
394
  } while (0)
357
395
  #endif
358
396
 
@@ -447,21 +485,10 @@ Error, UINTPTR_MAX is undefined
447
485
  #define UPB_ARM64_BTI_DEFAULT 0
448
486
  #endif
449
487
 
450
- /* This check is not fully robust: it does not require that we have "musttail"
451
- * support available. We need tail calls to avoid consuming arbitrary amounts
452
- * of stack space.
453
- *
454
- * GCC/Clang can mostly be trusted to generate tail calls as long as
455
- * optimization is enabled, but, debug builds will not generate tail calls
456
- * unless "musttail" is available.
457
- *
458
- * We should probably either:
459
- * 1. require that the compiler supports musttail.
460
- * 2. add some fallback code for when musttail isn't available (ie. return
461
- * instead of tail calling). This is safe and portable, but this comes at
462
- * a CPU cost.
463
- */
464
- #if (defined(__x86_64__) || defined(__aarch64__)) && defined(__GNUC__)
488
+ /* aarch64 supports big and little endian modes; fasttable performs multibyte
489
+ * tag loads assumes the tag of a varint is in the low bits. */
490
+ #if (defined(__x86_64__) || defined(__AARCH64EL__)) && \
491
+ UPB_HAS_ATTRIBUTE(preserve_none) && UPB_HAS_ATTRIBUTE(musttail)
465
492
  #define UPB_FASTTABLE_SUPPORTED 1
466
493
  #else
467
494
  #define UPB_FASTTABLE_SUPPORTED 0
@@ -472,7 +499,7 @@ Error, UINTPTR_MAX is undefined
472
499
  * for example for testing or benchmarking. */
473
500
  #if defined(UPB_ENABLE_FASTTABLE)
474
501
  #if !UPB_FASTTABLE_SUPPORTED
475
- #error fasttable is x86-64/ARM64 only and requires GCC or Clang.
502
+ #error fasttable is x86-64/ARM64le only and requires preserve_none and musttail.
476
503
  #endif
477
504
  #define UPB_FASTTABLE 1
478
505
  /* Define UPB_TRY_ENABLE_FASTTABLE to use fasttable if possible.
@@ -663,10 +690,10 @@ Error, UINTPTR_MAX is undefined
663
690
  * to prevent optimizers from removing the constructor. Our solution is to
664
691
  * create a dummy exported weak symbol that prevent this stripping.
665
692
  */
666
- #pragma section(".CRT$XCU", long, read)
693
+ #pragma section(".CRT$XCT", read)
667
694
  #define UPB_CONSTRUCTOR(name, unique_name) \
668
695
  static void __cdecl UPB_PRIVATE(name)(void); \
669
- __declspec(allocate(".CRT$XCU"), selectany) void( \
696
+ __declspec(allocate(".CRT$XCT"), selectany) void( \
670
697
  __cdecl * UPB_PRIVATE(name##_))(void) = UPB_PRIVATE(name); \
671
698
  __declspec(selectany, dllexport) void* UPB_PRIVATE(name##_force_linkage) = \
672
699
  &UPB_PRIVATE(name##_); \
@@ -710,7 +737,7 @@ Error, UINTPTR_MAX is undefined
710
737
  __asm__(".private_extern _" #to); \
711
738
  __asm__(".set _" #to ", _" #from);
712
739
 
713
- #elif defined(__ELF__)
740
+ #elif defined(__ELF__) || defined(__wasm__)
714
741
 
715
742
  // On ELF, weak aliases work properly, so we can have all weak MiniTables point
716
743
  // to the same empty singleton MiniTable. This reduces code size if many
@@ -739,12 +766,6 @@ Error, UINTPTR_MAX is undefined
739
766
  #define UPB_WEAK_ALIAS(type, from, to) weak_alias_not_supported_on_this_platform
740
767
  #define UPB_STRONG_ALIAS(type, from, to) \
741
768
  strong_alias_not_supported_on_this_platform
742
- #endif
743
-
744
- // Future versions of upb will include breaking changes to some APIs.
745
- // This macro can be set to enable these API changes ahead of time, so that
746
- // user code can be updated before upgrading versions of protobuf.
747
- #ifdef UPB_FUTURE_BREAKING_CHANGES
748
769
 
749
770
  #endif
750
771
 
@@ -908,7 +929,7 @@ struct upb_alloc {
908
929
  upb_alloc_func* func;
909
930
  };
910
931
 
911
- UPB_INLINE void* upb_malloc(upb_alloc* alloc, size_t size) {
932
+ UPB_NODISCARD UPB_INLINE void* upb_malloc(upb_alloc* alloc, size_t size) {
912
933
  UPB_ASSERT(alloc);
913
934
  return alloc->func(alloc, NULL, 0, size, NULL);
914
935
  }
@@ -927,8 +948,8 @@ UPB_INLINE upb_SizedPtr upb_SizeReturningMalloc(upb_alloc* alloc, size_t size) {
927
948
  return result;
928
949
  }
929
950
 
930
- UPB_INLINE void* upb_realloc(upb_alloc* alloc, void* ptr, size_t oldsize,
931
- size_t size) {
951
+ UPB_NODISCARD UPB_INLINE void* upb_realloc(upb_alloc* alloc, void* ptr,
952
+ size_t oldsize, size_t size) {
932
953
  UPB_ASSERT(alloc);
933
954
  return alloc->func(alloc, ptr, oldsize, size, NULL);
934
955
  }
@@ -952,11 +973,12 @@ extern upb_alloc upb_alloc_global;
952
973
  * We still get benefit because we can put custom logic into our global
953
974
  * allocator, like injecting out-of-memory faults in debug/testing builds. */
954
975
 
955
- UPB_INLINE void* upb_gmalloc(size_t size) {
976
+ UPB_NODISCARD UPB_INLINE void* upb_gmalloc(size_t size) {
956
977
  return upb_malloc(&upb_alloc_global, size);
957
978
  }
958
979
 
959
- UPB_INLINE void* upb_grealloc(void* ptr, size_t oldsize, size_t size) {
980
+ UPB_NODISCARD UPB_INLINE void* upb_grealloc(void* ptr, size_t oldsize,
981
+ size_t size) {
960
982
  return upb_realloc(&upb_alloc_global, ptr, oldsize, size);
961
983
  }
962
984
 
@@ -1252,9 +1274,9 @@ UPB_API_INLINE void upb_Arena_ShrinkLast(struct upb_Arena* a, void* ptr,
1252
1274
  // We can't reclaim any memory, but we need to verify that `ptr` really
1253
1275
  // does represent the most recent allocation.
1254
1276
  #ifndef NDEBUG
1255
- bool _upb_Arena_WasLastAlloc(struct upb_Arena * a, void* ptr,
1256
- size_t oldsize);
1257
- UPB_ASSERT(_upb_Arena_WasLastAlloc(a, ptr, oldsize));
1277
+ bool _upb_Arena_WasLastAllocFromPreviousBlock(struct upb_Arena * a,
1278
+ void* ptr, size_t oldsize);
1279
+ UPB_ASSERT(_upb_Arena_WasLastAllocFromPreviousBlock(a, ptr, oldsize));
1258
1280
  #endif
1259
1281
  }
1260
1282
  }
@@ -1308,6 +1330,58 @@ UPB_API_INLINE void* upb_Arena_Realloc(struct upb_Arena* a, void* ptr,
1308
1330
  return ret;
1309
1331
  }
1310
1332
 
1333
+ // Returns the next block size to allocate for the arena based on exponential
1334
+ // growth and size hint.
1335
+ size_t UPB_PRIVATE(_upb_Arena_NextBlockSize)(struct upb_Arena* a, size_t span,
1336
+ bool* one_off);
1337
+
1338
+ // Updates the arena's growth state based on the block size actually allocated.
1339
+ void UPB_PRIVATE(_upb_Arena_UpdateGrowthState)(struct upb_Arena* a, size_t span,
1340
+ size_t block_size, bool one_off);
1341
+
1342
+ // Allocates a block for the arena of at least the given size, but does not add
1343
+ // it to the arena. The block must either be added to the arena or manually
1344
+ // freed, otherwise memory will be leaked.
1345
+ //
1346
+ // Returns the allocated block (or NULL on failure), and writes the actual size
1347
+ // of the block to size.
1348
+ void* UPB_PRIVATE(_upb_Arena_AllocBlock)(struct upb_Arena* a, size_t* size);
1349
+
1350
+ // Adds a block previously allocated with _upb_Arena_AllocBlock() to the arena.
1351
+ // This will cause it to be owned by the arena and freed when the arena is
1352
+ // freed.
1353
+ //
1354
+ // Note that this call does *not* cause the block to be used for arena
1355
+ // allocations. Call _upb_Arena_UseBlock() to do that.
1356
+ //
1357
+ // This operation cannot be undone, so the caller should not call it until they
1358
+ // are sure that the block will be useful to the arena.
1359
+ void UPB_PRIVATE(_upb_Arena_AddBlock)(struct upb_Arena* a, void* block);
1360
+
1361
+ // Frees a block previously allocated with _upb_Arena_AllocBlock. This is only
1362
+ // necessary if the block ends up not being useful to the arena.
1363
+ void UPB_PRIVATE(_upb_Arena_FreeBlock)(struct upb_Arena* a, void* block);
1364
+
1365
+ // Sets the arena's current block to the given block. Subsequent allocations
1366
+ // may be made from this block.
1367
+ //
1368
+ // The given memory must be either:
1369
+ // - The arena block most recently returned by _upb_Arena_AllocBlock, or
1370
+ // - A block that was just stolen from the arena using _upb_Arena_Steal.
1371
+ //
1372
+ // After this call, the memory may only be used by the arena -- it is poisoned
1373
+ // against further use by the caller.
1374
+ //
1375
+ // Note: if the arena determines that this block is smaller than the block it
1376
+ // currently has, it may decide to not use the block.
1377
+ void UPB_PRIVATE(_upb_Arena_UseBlock)(struct upb_Arena* a, void* ptr,
1378
+ size_t size);
1379
+
1380
+ // Steals all available memory from the current arena block, but only if at
1381
+ // least `size` bytes are available. The number of bytes stolen is written to
1382
+ // size. The memory will be unpoisoned and ready for use.
1383
+ void* UPB_PRIVATE(_upb_Arena_Steal)(struct upb_Arena* a, size_t* size);
1384
+
1311
1385
  #ifdef __cplusplus
1312
1386
  } /* extern "C" */
1313
1387
  #endif
@@ -1333,7 +1407,8 @@ extern "C" {
1333
1407
  // no initial block, |n| is a hint of the size that should be allocated for the
1334
1408
  // first block of the arena, such that `upb_Arena_Malloc(hint)` will not require
1335
1409
  // another call to |alloc|.
1336
- UPB_API upb_Arena* upb_Arena_Init(void* mem, size_t n, upb_alloc* alloc);
1410
+ UPB_NODISCARD UPB_API upb_Arena* upb_Arena_Init(void* mem, size_t n,
1411
+ upb_alloc* alloc);
1337
1412
 
1338
1413
  UPB_API void upb_Arena_Free(upb_Arena* a);
1339
1414
  // Sets the cleanup function for the upb_alloc used by the arena. Only one
@@ -1346,7 +1421,8 @@ UPB_API void upb_Arena_SetAllocCleanup(upb_Arena* a,
1346
1421
  // transitively fused together will be freed until all of them have reached a
1347
1422
  // zero refcount. This operation is safe to use concurrently from multiple
1348
1423
  // threads.
1349
- UPB_API bool upb_Arena_Fuse(const upb_Arena* a, const upb_Arena* b);
1424
+ UPB_NODISCARD UPB_API bool upb_Arena_Fuse(const upb_Arena* a,
1425
+ const upb_Arena* b);
1350
1426
 
1351
1427
  // This operation is safe to use concurrently from multiple threads.
1352
1428
  UPB_API bool upb_Arena_IsFused(const upb_Arena* a, const upb_Arena* b);
@@ -1391,7 +1467,7 @@ void upb_Arena_DecRefFor(const upb_Arena* a, const void* owner);
1391
1467
  // with any other function on `from`.
1392
1468
  //
1393
1469
  // Returns whether the reference was created successfully.
1394
- bool upb_Arena_RefArena(upb_Arena* from, const upb_Arena* to);
1470
+ UPB_NODISCARD bool upb_Arena_RefArena(upb_Arena* from, const upb_Arena* to);
1395
1471
 
1396
1472
  #ifndef NDEBUG
1397
1473
  // Returns true if upb_Arena_RefArena(from, to) was previously called.
@@ -1420,18 +1496,20 @@ uint32_t upb_Arena_DebugRefCount(const upb_Arena* a);
1420
1496
  bool upb_Arena_HasRefChain(const upb_Arena* from, const upb_Arena* to);
1421
1497
  #endif
1422
1498
 
1423
- UPB_API_INLINE upb_Arena* upb_Arena_New(void) {
1499
+ UPB_NODISCARD UPB_API_INLINE upb_Arena* upb_Arena_New(void) {
1424
1500
  return upb_Arena_Init(NULL, 0, &upb_alloc_global);
1425
1501
  }
1426
1502
 
1427
- UPB_API_INLINE upb_Arena* upb_Arena_NewSized(size_t size_hint) {
1503
+ UPB_NODISCARD UPB_API_INLINE upb_Arena* upb_Arena_NewSized(size_t size_hint) {
1428
1504
  return upb_Arena_Init(NULL, size_hint, &upb_alloc_global);
1429
1505
  }
1430
1506
 
1431
- UPB_API_INLINE void* upb_Arena_Malloc(struct upb_Arena* a, size_t size);
1507
+ UPB_NODISCARD UPB_API_INLINE void* upb_Arena_Malloc(struct upb_Arena* a,
1508
+ size_t size);
1432
1509
 
1433
- UPB_API_INLINE void* upb_Arena_Realloc(upb_Arena* a, void* ptr, size_t oldsize,
1434
- size_t size);
1510
+ UPB_NODISCARD UPB_API_INLINE void* upb_Arena_Realloc(upb_Arena* a, void* ptr,
1511
+ size_t oldsize,
1512
+ size_t size);
1435
1513
 
1436
1514
  static const size_t UPB_PRIVATE(kUpbDefaultMaxBlockSize) =
1437
1515
  UPB_DEFAULT_MAX_BLOCK_SIZE;
@@ -1460,8 +1538,9 @@ UPB_API_INLINE void upb_Arena_ShrinkLast(upb_Arena* a, void* ptr,
1460
1538
  // allocation is unmodified. See also upb_Arena_Realloc.
1461
1539
  // REQUIRES: `size > oldsize`; to shrink, use `upb_Arena_Realloc` or
1462
1540
  // `upb_Arena_ShrinkLast`.
1463
- UPB_API_INLINE bool upb_Arena_TryExtend(upb_Arena* a, void* ptr, size_t oldsize,
1464
- size_t size);
1541
+ UPB_NODISCARD UPB_API_INLINE bool upb_Arena_TryExtend(upb_Arena* a, void* ptr,
1542
+ size_t oldsize,
1543
+ size_t size);
1465
1544
 
1466
1545
  #ifdef UPB_TRACING_ENABLED
1467
1546
  void upb_Arena_SetTraceHandler(void (*initArenaTraceHandler)(const upb_Arena*,
@@ -1604,6 +1683,8 @@ UPB_INLINE bool upb_FieldType_IsPackable(upb_FieldType field_type) {
1604
1683
  extern "C" {
1605
1684
  #endif
1606
1685
 
1686
+ #define _UPB_ARRAY_DEFAULT_INITIAL_SIZE 4
1687
+
1607
1688
  // LINT.IfChange(upb_Array)
1608
1689
 
1609
1690
  // Our internal representation for repeated fields.
@@ -1653,9 +1734,9 @@ UPB_API_INLINE void* upb_Array_MutableDataPtr(struct upb_Array* array) {
1653
1734
  return (void*)upb_Array_DataPtr(array);
1654
1735
  }
1655
1736
 
1656
- UPB_INLINE struct upb_Array* UPB_PRIVATE(_upb_Array_NewMaybeAllowSlow)(
1657
- upb_Arena* arena, size_t init_capacity, int elem_size_lg2,
1658
- bool allow_slow) {
1737
+ UPB_NODISCARD UPB_INLINE struct upb_Array* UPB_PRIVATE(
1738
+ _upb_Array_NewMaybeAllowSlow)(upb_Arena* arena, size_t init_capacity,
1739
+ int elem_size_lg2, bool allow_slow) {
1659
1740
  UPB_ASSERT(elem_size_lg2 != 1);
1660
1741
  UPB_ASSERT(elem_size_lg2 <= 4);
1661
1742
  const size_t array_size =
@@ -1672,27 +1753,26 @@ UPB_INLINE struct upb_Array* UPB_PRIVATE(_upb_Array_NewMaybeAllowSlow)(
1672
1753
  return array;
1673
1754
  }
1674
1755
 
1675
- UPB_INLINE struct upb_Array* UPB_PRIVATE(_upb_Array_New)(upb_Arena* arena,
1676
- size_t init_capacity,
1677
- int elem_size_lg2) {
1756
+ UPB_NODISCARD UPB_INLINE struct upb_Array* UPB_PRIVATE(_upb_Array_New)(
1757
+ upb_Arena* arena, size_t init_capacity, int elem_size_lg2) {
1678
1758
  return UPB_PRIVATE(_upb_Array_NewMaybeAllowSlow)(arena, init_capacity,
1679
1759
  elem_size_lg2, true);
1680
1760
  }
1681
1761
 
1682
- UPB_INLINE struct upb_Array* UPB_PRIVATE(_upb_Array_TryFastNew)(
1762
+ UPB_NODISCARD UPB_INLINE struct upb_Array* UPB_PRIVATE(_upb_Array_TryFastNew)(
1683
1763
  upb_Arena* arena, size_t init_capacity, int elem_size_lg2) {
1684
1764
  return UPB_PRIVATE(_upb_Array_NewMaybeAllowSlow)(arena, init_capacity,
1685
1765
  elem_size_lg2, false);
1686
1766
  }
1687
1767
 
1688
1768
  // Resizes the capacity of the array to be at least min_size.
1689
- bool UPB_PRIVATE(_upb_Array_Realloc)(struct upb_Array* array, size_t min_size,
1690
- upb_Arena* arena);
1769
+ UPB_NODISCARD bool UPB_PRIVATE(_upb_Array_Realloc)(struct upb_Array* array,
1770
+ size_t min_size,
1771
+ upb_Arena* arena);
1691
1772
 
1692
- UPB_FORCEINLINE
1693
- bool UPB_PRIVATE(_upb_Array_TryFastRealloc)(struct upb_Array* array,
1694
- size_t capacity, int elem_size_lg2,
1695
- upb_Arena* arena) {
1773
+ UPB_NODISCARD UPB_FORCEINLINE bool UPB_PRIVATE(_upb_Array_TryFastRealloc)(
1774
+ struct upb_Array* array, size_t capacity, int elem_size_lg2,
1775
+ upb_Arena* arena) {
1696
1776
  size_t old_bytes = array->UPB_PRIVATE(capacity) << elem_size_lg2;
1697
1777
  size_t new_bytes = capacity << elem_size_lg2;
1698
1778
  UPB_ASSUME(new_bytes > old_bytes);
@@ -1701,8 +1781,9 @@ bool UPB_PRIVATE(_upb_Array_TryFastRealloc)(struct upb_Array* array,
1701
1781
  return true;
1702
1782
  }
1703
1783
 
1704
- UPB_API_INLINE bool upb_Array_Reserve(struct upb_Array* array, size_t size,
1705
- upb_Arena* arena) {
1784
+ UPB_NODISCARD UPB_API_INLINE bool upb_Array_Reserve(struct upb_Array* array,
1785
+ size_t size,
1786
+ upb_Arena* arena) {
1706
1787
  UPB_ASSERT(!upb_Array_IsFrozen(array));
1707
1788
  if (array->UPB_PRIVATE(capacity) < size)
1708
1789
  return UPB_PRIVATE(_upb_Array_Realloc)(array, size, arena);
@@ -1710,7 +1791,7 @@ UPB_API_INLINE bool upb_Array_Reserve(struct upb_Array* array, size_t size,
1710
1791
  }
1711
1792
 
1712
1793
  // Resize without initializing new elements.
1713
- UPB_INLINE bool UPB_PRIVATE(_upb_Array_ResizeUninitialized)(
1794
+ UPB_NODISCARD UPB_INLINE bool UPB_PRIVATE(_upb_Array_ResizeUninitialized)(
1714
1795
  struct upb_Array* array, size_t size, upb_Arena* arena) {
1715
1796
  UPB_ASSERT(!upb_Array_IsFrozen(array));
1716
1797
  UPB_ASSERT(size <= array->UPB_ONLYBITS(size) ||
@@ -2283,6 +2364,7 @@ upb_MiniTableField_Type(const upb_MiniTableField* f);
2283
2364
 
2284
2365
  #include <stddef.h>
2285
2366
  #include <stdint.h>
2367
+ #include <string.h>
2286
2368
 
2287
2369
 
2288
2370
  #ifndef UPB_MINI_TABLE_INTERNAL_SUB_H_
@@ -2336,16 +2418,23 @@ UPB_API_INLINE const struct upb_MiniTable* upb_MiniTableSub_Message(
2336
2418
 
2337
2419
  struct upb_Decoder;
2338
2420
  struct upb_Message;
2421
+ struct upb_FastDecoder_Return;
2339
2422
 
2340
- typedef UPB_PRESERVE_NONE const char* _upb_FieldParser(
2423
+ typedef UPB_PRESERVE_NONE struct upb_FastDecoder_Return _upb_FieldParser(
2341
2424
  struct upb_Decoder* d, const char* ptr, struct upb_Message* msg,
2342
- intptr_t table, uint64_t hasbits, uint64_t data);
2425
+ const struct upb_MiniTable* table, uint64_t hasbits, uint64_t data,
2426
+ uint64_t data2);
2343
2427
 
2344
2428
  typedef struct {
2345
2429
  uint64_t field_data;
2346
2430
  _upb_FieldParser* field_parser;
2347
2431
  } _upb_FastTable_Entry;
2348
2432
 
2433
+ // Ext Mode consists of 4 bits:
2434
+ // * Extensibility
2435
+ // * MessageSet
2436
+ // * Map
2437
+ // * FastTable field coverage
2349
2438
  typedef enum {
2350
2439
  kUpb_ExtMode_NonExtendable = 0, // Non-extendable message.
2351
2440
  kUpb_ExtMode_Extendable = 1, // Normal extendable message.
@@ -2356,8 +2445,17 @@ typedef enum {
2356
2445
  // During table building we steal a bit to indicate that the message is a map
2357
2446
  // entry. *Only* used during table building!
2358
2447
  kUpb_ExtMode_IsMapEntry = 4,
2448
+
2449
+ // Indicates that all eligible fields (with 1- or 2-byte) tags were
2450
+ // successfully assigned to the fasttable.
2451
+ kUpb_ExtMode_AllFastFieldsAssigned = 8,
2359
2452
  } upb_ExtMode;
2360
2453
 
2454
+ // Check ExtMode base message info, excluding fasttable state info.
2455
+ UPB_FORCEINLINE uint8_t UPB_PRIVATE(_upb_ExtMode_Base)(uint8_t ext_mode) {
2456
+ return ext_mode & 7;
2457
+ }
2458
+
2361
2459
  enum {
2362
2460
  kUpb_Message_Align = 8,
2363
2461
  };
@@ -2385,9 +2483,9 @@ struct upb_MiniTable {
2385
2483
  const char* UPB_PRIVATE(full_name);
2386
2484
  #endif
2387
2485
 
2388
- #if UPB_FASTTABLE || !defined(__cplusplus)
2389
- // Flexible array member is not supported in C++, but it is an extension in
2390
- // every compiler that supports UPB_FASTTABLE.
2486
+ #if UPB_FASTTABLE
2487
+ // Flexible array member is not supported in C++ standard, but it is supported
2488
+ // as an extension in all compilers we support.
2391
2489
  _upb_FastTable_Entry UPB_PRIVATE(fasttable)[];
2392
2490
  #endif
2393
2491
  };
@@ -2419,52 +2517,19 @@ UPB_API_INLINE int upb_MiniTable_FieldCount(const struct upb_MiniTable* m) {
2419
2517
  return m->UPB_ONLYBITS(field_count);
2420
2518
  }
2421
2519
 
2422
- UPB_API_INLINE bool upb_MiniTable_IsMessageSet(const struct upb_MiniTable* m) {
2423
- return m->UPB_PRIVATE(ext) == kUpb_ExtMode_IsMessageSet;
2520
+ UPB_FORCEINLINE uint8_t
2521
+ UPB_PRIVATE(_upb_MiniTable_ExtModeBase)(const struct upb_MiniTable* m) {
2522
+ return UPB_PRIVATE(_upb_ExtMode_Base)(m->UPB_PRIVATE(ext));
2424
2523
  }
2425
2524
 
2426
- UPB_API_INLINE
2427
- const struct upb_MiniTableField* upb_MiniTable_FindFieldByNumber(
2428
- const struct upb_MiniTable* m, uint32_t number) {
2429
- const uint32_t i = number - 1; // 0 wraps to UINT32_MAX
2430
-
2431
- // Ideal case: index into dense fields
2432
- if (i < m->UPB_PRIVATE(dense_below)) {
2433
- UPB_ASSERT(m->UPB_ONLYBITS(fields)[i].UPB_ONLYBITS(number) == number);
2434
- return &m->UPB_ONLYBITS(fields)[i];
2435
- }
2436
-
2437
- // Early exit if the field number is out of range.
2438
- int32_t hi = m->UPB_ONLYBITS(field_count) - 1;
2439
- if (hi < 0 || number > m->UPB_ONLYBITS(fields)[hi].UPB_ONLYBITS(number)) {
2440
- return NULL;
2441
- }
2442
-
2443
- // Slow case: binary search
2444
- uint32_t lo = m->UPB_PRIVATE(dense_below);
2445
- const struct upb_MiniTableField* base = m->UPB_ONLYBITS(fields);
2446
- while (hi >= (int32_t)lo) {
2447
- uint32_t mid = ((uint32_t)hi + lo) / 2;
2448
- uint32_t num = base[mid].UPB_ONLYBITS(number);
2449
- // These comparison operations allow, on ARM machines, to fuse all these
2450
- // branches into one comparison followed by two CSELs to set the lo/hi
2451
- // values, followed by a BNE to continue or terminate the loop. Since binary
2452
- // search branches are generally unpredictable (50/50 in each direction),
2453
- // this is a good deal. We use signed for the high, as this decrement may
2454
- // underflow if mid is 0.
2455
- int32_t hi_mid = (int32_t)mid - 1;
2456
- uint32_t lo_mid = mid + 1;
2457
- if (num == number) {
2458
- return &base[mid];
2459
- }
2460
- if (UPB_UNPREDICTABLE(num < number)) {
2461
- lo = lo_mid;
2462
- } else {
2463
- hi = hi_mid;
2464
- }
2465
- }
2525
+ UPB_FORCEINLINE bool UPB_PRIVATE(_upb_MiniTable_IsExtendable)(
2526
+ const struct upb_MiniTable* m) {
2527
+ return UPB_PRIVATE(_upb_MiniTable_ExtModeBase)(m) == kUpb_ExtMode_Extendable;
2528
+ }
2466
2529
 
2467
- return NULL;
2530
+ UPB_API_INLINE bool upb_MiniTable_IsMessageSet(const struct upb_MiniTable* m) {
2531
+ return UPB_PRIVATE(_upb_MiniTable_ExtModeBase)(m) ==
2532
+ kUpb_ExtMode_IsMessageSet;
2468
2533
  }
2469
2534
 
2470
2535
  UPB_API_INLINE const struct upb_MiniTableField* upb_MiniTable_GetFieldByIndex(
@@ -2495,6 +2560,235 @@ UPB_API_INLINE bool upb_MiniTable_FieldIsLinked(
2495
2560
  return upb_MiniTable_GetSubMessageTable(f) != NULL;
2496
2561
  }
2497
2562
 
2563
+ UPB_FORCEINLINE
2564
+ const struct upb_MiniTableField* UPB_PRIVATE(upb_MiniTable_GenericLowerBound)(
2565
+ const struct upb_MiniTable* m, uint32_t lo, uint32_t search_len,
2566
+ uint32_t number) {
2567
+ const struct upb_MiniTableField* search_base = &m->UPB_ONLYBITS(fields)[lo];
2568
+ while (search_len > 1) {
2569
+ size_t mid_offset = search_len >> 1;
2570
+ if (UPB_UNPREDICTABLE(search_base[mid_offset].UPB_ONLYBITS(number) <=
2571
+ number)) {
2572
+ search_base = &search_base[mid_offset];
2573
+ }
2574
+ search_len -= mid_offset;
2575
+ }
2576
+
2577
+ return search_base;
2578
+ }
2579
+
2580
+ // This implements the same algorithm as upb_MiniTable_GenericLowerBound but
2581
+ // contorts itself to select specific arm instructions, which show significant
2582
+ // effects on little cores.
2583
+ UPB_FORCEINLINE const struct upb_MiniTableField* UPB_PRIVATE(
2584
+ upb_MiniTable_ArmOptimizedLowerBound)(const struct upb_MiniTable* m,
2585
+ uint32_t lo, uint32_t search_len,
2586
+ uint32_t number) {
2587
+ const uint32_t* search_base =
2588
+ &m->UPB_ONLYBITS(fields)[lo].UPB_ONLYBITS(number);
2589
+ UPB_STATIC_ASSERT(sizeof(struct upb_MiniTableField) == sizeof(uint32_t) * 3,
2590
+ "Need to update multiplication");
2591
+ // Address generation units can't multiply by 12, but they can by 4. So we
2592
+ // split it into multiplying by 3 (add and shift) and multiplying by 4 (shift)
2593
+ // This code is carefully tuned to produce an optimal assembly sequence on
2594
+ // arm64, which takes advantage of dual issue on in-order CPUs to maximize
2595
+ // what little instruction level parallelism they have.
2596
+ /*
2597
+ and w9, w1, #0xfffffffe
2598
+ add w9, w9, w1, lsr #1
2599
+ ldr w10, [x0, w9, uxtw #2]
2600
+ sub w1, w1, w1, lsr #1
2601
+ add x9, x0, w9, uxtw #2
2602
+ cmp w10, w2
2603
+ csel x0, x0, x9, hi
2604
+ cmp w1, #1
2605
+ b.hi .LBB3_1
2606
+ */
2607
+ // Doing this requires inhibiting the natural instincts of the compiler to
2608
+ // eliminate duplicate work, so we introduce an optimization barrier with
2609
+ // asm blocks to defeat common subexpression elimination.
2610
+ UPB_STATIC_ASSERT(
2611
+ offsetof(struct upb_MiniTableField, UPB_ONLYBITS(number)) == 0,
2612
+ "Tag number must be first element of minitable field struct");
2613
+ while (search_len > 1) {
2614
+ #if UPB_ARM64_ASM
2615
+ #define UPB_OPT_LAUNDER(val) __asm__("" : "+r"(val))
2616
+ #define UPB_OPT_LAUNDER2(val1, val2) __asm__("" : "+r"(val1), "+r"(val2))
2617
+ #else
2618
+ #define UPB_OPT_LAUNDER(val)
2619
+ #define UPB_OPT_LAUNDER2(val1, val2)
2620
+ #endif
2621
+ // (search_len & ~1) is exactly (half_len * 2). Adding half_len yields
2622
+ // (half_len * 3).
2623
+ //
2624
+ // and mid_offset_words, search_len, #0xfffffffe
2625
+ uint32_t mid_offset_words = search_len & 0xfffffffe;
2626
+
2627
+ // add mid_offset_words, mid_offset_words, search_len, lsr #1
2628
+ mid_offset_words = mid_offset_words + (search_len >> 1);
2629
+
2630
+ UPB_OPT_LAUNDER(search_len);
2631
+ UPB_OPT_LAUNDER(mid_offset_words);
2632
+
2633
+ // Arm processors, even little cores, have Address Generation Units capable
2634
+ // of performing these extensions, so we achieve more instruction level
2635
+ // parallelism by doing this shift by 2 redundantly with the mid pointer
2636
+ // calculation below.
2637
+ //
2638
+ // ldr mid_num, [search_base, mid_offset_words, uxtw #2]
2639
+ uint32_t mid_num = search_base[mid_offset_words];
2640
+
2641
+ // Shrink the search window by half
2642
+ // sub search_len, search_len, search_len, lsr #1
2643
+ search_len = search_len - (search_len >> 1);
2644
+ UPB_OPT_LAUNDER(search_len);
2645
+ UPB_OPT_LAUNDER(mid_offset_words);
2646
+
2647
+ // Calculate the mid pointer for the next iteration
2648
+ // add mid_ptr, search_base, mid_offset_words, uxtw #2
2649
+ const uint32_t* mid_ptr = search_base + mid_offset_words;
2650
+
2651
+ // Forbids LLVM's CSE pass from attempting to merge mid_ptr and mid_num's
2652
+ // math. It sees that it can do a select before adding, rather than after;
2653
+ // but if it orders it that way it creates a longer dependency chain. We
2654
+ // need both as input/output to the same asm block to force them to be
2655
+ // present in different registers at the same time; two separate LAUNDER
2656
+ // usages could get reordered.
2657
+ UPB_OPT_LAUNDER2(mid_ptr, mid_num);
2658
+
2659
+ // cmp + csel
2660
+ search_base = UPB_UNPREDICTABLE(mid_num <= number) ? mid_ptr : search_base;
2661
+ }
2662
+ #undef UPB_OPT_LAUNDER
2663
+ #undef UPB_OPT_LAUNDER2
2664
+ return (const struct upb_MiniTableField*)search_base;
2665
+ }
2666
+
2667
+ UPB_FORCEINLINE const struct upb_MiniTableField* UPB_PRIVATE(
2668
+ upb_MiniTable_LowerBound)(const struct upb_MiniTable* m, uint32_t lo,
2669
+ uint32_t search_len, uint32_t number) {
2670
+ #ifndef NDEBUG
2671
+ const struct upb_MiniTableField* candidate = UPB_PRIVATE(
2672
+ upb_MiniTable_ArmOptimizedLowerBound)(m, lo, search_len, number);
2673
+ UPB_ASSERT(candidate == UPB_PRIVATE(upb_MiniTable_GenericLowerBound)(
2674
+ m, lo, search_len, number));
2675
+ return candidate;
2676
+ #elif UPB_ARM64_ASM
2677
+ return UPB_PRIVATE(upb_MiniTable_ArmOptimizedLowerBound)(m, lo, search_len,
2678
+ number);
2679
+ #else
2680
+ return UPB_PRIVATE(upb_MiniTable_GenericLowerBound)(m, lo, search_len,
2681
+ number);
2682
+ #endif
2683
+ }
2684
+
2685
+ UPB_API_INLINE
2686
+ const struct upb_MiniTableField* upb_MiniTable_FindFieldByNumber(
2687
+ const struct upb_MiniTable* m, uint32_t number) {
2688
+ const uint32_t i = number - 1; // 0 wraps to UINT32_MAX
2689
+
2690
+ // Ideal case: index into dense fields
2691
+ if (i < m->UPB_PRIVATE(dense_below)) {
2692
+ UPB_ASSERT(m->UPB_ONLYBITS(fields)[i].UPB_ONLYBITS(number) == number);
2693
+ return &m->UPB_ONLYBITS(fields)[i];
2694
+ }
2695
+
2696
+ // Early exit if the field number is out of range.
2697
+ uint32_t hi = m->UPB_ONLYBITS(field_count);
2698
+ uint32_t lo = m->UPB_PRIVATE(dense_below);
2699
+ UPB_ASSERT(hi >= lo);
2700
+ uint32_t search_len = hi - lo;
2701
+ if (search_len == 0 ||
2702
+ number > m->UPB_ONLYBITS(fields)[hi - 1].UPB_ONLYBITS(number)) {
2703
+ return NULL;
2704
+ }
2705
+
2706
+ // Slow case: binary search
2707
+ const struct upb_MiniTableField* candidate =
2708
+ UPB_PRIVATE(upb_MiniTable_LowerBound)(m, lo, search_len, number);
2709
+
2710
+ return candidate->UPB_ONLYBITS(number) == number ? candidate : NULL;
2711
+ }
2712
+
2713
+ UPB_FORCEINLINE bool UPB_PRIVATE(_upb_MiniTable_GapIfUnlinked)(
2714
+ const struct upb_MiniTableField* field, uint32_t number,
2715
+ uint32_t* out_gap_lo, uint32_t* out_gap_hi) {
2716
+ UPB_STATIC_ASSERT(sizeof(upb_MiniTableSubInternal) == sizeof(void*),
2717
+ "SubInternal size must be pointer sized.");
2718
+ if (field->UPB_PRIVATE(submsg_ofs) != kUpb_NoSub) {
2719
+ upb_MiniTableSubInternal* sub = UPB_PTR_AT(
2720
+ field, field->UPB_PRIVATE(submsg_ofs) * kUpb_SubmsgOffsetBytes,
2721
+ upb_MiniTableSubInternal);
2722
+ // Type punning via union is legal in C and we're just checking if it's NULL
2723
+ // but it's UB in C++, and this header could be included in C++.
2724
+ void* sub_ptr;
2725
+ memcpy(&sub_ptr, sub, sizeof(void*));
2726
+ if (sub_ptr == NULL) {
2727
+ UPB_ASSERT(!upb_MiniTableField_IsClosedEnum(field));
2728
+ *out_gap_lo = number - 1;
2729
+ *out_gap_hi = number + 1;
2730
+ return true;
2731
+ }
2732
+ }
2733
+ return false;
2734
+ }
2735
+
2736
+ // Given a tag number, finds the known field tags bounding the gap of unknown
2737
+ // fields containing it. Returns false and does not set bounds if the tag number
2738
+ // matches a known field and it is linked or primitive. Otherwise returns true
2739
+ // and sets out_gap_lo and out_gap_hi (exclusive/exclusive) to define the range
2740
+ // of unknown fields (out_gap_lo, out_gap_hi). Unlinked submessages are treated
2741
+ // as gaps.
2742
+ UPB_FORCEINLINE bool UPB_PRIVATE(_upb_MiniTable_FindUnknownGap)(
2743
+ const struct upb_MiniTable* m, uint32_t number, uint32_t* out_gap_lo,
2744
+ uint32_t* out_gap_hi) {
2745
+ UPB_ASSERT(number != 0);
2746
+ UPB_ASSERT(number < ((uint32_t)1 << 29));
2747
+ const uint32_t i = number - 1;
2748
+ if (i < m->UPB_PRIVATE(dense_below)) {
2749
+ // Dense field; we know it's present.
2750
+ return UPB_PRIVATE(_upb_MiniTable_GapIfUnlinked)(
2751
+ &m->UPB_ONLYBITS(fields)[i], number, out_gap_lo, out_gap_hi);
2752
+ }
2753
+
2754
+ uint32_t hi = m->UPB_ONLYBITS(field_count);
2755
+ uint32_t lo = m->UPB_PRIVATE(dense_below);
2756
+ if (hi == lo) {
2757
+ *out_gap_lo = lo;
2758
+ *out_gap_hi = UINT32_MAX;
2759
+ return true;
2760
+ }
2761
+
2762
+ uint32_t max_field = m->UPB_ONLYBITS(fields)[hi - 1].UPB_ONLYBITS(number);
2763
+ if (number > max_field) {
2764
+ *out_gap_lo = max_field;
2765
+ *out_gap_hi = UINT32_MAX;
2766
+ return true;
2767
+ }
2768
+
2769
+ uint32_t search_len = hi - lo;
2770
+ const struct upb_MiniTableField* candidate =
2771
+ UPB_PRIVATE(upb_MiniTable_LowerBound)(m, lo, search_len, number);
2772
+
2773
+ uint32_t candidate_num = candidate->UPB_ONLYBITS(number);
2774
+ if (candidate_num == number) {
2775
+ return UPB_PRIVATE(_upb_MiniTable_GapIfUnlinked)(candidate, number,
2776
+ out_gap_lo, out_gap_hi);
2777
+ }
2778
+
2779
+ if (candidate_num < number) {
2780
+ *out_gap_lo = candidate_num;
2781
+ // Checking this next pointer is safe as we have already validated that the
2782
+ // field we're searching for is not greater than or equal to the last field
2783
+ *out_gap_hi = (candidate + 1)->UPB_ONLYBITS(number);
2784
+ } else {
2785
+ UPB_ASSERT(candidate == &m->UPB_ONLYBITS(fields)[lo]);
2786
+ *out_gap_lo = lo;
2787
+ *out_gap_hi = candidate_num;
2788
+ }
2789
+ return true;
2790
+ }
2791
+
2498
2792
  UPB_API_INLINE const struct upb_MiniTable* upb_MiniTable_MapEntrySubMessage(
2499
2793
  const struct upb_MiniTableField* f) {
2500
2794
  UPB_ASSERT(upb_MiniTable_FieldIsLinked(f)); // Map entries must be linked.
@@ -2672,7 +2966,7 @@ extern "C" {
2672
2966
  #endif
2673
2967
 
2674
2968
  // Creates a new array on the given arena that holds elements of this type.
2675
- UPB_API upb_Array* upb_Array_New(upb_Arena* a, upb_CType type);
2969
+ UPB_NODISCARD UPB_API upb_Array* upb_Array_New(upb_Arena* a, upb_CType type);
2676
2970
 
2677
2971
  // Returns the number of elements in the array.
2678
2972
  UPB_API_INLINE size_t upb_Array_Size(const upb_Array* arr);
@@ -2691,18 +2985,20 @@ UPB_API struct upb_Message* upb_Array_GetMutable(upb_Array* arr, size_t i);
2691
2985
  UPB_API void upb_Array_Set(upb_Array* arr, size_t i, upb_MessageValue val);
2692
2986
 
2693
2987
  // Appends an element to the array. Returns false on allocation failure.
2694
- UPB_API bool upb_Array_Append(upb_Array* array, upb_MessageValue val,
2695
- upb_Arena* arena);
2988
+ UPB_NODISCARD UPB_API bool upb_Array_Append(upb_Array* array,
2989
+ upb_MessageValue val,
2990
+ upb_Arena* arena);
2696
2991
 
2697
2992
  // Copies elements from |src| to |dst|, resizing |dst| to match |src| size.
2698
2993
  // Returns false on allocation failure.
2699
- UPB_API bool upb_Array_Copy(upb_Array* dst, const upb_Array* src,
2700
- upb_Arena* arena);
2994
+ UPB_NODISCARD UPB_API bool upb_Array_Copy(upb_Array* dst, const upb_Array* src,
2995
+ upb_Arena* arena);
2701
2996
 
2702
2997
  // Appends all elements from |src| to the end of |dst|.
2703
2998
  // Returns false on allocation failure.
2704
- UPB_API bool upb_Array_AppendAll(upb_Array* dst, const upb_Array* src,
2705
- upb_Arena* arena);
2999
+ UPB_NODISCARD UPB_API bool upb_Array_AppendAll(upb_Array* dst,
3000
+ const upb_Array* src,
3001
+ upb_Arena* arena);
2706
3002
 
2707
3003
  // Moves elements within the array using memmove().
2708
3004
  // Like memmove(), the source and destination elements may be overlapping.
@@ -2713,8 +3009,8 @@ UPB_API void upb_Array_Move(upb_Array* array, size_t dst_idx, size_t src_idx,
2713
3009
  // Existing elements are shifted right.
2714
3010
  // The new elements have undefined state and must be set with `upb_Array_Set()`.
2715
3011
  // REQUIRES: `i <= upb_Array_Size(arr)`
2716
- UPB_API bool upb_Array_Insert(upb_Array* array, size_t i, size_t count,
2717
- upb_Arena* arena);
3012
+ UPB_NODISCARD UPB_API bool upb_Array_Insert(upb_Array* array, size_t i,
3013
+ size_t count, upb_Arena* arena);
2718
3014
 
2719
3015
  // Deletes one or more elements from the array.
2720
3016
  // Existing elements are shifted left.
@@ -2722,12 +3018,14 @@ UPB_API bool upb_Array_Insert(upb_Array* array, size_t i, size_t count,
2722
3018
  UPB_API void upb_Array_Delete(upb_Array* array, size_t i, size_t count);
2723
3019
 
2724
3020
  // Reserves |size| elements of storage for the array.
2725
- UPB_API_INLINE bool upb_Array_Reserve(struct upb_Array* array, size_t size,
2726
- upb_Arena* arena);
3021
+ UPB_NODISCARD UPB_API_INLINE bool upb_Array_Reserve(struct upb_Array* array,
3022
+ size_t size,
3023
+ upb_Arena* arena);
2727
3024
 
2728
3025
  // Changes the size of a vector. New elements are initialized to NULL/0.
2729
3026
  // Returns false on allocation failure.
2730
- UPB_API bool upb_Array_Resize(upb_Array* array, size_t size, upb_Arena* arena);
3027
+ UPB_NODISCARD UPB_API bool upb_Array_Resize(upb_Array* array, size_t size,
3028
+ upb_Arena* arena);
2731
3029
 
2732
3030
  // Returns pointer to array data.
2733
3031
  UPB_API_INLINE const void* upb_Array_DataPtr(const upb_Array* arr);
@@ -2929,11 +3227,13 @@ typedef struct _upb_tabent {
2929
3227
  upb_value val;
2930
3228
  upb_key key;
2931
3229
 
2932
- /* Internal chaining. This is const so we can create static initializers for
2933
- * tables. We cast away const sometimes, but *only* when the containing
2934
- * upb_table is known to be non-const. This requires a bit of care, but
2935
- * the subtlety is confined to table.c. */
2936
- const struct _upb_tabent* next;
3230
+ /* Internal chaining and presence:
3231
+ * - next == NULL: The entry is empty.
3232
+ * - ent.next == kUpb_NoNextTabent indicating the entry is occupied but has no
3233
+ * successor.
3234
+ * - otherwise: The entry is occupied, and next points to the next entry in
3235
+ * the collision chain. */
3236
+ uintptr_t next;
2937
3237
  } upb_tabent;
2938
3238
 
2939
3239
  typedef struct {
@@ -2949,24 +3249,40 @@ UPB_INLINE size_t upb_table_size(const upb_table* t) { return t->mask + 1; }
2949
3249
 
2950
3250
  // Internal-only functions, in .h file only out of necessity.
2951
3251
 
2952
- UPB_INLINE upb_key upb_key_empty(void) {
2953
- upb_key ret;
2954
- memset(&ret, 0, sizeof(upb_key));
2955
- return ret;
3252
+ UPB_INLINE bool upb_tabent_isempty(const upb_tabent* e) { return e->next == 0; }
3253
+
3254
+ #define kUpb_NoNextTabent ((uintptr_t)1)
3255
+
3256
+ UPB_INLINE bool upb_tabent_hasnext(const upb_tabent* e) {
3257
+ UPB_STATIC_ASSERT(UPB_ALIGN_OF(upb_tabent) > 1,
3258
+ "valid upb_tabent* can't reference address 1");
3259
+ return e->next != kUpb_NoNextTabent;
3260
+ }
3261
+
3262
+ UPB_INLINE void upb_tabent_clearnext(upb_tabent* e) {
3263
+ e->next = kUpb_NoNextTabent;
3264
+ }
3265
+
3266
+ UPB_INLINE void upb_tabent_clear(upb_tabent* e) {
3267
+ e->next = 0;
3268
+ UPB_ASSERT(upb_tabent_isempty(e));
3269
+ }
3270
+
3271
+ UPB_INLINE upb_tabent* upb_tabent_next(const upb_tabent* e) {
3272
+ UPB_ASSERT(upb_tabent_hasnext(e));
3273
+ return (upb_tabent*)e->next;
2956
3274
  }
2957
3275
 
2958
- UPB_INLINE bool upb_tabent_isempty(const upb_tabent* e) {
2959
- upb_key key = e->key;
2960
- UPB_STATIC_ASSERT(sizeof(key.num) == sizeof(key.str), "Sizes don't match");
2961
- uintptr_t val;
2962
- memcpy(&val, &key, sizeof(val));
2963
- // Note: for upb_inttables a tab_key is a true integer key value, but the
2964
- // inttable maintains the invariant that 0 value is always stored in the
2965
- // compact table and never as a upb_tabent* so we can always use the 0
2966
- // key value to identify an empty tabent.
2967
- return val == 0;
3276
+ UPB_INLINE void upb_tabent_setnext(upb_tabent* e, upb_tabent* next) {
3277
+ UPB_ASSERT((uintptr_t)next != 0);
3278
+ UPB_ASSERT(next != e);
3279
+ UPB_ASSERT((uintptr_t)next != kUpb_NoNextTabent);
3280
+ e->next = (uintptr_t)next;
3281
+ UPB_ASSERT(upb_tabent_hasnext(e));
2968
3282
  }
2969
3283
 
3284
+ #undef kUpb_NoNextTabent
3285
+
2970
3286
  uint32_t _upb_Hash(const void* p, size_t n, uint64_t seed);
2971
3287
 
2972
3288
  #ifdef __cplusplus
@@ -2986,18 +3302,7 @@ uint32_t _upb_Hash(const void* p, size_t n, uint64_t seed);
2986
3302
  // Must be last.
2987
3303
 
2988
3304
  typedef struct {
2989
- upb_table t; // For entries that don't fit in the array part.
2990
- // Array part of the table.
2991
- // Pointers on this table are const so we can create static initializers for
2992
- // tables. We cast away const sometimes, but *only* when the containing
2993
- // upb_table is known to be non-const. This requires a bit of care, but
2994
- // the subtlety is confined to table.c.
2995
- const upb_value* array;
2996
- // Track presence in the array part. Each bit at index (key % 8) at the
2997
- // presence_mask[key/8] indicates if the element is present in the array part.
2998
- const uint8_t* presence_mask;
2999
- uint32_t array_size; // Array part size.
3000
- uint32_t array_count; // Array part number of elements.
3305
+ upb_table t;
3001
3306
  } upb_inttable;
3002
3307
 
3003
3308
  #ifdef __cplusplus
@@ -3006,19 +3311,18 @@ extern "C" {
3006
3311
 
3007
3312
  // Initialize a table. If memory allocation failed, false is returned and
3008
3313
  // the table is uninitialized.
3009
- bool upb_inttable_init(upb_inttable* table, upb_Arena* a);
3314
+ UPB_NODISCARD bool upb_inttable_init(upb_inttable* table, upb_Arena* a);
3010
3315
 
3011
3316
  // Returns the number of values in the table.
3012
3317
  size_t upb_inttable_count(const upb_inttable* t);
3013
3318
 
3014
3319
  // Inserts the given key into the hashtable with the given value.
3015
3320
  // The key must not already exist in the hash table.
3016
- // The value must not be UINTPTR_MAX.
3017
3321
  //
3018
3322
  // If a table resize was required but memory allocation failed, false is
3019
3323
  // returned and the table is unchanged.
3020
- bool upb_inttable_insert(upb_inttable* t, uintptr_t key, upb_value val,
3021
- upb_Arena* a);
3324
+ UPB_NODISCARD bool upb_inttable_insert(upb_inttable* t, uintptr_t key,
3325
+ upb_value val, upb_Arena* a);
3022
3326
 
3023
3327
  // Looks up key in this table, returning "true" if the key was found.
3024
3328
  // If v is non-NULL, copies the value for this key into *v.
@@ -3033,12 +3337,6 @@ bool upb_inttable_remove(upb_inttable* t, uintptr_t key, upb_value* val);
3033
3337
  // Unlike insert/remove, this does not invalidate iterators.
3034
3338
  bool upb_inttable_replace(upb_inttable* t, uintptr_t key, upb_value val);
3035
3339
 
3036
- // Optimizes the table for the current set of entries, for both memory use and
3037
- // lookup time. Client should call this after all entries have been inserted;
3038
- // inserting more entries is legal, but will likely require a table resize.
3039
- // Returns false if reallocation fails.
3040
- bool upb_inttable_compact(upb_inttable* t, upb_Arena* a);
3041
-
3042
3340
  // Clears the table.
3043
3341
  void upb_inttable_clear(upb_inttable* t);
3044
3342
 
@@ -3061,10 +3359,6 @@ bool upb_inttable_done(const upb_inttable* t, intptr_t i);
3061
3359
  uintptr_t upb_inttable_iter_key(const upb_inttable* t, intptr_t iter);
3062
3360
  upb_value upb_inttable_iter_value(const upb_inttable* t, intptr_t iter);
3063
3361
 
3064
- UPB_INLINE bool upb_inttable_arrhas(const upb_inttable* t, uintptr_t key) {
3065
- return (t->presence_mask[key / 8] & (1 << (key % 8))) != 0;
3066
- }
3067
-
3068
3362
  #ifdef __cplusplus
3069
3363
  } /* extern "C" */
3070
3364
  #endif
@@ -3092,7 +3386,8 @@ extern "C" {
3092
3386
 
3093
3387
  // Initialize a table. If memory allocation failed, false is returned and
3094
3388
  // the table is uninitialized.
3095
- bool upb_strtable_init(upb_strtable* table, size_t expected_size, upb_Arena* a);
3389
+ UPB_NODISCARD bool upb_strtable_init(upb_strtable* table, size_t expected_size,
3390
+ upb_Arena* a);
3096
3391
 
3097
3392
  // Returns the number of values in the table.
3098
3393
  UPB_INLINE size_t upb_strtable_count(const upb_strtable* t) {
@@ -3107,8 +3402,8 @@ void upb_strtable_clear(upb_strtable* t);
3107
3402
  //
3108
3403
  // If a table resize was required but memory allocation failed, false is
3109
3404
  // returned and the table is unchanged. */
3110
- bool upb_strtable_insert(upb_strtable* t, const char* key, size_t len,
3111
- upb_value val, upb_Arena* a);
3405
+ UPB_NODISCARD bool upb_strtable_insert(upb_strtable* t, const char* key,
3406
+ size_t len, upb_value val, upb_Arena* a);
3112
3407
 
3113
3408
  // Looks up key in this table, returning "true" if the key was found.
3114
3409
  // If v is non-NULL, copies the value for this key into *v.
@@ -3132,7 +3427,8 @@ UPB_INLINE bool upb_strtable_remove(upb_strtable* t, const char* key,
3132
3427
  }
3133
3428
 
3134
3429
  // Exposed for testing only.
3135
- bool upb_strtable_resize(upb_strtable* t, size_t size_lg2, upb_Arena* a);
3430
+ UPB_NODISCARD bool upb_strtable_resize(upb_strtable* t, size_t size_lg2,
3431
+ upb_Arena* a);
3136
3432
 
3137
3433
  /* Iteration over strtable:
3138
3434
  *
@@ -3436,6 +3732,12 @@ struct upb_MiniTableExtension {
3436
3732
  struct upb_MiniTableField UPB_PRIVATE(field);
3437
3733
 
3438
3734
  union upb_MiniTableSub UPB_PRIVATE(sub); // NULL unless submsg or proto2 enum
3735
+
3736
+ // A known extendee schema for a canonical extension. For a non-canonical
3737
+ // extension, it's typically converted from a canonical extension via the
3738
+ // upb_Message_Convert() API, but is not registered on the extension
3739
+ // registry of the target message when it gets converted. In this case, the
3740
+ // `extendee` info is present on the source message before conversion.
3439
3741
  const struct upb_MiniTable* UPB_PRIVATE(extendee);
3440
3742
  };
3441
3743
 
@@ -3574,10 +3876,18 @@ extern "C" {
3574
3876
  // Adds the given extension data to the given message.
3575
3877
  // |ext| is copied into the message instance.
3576
3878
  // This logically replaces any previously-added extension with this number.
3577
- upb_Extension* UPB_PRIVATE(_upb_Message_GetOrCreateExtension)(
3879
+ UPB_NODISCARD upb_Extension* UPB_PRIVATE(_upb_Message_GetOrCreateExtension)(
3578
3880
  struct upb_Message* msg, const upb_MiniTableExtension* ext,
3579
3881
  upb_Arena* arena);
3580
3882
 
3883
+ // Adds the given non-canonical extension data to the given message.
3884
+ // |ext| is copied into the message instance.
3885
+ // This logically replaces any previously-added extension with this number.
3886
+ UPB_NODISCARD upb_Extension* UPB_PRIVATE(
3887
+ _upb_Message_CreateNonCanonicalExtension)(struct upb_Message* msg,
3888
+ const upb_MiniTableExtension* ext,
3889
+ upb_Arena* arena);
3890
+
3581
3891
  // Returns an extension for a message with a given mini table,
3582
3892
  // or NULL if no extension exists with this mini table.
3583
3893
  const upb_Extension* UPB_PRIVATE(_upb_Message_Getext)(
@@ -3631,15 +3941,27 @@ extern const double kUpb_NaN;
3631
3941
  // Internal members of a upb_Message that track unknown fields and/or
3632
3942
  // extensions. We can change this without breaking binary compatibility.
3633
3943
 
3944
+ // LINT.IfChange(tagged_aux_type)
3634
3945
  typedef struct upb_TaggedAuxPtr {
3635
- // Two lowest bits form a tag:
3636
- // 00 - non-aliased unknown data
3637
- // 10 - aliased unknown data
3638
- // 01 - extension
3946
+ // Three lowest bits form a tag:
3947
+ // 000 - non-aliased unknown data (upb_StringView*)
3948
+ // 100 - aliased unknown data (upb_StringView*)
3949
+ // 001 - non-canonical extension (upb_Extension*)
3950
+ // 011 - canonical extension (upb_Extension*)
3639
3951
  //
3640
- // The main semantic difference between aliased and non-aliased unknown data
3641
- // is that non-aliased unknown data can be assumed to have the following
3642
- // layout:
3952
+ // Bit 0 (lowest bit): Represents the data format in memory (1 for parsed
3953
+ // form, 0 for serialized form).
3954
+ // Bit 1 (middle bit): Represents whether the data is semantically known or
3955
+ // not (1 for known, 0 for unknown).
3956
+ // Bit 2 (highest bit): Aliased/Non-aliased (1 for aliased, 0 for
3957
+ // non-aliased).
3958
+ //
3959
+ // Following this tag structure, we can later use tag `010` for lazy
3960
+ // extensions.
3961
+ //
3962
+ // The main semantic difference between aliased and non-aliased
3963
+ // unknown data is that non-aliased unknown data can be assumed to have the
3964
+ // following layout:
3643
3965
  //
3644
3966
  // [upb_StringView] [data]
3645
3967
  //
@@ -3653,33 +3975,75 @@ typedef struct upb_TaggedAuxPtr {
3653
3975
  // For aliased unknown data, this layout is _not_ guaranteed, since the
3654
3976
  // pointer to the StringView can be anywhere in the allocation, and the
3655
3977
  // StringView may point to non-data memory.
3978
+ //
3979
+ // For a non-canonical extension, its schema is known but not
3980
+ // the one expected by the message, so it should be treated like an unknown
3981
+ // field, but is stored as an extension to lazily defer serialization.
3656
3982
  uintptr_t ptr;
3657
3983
  } upb_TaggedAuxPtr;
3658
3984
 
3659
- UPB_INLINE bool upb_TaggedAuxPtr_IsNull(upb_TaggedAuxPtr ptr) {
3660
- return ptr.ptr == 0;
3985
+ // If this returns true, then the entry is semantically known (but may be in
3986
+ // either parsed or unparsed form).
3987
+ UPB_INLINE bool upb_TaggedAuxPtr_IsSemanticallyKnown(upb_TaggedAuxPtr ptr) {
3988
+ return (ptr.ptr & 0x2) != 0;
3989
+ }
3990
+
3991
+ UPB_INLINE bool upb_TaggedAuxPtr_IsCanonicalExtension(upb_TaggedAuxPtr ptr) {
3992
+ return (ptr.ptr & 3) == 3;
3661
3993
  }
3662
3994
 
3663
- UPB_INLINE bool upb_TaggedAuxPtr_IsExtension(upb_TaggedAuxPtr ptr) {
3664
- return ptr.ptr & 1;
3995
+ UPB_INLINE bool upb_TaggedAuxPtr_IsNonCanonicalExtension(upb_TaggedAuxPtr ptr) {
3996
+ return (ptr.ptr & 3) == 1;
3665
3997
  }
3666
3998
 
3667
- UPB_INLINE bool upb_TaggedAuxPtr_IsUnknown(upb_TaggedAuxPtr ptr) {
3668
- return (ptr.ptr != 0) && ((ptr.ptr & 1) == 0);
3999
+ // Returns true if the entry is aliased/non-aliased unknown data.
4000
+ UPB_INLINE bool upb_TaggedAuxPtr_IsUnknownStringView(upb_TaggedAuxPtr ptr) {
4001
+ return (ptr.ptr != 0) && ((ptr.ptr & 3) == 0);
3669
4002
  }
3670
4003
 
3671
4004
  UPB_INLINE bool upb_TaggedAuxPtr_IsUnknownAliased(upb_TaggedAuxPtr ptr) {
3672
- return (ptr.ptr != 0) && ((ptr.ptr & 2) == 2);
4005
+ return (ptr.ptr != 0) && ((ptr.ptr & 5) == 4);
4006
+ }
4007
+
4008
+ UPB_INLINE upb_Extension* upb_TaggedAuxPtr_CanonicalExtension(
4009
+ upb_TaggedAuxPtr ptr) {
4010
+ UPB_ASSERT(upb_TaggedAuxPtr_IsCanonicalExtension(ptr));
4011
+ return (upb_Extension*)(ptr.ptr & ~7ULL);
4012
+ }
4013
+
4014
+ UPB_INLINE upb_Extension* upb_TaggedAuxPtr_NonCanonicalExtension(
4015
+ upb_TaggedAuxPtr ptr) {
4016
+ UPB_ASSERT(upb_TaggedAuxPtr_IsNonCanonicalExtension(ptr));
4017
+ return (upb_Extension*)(ptr.ptr & ~7ULL);
3673
4018
  }
3674
4019
 
3675
- UPB_INLINE upb_Extension* upb_TaggedAuxPtr_Extension(upb_TaggedAuxPtr ptr) {
3676
- UPB_ASSERT(upb_TaggedAuxPtr_IsExtension(ptr));
3677
- return (upb_Extension*)(ptr.ptr & ~3ULL);
4020
+ // Returns a pointer to the aliased or unaliased unknown upb_StringView* data.
4021
+ UPB_INLINE upb_StringView* upb_TaggedPtrAux_StringViewRepr(
4022
+ upb_TaggedAuxPtr ptr) {
4023
+ UPB_ASSERT(upb_TaggedAuxPtr_IsUnknownStringView(ptr));
4024
+ return (upb_StringView*)(ptr.ptr & ~7ULL);
3678
4025
  }
3679
4026
 
3680
- UPB_INLINE upb_StringView* upb_TaggedAuxPtr_UnknownData(upb_TaggedAuxPtr ptr) {
3681
- UPB_ASSERT(!upb_TaggedAuxPtr_IsExtension(ptr));
3682
- return (upb_StringView*)(ptr.ptr & ~3ULL);
4027
+ // LINT.ThenChange(//depot/google3/third_party/upb/bits/golang/message.go:tagged_aux_type)
4028
+
4029
+ typedef enum {
4030
+ kUpb_TaggedAuxType_Unknown = 0, // tag 000
4031
+ kUpb_TaggedAuxType_NonCanonicalExtension = 1, // tag 001
4032
+ kUpb_TaggedAuxType_CanonicalExtension = 3, // tag 011
4033
+ kUpb_TaggedAuxType_AliasedUnknown = 4 // tag 100
4034
+ } upb_TaggedAuxType;
4035
+
4036
+ typedef union {
4037
+ upb_Extension* extension;
4038
+ const upb_StringView* unknown_data;
4039
+ } upb_TaggedAux;
4040
+
4041
+ UPB_INLINE upb_TaggedAuxType upb_TaggedAux_Get(upb_TaggedAuxPtr ptr,
4042
+ upb_TaggedAux* data) {
4043
+ uintptr_t untagged = ptr.ptr & ~7ULL;
4044
+ UPB_ASSERT((untagged & 7) == 0);
4045
+ memcpy(data, &untagged, sizeof(*data));
4046
+ return (upb_TaggedAuxType)(ptr.ptr & 7);
3683
4047
  }
3684
4048
 
3685
4049
  UPB_INLINE upb_TaggedAuxPtr upb_TaggedAuxPtr_Null(void) {
@@ -3689,7 +4053,16 @@ UPB_INLINE upb_TaggedAuxPtr upb_TaggedAuxPtr_Null(void) {
3689
4053
  }
3690
4054
 
3691
4055
  UPB_INLINE upb_TaggedAuxPtr
3692
- upb_TaggedAuxPtr_MakeExtension(const upb_Extension* e) {
4056
+ upb_TaggedAuxPtr_MakeCanonicalExtension(const upb_Extension* e) {
4057
+ UPB_ASSERT(((uintptr_t)e & 7) == 0);
4058
+ upb_TaggedAuxPtr ptr;
4059
+ ptr.ptr = (uintptr_t)e | 3;
4060
+ return ptr;
4061
+ }
4062
+
4063
+ UPB_INLINE upb_TaggedAuxPtr
4064
+ upb_TaggedAuxPtr_MakeNonCanonicalExtension(const upb_Extension* e) {
4065
+ UPB_ASSERT(((uintptr_t)e & 7) == 0);
3693
4066
  upb_TaggedAuxPtr ptr;
3694
4067
  ptr.ptr = (uintptr_t)e | 1;
3695
4068
  return ptr;
@@ -3700,6 +4073,7 @@ upb_TaggedAuxPtr_MakeExtension(const upb_Extension* e) {
3700
4073
  // view.
3701
4074
  UPB_INLINE upb_TaggedAuxPtr
3702
4075
  upb_TaggedAuxPtr_MakeUnknownData(const upb_StringView* sv) {
4076
+ UPB_ASSERT(((uintptr_t)sv & 7) == 0);
3703
4077
  upb_TaggedAuxPtr ptr;
3704
4078
  ptr.ptr = (uintptr_t)sv;
3705
4079
  return ptr;
@@ -3709,8 +4083,9 @@ upb_TaggedAuxPtr_MakeUnknownData(const upb_StringView* sv) {
3709
4083
  // the data it points to.
3710
4084
  UPB_INLINE upb_TaggedAuxPtr
3711
4085
  upb_TaggedAuxPtr_MakeUnknownDataAliased(const upb_StringView* sv) {
4086
+ UPB_ASSERT(((uintptr_t)sv & 7) == 0);
3712
4087
  upb_TaggedAuxPtr ptr;
3713
- ptr.ptr = (uintptr_t)sv | 2;
4088
+ ptr.ptr = (uintptr_t)sv | 4;
3714
4089
  return ptr;
3715
4090
  }
3716
4091
 
@@ -3729,9 +4104,63 @@ UPB_API void upb_Message_SetNewMessageTraceHandler(
3729
4104
  void (*handler)(const upb_MiniTable*, const upb_Arena*));
3730
4105
  #endif // UPB_TRACING_ENABLED
3731
4106
 
4107
+ // We want to avoid the PLT and register spills for the many tiny memsets used
4108
+ // to initialize messages; the dedicated memset instructions won't do that
4109
+ #ifdef __ARM_FEAT_MOPS
4110
+ #define UPB_ARM_MOPS __ARM_FEAT_MOPS
4111
+ #else
4112
+ #define UPB_ARM_MOPS 0
4113
+ #endif
4114
+
4115
+ UPB_FORCEINLINE void _upb_Message_AlignedMemsetZero(void* dst, size_t size) {
4116
+ UPB_ASSUME(size % kUpb_Message_Align == 0);
4117
+ UPB_ASSUME(size != 0);
4118
+ UPB_ASSUME((uintptr_t)dst % kUpb_Message_Align == 0);
4119
+ #if UPB_ARM64_ASM && !UPB_ARM_MOPS
4120
+ #if UPB_HAS_BUILTIN(__builtin_constant_p)
4121
+ if (__builtin_constant_p(size)) {
4122
+ // We assume the compiler will do something intelligent with a known-length
4123
+ // memset.
4124
+ memset(dst, 0, size);
4125
+ return;
4126
+ }
4127
+ #endif
4128
+ char* ptr = (char*)dst;
4129
+ char* end = ptr + size;
4130
+ __asm__(
4131
+ // Unconditionally zero the first 8 byte chunk; if the loop runs this is
4132
+ // wasted work, but doing it unconditionally is cheaper than adding
4133
+ // another branch.
4134
+ "str xzr, [%x[ptr]]\n\t"
4135
+
4136
+ // If size == 8, skip the loop.
4137
+ "cmp %x[count], #8\n\t"
4138
+ "b.eq 2f\n\t"
4139
+
4140
+ // Loop for size >= 16.
4141
+ // In each iteration, we zero 16 bytes from the ptr and 16 bytes from the
4142
+ // end. These regions may overlap, which is OK; doing it this way lets us
4143
+ // process two chunks per loop iteration.
4144
+ "1:\n\t"
4145
+ "stp xzr, xzr, [%x[ptr]], #16\n\t" // Store then increment by 16
4146
+ "stp xzr, xzr, [%x[end], #-16]!\n\t" // Decrement by 16 then store
4147
+ // End the loop when pointers cross or meet.
4148
+ "cmp %x[ptr], %x[end]\n\t"
4149
+ "b.lo 1b\n\t"
4150
+ "2:\n\t"
4151
+ : [ptr] "+&r"(ptr), [end] "+&r"(end), "=m"(*(char (*)[])dst)
4152
+ : [count] "r"(size)
4153
+ : "cc");
4154
+ UPB_PRIVATE(upb_Xsan_MarkInitialized)(dst, size);
4155
+ #else
4156
+ memset(dst, 0, size);
4157
+ #endif
4158
+ }
4159
+ #undef UPB_ARM_MOPS
4160
+
3732
4161
  // Inline version upb_Message_New(), for internal use.
3733
- UPB_INLINE struct upb_Message* _upb_Message_New(const upb_MiniTable* m,
3734
- upb_Arena* a) {
4162
+ UPB_NODISCARD UPB_INLINE struct upb_Message* _upb_Message_New(
4163
+ const upb_MiniTable* m, upb_Arena* a) {
3735
4164
  UPB_PRIVATE(upb_MiniTable_CheckInvariants)(m);
3736
4165
  #ifdef UPB_TRACING_ENABLED
3737
4166
  upb_Message_LogNewMessage(m, a);
@@ -3743,14 +4172,14 @@ UPB_INLINE struct upb_Message* _upb_Message_New(const upb_MiniTable* m,
3743
4172
  UPB_ASSUME(size % kUpb_Message_Align == 0);
3744
4173
  struct upb_Message* msg = (struct upb_Message*)upb_Arena_Malloc(a, size);
3745
4174
  if (UPB_UNLIKELY(!msg)) return NULL;
3746
- memset(msg, 0, size);
4175
+ _upb_Message_AlignedMemsetZero(msg, size);
3747
4176
  return msg;
3748
4177
  }
3749
4178
 
3750
4179
  // Discards the unknown fields for this message only.
3751
4180
  void _upb_Message_DiscardUnknown_shallow(struct upb_Message* msg);
3752
4181
 
3753
- UPB_NOINLINE bool UPB_PRIVATE(_upb_Message_AddUnknownSlowPath)(
4182
+ UPB_NODISCARD UPB_NOINLINE bool UPB_PRIVATE(_upb_Message_AddUnknownSlowPath)(
3754
4183
  struct upb_Message* msg, const char* data, size_t len, upb_Arena* arena,
3755
4184
  bool alias);
3756
4185
 
@@ -3766,6 +4195,36 @@ typedef enum {
3766
4195
  kUpb_AddUnknown_AliasAllowMerge = 2,
3767
4196
  } upb_AddUnknownMode;
3768
4197
 
4198
+ UPB_NODISCARD UPB_INLINE bool UPB_PRIVATE(
4199
+ _upb_Message_TryAddUnknownAliasAllowMerge)(struct upb_Message* msg,
4200
+ const char* data, size_t len,
4201
+ upb_Arena* arena,
4202
+ upb_AddUnknownMode mode) {
4203
+ UPB_ASSERT(!upb_Message_IsFrozen(msg));
4204
+ UPB_ASSERT(mode == kUpb_AddUnknown_AliasAllowMerge);
4205
+ // Aliasing parse of a message with sequential unknown fields is a simple
4206
+ // pointer bump, so inline it.
4207
+ upb_Message_Internal* in = UPB_PRIVATE(_upb_Message_GetInternal)(msg);
4208
+ if (in && in->size) {
4209
+ upb_TaggedAuxPtr ptr = in->aux_data[in->size - 1];
4210
+ if (upb_TaggedAuxPtr_IsUnknownStringView(ptr)) {
4211
+ upb_StringView* existing = upb_TaggedPtrAux_StringViewRepr(ptr);
4212
+ // Fast path if the field we're adding is immediately after the last
4213
+ // added unknown field.
4214
+ //
4215
+ // The caller has guaranteed to us, by passing
4216
+ // kUpb_AddUnknown_AliasAllowMerge, that there is no risk that these two
4217
+ // regions of memory are from different objects that are contiguous in
4218
+ // memory by coincidence.
4219
+ if (existing->data + existing->size == data) {
4220
+ existing->size += len;
4221
+ return true;
4222
+ }
4223
+ }
4224
+ }
4225
+ return false;
4226
+ }
4227
+
3769
4228
  // Adds unknown data (serialized protobuf data) to the given message. The data
3770
4229
  // must represent one or more complete and well formed proto fields.
3771
4230
  //
@@ -3776,33 +4235,14 @@ typedef enum {
3776
4235
  // to mark the boundary of the buffer, so that we do not inappropriately
3777
4236
  // coalesce two buffers that are separate objects but happen to be contiguous
3778
4237
  // in memory.
3779
- UPB_INLINE bool UPB_PRIVATE(_upb_Message_AddUnknown)(struct upb_Message* msg,
3780
- const char* data,
3781
- size_t len,
3782
- upb_Arena* arena,
3783
- upb_AddUnknownMode mode) {
4238
+ UPB_NODISCARD UPB_INLINE bool UPB_PRIVATE(_upb_Message_AddUnknown)(
4239
+ struct upb_Message* msg, const char* data, size_t len, upb_Arena* arena,
4240
+ upb_AddUnknownMode mode) {
3784
4241
  UPB_ASSERT(!upb_Message_IsFrozen(msg));
3785
- if (mode == kUpb_AddUnknown_AliasAllowMerge) {
3786
- // Aliasing parse of a message with sequential unknown fields is a simple
3787
- // pointer bump, so inline it.
3788
- upb_Message_Internal* in = UPB_PRIVATE(_upb_Message_GetInternal)(msg);
3789
- if (in && in->size) {
3790
- upb_TaggedAuxPtr ptr = in->aux_data[in->size - 1];
3791
- if (upb_TaggedAuxPtr_IsUnknown(ptr)) {
3792
- upb_StringView* existing = upb_TaggedAuxPtr_UnknownData(ptr);
3793
- // Fast path if the field we're adding is immediately after the last
3794
- // added unknown field.
3795
- //
3796
- // The caller has guaranteed to us, by passing
3797
- // kUpb_AddUnknown_AliasAllowMerge, that there is no risk that these two
3798
- // regions of memory are from different objects that are contiguous in
3799
- // memory by coincidence.
3800
- if (existing->data + existing->size == data) {
3801
- existing->size += len;
3802
- return true;
3803
- }
3804
- }
3805
- }
4242
+ if (mode == kUpb_AddUnknown_AliasAllowMerge &&
4243
+ UPB_PRIVATE(_upb_Message_TryAddUnknownAliasAllowMerge)(msg, data, len,
4244
+ arena, mode)) {
4245
+ return true;
3806
4246
  }
3807
4247
  return UPB_PRIVATE(_upb_Message_AddUnknownSlowPath)(
3808
4248
  msg, data, len, arena, mode != kUpb_AddUnknown_Copy);
@@ -3812,14 +4252,35 @@ UPB_INLINE bool UPB_PRIVATE(_upb_Message_AddUnknown)(struct upb_Message* msg,
3812
4252
  // The data is copied into the message instance. Data when concatenated together
3813
4253
  // must represent one or more complete and well formed proto fields, but the
3814
4254
  // individual spans may point only to partial fields.
3815
- bool UPB_PRIVATE(_upb_Message_AddUnknownV)(struct upb_Message* msg,
3816
- upb_Arena* arena,
3817
- upb_StringView data[], size_t count);
4255
+ UPB_NODISCARD bool UPB_PRIVATE(_upb_Message_AddUnknownV)(
4256
+ struct upb_Message* msg, upb_Arena* arena, upb_StringView data[],
4257
+ size_t count);
3818
4258
 
3819
4259
  // Ensures at least one slot is available in the aux_data of this message.
3820
4260
  // Returns false if a reallocation is needed to satisfy the request, and fails.
3821
- bool UPB_PRIVATE(_upb_Message_ReserveSlot)(struct upb_Message* msg,
3822
- upb_Arena* arena);
4261
+ UPB_NODISCARD bool UPB_PRIVATE(_upb_Message_ReserveSlot)(
4262
+ struct upb_Message* msg, upb_Arena* arena);
4263
+
4264
+ typedef enum {
4265
+ kUpb_MessageUnknownType_StringView,
4266
+ kUpb_MessageUnknownType_NonCanonicalExtension,
4267
+ } upb_MessageUnknownType;
4268
+
4269
+ // Represents an unknown field in a message, whether it's in a serialized
4270
+ // (upb_StringView) or parsed non-canonical extension (upb_Extension*) format.
4271
+ typedef struct upb_MessageUnknown {
4272
+ uint8_t type;
4273
+ union {
4274
+ upb_StringView bytes;
4275
+ const upb_Extension* extension;
4276
+ } value;
4277
+ } upb_MessageUnknown;
4278
+
4279
+ typedef enum upb_Message_DeleteUnknownStatus {
4280
+ kUpb_DeleteUnknown_DeletedLast,
4281
+ kUpb_DeleteUnknown_IterUpdated,
4282
+ kUpb_DeleteUnknown_AllocFail,
4283
+ } upb_Message_DeleteUnknownStatus;
3823
4284
 
3824
4285
  #define kUpb_Message_UnknownBegin 0
3825
4286
  #define kUpb_Message_ExtensionBegin 0
@@ -3831,8 +4292,8 @@ UPB_INLINE bool upb_Message_NextUnknown(const struct upb_Message* msg,
3831
4292
  if (in) {
3832
4293
  while (i < in->size) {
3833
4294
  upb_TaggedAuxPtr tagged_ptr = in->aux_data[i++];
3834
- if (upb_TaggedAuxPtr_IsUnknown(tagged_ptr)) {
3835
- *data = *upb_TaggedAuxPtr_UnknownData(tagged_ptr);
4295
+ if (upb_TaggedAuxPtr_IsUnknownStringView(tagged_ptr)) {
4296
+ *data = *upb_TaggedPtrAux_StringViewRepr(tagged_ptr);
3836
4297
  *iter = i;
3837
4298
  return true;
3838
4299
  }
@@ -3844,12 +4305,6 @@ UPB_INLINE bool upb_Message_NextUnknown(const struct upb_Message* msg,
3844
4305
  return false;
3845
4306
  }
3846
4307
 
3847
- UPB_INLINE bool upb_Message_HasUnknown(const struct upb_Message* msg) {
3848
- upb_StringView data;
3849
- uintptr_t iter = kUpb_Message_UnknownBegin;
3850
- return upb_Message_NextUnknown(msg, &data, &iter);
3851
- }
3852
-
3853
4308
  UPB_INLINE bool upb_Message_NextExtension(const struct upb_Message* msg,
3854
4309
  const upb_MiniTableExtension** out_e,
3855
4310
  upb_MessageValue* out_v,
@@ -3859,8 +4314,9 @@ UPB_INLINE bool upb_Message_NextExtension(const struct upb_Message* msg,
3859
4314
  if (in) {
3860
4315
  while (i < in->size) {
3861
4316
  upb_TaggedAuxPtr tagged_ptr = in->aux_data[i++];
3862
- if (upb_TaggedAuxPtr_IsExtension(tagged_ptr)) {
3863
- const upb_Extension* ext = upb_TaggedAuxPtr_Extension(tagged_ptr);
4317
+ if (upb_TaggedAuxPtr_IsCanonicalExtension(tagged_ptr)) {
4318
+ const upb_Extension* ext =
4319
+ upb_TaggedAuxPtr_CanonicalExtension(tagged_ptr);
3864
4320
 
3865
4321
  // Empty repeated fields or maps semantically don't exist.
3866
4322
  if (UPB_PRIVATE(_upb_Extension_IsEmpty)(ext)) continue;
@@ -3887,10 +4343,10 @@ UPB_INLINE bool UPB_PRIVATE(_upb_Message_NextExtensionReverse)(
3887
4343
  while (i < size) {
3888
4344
  upb_TaggedAuxPtr tagged_ptr = in->aux_data[size - 1 - i];
3889
4345
  i++;
3890
- if (!upb_TaggedAuxPtr_IsExtension(tagged_ptr)) {
4346
+ if (!upb_TaggedAuxPtr_IsCanonicalExtension(tagged_ptr)) {
3891
4347
  continue;
3892
4348
  }
3893
- const upb_Extension* ext = upb_TaggedAuxPtr_Extension(tagged_ptr);
4349
+ const upb_Extension* ext = upb_TaggedAuxPtr_CanonicalExtension(tagged_ptr);
3894
4350
 
3895
4351
  // Empty repeated fields or maps semantically don't exist.
3896
4352
  if (UPB_PRIVATE(_upb_Extension_IsEmpty)(ext)) continue;
@@ -4025,6 +4481,7 @@ UPB_INLINE bool UPB_PRIVATE(_upb_Message_IsInitializedShallow)(
4025
4481
  return (UPB_PRIVATE(_upb_MiniTable_RequiredMask)(m) & ~bits) == 0;
4026
4482
  }
4027
4483
 
4484
+ // LINT.IfChange(message_raw_fields)
4028
4485
  UPB_INLINE void* UPB_PRIVATE(_upb_Message_MutableDataPtr)(
4029
4486
  struct upb_Message* msg, const upb_MiniTableField* f) {
4030
4487
  return (char*)msg + f->UPB_ONLYBITS(offset);
@@ -4063,6 +4520,7 @@ UPB_INLINE_IF_NOT_GCC void UPB_PRIVATE(_upb_MiniTableField_DataCopy)(
4063
4520
  }
4064
4521
  UPB_UNREACHABLE();
4065
4522
  }
4523
+ // LINT.ThenChange(//depot/google3/third_party/upb/bits/golang/message.go:message_raw_fields)
4066
4524
 
4067
4525
  UPB_INLINE_IF_NOT_GCC bool UPB_PRIVATE(_upb_MiniTableField_DataEquals)(
4068
4526
  const upb_MiniTableField* f, const void* a, const void* b) {
@@ -4213,6 +4671,19 @@ UPB_API_INLINE bool upb_Message_SetExtension(struct upb_Message* msg,
4213
4671
  return true;
4214
4672
  }
4215
4673
 
4674
+ UPB_API_INLINE bool UPB_PRIVATE(_upb_Message_SetNonCanonicalExtension)(
4675
+ struct upb_Message* msg, const upb_MiniTableExtension* e, const void* val,
4676
+ upb_Arena* a) {
4677
+ UPB_ASSERT(!upb_Message_IsFrozen(msg));
4678
+ UPB_ASSERT(a);
4679
+ upb_Extension* ext =
4680
+ UPB_PRIVATE(_upb_Message_CreateNonCanonicalExtension)(msg, e, a);
4681
+ if (!ext) return false;
4682
+ UPB_PRIVATE(_upb_MiniTableField_DataCopy)
4683
+ (&e->UPB_PRIVATE(field), &ext->data, val);
4684
+ return true;
4685
+ }
4686
+
4216
4687
  // Sets the value of the given field in the given msg. The return value is true
4217
4688
  // if the operation completed successfully, or false if memory allocation
4218
4689
  // failed.
@@ -4334,14 +4805,15 @@ UPB_API_INLINE struct upb_Message* upb_Message_GetMutableMessage(
4334
4805
  return (struct upb_Message*)upb_Message_GetMessage(msg, f);
4335
4806
  }
4336
4807
 
4337
- UPB_API_INLINE upb_Array* upb_Message_GetOrCreateMutableArray(
4808
+ UPB_NODISCARD UPB_API_INLINE upb_Array* upb_Message_GetOrCreateMutableArray(
4338
4809
  struct upb_Message* msg, const upb_MiniTableField* f, upb_Arena* arena) {
4339
4810
  UPB_ASSERT(arena);
4340
4811
  UPB_PRIVATE(_upb_MiniTableField_CheckIsArray)(f);
4341
4812
  upb_Array* array = upb_Message_GetMutableArray(msg, f);
4342
4813
  if (!array) {
4343
4814
  array = UPB_PRIVATE(_upb_Array_New)(
4344
- arena, 4, UPB_PRIVATE(_upb_MiniTableField_ElemSizeLg2)(f));
4815
+ arena, _UPB_ARRAY_DEFAULT_INITIAL_SIZE,
4816
+ UPB_PRIVATE(_upb_MiniTableField_ElemSizeLg2)(f));
4345
4817
  // Check again due to: https://godbolt.org/z/7WfaoKG1r
4346
4818
  UPB_PRIVATE(_upb_MiniTableField_CheckIsArray)(f);
4347
4819
  upb_MessageValue val;
@@ -4351,7 +4823,7 @@ UPB_API_INLINE upb_Array* upb_Message_GetOrCreateMutableArray(
4351
4823
  return array;
4352
4824
  }
4353
4825
 
4354
- UPB_INLINE struct upb_Map* _upb_Message_GetOrCreateMutableMap(
4826
+ UPB_NODISCARD UPB_INLINE struct upb_Map* _upb_Message_GetOrCreateMutableMap(
4355
4827
  struct upb_Message* msg, const upb_MiniTableField* field, size_t key_size,
4356
4828
  size_t val_size, upb_Arena* arena) {
4357
4829
  UPB_PRIVATE(_upb_MiniTableField_CheckIsMap)(field);
@@ -4367,7 +4839,7 @@ UPB_INLINE struct upb_Map* _upb_Message_GetOrCreateMutableMap(
4367
4839
  return map;
4368
4840
  }
4369
4841
 
4370
- UPB_API_INLINE struct upb_Map* upb_Message_GetOrCreateMutableMap(
4842
+ UPB_NODISCARD UPB_API_INLINE struct upb_Map* upb_Message_GetOrCreateMutableMap(
4371
4843
  struct upb_Message* msg, const upb_MiniTable* map_entry_mini_table,
4372
4844
  const upb_MiniTableField* f, upb_Arena* arena) {
4373
4845
  UPB_ASSUME(upb_MiniTableField_CType(f) == kUpb_CType_Message);
@@ -4381,8 +4853,10 @@ UPB_API_INLINE struct upb_Map* upb_Message_GetOrCreateMutableMap(
4381
4853
  arena);
4382
4854
  }
4383
4855
 
4384
- UPB_API_INLINE struct upb_Message* upb_Message_GetOrCreateMutableMessage(
4385
- struct upb_Message* msg, const upb_MiniTableField* f, upb_Arena* arena) {
4856
+ UPB_NODISCARD UPB_API_INLINE struct upb_Message*
4857
+ upb_Message_GetOrCreateMutableMessage(struct upb_Message* msg,
4858
+ const upb_MiniTableField* f,
4859
+ upb_Arena* arena) {
4386
4860
  UPB_ASSERT(arena);
4387
4861
  UPB_ASSUME(upb_MiniTableField_CType(f) == kUpb_CType_Message);
4388
4862
  UPB_ASSUME(!upb_MiniTableField_IsExtension(f));
@@ -4495,6 +4969,27 @@ UPB_API_INLINE void upb_Message_SetBaseFieldMessage(struct upb_Message* msg,
4495
4969
  upb_Message_SetBaseField(msg, f, &value);
4496
4970
  }
4497
4971
 
4972
+ UPB_API_INLINE void upb_Message_SetBaseFieldArray(struct upb_Message* msg,
4973
+ const upb_MiniTableField* f,
4974
+ upb_Array* arr,
4975
+ const upb_MiniTable* arr_mt) {
4976
+ UPB_ASSERT(upb_MiniTableField_IsArray(f));
4977
+ UPB_ASSERT(arr_mt == upb_MiniTable_SubMessage(f));
4978
+ UPB_ASSUME(UPB_PRIVATE(_upb_MiniTableField_GetRep)(f) ==
4979
+ kUpb_FieldRep_NativePointer);
4980
+ upb_Message_SetBaseField(msg, f, &arr);
4981
+ }
4982
+
4983
+ UPB_API_INLINE void upb_Message_SetBaseFieldMap(
4984
+ struct upb_Message* msg, const upb_MiniTableField* f, struct upb_Map* map,
4985
+ const upb_MiniTable* map_entry_mt) {
4986
+ UPB_ASSERT(upb_MiniTableField_IsMap(f));
4987
+ UPB_ASSERT(map_entry_mt == upb_MiniTable_MapEntrySubMessage(f));
4988
+ UPB_ASSUME(UPB_PRIVATE(_upb_MiniTableField_GetRep)(f) ==
4989
+ kUpb_FieldRep_NativePointer);
4990
+ upb_Message_SetBaseField(msg, f, &map);
4991
+ }
4992
+
4498
4993
  UPB_API_INLINE void upb_Message_SetBaseFieldString(struct upb_Message* msg,
4499
4994
  const upb_MiniTableField* f,
4500
4995
  upb_StringView value) {
@@ -4536,7 +5031,7 @@ UPB_API_INLINE void upb_Message_SetClosedEnum(struct upb_Message* msg,
4536
5031
 
4537
5032
  // Extension Setters ///////////////////////////////////////////////////////////
4538
5033
 
4539
- UPB_API_INLINE bool upb_Message_SetExtensionMessage(
5034
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionMessage(
4540
5035
  struct upb_Message* msg, const upb_MiniTableExtension* e,
4541
5036
  struct upb_Message* value, upb_Arena* a) {
4542
5037
  UPB_ASSERT(value);
@@ -4546,7 +5041,7 @@ UPB_API_INLINE bool upb_Message_SetExtensionMessage(
4546
5041
  return upb_Message_SetExtension(msg, e, &value, a);
4547
5042
  }
4548
5043
 
4549
- UPB_API_INLINE bool upb_Message_SetExtensionBool(
5044
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionBool(
4550
5045
  struct upb_Message* msg, const upb_MiniTableExtension* e, bool value,
4551
5046
  upb_Arena* a) {
4552
5047
  UPB_ASSUME(upb_MiniTableExtension_CType(e) == kUpb_CType_Bool);
@@ -4555,7 +5050,7 @@ UPB_API_INLINE bool upb_Message_SetExtensionBool(
4555
5050
  return upb_Message_SetExtension(msg, e, &value, a);
4556
5051
  }
4557
5052
 
4558
- UPB_API_INLINE bool upb_Message_SetExtensionDouble(
5053
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionDouble(
4559
5054
  struct upb_Message* msg, const upb_MiniTableExtension* e, double value,
4560
5055
  upb_Arena* a) {
4561
5056
  UPB_ASSUME(upb_MiniTableExtension_CType(e) == kUpb_CType_Double);
@@ -4564,7 +5059,7 @@ UPB_API_INLINE bool upb_Message_SetExtensionDouble(
4564
5059
  return upb_Message_SetExtension(msg, e, &value, a);
4565
5060
  }
4566
5061
 
4567
- UPB_API_INLINE bool upb_Message_SetExtensionFloat(
5062
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionFloat(
4568
5063
  struct upb_Message* msg, const upb_MiniTableExtension* e, float value,
4569
5064
  upb_Arena* a) {
4570
5065
  UPB_ASSUME(upb_MiniTableExtension_CType(e) == kUpb_CType_Float);
@@ -4573,7 +5068,7 @@ UPB_API_INLINE bool upb_Message_SetExtensionFloat(
4573
5068
  return upb_Message_SetExtension(msg, e, &value, a);
4574
5069
  }
4575
5070
 
4576
- UPB_API_INLINE bool upb_Message_SetExtensionInt32(
5071
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionInt32(
4577
5072
  struct upb_Message* msg, const upb_MiniTableExtension* e, int32_t value,
4578
5073
  upb_Arena* a) {
4579
5074
  UPB_ASSUME(upb_MiniTableExtension_CType(e) == kUpb_CType_Int32 ||
@@ -4583,7 +5078,7 @@ UPB_API_INLINE bool upb_Message_SetExtensionInt32(
4583
5078
  return upb_Message_SetExtension(msg, e, &value, a);
4584
5079
  }
4585
5080
 
4586
- UPB_API_INLINE bool upb_Message_SetExtensionInt64(
5081
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionInt64(
4587
5082
  struct upb_Message* msg, const upb_MiniTableExtension* e, int64_t value,
4588
5083
  upb_Arena* a) {
4589
5084
  UPB_ASSUME(upb_MiniTableExtension_CType(e) == kUpb_CType_Int64);
@@ -4592,7 +5087,7 @@ UPB_API_INLINE bool upb_Message_SetExtensionInt64(
4592
5087
  return upb_Message_SetExtension(msg, e, &value, a);
4593
5088
  }
4594
5089
 
4595
- UPB_API_INLINE bool upb_Message_SetExtensionString(
5090
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionString(
4596
5091
  struct upb_Message* msg, const upb_MiniTableExtension* e,
4597
5092
  upb_StringView value, upb_Arena* a) {
4598
5093
  UPB_ASSUME(upb_MiniTableExtension_CType(e) == kUpb_CType_String ||
@@ -4602,7 +5097,7 @@ UPB_API_INLINE bool upb_Message_SetExtensionString(
4602
5097
  return upb_Message_SetExtension(msg, e, &value, a);
4603
5098
  }
4604
5099
 
4605
- UPB_API_INLINE bool upb_Message_SetExtensionUInt32(
5100
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionUInt32(
4606
5101
  struct upb_Message* msg, const upb_MiniTableExtension* e, uint32_t value,
4607
5102
  upb_Arena* a) {
4608
5103
  UPB_ASSUME(upb_MiniTableExtension_CType(e) == kUpb_CType_UInt32);
@@ -4611,7 +5106,7 @@ UPB_API_INLINE bool upb_Message_SetExtensionUInt32(
4611
5106
  return upb_Message_SetExtension(msg, e, &value, a);
4612
5107
  }
4613
5108
 
4614
- UPB_API_INLINE bool upb_Message_SetExtensionUInt64(
5109
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionUInt64(
4615
5110
  struct upb_Message* msg, const upb_MiniTableExtension* e, uint64_t value,
4616
5111
  upb_Arena* a) {
4617
5112
  UPB_ASSUME(upb_MiniTableExtension_CType(e) == kUpb_CType_UInt64);
@@ -4622,45 +5117,45 @@ UPB_API_INLINE bool upb_Message_SetExtensionUInt64(
4622
5117
 
4623
5118
  // Universal Setters ///////////////////////////////////////////////////////////
4624
5119
 
4625
- UPB_API_INLINE bool upb_Message_SetBool(struct upb_Message* msg,
4626
- const upb_MiniTableField* f, bool value,
4627
- upb_Arena* a) {
5120
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetBool(
5121
+ struct upb_Message* msg, const upb_MiniTableField* f, bool value,
5122
+ upb_Arena* a) {
4628
5123
  return upb_MiniTableField_IsExtension(f)
4629
5124
  ? upb_Message_SetExtensionBool(
4630
5125
  msg, (const upb_MiniTableExtension*)f, value, a)
4631
5126
  : (upb_Message_SetBaseFieldBool(msg, f, value), true);
4632
5127
  }
4633
5128
 
4634
- UPB_API_INLINE bool upb_Message_SetDouble(struct upb_Message* msg,
4635
- const upb_MiniTableField* f,
4636
- double value, upb_Arena* a) {
5129
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetDouble(
5130
+ struct upb_Message* msg, const upb_MiniTableField* f, double value,
5131
+ upb_Arena* a) {
4637
5132
  return upb_MiniTableField_IsExtension(f)
4638
5133
  ? upb_Message_SetExtensionDouble(
4639
5134
  msg, (const upb_MiniTableExtension*)f, value, a)
4640
5135
  : (upb_Message_SetBaseFieldDouble(msg, f, value), true);
4641
5136
  }
4642
5137
 
4643
- UPB_API_INLINE bool upb_Message_SetFloat(struct upb_Message* msg,
4644
- const upb_MiniTableField* f,
4645
- float value, upb_Arena* a) {
5138
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetFloat(
5139
+ struct upb_Message* msg, const upb_MiniTableField* f, float value,
5140
+ upb_Arena* a) {
4646
5141
  return upb_MiniTableField_IsExtension(f)
4647
5142
  ? upb_Message_SetExtensionFloat(
4648
5143
  msg, (const upb_MiniTableExtension*)f, value, a)
4649
5144
  : (upb_Message_SetBaseFieldFloat(msg, f, value), true);
4650
5145
  }
4651
5146
 
4652
- UPB_API_INLINE bool upb_Message_SetInt32(struct upb_Message* msg,
4653
- const upb_MiniTableField* f,
4654
- int32_t value, upb_Arena* a) {
5147
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetInt32(
5148
+ struct upb_Message* msg, const upb_MiniTableField* f, int32_t value,
5149
+ upb_Arena* a) {
4655
5150
  return upb_MiniTableField_IsExtension(f)
4656
5151
  ? upb_Message_SetExtensionInt32(
4657
5152
  msg, (const upb_MiniTableExtension*)f, value, a)
4658
5153
  : (upb_Message_SetBaseFieldInt32(msg, f, value), true);
4659
5154
  }
4660
5155
 
4661
- UPB_API_INLINE bool upb_Message_SetInt64(struct upb_Message* msg,
4662
- const upb_MiniTableField* f,
4663
- int64_t value, upb_Arena* a) {
5156
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetInt64(
5157
+ struct upb_Message* msg, const upb_MiniTableField* f, int64_t value,
5158
+ upb_Arena* a) {
4664
5159
  return upb_MiniTableField_IsExtension(f)
4665
5160
  ? upb_Message_SetExtensionInt64(
4666
5161
  msg, (const upb_MiniTableExtension*)f, value, a)
@@ -4680,27 +5175,27 @@ UPB_API_INLINE void upb_Message_SetMessage(struct upb_Message* msg,
4680
5175
  // copied, so it is the caller's responsibility to ensure that they remain valid
4681
5176
  // for the lifetime of `msg`. That might be done by copying them into the given
4682
5177
  // arena, or by fusing that arena with the arena the bytes live in, for example.
4683
- UPB_API_INLINE bool upb_Message_SetString(struct upb_Message* msg,
4684
- const upb_MiniTableField* f,
4685
- upb_StringView value, upb_Arena* a) {
5178
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetString(
5179
+ struct upb_Message* msg, const upb_MiniTableField* f, upb_StringView value,
5180
+ upb_Arena* a) {
4686
5181
  return upb_MiniTableField_IsExtension(f)
4687
5182
  ? upb_Message_SetExtensionString(
4688
5183
  msg, (const upb_MiniTableExtension*)f, value, a)
4689
5184
  : (upb_Message_SetBaseFieldString(msg, f, value), true);
4690
5185
  }
4691
5186
 
4692
- UPB_API_INLINE bool upb_Message_SetUInt32(struct upb_Message* msg,
4693
- const upb_MiniTableField* f,
4694
- uint32_t value, upb_Arena* a) {
5187
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetUInt32(
5188
+ struct upb_Message* msg, const upb_MiniTableField* f, uint32_t value,
5189
+ upb_Arena* a) {
4695
5190
  return upb_MiniTableField_IsExtension(f)
4696
5191
  ? upb_Message_SetExtensionUInt32(
4697
5192
  msg, (const upb_MiniTableExtension*)f, value, a)
4698
5193
  : (upb_Message_SetBaseFieldUInt32(msg, f, value), true);
4699
5194
  }
4700
5195
 
4701
- UPB_API_INLINE bool upb_Message_SetUInt64(struct upb_Message* msg,
4702
- const upb_MiniTableField* f,
4703
- uint64_t value, upb_Arena* a) {
5196
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetUInt64(
5197
+ struct upb_Message* msg, const upb_MiniTableField* f, uint64_t value,
5198
+ upb_Arena* a) {
4704
5199
  return upb_MiniTableField_IsExtension(f)
4705
5200
  ? upb_Message_SetExtensionUInt64(
4706
5201
  msg, (const upb_MiniTableExtension*)f, value, a)
@@ -4740,8 +5235,9 @@ UPB_API_INLINE void upb_Message_ClearExtension(
4740
5235
  if (!in) return;
4741
5236
  for (size_t i = 0; i < in->size; i++) {
4742
5237
  upb_TaggedAuxPtr tagged_ptr = in->aux_data[i];
4743
- if (upb_TaggedAuxPtr_IsExtension(tagged_ptr)) {
4744
- const upb_Extension* ext = upb_TaggedAuxPtr_Extension(tagged_ptr);
5238
+ if (upb_TaggedAuxPtr_IsCanonicalExtension(tagged_ptr)) {
5239
+ const upb_Extension* ext =
5240
+ upb_TaggedAuxPtr_CanonicalExtension(tagged_ptr);
4745
5241
  if (ext->ext == e) {
4746
5242
  in->aux_data[i] = upb_TaggedAuxPtr_Null();
4747
5243
  return;
@@ -4765,7 +5261,7 @@ UPB_API_INLINE void upb_Message_ClearOneof(struct upb_Message* msg,
4765
5261
  upb_Message_ClearBaseField(msg, field);
4766
5262
  }
4767
5263
 
4768
- UPB_API_INLINE void* upb_Message_ResizeArrayUninitialized(
5264
+ UPB_NODISCARD UPB_API_INLINE void* upb_Message_ResizeArrayUninitialized(
4769
5265
  struct upb_Message* msg, const upb_MiniTableField* f, size_t size,
4770
5266
  upb_Arena* arena) {
4771
5267
  UPB_PRIVATE(_upb_MiniTableField_CheckIsArray)(f);
@@ -4929,8 +5425,8 @@ extern "C" {
4929
5425
  #endif
4930
5426
 
4931
5427
  // Creates a new map on the given arena with the given key/value size.
4932
- UPB_API upb_Map* upb_Map_New(upb_Arena* a, upb_CType key_type,
4933
- upb_CType value_type);
5428
+ UPB_NODISCARD UPB_API upb_Map* upb_Map_New(upb_Arena* a, upb_CType key_type,
5429
+ upb_CType value_type);
4934
5430
 
4935
5431
  // Returns the number of entries in the map.
4936
5432
  UPB_API size_t upb_Map_Size(const upb_Map* map);
@@ -4953,15 +5449,18 @@ UPB_API void upb_Map_Clear(upb_Map* map);
4953
5449
  // Sets the given key to the given value, returning whether the key was inserted
4954
5450
  // or replaced. If the key was inserted, then any existing iterators will be
4955
5451
  // invalidated.
4956
- UPB_API upb_MapInsertStatus upb_Map_Insert(upb_Map* map, upb_MessageValue key,
4957
- upb_MessageValue val,
4958
- upb_Arena* arena);
5452
+ UPB_NODISCARD UPB_API upb_MapInsertStatus upb_Map_Insert(upb_Map* map,
5453
+ upb_MessageValue key,
5454
+ upb_MessageValue val,
5455
+ upb_Arena* arena);
4959
5456
 
4960
5457
  // Sets the given key to the given value. Returns false if memory allocation
4961
5458
  // failed. If the key is newly inserted, then any existing iterators will be
4962
5459
  // invalidated.
4963
- UPB_API_INLINE bool upb_Map_Set(upb_Map* map, upb_MessageValue key,
4964
- upb_MessageValue val, upb_Arena* arena) {
5460
+ UPB_NODISCARD UPB_API_INLINE bool upb_Map_Set(upb_Map* map,
5461
+ upb_MessageValue key,
5462
+ upb_MessageValue val,
5463
+ upb_Arena* arena) {
4965
5464
  return upb_Map_Insert(map, key, val, arena) !=
4966
5465
  kUpb_MapInsertStatus_OutOfMemory;
4967
5466
  }
@@ -5049,7 +5548,8 @@ extern "C" {
5049
5548
  #endif
5050
5549
 
5051
5550
  // Creates a new message with the given mini_table on the given arena.
5052
- UPB_API upb_Message* upb_Message_New(const upb_MiniTable* m, upb_Arena* arena);
5551
+ UPB_NODISCARD UPB_API upb_Message* upb_Message_New(const upb_MiniTable* m,
5552
+ upb_Arena* arena);
5053
5553
 
5054
5554
  //
5055
5555
  // Unknown data may be stored non-contiguously. Each segment stores a block of
@@ -5065,10 +5565,24 @@ UPB_API upb_Message* upb_Message_New(const upb_MiniTable* m, upb_Arena* arena);
5065
5565
  #define kUpb_Message_UnknownBegin 0
5066
5566
  #define kUpb_Message_ExtensionBegin 0
5067
5567
 
5568
+ // TODO: b/510055656 - Legacy API that works with messages that only have
5569
+ // unknown data in upb_StringView format. Use `upb_Message_NextUnknown2` for
5570
+ // messages that may have non-canonical extensions.
5068
5571
  UPB_INLINE bool upb_Message_NextUnknown(const upb_Message* msg,
5069
5572
  upb_StringView* data, uintptr_t* iter);
5070
5573
 
5071
- UPB_INLINE bool upb_Message_HasUnknown(const upb_Message* msg);
5574
+ UPB_INLINE bool upb_Message_HasUnknown(const upb_Message* msg) {
5575
+ const upb_Message_Internal* in = UPB_PRIVATE(_upb_Message_GetInternal)(msg);
5576
+ if (!in) return false;
5577
+ for (size_t i = 0; i < in->size; i++) {
5578
+ upb_TaggedAuxPtr tagged_ptr = in->aux_data[i];
5579
+ if (tagged_ptr.ptr != 0 &&
5580
+ !upb_TaggedAuxPtr_IsSemanticallyKnown(tagged_ptr)) {
5581
+ return true;
5582
+ }
5583
+ }
5584
+ return false;
5585
+ }
5072
5586
 
5073
5587
  // Removes a segment of unknown data from the message, advancing to the next
5074
5588
  // segment. Returns false if the removed segment was at the end of the last
@@ -5096,15 +5610,12 @@ UPB_INLINE bool upb_Message_HasUnknown(const upb_Message* msg);
5096
5610
  //
5097
5611
  // The range given in `data` must be contained inside the most recently
5098
5612
  // returned region.
5099
- typedef enum upb_Message_DeleteUnknownStatus {
5100
- kUpb_DeleteUnknown_DeletedLast,
5101
- kUpb_DeleteUnknown_IterUpdated,
5102
- kUpb_DeleteUnknown_AllocFail,
5103
- } upb_Message_DeleteUnknownStatus;
5104
- upb_Message_DeleteUnknownStatus upb_Message_DeleteUnknown(upb_Message* msg,
5105
- upb_StringView* data,
5106
- uintptr_t* iter,
5107
- upb_Arena* arena);
5613
+ //
5614
+ // TODO: b/510055656 - Legacy API that works with messages that only have
5615
+ // unknown data in upb_StringView format. Use `upb_Message_DeleteUnknown2` for
5616
+ // messages that may have non-canonical extensions.
5617
+ UPB_NODISCARD upb_Message_DeleteUnknownStatus upb_Message_DeleteUnknown(
5618
+ upb_Message* msg, upb_StringView* data, uintptr_t* iter, upb_Arena* arena);
5108
5619
 
5109
5620
  // Returns the number of extensions present in this message.
5110
5621
  size_t upb_Message_ExtensionCount(const upb_Message* msg);
@@ -5213,14 +5724,14 @@ UPB_API_INLINE upb_Map* upb_Message_GetMutableMap(upb_Message* msg,
5213
5724
  UPB_API_INLINE upb_Message* upb_Message_GetMutableMessage(
5214
5725
  upb_Message* msg, const upb_MiniTableField* f);
5215
5726
 
5216
- UPB_API_INLINE upb_Array* upb_Message_GetOrCreateMutableArray(
5727
+ UPB_NODISCARD UPB_API_INLINE upb_Array* upb_Message_GetOrCreateMutableArray(
5217
5728
  upb_Message* msg, const upb_MiniTableField* f, upb_Arena* arena);
5218
5729
 
5219
- UPB_API_INLINE upb_Map* upb_Message_GetOrCreateMutableMap(
5730
+ UPB_NODISCARD UPB_API_INLINE upb_Map* upb_Message_GetOrCreateMutableMap(
5220
5731
  upb_Message* msg, const upb_MiniTable* map_entry_mini_table,
5221
5732
  const upb_MiniTableField* f, upb_Arena* arena);
5222
5733
 
5223
- UPB_API_INLINE upb_Message* upb_Message_GetOrCreateMutableMessage(
5734
+ UPB_NODISCARD UPB_API_INLINE upb_Message* upb_Message_GetOrCreateMutableMessage(
5224
5735
  upb_Message* msg, const upb_MiniTableField* f, upb_Arena* arena);
5225
5736
 
5226
5737
  UPB_API_INLINE upb_StringView
@@ -5269,6 +5780,15 @@ UPB_API_INLINE void upb_Message_SetBaseFieldMessage(struct upb_Message* msg,
5269
5780
  const upb_MiniTableField* f,
5270
5781
  upb_Message* value);
5271
5782
 
5783
+ UPB_API_INLINE void upb_Message_SetBaseFieldArray(struct upb_Message* msg,
5784
+ const upb_MiniTableField* f,
5785
+ upb_Array* arr,
5786
+ const upb_MiniTable* arr_mt);
5787
+
5788
+ UPB_API_INLINE void upb_Message_SetBaseFieldMap(
5789
+ struct upb_Message* msg, const upb_MiniTableField* f, struct upb_Map* map,
5790
+ const upb_MiniTable* map_entry_mt);
5791
+
5272
5792
  UPB_API_INLINE void upb_Message_SetBaseFieldString(struct upb_Message* msg,
5273
5793
  const upb_MiniTableField* f,
5274
5794
  upb_StringView value);
@@ -5324,67 +5844,62 @@ UPB_API_INLINE upb_Array* upb_Message_GetExtensionMutableArray(
5324
5844
 
5325
5845
  // Extension Setters ///////////////////////////////////////////////////////////
5326
5846
 
5327
- UPB_API_INLINE bool upb_Message_SetExtension(upb_Message* msg,
5328
- const upb_MiniTableExtension* e,
5329
- const void* value, upb_Arena* a);
5847
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtension(
5848
+ upb_Message* msg, const upb_MiniTableExtension* e, const void* value,
5849
+ upb_Arena* a);
5330
5850
 
5331
- UPB_API_INLINE bool upb_Message_SetExtensionMessage(
5851
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionMessage(
5332
5852
  struct upb_Message* msg, const upb_MiniTableExtension* e,
5333
5853
  struct upb_Message* value, upb_Arena* a);
5334
5854
 
5335
- UPB_API_INLINE bool upb_Message_SetExtensionBool(
5855
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionBool(
5336
5856
  struct upb_Message* msg, const upb_MiniTableExtension* e, bool value,
5337
5857
  upb_Arena* a);
5338
5858
 
5339
- UPB_API_INLINE bool upb_Message_SetExtensionDouble(
5859
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionDouble(
5340
5860
  struct upb_Message* msg, const upb_MiniTableExtension* e, double value,
5341
5861
  upb_Arena* a);
5342
5862
 
5343
- UPB_API_INLINE bool upb_Message_SetExtensionFloat(
5863
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionFloat(
5344
5864
  struct upb_Message* msg, const upb_MiniTableExtension* e, float value,
5345
5865
  upb_Arena* a);
5346
5866
 
5347
- UPB_API_INLINE bool upb_Message_SetExtensionInt32(
5867
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionInt32(
5348
5868
  struct upb_Message* msg, const upb_MiniTableExtension* e, int32_t value,
5349
5869
  upb_Arena* a);
5350
5870
 
5351
- UPB_API_INLINE bool upb_Message_SetExtensionInt64(
5871
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionInt64(
5352
5872
  struct upb_Message* msg, const upb_MiniTableExtension* e, int64_t value,
5353
5873
  upb_Arena* a);
5354
5874
 
5355
- UPB_API_INLINE bool upb_Message_SetExtensionString(
5875
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionString(
5356
5876
  struct upb_Message* msg, const upb_MiniTableExtension* e,
5357
5877
  upb_StringView value, upb_Arena* a);
5358
5878
 
5359
- UPB_API_INLINE bool upb_Message_SetExtensionUInt32(
5879
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionUInt32(
5360
5880
  struct upb_Message* msg, const upb_MiniTableExtension* e, uint32_t value,
5361
5881
  upb_Arena* a);
5362
5882
 
5363
- UPB_API_INLINE bool upb_Message_SetExtensionUInt64(
5883
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetExtensionUInt64(
5364
5884
  struct upb_Message* msg, const upb_MiniTableExtension* e, uint64_t value,
5365
5885
  upb_Arena* a);
5366
5886
 
5367
5887
  // Universal Setters ///////////////////////////////////////////////////////////
5368
5888
 
5369
- UPB_API_INLINE bool upb_Message_SetBool(upb_Message* msg,
5370
- const upb_MiniTableField* f, bool value,
5371
- upb_Arena* a);
5889
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetBool(
5890
+ upb_Message* msg, const upb_MiniTableField* f, bool value, upb_Arena* a);
5372
5891
 
5373
- UPB_API_INLINE bool upb_Message_SetDouble(upb_Message* msg,
5374
- const upb_MiniTableField* f,
5375
- double value, upb_Arena* a);
5892
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetDouble(
5893
+ upb_Message* msg, const upb_MiniTableField* f, double value, upb_Arena* a);
5376
5894
 
5377
- UPB_API_INLINE bool upb_Message_SetFloat(upb_Message* msg,
5378
- const upb_MiniTableField* f,
5379
- float value, upb_Arena* a);
5895
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetFloat(
5896
+ upb_Message* msg, const upb_MiniTableField* f, float value, upb_Arena* a);
5380
5897
 
5381
- UPB_API_INLINE bool upb_Message_SetInt32(upb_Message* msg,
5382
- const upb_MiniTableField* f,
5383
- int32_t value, upb_Arena* a);
5898
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetInt32(
5899
+ upb_Message* msg, const upb_MiniTableField* f, int32_t value, upb_Arena* a);
5384
5900
 
5385
- UPB_API_INLINE bool upb_Message_SetInt64(upb_Message* msg,
5386
- const upb_MiniTableField* f,
5387
- int64_t value, upb_Arena* a);
5901
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetInt64(
5902
+ upb_Message* msg, const upb_MiniTableField* f, int64_t value, upb_Arena* a);
5388
5903
 
5389
5904
  // Unlike the other similarly-named setters, this function can only be
5390
5905
  // called on base fields. Prefer upb_Message_SetBaseFieldMessage().
@@ -5392,21 +5907,21 @@ UPB_API_INLINE void upb_Message_SetMessage(upb_Message* msg,
5392
5907
  const upb_MiniTableField* f,
5393
5908
  upb_Message* value);
5394
5909
 
5395
- UPB_API_INLINE bool upb_Message_SetString(upb_Message* msg,
5396
- const upb_MiniTableField* f,
5397
- upb_StringView value, upb_Arena* a);
5910
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetString(
5911
+ upb_Message* msg, const upb_MiniTableField* f, upb_StringView value,
5912
+ upb_Arena* a);
5398
5913
 
5399
- UPB_API_INLINE bool upb_Message_SetUInt32(upb_Message* msg,
5400
- const upb_MiniTableField* f,
5401
- uint32_t value, upb_Arena* a);
5914
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetUInt32(
5915
+ upb_Message* msg, const upb_MiniTableField* f, uint32_t value,
5916
+ upb_Arena* a);
5402
5917
 
5403
- UPB_API_INLINE bool upb_Message_SetUInt64(upb_Message* msg,
5404
- const upb_MiniTableField* f,
5405
- uint64_t value, upb_Arena* a);
5918
+ UPB_NODISCARD UPB_API_INLINE bool upb_Message_SetUInt64(
5919
+ upb_Message* msg, const upb_MiniTableField* f, uint64_t value,
5920
+ upb_Arena* a);
5406
5921
 
5407
5922
  ////////////////////////////////////////////////////////////////////////////////
5408
5923
 
5409
- UPB_API_INLINE void* upb_Message_ResizeArrayUninitialized(
5924
+ UPB_NODISCARD UPB_API_INLINE void* upb_Message_ResizeArrayUninitialized(
5410
5925
  upb_Message* msg, const upb_MiniTableField* f, size_t size,
5411
5926
  upb_Arena* arena);
5412
5927
 
@@ -5420,8 +5935,10 @@ UPB_API_INLINE const upb_MiniTableField* upb_Message_WhichOneof(
5420
5935
  const upb_MiniTableField* f);
5421
5936
 
5422
5937
  // Updates a map entry given an entry message.
5423
- bool upb_Message_SetMapEntry(upb_Map* map, const upb_MiniTableField* field,
5424
- upb_Message* map_entry_message, upb_Arena* arena);
5938
+ UPB_NODISCARD bool upb_Message_SetMapEntry(upb_Map* map,
5939
+ const upb_MiniTableField* field,
5940
+ upb_Message* map_entry_message,
5941
+ upb_Arena* arena);
5425
5942
 
5426
5943
  #ifdef __cplusplus
5427
5944
  } /* extern "C" */
@@ -5430,7 +5947,7 @@ bool upb_Message_SetMapEntry(upb_Map* map, const upb_MiniTableField* field,
5430
5947
  #if defined(__cplusplus)
5431
5948
  // Temporary overloads for functions whose signature has recently changed.
5432
5949
  UPB_DEPRECATE_AND_INLINE()
5433
- inline upb_Message* upb_Message_GetOrCreateMutableMessage(
5950
+ UPB_NODISCARD inline upb_Message* upb_Message_GetOrCreateMutableMessage(
5434
5951
  upb_Message* msg, const upb_MiniTable* mini_table,
5435
5952
  const upb_MiniTableField* f, upb_Arena* arena) {
5436
5953
  return upb_Message_GetOrCreateMutableMessage(msg, f, arena);
@@ -5445,6 +5962,7 @@ inline void upb_Message_SetClosedEnum(upb_Message* msg,
5445
5962
  }
5446
5963
 
5447
5964
  UPB_DEPRECATE_AND_INLINE()
5965
+ UPB_NODISCARD
5448
5966
  inline bool upb_Message_SetMapEntry(upb_Map* map,
5449
5967
  const upb_MiniTable* mini_table,
5450
5968
  const upb_MiniTableField* field,
@@ -5562,9 +6080,8 @@ extern "C" {
5562
6080
 
5563
6081
  // Builds a upb_MiniTableEnum from an enum mini descriptor.
5564
6082
  // The mini descriptor must be for an enum, not a message.
5565
- UPB_API upb_MiniTableEnum* upb_MiniTableEnum_Build(const char* data, size_t len,
5566
- upb_Arena* arena,
5567
- upb_Status* status);
6083
+ UPB_NODISCARD UPB_API upb_MiniTableEnum* upb_MiniTableEnum_Build(
6084
+ const char* data, size_t len, upb_Arena* arena, upb_Status* status);
5568
6085
 
5569
6086
  #ifdef __cplusplus
5570
6087
  } /* extern "C" */
@@ -5598,16 +6115,15 @@ extern "C" {
5598
6115
  // as unknown. However there is no synchronization for this operation, which
5599
6116
  // means parallel mutation requires external synchronization.
5600
6117
  // Returns success/failure.
5601
- UPB_API bool upb_MiniTable_SetSubMessage(upb_MiniTable* table,
5602
- upb_MiniTableField* field,
5603
- const upb_MiniTable* sub);
6118
+ UPB_NODISCARD UPB_API bool upb_MiniTable_SetSubMessage(
6119
+ upb_MiniTable* table, upb_MiniTableField* field, const upb_MiniTable* sub);
5604
6120
 
5605
6121
  // Links an enum field to a MiniTable for that enum.
5606
6122
  // All enum fields must be linked prior to parsing.
5607
6123
  // Returns success/failure.
5608
- UPB_API bool upb_MiniTable_SetSubEnum(upb_MiniTable* table,
5609
- upb_MiniTableField* field,
5610
- const upb_MiniTableEnum* sub);
6124
+ UPB_NODISCARD UPB_API bool upb_MiniTable_SetSubEnum(
6125
+ upb_MiniTable* table, upb_MiniTableField* field,
6126
+ const upb_MiniTableEnum* sub);
5611
6127
 
5612
6128
  // Returns a list of fields that require linking at runtime, to connect the
5613
6129
  // MiniTable to its sub-messages and sub-enums. The list of fields will be
@@ -5630,11 +6146,9 @@ UPB_API uint32_t upb_MiniTable_GetSubList(const upb_MiniTable* mt,
5630
6146
  //
5631
6147
  // Returns false if either array is too short, or if any of the tables fails
5632
6148
  // to link.
5633
- UPB_API bool upb_MiniTable_Link(upb_MiniTable* mt,
5634
- const upb_MiniTable** sub_tables,
5635
- size_t sub_table_count,
5636
- const upb_MiniTableEnum** sub_enums,
5637
- size_t sub_enum_count);
6149
+ UPB_NODISCARD UPB_API bool upb_MiniTable_Link(
6150
+ upb_MiniTable* mt, const upb_MiniTable** sub_tables, size_t sub_table_count,
6151
+ const upb_MiniTableEnum** sub_enums, size_t sub_enum_count);
5638
6152
 
5639
6153
  #ifdef __cplusplus
5640
6154
  } /* extern "C" */
@@ -5661,13 +6175,12 @@ extern "C" {
5661
6175
  // errors occur, returns NULL and sets a status message. In the success case,
5662
6176
  // the caller must call upb_MiniTable_SetSub*() for all message or proto2 enum
5663
6177
  // fields to link the table to the appropriate sub-tables.
5664
- upb_MiniTable* _upb_MiniTable_Build(const char* data, size_t len,
5665
- upb_MiniTablePlatform platform,
5666
- upb_Arena* arena, upb_Status* status);
6178
+ UPB_NODISCARD upb_MiniTable* _upb_MiniTable_Build(
6179
+ const char* data, size_t len, upb_MiniTablePlatform platform,
6180
+ upb_Arena* arena, upb_Status* status);
5667
6181
 
5668
- UPB_API_INLINE upb_MiniTable* upb_MiniTable_Build(const char* data, size_t len,
5669
- upb_Arena* arena,
5670
- upb_Status* status) {
6182
+ UPB_NODISCARD UPB_API_INLINE upb_MiniTable* upb_MiniTable_Build(
6183
+ const char* data, size_t len, upb_Arena* arena, upb_Status* status) {
5671
6184
  return _upb_MiniTable_Build(data, len, kUpb_MiniTablePlatform_Native, arena,
5672
6185
  status);
5673
6186
  }
@@ -5675,44 +6188,47 @@ UPB_API_INLINE upb_MiniTable* upb_MiniTable_Build(const char* data, size_t len,
5675
6188
  // Initializes a MiniTableExtension buffer that has already been allocated.
5676
6189
  // This is needed by upb_FileDef and upb_MessageDef, which allocate all of the
5677
6190
  // extensions together in a single contiguous array.
5678
- const char* _upb_MiniTableExtension_Init(const char* data, size_t len,
5679
- upb_MiniTableExtension* ext,
5680
- const upb_MiniTable* extendee,
5681
- upb_MiniTableSub sub,
5682
- upb_MiniTablePlatform platform,
5683
- upb_Status* status);
5684
-
5685
- UPB_API_INLINE const char* upb_MiniTableExtension_Init(
6191
+ UPB_NODISCARD const char* _upb_MiniTableExtension_Init(
6192
+ const char* data, size_t len, upb_MiniTableExtension* ext,
6193
+ const upb_MiniTable* extendee, upb_MiniTableSub sub,
6194
+ upb_MiniTablePlatform platform, upb_Status* status);
6195
+
6196
+ UPB_NODISCARD UPB_API_INLINE const char* upb_MiniTableExtension_Init(
5686
6197
  const char* data, size_t len, upb_MiniTableExtension* ext,
5687
6198
  const upb_MiniTable* extendee, upb_MiniTableSub sub, upb_Status* status) {
5688
6199
  return _upb_MiniTableExtension_Init(data, len, ext, extendee, sub,
5689
6200
  kUpb_MiniTablePlatform_Native, status);
5690
6201
  }
5691
6202
 
5692
- UPB_API upb_MiniTableExtension* _upb_MiniTableExtension_Build(
6203
+ UPB_NODISCARD UPB_API upb_MiniTableExtension* _upb_MiniTableExtension_Build(
5693
6204
  const char* data, size_t len, const upb_MiniTable* extendee,
5694
6205
  upb_MiniTableSub sub, upb_MiniTablePlatform platform, upb_Arena* arena,
5695
6206
  upb_Status* status);
5696
6207
 
5697
- UPB_API_INLINE upb_MiniTableExtension* upb_MiniTableExtension_Build(
5698
- const char* data, size_t len, const upb_MiniTable* extendee,
5699
- upb_Arena* arena, upb_Status* status) {
6208
+ UPB_NODISCARD UPB_API_INLINE upb_MiniTableExtension*
6209
+ upb_MiniTableExtension_Build(const char* data, size_t len,
6210
+ const upb_MiniTable* extendee, upb_Arena* arena,
6211
+ upb_Status* status) {
5700
6212
  upb_MiniTableSub sub = upb_MiniTableSub_FromMessage(NULL);
5701
6213
  return _upb_MiniTableExtension_Build(
5702
6214
  data, len, extendee, sub, kUpb_MiniTablePlatform_Native, arena, status);
5703
6215
  }
5704
6216
 
5705
- UPB_API_INLINE upb_MiniTableExtension* upb_MiniTableExtension_BuildMessage(
5706
- const char* data, size_t len, const upb_MiniTable* extendee,
5707
- const upb_MiniTable* submsg, upb_Arena* arena, upb_Status* status) {
6217
+ UPB_NODISCARD UPB_API_INLINE upb_MiniTableExtension*
6218
+ upb_MiniTableExtension_BuildMessage(const char* data, size_t len,
6219
+ const upb_MiniTable* extendee,
6220
+ const upb_MiniTable* submsg,
6221
+ upb_Arena* arena, upb_Status* status) {
5708
6222
  upb_MiniTableSub sub = upb_MiniTableSub_FromMessage(submsg);
5709
6223
  return _upb_MiniTableExtension_Build(
5710
6224
  data, len, extendee, sub, kUpb_MiniTablePlatform_Native, arena, status);
5711
6225
  }
5712
6226
 
5713
- UPB_API_INLINE upb_MiniTableExtension* upb_MiniTableExtension_BuildEnum(
5714
- const char* data, size_t len, const upb_MiniTable* extendee,
5715
- const upb_MiniTableEnum* subenum, upb_Arena* arena, upb_Status* status) {
6227
+ UPB_NODISCARD UPB_API_INLINE upb_MiniTableExtension*
6228
+ upb_MiniTableExtension_BuildEnum(const char* data, size_t len,
6229
+ const upb_MiniTable* extendee,
6230
+ const upb_MiniTableEnum* subenum,
6231
+ upb_Arena* arena, upb_Status* status) {
5716
6232
  upb_MiniTableSub sub = upb_MiniTableSub_FromEnum(subenum);
5717
6233
  return _upb_MiniTableExtension_Build(
5718
6234
  data, len, extendee, sub, kUpb_MiniTablePlatform_Native, arena, status);
@@ -5725,10 +6241,9 @@ UPB_API_INLINE upb_MiniTableExtension* upb_MiniTableExtension_BuildEnum(
5725
6241
  // The caller owns `*buf` both before and after the call, and must upb_gfree()
5726
6242
  // it when it is no longer in use. The function will upb_grealloc() `*buf` as
5727
6243
  // necessary, updating `*size` accordingly.
5728
- upb_MiniTable* upb_MiniTable_BuildWithBuf(const char* data, size_t len,
5729
- upb_MiniTablePlatform platform,
5730
- upb_Arena* arena, void** buf,
5731
- size_t* buf_size, upb_Status* status);
6244
+ UPB_NODISCARD upb_MiniTable* upb_MiniTable_BuildWithBuf(
6245
+ const char* data, size_t len, upb_MiniTablePlatform platform,
6246
+ upb_Arena* arena, void** buf, size_t* buf_size, upb_Status* status);
5732
6247
 
5733
6248
  #ifdef __cplusplus
5734
6249
  } /* extern "C" */
@@ -5791,22 +6306,22 @@ typedef enum {
5791
6306
  kUpb_ExtensionRegistryStatus_Ok = 0,
5792
6307
  kUpb_ExtensionRegistryStatus_DuplicateEntry = 1,
5793
6308
  kUpb_ExtensionRegistryStatus_OutOfMemory = 2,
5794
- kUpb_ExtensionRegistryStatus_InvalidExtension = 3,
5795
6309
  } upb_ExtensionRegistryStatus;
5796
6310
  // LINT.ThenChange(//depot/google3/third_party/upb/rust/sys/mini_table/extension_registry.rs)
5797
6311
 
5798
6312
  // Creates a upb_ExtensionRegistry in the given arena.
5799
6313
  // The arena must outlive any use of the extreg.
5800
- UPB_API upb_ExtensionRegistry* upb_ExtensionRegistry_New(upb_Arena* arena);
6314
+ UPB_NODISCARD UPB_API upb_ExtensionRegistry* upb_ExtensionRegistry_New(
6315
+ upb_Arena* arena);
5801
6316
 
5802
- UPB_API upb_ExtensionRegistryStatus upb_ExtensionRegistry_Add(
6317
+ UPB_NODISCARD UPB_API upb_ExtensionRegistryStatus upb_ExtensionRegistry_Add(
5803
6318
  upb_ExtensionRegistry* r, const upb_MiniTableExtension* e);
5804
6319
 
5805
6320
  // Adds the given extension info for the array |e| of size |count| into the
5806
6321
  // registry. If there are any errors, the entire array is backed out.
5807
6322
  // The extensions must outlive the registry.
5808
6323
  // Possible errors include OOM or an extension number that already exists.
5809
- upb_ExtensionRegistryStatus upb_ExtensionRegistry_AddArray(
6324
+ UPB_NODISCARD upb_ExtensionRegistryStatus upb_ExtensionRegistry_AddArray(
5810
6325
  upb_ExtensionRegistry* r, const upb_MiniTableExtension** e, size_t count);
5811
6326
 
5812
6327
  // Looks up the extension (if any) defined for message type |t| and field
@@ -5953,6 +6468,78 @@ struct upb_GeneratedRegistryRef {
5953
6468
  #include <stdint.h>
5954
6469
 
5955
6470
 
6471
+ #ifndef GOOGLE_UPB_UPB_BASE_ERROR_HANDLER_H__
6472
+ #define GOOGLE_UPB_UPB_BASE_ERROR_HANDLER_H__
6473
+
6474
+ #include <setjmp.h>
6475
+
6476
+ // Must be last.
6477
+
6478
+ // upb_ErrorHandler is a standard longjmp()-based exception handler for UPB.
6479
+ // It is used for efficient error handling in cases where longjmp() is safe to
6480
+ // use, such as in highly performance-sensitive C parsing code.
6481
+ //
6482
+ // This structure contains both a jmp_buf and an error code; the error code is
6483
+ // stored in the structure prior to calling longjmp(). This is necessary because
6484
+ // per the C standard, it is not possible to store the result of setjmp(), so
6485
+ // the error code must be passed out-of-band.
6486
+ //
6487
+ // upb_ErrorHandler is generally not C++-compatible, because longjmp() does not
6488
+ // run C++ destructors. So any library that supports upb_ErrorHandler should
6489
+ // also support a regular return-based error handling mechanism. (Note: we
6490
+ // could conceivably extend this to take a callback, which could either call
6491
+ // longjmp() or throw a C++ exception. But since C++ exceptions are forbidden
6492
+ // by the C++ style guide, there's not likely to be a demand for this.)
6493
+ //
6494
+ // To support both cases (longjmp() or return-based status) efficiently, code
6495
+ // can be written like this:
6496
+ //
6497
+ // UPB_ATTR_CONST bool upb_Arena_HasErrHandler(const upb_Arena* a);
6498
+ //
6499
+ // INLINE void* upb_Arena_Malloc(upb_Arena* a, size_t size) {
6500
+ // if (UPB_UNLIKELY(a->end - a->ptr < size)) {
6501
+ // void* ret = upb_Arena_MallocFallback(a, size);
6502
+ // UPB_MAYBE_ASSUME(upb_Arena_HasErrHandler(a), ret != NULL);
6503
+ // return ret;
6504
+ // }
6505
+ // void* ret = a->ptr;
6506
+ // a->ptr += size;
6507
+ // UPB_ASSUME(ret != NULL);
6508
+ // return ret;
6509
+ // }
6510
+ //
6511
+ // If the optimizer can prove that an error handler is present, it can assume
6512
+ // that upb_Arena_Malloc() will not return NULL.
6513
+
6514
+ // We need to standardize on any error code that might be thrown by an error
6515
+ // handler.
6516
+
6517
+ typedef enum {
6518
+ kUpb_ErrorCode_Ok = 0,
6519
+ kUpb_ErrorCode_OutOfMemory = 1,
6520
+ kUpb_ErrorCode_Malformed = 2,
6521
+ kUpb_ErrorCode_MaxDepthExceeded = 3,
6522
+ } upb_ErrorCode;
6523
+
6524
+ typedef struct {
6525
+ int code;
6526
+ jmp_buf buf;
6527
+ } upb_ErrorHandler;
6528
+
6529
+ UPB_INLINE void upb_ErrorHandler_Init(upb_ErrorHandler* e) {
6530
+ e->code = kUpb_ErrorCode_Ok;
6531
+ }
6532
+
6533
+ UPB_INLINE UPB_NORETURN void upb_ErrorHandler_ThrowError(upb_ErrorHandler* e,
6534
+ int code) {
6535
+ UPB_ASSERT(code != kUpb_ErrorCode_Ok);
6536
+ e->code = code;
6537
+ UPB_LONGJMP(e->buf, 1);
6538
+ }
6539
+
6540
+
6541
+ #endif // GOOGLE_UPB_UPB_BASE_ERROR_HANDLER_H__
6542
+
5956
6543
  // Must be last.
5957
6544
 
5958
6545
  #ifdef __cplusplus
@@ -6017,34 +6604,36 @@ UPB_INLINE int upb_Decode_LimitDepth(uint32_t decode_options, uint32_t limit) {
6017
6604
 
6018
6605
  // LINT.IfChange
6019
6606
  typedef enum {
6020
- kUpb_DecodeStatus_Ok = 0,
6021
- kUpb_DecodeStatus_OutOfMemory = 1, // Arena alloc failed
6022
- kUpb_DecodeStatus_Malformed = 2, // Wire format was corrupt
6023
- kUpb_DecodeStatus_BadUtf8 = 3, // String field had bad UTF-8
6607
+ kUpb_DecodeStatus_Ok = kUpb_ErrorCode_Ok,
6608
+ kUpb_DecodeStatus_OutOfMemory =
6609
+ kUpb_ErrorCode_OutOfMemory, // Arena alloc failed
6610
+ kUpb_DecodeStatus_Malformed =
6611
+ kUpb_ErrorCode_Malformed, // Wire format was corrupt
6024
6612
  kUpb_DecodeStatus_MaxDepthExceeded =
6025
- 4, // Exceeded upb_DecodeOptions_MaxDepth
6613
+ kUpb_ErrorCode_MaxDepthExceeded, // Exceeded upb_DecodeOptions_MaxDepth
6614
+
6615
+ kUpb_DecodeStatus_BadUtf8 = 10, // String field had bad UTF-8
6026
6616
 
6027
6617
  // kUpb_DecodeOption_CheckRequired failed (see above), but the parse otherwise
6028
6618
  // succeeded.
6029
- kUpb_DecodeStatus_MissingRequired = 5,
6619
+ kUpb_DecodeStatus_MissingRequired = 11,
6030
6620
  } upb_DecodeStatus;
6031
6621
  // LINT.ThenChange(//depot/google3/third_party/upb/rust/sys/wire/wire.rs:decode_status)
6032
6622
 
6033
- UPB_API upb_DecodeStatus upb_Decode(const char* buf, size_t size,
6034
- upb_Message* msg, const upb_MiniTable* mt,
6035
- const upb_ExtensionRegistry* extreg,
6036
- int options, upb_Arena* arena);
6623
+ UPB_NODISCARD UPB_API upb_DecodeStatus upb_Decode(
6624
+ const char* buf, size_t size, upb_Message* msg, const upb_MiniTable* mt,
6625
+ const upb_ExtensionRegistry* extreg, int options, upb_Arena* arena);
6037
6626
 
6038
6627
  // Same as upb_Decode but with a varint-encoded length prepended.
6039
6628
  // On success 'num_bytes_read' will be set to the how many bytes were read,
6040
6629
  // on failure the contents of num_bytes_read is undefined.
6041
- UPB_API upb_DecodeStatus upb_DecodeLengthPrefixed(
6630
+ UPB_NODISCARD UPB_API upb_DecodeStatus upb_DecodeLengthPrefixed(
6042
6631
  const char* buf, size_t size, upb_Message* msg, size_t* num_bytes_read,
6043
6632
  const upb_MiniTable* mt, const upb_ExtensionRegistry* extreg, int options,
6044
6633
  upb_Arena* arena);
6045
6634
 
6046
6635
  // For testing: decode with tracing.
6047
- UPB_API upb_DecodeStatus upb_DecodeWithTrace(
6636
+ UPB_NODISCARD UPB_API upb_DecodeStatus upb_DecodeWithTrace(
6048
6637
  const char* buf, size_t size, upb_Message* msg, const upb_MiniTable* mt,
6049
6638
  const upb_ExtensionRegistry* extreg, int options, upb_Arena* arena,
6050
6639
  char* trace_buf, size_t trace_size);
@@ -6068,6 +6657,27 @@ UPB_API const char* upb_DecodeStatus_String(upb_DecodeStatus status);
6068
6657
  #include <stdint.h>
6069
6658
 
6070
6659
 
6660
+ #ifndef UPB_WIRE_INTERNAL_CONSTANTS_H_
6661
+ #define UPB_WIRE_INTERNAL_CONSTANTS_H_
6662
+
6663
+ #define kUpb_WireFormat_DefaultDepthLimit 100
6664
+
6665
+ // MessageSet wire format is:
6666
+ // message MessageSet {
6667
+ // repeated group Item = 1 {
6668
+ // required int32 type_id = 2;
6669
+ // required bytes message = 3;
6670
+ // }
6671
+ // }
6672
+
6673
+ enum {
6674
+ kUpb_MsgSet_Item = 1,
6675
+ kUpb_MsgSet_TypeId = 2,
6676
+ kUpb_MsgSet_Message = 3,
6677
+ };
6678
+
6679
+ #endif /* UPB_WIRE_INTERNAL_CONSTANTS_H_ */
6680
+
6071
6681
  // Must be last.
6072
6682
 
6073
6683
  #ifdef __cplusplus
@@ -6092,16 +6702,16 @@ enum {
6092
6702
 
6093
6703
  // LINT.IfChange
6094
6704
  typedef enum {
6095
- kUpb_EncodeStatus_Ok = 0,
6096
- kUpb_EncodeStatus_OutOfMemory = 1, // Arena alloc failed
6097
- kUpb_EncodeStatus_MaxDepthExceeded = 2,
6098
-
6705
+ kUpb_EncodeStatus_Ok = kUpb_ErrorCode_Ok,
6706
+ kUpb_EncodeStatus_OutOfMemory =
6707
+ kUpb_ErrorCode_OutOfMemory, // Arena alloc failed
6099
6708
  // One or more required fields are missing. Only returned if
6100
6709
  // kUpb_EncodeOption_CheckRequired is set.
6101
- kUpb_EncodeStatus_MissingRequired = 3,
6710
+ kUpb_EncodeStatus_MaxDepthExceeded = kUpb_ErrorCode_MaxDepthExceeded,
6102
6711
 
6712
+ kUpb_EncodeStatus_MissingRequired = 10,
6103
6713
  // The message is larger than protobuf's 2GB size limit.
6104
- kUpb_EncodeStatus_MaxSizeExceeded = 4,
6714
+ kUpb_EncodeStatus_MaxSizeExceeded = 11,
6105
6715
  } upb_EncodeStatus;
6106
6716
  // LINT.ThenChange(//depot/google3/third_party/upb/rust/sys/wire/wire.rs:encode_status)
6107
6717
 
@@ -6109,7 +6719,14 @@ UPB_INLINE uint32_t upb_EncodeOptions_MaxDepth(uint16_t depth) {
6109
6719
  return (uint32_t)depth << 16;
6110
6720
  }
6111
6721
 
6112
- uint16_t upb_EncodeOptions_GetEffectiveMaxDepth(uint32_t options);
6722
+ UPB_INLINE uint16_t upb_EncodeOptions_GetMaxDepth(uint32_t options) {
6723
+ return options >> 16;
6724
+ }
6725
+
6726
+ UPB_INLINE uint16_t upb_EncodeOptions_GetEffectiveMaxDepth(uint32_t options) {
6727
+ uint16_t max_depth = upb_EncodeOptions_GetMaxDepth(options);
6728
+ return max_depth ? max_depth : kUpb_WireFormat_DefaultDepthLimit;
6729
+ }
6113
6730
 
6114
6731
  // Enforce an upper bound on recursion depth.
6115
6732
  UPB_INLINE int upb_Encode_LimitDepth(uint32_t encode_options, uint32_t limit) {
@@ -6119,15 +6736,15 @@ UPB_INLINE int upb_Encode_LimitDepth(uint32_t encode_options, uint32_t limit) {
6119
6736
  (encode_options & 0xffff));
6120
6737
  }
6121
6738
 
6122
- UPB_API upb_EncodeStatus upb_Encode(const upb_Message* msg,
6123
- const upb_MiniTable* l, int options,
6124
- upb_Arena* arena, char** buf, size_t* size);
6125
-
6126
- // Encodes the message prepended by a varint of the serialized length.
6127
- UPB_API upb_EncodeStatus upb_EncodeLengthPrefixed(const upb_Message* msg,
6739
+ UPB_NODISCARD UPB_API upb_EncodeStatus upb_Encode(const upb_Message* msg,
6128
6740
  const upb_MiniTable* l,
6129
6741
  int options, upb_Arena* arena,
6130
6742
  char** buf, size_t* size);
6743
+
6744
+ // Encodes the message prepended by a varint of the serialized length.
6745
+ UPB_NODISCARD UPB_API upb_EncodeStatus upb_EncodeLengthPrefixed(
6746
+ const upb_Message* msg, const upb_MiniTable* l, int options,
6747
+ upb_Arena* arena, char** buf, size_t* size);
6131
6748
  // Utility function for wrapper languages to get an error string from a
6132
6749
  // upb_EncodeStatus.
6133
6750
  UPB_API const char* upb_EncodeStatus_String(upb_EncodeStatus status);
@@ -6191,6 +6808,7 @@ extern const upb_MiniTable google__protobuf__UninterpretedOption_msg_init;
6191
6808
  extern const upb_MiniTable google__protobuf__UninterpretedOption__NamePart_msg_init;
6192
6809
  extern const upb_MiniTable google__protobuf__FeatureSet_msg_init;
6193
6810
  extern const upb_MiniTable google__protobuf__FeatureSet__VisibilityFeature_msg_init;
6811
+ extern const upb_MiniTable google__protobuf__FeatureSet__ProtoLimitsFeature_msg_init;
6194
6812
  extern const upb_MiniTable google__protobuf__FeatureSetDefaults_msg_init;
6195
6813
  extern const upb_MiniTable google__protobuf__FeatureSetDefaults__FeatureSetEditionDefault_msg_init;
6196
6814
  extern const upb_MiniTable google__protobuf__SourceCodeInfo_msg_init;
@@ -6205,6 +6823,7 @@ extern const upb_MiniTableEnum google__protobuf__FeatureSet__EnumType_enum_init;
6205
6823
  extern const upb_MiniTableEnum google__protobuf__FeatureSet__FieldPresence_enum_init;
6206
6824
  extern const upb_MiniTableEnum google__protobuf__FeatureSet__JsonFormat_enum_init;
6207
6825
  extern const upb_MiniTableEnum google__protobuf__FeatureSet__MessageEncoding_enum_init;
6826
+ extern const upb_MiniTableEnum google__protobuf__FeatureSet__ProtoLimitsFeature__EnforceProtoLimits_enum_init;
6208
6827
  extern const upb_MiniTableEnum google__protobuf__FeatureSet__RepeatedFieldEncoding_enum_init;
6209
6828
  extern const upb_MiniTableEnum google__protobuf__FeatureSet__Utf8Validation_enum_init;
6210
6829
  extern const upb_MiniTableEnum google__protobuf__FeatureSet__VisibilityFeature__DefaultSymbolVisibility_enum_init;
@@ -6251,7 +6870,7 @@ UPB_INLINE int upb_Log2Ceiling(size_t x) {
6251
6870
  #else
6252
6871
  if (x > SIZE_MAX / 2) return sizeof(size_t) * CHAR_BIT;
6253
6872
  int lg2 = 0;
6254
- while ((1 << lg2) < x) lg2++;
6873
+ while (((size_t)1 << lg2) < x) lg2++;
6255
6874
  return lg2;
6256
6875
  #endif
6257
6876
  }
@@ -6301,7 +6920,8 @@ extern "C" {
6301
6920
 
6302
6921
  // Initialize a table. If memory allocation failed, false is returned and
6303
6922
  // the table is uninitialized.
6304
- bool upb_exttable_init(upb_exttable* table, size_t expected_size, upb_Arena* a);
6923
+ UPB_NODISCARD bool upb_exttable_init(upb_exttable* table, size_t expected_size,
6924
+ upb_Arena* a);
6305
6925
 
6306
6926
  // Returns the number of values in the table.
6307
6927
  UPB_INLINE size_t upb_exttable_count(const upb_exttable* t) {
@@ -6315,8 +6935,8 @@ void upb_exttable_clear(upb_exttable* t);
6315
6935
  //
6316
6936
  // If a table resize was required but memory allocation failed, false is
6317
6937
  // returned and the table is unchanged.
6318
- bool upb_exttable_insert(upb_exttable* t, const void* k, const uint32_t* v,
6319
- upb_Arena* a);
6938
+ UPB_NODISCARD bool upb_exttable_insert(upb_exttable* t, const void* k,
6939
+ const uint32_t* v, upb_Arena* a);
6320
6940
 
6321
6941
  // Looks up key and ext_number in this table, returning the value if the key was
6322
6942
  // found, or NULL otherwise.
@@ -6353,6 +6973,9 @@ size_t upb_exttable_size(const upb_exttable* t);
6353
6973
  #ifndef UPB_REFLECTION_DEF_POOL_H_
6354
6974
  #define UPB_REFLECTION_DEF_POOL_H_
6355
6975
 
6976
+ #include <stddef.h>
6977
+ #include <stdint.h>
6978
+
6356
6979
 
6357
6980
  // IWYU pragma: private, include "upb/reflection/def.h"
6358
6981
 
@@ -6501,6 +7124,10 @@ typedef struct google_protobuf_FeatureSet_VisibilityFeature {
6501
7124
  upb_Message UPB_PRIVATE(base);
6502
7125
  } google_protobuf_FeatureSet_VisibilityFeature;
6503
7126
 
7127
+ typedef struct google_protobuf_FeatureSet_ProtoLimitsFeature {
7128
+ upb_Message UPB_PRIVATE(base);
7129
+ } google_protobuf_FeatureSet_ProtoLimitsFeature;
7130
+
6504
7131
  typedef struct google_protobuf_FeatureSetDefaults {
6505
7132
  upb_Message UPB_PRIVATE(base);
6506
7133
  } google_protobuf_FeatureSetDefaults;
@@ -6580,6 +7207,12 @@ typedef enum {
6580
7207
  google_protobuf_FeatureSet_DELIMITED = 2
6581
7208
  } google_protobuf_FeatureSet_MessageEncoding;
6582
7209
 
7210
+ typedef enum {
7211
+ google_protobuf_FeatureSet_ProtoLimitsFeature_PROTO_LIMITS_UNKNOWN = 0,
7212
+ google_protobuf_FeatureSet_ProtoLimitsFeature_LEGACY_NO_EXPLICIT_LIMITS = 1,
7213
+ google_protobuf_FeatureSet_ProtoLimitsFeature_PROTO_LIMITS2026 = 2
7214
+ } google_protobuf_FeatureSet_ProtoLimitsFeature_EnforceProtoLimits;
7215
+
6583
7216
  typedef enum {
6584
7217
  google_protobuf_FeatureSet_REPEATED_FIELD_ENCODING_UNKNOWN = 0,
6585
7218
  google_protobuf_FeatureSet_PACKED = 1,
@@ -12971,164 +13604,184 @@ UPB_INLINE char* google_protobuf_FeatureSet_serialize_ex(const google_protobuf_F
12971
13604
  return ptr;
12972
13605
  }
12973
13606
  UPB_INLINE void google_protobuf_FeatureSet_clear_field_presence(google_protobuf_FeatureSet* msg) {
12974
- const upb_MiniTableField field = {1, 12, 64, 24, 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13607
+ const upb_MiniTableField field = {1, 12, 64, UPB_SIZE(27, 28), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
12975
13608
  upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
12976
13609
  }
12977
13610
  UPB_INLINE int32_t google_protobuf_FeatureSet_field_presence(const google_protobuf_FeatureSet* msg) {
12978
13611
  int32_t default_val = 0;
12979
13612
  int32_t ret;
12980
- const upb_MiniTableField field = {1, 12, 64, 24, 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13613
+ const upb_MiniTableField field = {1, 12, 64, UPB_SIZE(27, 28), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
12981
13614
  _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
12982
13615
  &default_val, &ret);
12983
13616
  return ret;
12984
13617
  }
12985
13618
  UPB_INLINE bool google_protobuf_FeatureSet_has_field_presence(const google_protobuf_FeatureSet* msg) {
12986
- const upb_MiniTableField field = {1, 12, 64, 24, 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13619
+ const upb_MiniTableField field = {1, 12, 64, UPB_SIZE(27, 28), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
12987
13620
  return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
12988
13621
  }
12989
13622
  UPB_INLINE void google_protobuf_FeatureSet_clear_enum_type(google_protobuf_FeatureSet* msg) {
12990
- const upb_MiniTableField field = {2, 16, 65, UPB_SIZE(22, 23), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13623
+ const upb_MiniTableField field = {2, 16, 65, UPB_SIZE(25, 27), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
12991
13624
  upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
12992
13625
  }
12993
13626
  UPB_INLINE int32_t google_protobuf_FeatureSet_enum_type(const google_protobuf_FeatureSet* msg) {
12994
13627
  int32_t default_val = 0;
12995
13628
  int32_t ret;
12996
- const upb_MiniTableField field = {2, 16, 65, UPB_SIZE(22, 23), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13629
+ const upb_MiniTableField field = {2, 16, 65, UPB_SIZE(25, 27), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
12997
13630
  _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
12998
13631
  &default_val, &ret);
12999
13632
  return ret;
13000
13633
  }
13001
13634
  UPB_INLINE bool google_protobuf_FeatureSet_has_enum_type(const google_protobuf_FeatureSet* msg) {
13002
- const upb_MiniTableField field = {2, 16, 65, UPB_SIZE(22, 23), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13635
+ const upb_MiniTableField field = {2, 16, 65, UPB_SIZE(25, 27), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13003
13636
  return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
13004
13637
  }
13005
13638
  UPB_INLINE void google_protobuf_FeatureSet_clear_repeated_field_encoding(google_protobuf_FeatureSet* msg) {
13006
- const upb_MiniTableField field = {3, 20, 66, UPB_SIZE(20, 22), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13639
+ const upb_MiniTableField field = {3, 20, 66, UPB_SIZE(23, 26), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13007
13640
  upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
13008
13641
  }
13009
13642
  UPB_INLINE int32_t google_protobuf_FeatureSet_repeated_field_encoding(const google_protobuf_FeatureSet* msg) {
13010
13643
  int32_t default_val = 0;
13011
13644
  int32_t ret;
13012
- const upb_MiniTableField field = {3, 20, 66, UPB_SIZE(20, 22), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13645
+ const upb_MiniTableField field = {3, 20, 66, UPB_SIZE(23, 26), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13013
13646
  _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
13014
13647
  &default_val, &ret);
13015
13648
  return ret;
13016
13649
  }
13017
13650
  UPB_INLINE bool google_protobuf_FeatureSet_has_repeated_field_encoding(const google_protobuf_FeatureSet* msg) {
13018
- const upb_MiniTableField field = {3, 20, 66, UPB_SIZE(20, 22), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13651
+ const upb_MiniTableField field = {3, 20, 66, UPB_SIZE(23, 26), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13019
13652
  return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
13020
13653
  }
13021
13654
  UPB_INLINE void google_protobuf_FeatureSet_clear_utf8_validation(google_protobuf_FeatureSet* msg) {
13022
- const upb_MiniTableField field = {4, 24, 67, UPB_SIZE(18, 21), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13655
+ const upb_MiniTableField field = {4, 24, 67, UPB_SIZE(21, 25), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13023
13656
  upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
13024
13657
  }
13025
13658
  UPB_INLINE int32_t google_protobuf_FeatureSet_utf8_validation(const google_protobuf_FeatureSet* msg) {
13026
13659
  int32_t default_val = 0;
13027
13660
  int32_t ret;
13028
- const upb_MiniTableField field = {4, 24, 67, UPB_SIZE(18, 21), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13661
+ const upb_MiniTableField field = {4, 24, 67, UPB_SIZE(21, 25), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13029
13662
  _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
13030
13663
  &default_val, &ret);
13031
13664
  return ret;
13032
13665
  }
13033
13666
  UPB_INLINE bool google_protobuf_FeatureSet_has_utf8_validation(const google_protobuf_FeatureSet* msg) {
13034
- const upb_MiniTableField field = {4, 24, 67, UPB_SIZE(18, 21), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13667
+ const upb_MiniTableField field = {4, 24, 67, UPB_SIZE(21, 25), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13035
13668
  return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
13036
13669
  }
13037
13670
  UPB_INLINE void google_protobuf_FeatureSet_clear_message_encoding(google_protobuf_FeatureSet* msg) {
13038
- const upb_MiniTableField field = {5, 28, 68, UPB_SIZE(16, 20), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13671
+ const upb_MiniTableField field = {5, 28, 68, UPB_SIZE(19, 24), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13039
13672
  upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
13040
13673
  }
13041
13674
  UPB_INLINE int32_t google_protobuf_FeatureSet_message_encoding(const google_protobuf_FeatureSet* msg) {
13042
13675
  int32_t default_val = 0;
13043
13676
  int32_t ret;
13044
- const upb_MiniTableField field = {5, 28, 68, UPB_SIZE(16, 20), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13677
+ const upb_MiniTableField field = {5, 28, 68, UPB_SIZE(19, 24), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13045
13678
  _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
13046
13679
  &default_val, &ret);
13047
13680
  return ret;
13048
13681
  }
13049
13682
  UPB_INLINE bool google_protobuf_FeatureSet_has_message_encoding(const google_protobuf_FeatureSet* msg) {
13050
- const upb_MiniTableField field = {5, 28, 68, UPB_SIZE(16, 20), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13683
+ const upb_MiniTableField field = {5, 28, 68, UPB_SIZE(19, 24), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13051
13684
  return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
13052
13685
  }
13053
13686
  UPB_INLINE void google_protobuf_FeatureSet_clear_json_format(google_protobuf_FeatureSet* msg) {
13054
- const upb_MiniTableField field = {6, 32, 69, UPB_SIZE(14, 19), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13687
+ const upb_MiniTableField field = {6, 32, 69, UPB_SIZE(17, 23), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13055
13688
  upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
13056
13689
  }
13057
13690
  UPB_INLINE int32_t google_protobuf_FeatureSet_json_format(const google_protobuf_FeatureSet* msg) {
13058
13691
  int32_t default_val = 0;
13059
13692
  int32_t ret;
13060
- const upb_MiniTableField field = {6, 32, 69, UPB_SIZE(14, 19), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13693
+ const upb_MiniTableField field = {6, 32, 69, UPB_SIZE(17, 23), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13061
13694
  _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
13062
13695
  &default_val, &ret);
13063
13696
  return ret;
13064
13697
  }
13065
13698
  UPB_INLINE bool google_protobuf_FeatureSet_has_json_format(const google_protobuf_FeatureSet* msg) {
13066
- const upb_MiniTableField field = {6, 32, 69, UPB_SIZE(14, 19), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13699
+ const upb_MiniTableField field = {6, 32, 69, UPB_SIZE(17, 23), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13067
13700
  return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
13068
13701
  }
13069
13702
  UPB_INLINE void google_protobuf_FeatureSet_clear_enforce_naming_style(google_protobuf_FeatureSet* msg) {
13070
- const upb_MiniTableField field = {7, 36, 70, UPB_SIZE(12, 18), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13703
+ const upb_MiniTableField field = {7, 36, 70, UPB_SIZE(15, 22), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13071
13704
  upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
13072
13705
  }
13073
13706
  UPB_INLINE int32_t google_protobuf_FeatureSet_enforce_naming_style(const google_protobuf_FeatureSet* msg) {
13074
13707
  int32_t default_val = 0;
13075
13708
  int32_t ret;
13076
- const upb_MiniTableField field = {7, 36, 70, UPB_SIZE(12, 18), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13709
+ const upb_MiniTableField field = {7, 36, 70, UPB_SIZE(15, 22), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13077
13710
  _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
13078
13711
  &default_val, &ret);
13079
13712
  return ret;
13080
13713
  }
13081
13714
  UPB_INLINE bool google_protobuf_FeatureSet_has_enforce_naming_style(const google_protobuf_FeatureSet* msg) {
13082
- const upb_MiniTableField field = {7, 36, 70, UPB_SIZE(12, 18), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13715
+ const upb_MiniTableField field = {7, 36, 70, UPB_SIZE(15, 22), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13083
13716
  return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
13084
13717
  }
13085
13718
  UPB_INLINE void google_protobuf_FeatureSet_clear_default_symbol_visibility(google_protobuf_FeatureSet* msg) {
13086
- const upb_MiniTableField field = {8, 40, 71, UPB_SIZE(10, 17), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13719
+ const upb_MiniTableField field = {8, 40, 71, UPB_SIZE(13, 21), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13087
13720
  upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
13088
13721
  }
13089
13722
  UPB_INLINE int32_t google_protobuf_FeatureSet_default_symbol_visibility(const google_protobuf_FeatureSet* msg) {
13090
13723
  int32_t default_val = 0;
13091
13724
  int32_t ret;
13092
- const upb_MiniTableField field = {8, 40, 71, UPB_SIZE(10, 17), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13725
+ const upb_MiniTableField field = {8, 40, 71, UPB_SIZE(13, 21), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13093
13726
  _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
13094
13727
  &default_val, &ret);
13095
13728
  return ret;
13096
13729
  }
13097
13730
  UPB_INLINE bool google_protobuf_FeatureSet_has_default_symbol_visibility(const google_protobuf_FeatureSet* msg) {
13098
- const upb_MiniTableField field = {8, 40, 71, UPB_SIZE(10, 17), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13731
+ const upb_MiniTableField field = {8, 40, 71, UPB_SIZE(13, 21), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13732
+ return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
13733
+ }
13734
+ UPB_INLINE void google_protobuf_FeatureSet_clear_enforce_proto_limits(google_protobuf_FeatureSet* msg) {
13735
+ const upb_MiniTableField field = {9, 44, 72, UPB_SIZE(11, 20), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13736
+ upb_Message_ClearBaseField(UPB_UPCAST(msg), &field);
13737
+ }
13738
+ UPB_INLINE int32_t google_protobuf_FeatureSet_enforce_proto_limits(const google_protobuf_FeatureSet* msg) {
13739
+ int32_t default_val = 0;
13740
+ int32_t ret;
13741
+ const upb_MiniTableField field = {9, 44, 72, UPB_SIZE(11, 20), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13742
+ _upb_Message_GetNonExtensionField(UPB_UPCAST(msg), &field,
13743
+ &default_val, &ret);
13744
+ return ret;
13745
+ }
13746
+ UPB_INLINE bool google_protobuf_FeatureSet_has_enforce_proto_limits(const google_protobuf_FeatureSet* msg) {
13747
+ const upb_MiniTableField field = {9, 44, 72, UPB_SIZE(11, 20), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13099
13748
  return upb_Message_HasBaseField(UPB_UPCAST(msg), &field);
13100
13749
  }
13101
13750
 
13102
13751
  UPB_INLINE void google_protobuf_FeatureSet_set_field_presence(google_protobuf_FeatureSet* msg, int32_t value) {
13103
- const upb_MiniTableField field = {1, 12, 64, 24, 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13752
+ const upb_MiniTableField field = {1, 12, 64, UPB_SIZE(27, 28), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13104
13753
  upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13105
13754
  }
13106
13755
  UPB_INLINE void google_protobuf_FeatureSet_set_enum_type(google_protobuf_FeatureSet* msg, int32_t value) {
13107
- const upb_MiniTableField field = {2, 16, 65, UPB_SIZE(22, 23), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13756
+ const upb_MiniTableField field = {2, 16, 65, UPB_SIZE(25, 27), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13108
13757
  upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13109
13758
  }
13110
13759
  UPB_INLINE void google_protobuf_FeatureSet_set_repeated_field_encoding(google_protobuf_FeatureSet* msg, int32_t value) {
13111
- const upb_MiniTableField field = {3, 20, 66, UPB_SIZE(20, 22), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13760
+ const upb_MiniTableField field = {3, 20, 66, UPB_SIZE(23, 26), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13112
13761
  upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13113
13762
  }
13114
13763
  UPB_INLINE void google_protobuf_FeatureSet_set_utf8_validation(google_protobuf_FeatureSet* msg, int32_t value) {
13115
- const upb_MiniTableField field = {4, 24, 67, UPB_SIZE(18, 21), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13764
+ const upb_MiniTableField field = {4, 24, 67, UPB_SIZE(21, 25), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13116
13765
  upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13117
13766
  }
13118
13767
  UPB_INLINE void google_protobuf_FeatureSet_set_message_encoding(google_protobuf_FeatureSet* msg, int32_t value) {
13119
- const upb_MiniTableField field = {5, 28, 68, UPB_SIZE(16, 20), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13768
+ const upb_MiniTableField field = {5, 28, 68, UPB_SIZE(19, 24), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13120
13769
  upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13121
13770
  }
13122
13771
  UPB_INLINE void google_protobuf_FeatureSet_set_json_format(google_protobuf_FeatureSet* msg, int32_t value) {
13123
- const upb_MiniTableField field = {6, 32, 69, UPB_SIZE(14, 19), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13772
+ const upb_MiniTableField field = {6, 32, 69, UPB_SIZE(17, 23), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13124
13773
  upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13125
13774
  }
13126
13775
  UPB_INLINE void google_protobuf_FeatureSet_set_enforce_naming_style(google_protobuf_FeatureSet* msg, int32_t value) {
13127
- const upb_MiniTableField field = {7, 36, 70, UPB_SIZE(12, 18), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13776
+ const upb_MiniTableField field = {7, 36, 70, UPB_SIZE(15, 22), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13128
13777
  upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13129
13778
  }
13130
13779
  UPB_INLINE void google_protobuf_FeatureSet_set_default_symbol_visibility(google_protobuf_FeatureSet* msg, int32_t value) {
13131
- const upb_MiniTableField field = {8, 40, 71, UPB_SIZE(10, 17), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13780
+ const upb_MiniTableField field = {8, 40, 71, UPB_SIZE(13, 21), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13781
+ upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13782
+ }
13783
+ UPB_INLINE void google_protobuf_FeatureSet_set_enforce_proto_limits(google_protobuf_FeatureSet* msg, int32_t value) {
13784
+ const upb_MiniTableField field = {9, 44, 72, UPB_SIZE(11, 20), 14, (int)kUpb_FieldMode_Scalar | ((int)kUpb_FieldRep_4Byte << kUpb_FieldRep_Shift)};
13132
13785
  upb_Message_SetBaseField((upb_Message*)msg, &field, &value);
13133
13786
  }
13134
13787
 
@@ -13172,6 +13825,46 @@ UPB_INLINE char* google_protobuf_FeatureSet_VisibilityFeature_serialize_ex(const
13172
13825
  }
13173
13826
 
13174
13827
 
13828
+ /* google.protobuf.FeatureSet.ProtoLimitsFeature */
13829
+ UPB_INLINE google_protobuf_FeatureSet_ProtoLimitsFeature* google_protobuf_FeatureSet_ProtoLimitsFeature_new(upb_Arena* arena) {
13830
+ return (google_protobuf_FeatureSet_ProtoLimitsFeature*)_upb_Message_New(&google__protobuf__FeatureSet__ProtoLimitsFeature_msg_init, arena);
13831
+ }
13832
+ UPB_INLINE google_protobuf_FeatureSet_ProtoLimitsFeature* google_protobuf_FeatureSet_ProtoLimitsFeature_parse(const char* buf, size_t size,
13833
+ upb_Arena* arena) {
13834
+ google_protobuf_FeatureSet_ProtoLimitsFeature* ret = google_protobuf_FeatureSet_ProtoLimitsFeature_new(arena);
13835
+ if (!ret) return NULL;
13836
+ if (upb_Decode(buf, size, UPB_UPCAST(ret), &google__protobuf__FeatureSet__ProtoLimitsFeature_msg_init, NULL, 0,
13837
+ arena) != kUpb_DecodeStatus_Ok) {
13838
+ return NULL;
13839
+ }
13840
+ return ret;
13841
+ }
13842
+ UPB_INLINE google_protobuf_FeatureSet_ProtoLimitsFeature* google_protobuf_FeatureSet_ProtoLimitsFeature_parse_ex(
13843
+ const char* buf, size_t size, const upb_ExtensionRegistry* extreg,
13844
+ int options, upb_Arena* arena) {
13845
+ google_protobuf_FeatureSet_ProtoLimitsFeature* ret = google_protobuf_FeatureSet_ProtoLimitsFeature_new(arena);
13846
+ if (!ret) return NULL;
13847
+ if (upb_Decode(buf, size, UPB_UPCAST(ret), &google__protobuf__FeatureSet__ProtoLimitsFeature_msg_init, extreg,
13848
+ options, arena) != kUpb_DecodeStatus_Ok) {
13849
+ return NULL;
13850
+ }
13851
+ return ret;
13852
+ }
13853
+ UPB_INLINE char* google_protobuf_FeatureSet_ProtoLimitsFeature_serialize(const google_protobuf_FeatureSet_ProtoLimitsFeature* msg,
13854
+ upb_Arena* arena, size_t* len) {
13855
+ char* ptr;
13856
+ (void)upb_Encode(UPB_UPCAST(msg), &google__protobuf__FeatureSet__ProtoLimitsFeature_msg_init, 0, arena, &ptr, len);
13857
+ return ptr;
13858
+ }
13859
+ UPB_INLINE char* google_protobuf_FeatureSet_ProtoLimitsFeature_serialize_ex(const google_protobuf_FeatureSet_ProtoLimitsFeature* msg,
13860
+ int options, upb_Arena* arena,
13861
+ size_t* len) {
13862
+ char* ptr;
13863
+ (void)upb_Encode(UPB_UPCAST(msg), &google__protobuf__FeatureSet__ProtoLimitsFeature_msg_init, options, arena, &ptr, len);
13864
+ return ptr;
13865
+ }
13866
+
13867
+
13175
13868
  /* google.protobuf.FeatureSetDefaults */
13176
13869
  UPB_INLINE google_protobuf_FeatureSetDefaults* google_protobuf_FeatureSetDefaults_new(upb_Arena* arena) {
13177
13870
  return (google_protobuf_FeatureSetDefaults*)_upb_Message_New(&google__protobuf__FeatureSetDefaults_msg_init, arena);
@@ -14213,60 +14906,6 @@ typedef struct upb_DefBuilder upb_DefBuilder;
14213
14906
 
14214
14907
  #endif /* UPB_REFLECTION_COMMON_H_ */
14215
14908
 
14216
- #ifndef UPB_REFLECTION_DEF_TYPE_H_
14217
- #define UPB_REFLECTION_DEF_TYPE_H_
14218
-
14219
-
14220
- // Must be last.
14221
-
14222
- // Inside a symtab we store tagged pointers to specific def types.
14223
- typedef enum {
14224
- UPB_DEFTYPE_MASK = 7,
14225
-
14226
- // Only inside symtab table.
14227
- UPB_DEFTYPE_EXT = 0,
14228
- UPB_DEFTYPE_MSG = 1,
14229
- UPB_DEFTYPE_ENUM = 2,
14230
- UPB_DEFTYPE_ENUMVAL = 3,
14231
- UPB_DEFTYPE_SERVICE = 4,
14232
-
14233
- // Only inside message table.
14234
- UPB_DEFTYPE_FIELD = 0,
14235
- UPB_DEFTYPE_ONEOF = 1,
14236
-
14237
- // Only inside service table.
14238
- UPB_DEFTYPE_METHOD = 0,
14239
- } upb_deftype_t;
14240
-
14241
- #ifdef __cplusplus
14242
- extern "C" {
14243
- #endif
14244
-
14245
- // Our 3-bit pointer tagging requires all pointers to be multiples of 8.
14246
- // The arena will always yield 8-byte-aligned addresses, however we put
14247
- // the defs into arrays. For each element in the array to be 8-byte-aligned,
14248
- // the sizes of each def type must also be a multiple of 8.
14249
- //
14250
- // If any of these asserts fail, we need to add or remove padding on 32-bit
14251
- // machines (64-bit machines will have 8-byte alignment already due to
14252
- // pointers, which all of these structs have).
14253
- UPB_INLINE void _upb_DefType_CheckPadding(size_t size) {
14254
- UPB_ASSERT((size & UPB_DEFTYPE_MASK) == 0);
14255
- }
14256
-
14257
- upb_deftype_t _upb_DefType_Type(upb_value v);
14258
-
14259
- upb_value _upb_DefType_Pack(const void* ptr, upb_deftype_t type);
14260
-
14261
- const void* _upb_DefType_Unpack(upb_value v, upb_deftype_t type);
14262
-
14263
- #ifdef __cplusplus
14264
- } /* extern "C" */
14265
- #endif
14266
-
14267
-
14268
- #endif /* UPB_REFLECTION_DEF_TYPE_H_ */
14269
-
14270
14909
  // Must be last.
14271
14910
 
14272
14911
  #ifdef __cplusplus
@@ -14275,15 +14914,14 @@ extern "C" {
14275
14914
 
14276
14915
  UPB_API void upb_DefPool_Free(upb_DefPool* s);
14277
14916
 
14278
- UPB_API upb_DefPool* upb_DefPool_New(void);
14917
+ UPB_NODISCARD UPB_API upb_DefPool* upb_DefPool_New(void);
14279
14918
 
14280
14919
  UPB_API const google_protobuf_FeatureSetDefaults* upb_DefPool_FeatureSetDefaults(
14281
14920
  const upb_DefPool* s);
14282
14921
 
14283
- UPB_API bool upb_DefPool_SetFeatureSetDefaults(upb_DefPool* s,
14284
- const char* serialized_defaults,
14285
- size_t serialized_len,
14286
- upb_Status* status);
14922
+ UPB_NODISCARD UPB_API bool upb_DefPool_SetFeatureSetDefaults(
14923
+ upb_DefPool* s, const char* serialized_defaults, size_t serialized_len,
14924
+ upb_Status* status);
14287
14925
 
14288
14926
  UPB_API const upb_MessageDef* upb_DefPool_FindMessageByName(
14289
14927
  const upb_DefPool* s, const char* sym);
@@ -14332,7 +14970,7 @@ const upb_ServiceDef* upb_DefPool_FindServiceByNameWithSize(
14332
14970
  const upb_FileDef* upb_DefPool_FindFileContainingSymbol(const upb_DefPool* s,
14333
14971
  const char* name);
14334
14972
 
14335
- UPB_API const upb_FileDef* upb_DefPool_AddFile(
14973
+ UPB_NODISCARD UPB_API const upb_FileDef* upb_DefPool_AddFile(
14336
14974
  upb_DefPool* s, const google_protobuf_FileDescriptorProto* file_proto,
14337
14975
  upb_Status* status);
14338
14976
 
@@ -14404,8 +15042,9 @@ bool upb_EnumDef_HasOptions(const upb_EnumDef* e);
14404
15042
  bool upb_EnumDef_IsClosed(const upb_EnumDef* e);
14405
15043
 
14406
15044
  // Creates a mini descriptor string for an enum, returns true on success.
14407
- bool upb_EnumDef_MiniDescriptorEncode(const upb_EnumDef* e, upb_Arena* a,
14408
- upb_StringView* out);
15045
+ UPB_NODISCARD bool upb_EnumDef_MiniDescriptorEncode(const upb_EnumDef* e,
15046
+ upb_Arena* a,
15047
+ upb_StringView* out);
14409
15048
 
14410
15049
  const char* upb_EnumDef_Name(const upb_EnumDef* e);
14411
15050
  const google_protobuf_EnumOptions* upb_EnumDef_Options(const upb_EnumDef* e);
@@ -14541,8 +15180,9 @@ bool _upb_FieldDef_ValidateUtf8(const upb_FieldDef* f);
14541
15180
  bool _upb_FieldDef_IsGroupLike(const upb_FieldDef* f);
14542
15181
 
14543
15182
  // Creates a mini descriptor string for a field, returns true on success.
14544
- bool upb_FieldDef_MiniDescriptorEncode(const upb_FieldDef* f, upb_Arena* a,
14545
- upb_StringView* out);
15183
+ UPB_NODISCARD bool upb_FieldDef_MiniDescriptorEncode(const upb_FieldDef* f,
15184
+ upb_Arena* a,
15185
+ upb_StringView* out);
14546
15186
 
14547
15187
  const upb_MiniTableField* upb_FieldDef_MiniTable(const upb_FieldDef* f);
14548
15188
  const upb_MiniTableExtension* upb_FieldDef_MiniTableExtension(
@@ -14719,8 +15359,9 @@ bool upb_MessageDef_IsMapEntry(const upb_MessageDef* m);
14719
15359
  bool upb_MessageDef_IsMessageSet(const upb_MessageDef* m);
14720
15360
 
14721
15361
  // Creates a mini descriptor string for a message, returns true on success.
14722
- bool upb_MessageDef_MiniDescriptorEncode(const upb_MessageDef* m, upb_Arena* a,
14723
- upb_StringView* out);
15362
+ UPB_NODISCARD bool upb_MessageDef_MiniDescriptorEncode(const upb_MessageDef* m,
15363
+ upb_Arena* a,
15364
+ upb_StringView* out);
14724
15365
 
14725
15366
  UPB_API const upb_MiniTable* upb_MessageDef_MiniTable(const upb_MessageDef* m);
14726
15367
  const char* upb_MessageDef_Name(const upb_MessageDef* m);
@@ -14888,17 +15529,17 @@ enum {
14888
15529
  kUpb_JsonDecodeResult_Error = 2,
14889
15530
  };
14890
15531
 
14891
- UPB_API int upb_JsonDecodeDetectingNonconformance(const char* buf, size_t size,
14892
- upb_Message* msg,
14893
- const upb_MessageDef* m,
14894
- const upb_DefPool* symtab,
14895
- int options, upb_Arena* arena,
14896
- upb_Status* status);
15532
+ UPB_NODISCARD UPB_API int upb_JsonDecodeDetectingNonconformance(
15533
+ const char* buf, size_t size, upb_Message* msg, const upb_MessageDef* m,
15534
+ const upb_DefPool* symtab, int options, upb_Arena* arena,
15535
+ upb_Status* status);
14897
15536
 
14898
- UPB_API_INLINE bool upb_JsonDecode(const char* buf, size_t size,
14899
- upb_Message* msg, const upb_MessageDef* m,
14900
- const upb_DefPool* symtab, int options,
14901
- upb_Arena* arena, upb_Status* status) {
15537
+ UPB_NODISCARD UPB_API_INLINE bool upb_JsonDecode(const char* buf, size_t size,
15538
+ upb_Message* msg,
15539
+ const upb_MessageDef* m,
15540
+ const upb_DefPool* symtab,
15541
+ int options, upb_Arena* arena,
15542
+ upb_Status* status) {
14902
15543
  return upb_JsonDecodeDetectingNonconformance(buf, size, msg, m, symtab,
14903
15544
  options, arena, status) ==
14904
15545
  kUpb_JsonDecodeResult_Ok;
@@ -15004,9 +15645,8 @@ extern "C" {
15004
15645
  // Returns a mutable pointer to a map, array, or submessage value. If the given
15005
15646
  // arena is non-NULL this will construct a new object if it was not previously
15006
15647
  // present. May not be called for primitive fields.
15007
- UPB_API upb_MutableMessageValue upb_Message_Mutable(upb_Message* msg,
15008
- const upb_FieldDef* f,
15009
- upb_Arena* a);
15648
+ UPB_NODISCARD UPB_API upb_MutableMessageValue
15649
+ upb_Message_Mutable(upb_Message* msg, const upb_FieldDef* f, upb_Arena* a);
15010
15650
 
15011
15651
  // Returns the field that is set in the oneof, or NULL if none are set.
15012
15652
  UPB_API const upb_FieldDef* upb_Message_WhichOneofByDef(const upb_Message* msg,
@@ -15032,8 +15672,10 @@ UPB_API upb_MessageValue upb_Message_GetFieldByDef(const upb_Message* msg,
15032
15672
  // the same arena or a different arena that outlives it).
15033
15673
  //
15034
15674
  // Returns false if allocation fails.
15035
- UPB_API bool upb_Message_SetFieldByDef(upb_Message* msg, const upb_FieldDef* f,
15036
- upb_MessageValue val, upb_Arena* a);
15675
+ UPB_NODISCARD UPB_API bool upb_Message_SetFieldByDef(upb_Message* msg,
15676
+ const upb_FieldDef* f,
15677
+ upb_MessageValue val,
15678
+ upb_Arena* a);
15037
15679
 
15038
15680
  // Iterate over present fields.
15039
15681
  //
@@ -15158,24 +15800,6 @@ UPB_INLINE int _upb_vsnprintf(char* buf, size_t size, const char* fmt,
15158
15800
 
15159
15801
  #endif // UPB_PORT_VSNPRINTF_COMPAT_H_
15160
15802
 
15161
- #ifndef UPB_LEX_STRTOD_H_
15162
- #define UPB_LEX_STRTOD_H_
15163
-
15164
- // Must be last.
15165
-
15166
- #ifdef __cplusplus
15167
- extern "C" {
15168
- #endif
15169
-
15170
- double _upb_NoLocaleStrtod(const char *str, char **endptr);
15171
-
15172
- #ifdef __cplusplus
15173
- } /* extern "C" */
15174
- #endif
15175
-
15176
-
15177
- #endif /* UPB_LEX_STRTOD_H_ */
15178
-
15179
15803
  #ifndef UPB_PORT_ATOMIC_H_
15180
15804
  #define UPB_PORT_ATOMIC_H_
15181
15805
 
@@ -15633,130 +16257,115 @@ bool _upb_mapsorter_pushexts(_upb_mapsorter* s, const upb_Message_Internal* in,
15633
16257
 
15634
16258
  #endif /* UPB_MESSAGE_INTERNAL_MAP_SORTER_H_ */
15635
16259
 
15636
- #ifndef UPB_MESSAGE_COMPARE_H_
15637
- #define UPB_MESSAGE_COMPARE_H_
16260
+ #ifndef UPB_MESSAGE_UNKNOWN_FIELDS_H_
16261
+ #define UPB_MESSAGE_UNKNOWN_FIELDS_H_
15638
16262
 
15639
16263
  #include <stddef.h>
16264
+ #include <stdint.h>
15640
16265
 
15641
16266
 
15642
16267
  // Must be last.
15643
16268
 
15644
- enum {
15645
- // If set, upb_Message_IsEqual() will attempt to compare unknown fields.
15646
- // By its very nature this comparison is inexact.
15647
- kUpb_CompareOption_IncludeUnknownFields = (1 << 0)
15648
- };
15649
-
15650
16269
  #ifdef __cplusplus
15651
16270
  extern "C" {
15652
16271
  #endif
15653
16272
 
15654
- // Returns true if no known fields or extensions are set in the message.
15655
- UPB_API bool upb_Message_IsEmpty(const upb_Message* msg,
15656
- const upb_MiniTable* m);
15657
-
15658
- UPB_API bool upb_Message_IsEqual(const upb_Message* msg1,
15659
- const upb_Message* msg2,
15660
- const upb_MiniTable* m, int options);
15661
-
15662
- // If |ctype| is a message then |m| must point to its minitable.
15663
- UPB_API_INLINE bool upb_MessageValue_IsEqual(upb_MessageValue val1,
15664
- upb_MessageValue val2,
15665
- upb_CType ctype,
15666
- const upb_MiniTable* m,
15667
- int options) {
15668
- switch (ctype) {
15669
- case kUpb_CType_Bool:
15670
- return val1.bool_val == val2.bool_val;
15671
-
15672
- case kUpb_CType_Float:
15673
- case kUpb_CType_Int32:
15674
- case kUpb_CType_UInt32:
15675
- case kUpb_CType_Enum:
15676
- return val1.int32_val == val2.int32_val;
15677
-
15678
- case kUpb_CType_Double:
15679
- case kUpb_CType_Int64:
15680
- case kUpb_CType_UInt64:
15681
- return val1.int64_val == val2.int64_val;
15682
-
15683
- case kUpb_CType_String:
15684
- case kUpb_CType_Bytes:
15685
- return upb_StringView_IsEqual(val1.str_val, val2.str_val);
15686
-
15687
- case kUpb_CType_Message:
15688
- return upb_Message_IsEqual(val1.msg_val, val2.msg_val, m, options);
15689
-
15690
- default:
15691
- UPB_UNREACHABLE();
15692
- return false;
16273
+ // Support iteration over unknown (upb_MessageUnknown*), including unknown
16274
+ // upb_StringView and non-canonical extensions (upb_Extension*).
16275
+ UPB_INLINE bool upb_Message_NextUnknown2(const struct upb_Message* msg,
16276
+ struct upb_MessageUnknown* data,
16277
+ uintptr_t* iter) {
16278
+ const upb_Message_Internal* in = UPB_PRIVATE(_upb_Message_GetInternal)(msg);
16279
+ size_t i = *iter;
16280
+ if (in) {
16281
+ while (i < in->size) {
16282
+ upb_TaggedAuxPtr tagged_ptr = in->aux_data[i++];
16283
+ if (upb_TaggedAuxPtr_IsUnknownStringView(tagged_ptr)) {
16284
+ data->type = kUpb_MessageUnknownType_StringView;
16285
+ data->value.bytes = *upb_TaggedPtrAux_StringViewRepr(tagged_ptr);
16286
+ *iter = i;
16287
+ return true;
16288
+ } else if (upb_TaggedAuxPtr_IsNonCanonicalExtension(tagged_ptr)) {
16289
+ data->type = kUpb_MessageUnknownType_NonCanonicalExtension;
16290
+ data->value.extension =
16291
+ upb_TaggedAuxPtr_NonCanonicalExtension(tagged_ptr);
16292
+ *iter = i;
16293
+ return true;
16294
+ }
16295
+ }
15693
16296
  }
16297
+ data->type = kUpb_MessageUnknownType_StringView;
16298
+ data->value.bytes.size = 0;
16299
+ data->value.bytes.data = NULL;
16300
+ *iter = i;
16301
+ return false;
15694
16302
  }
15695
16303
 
15696
- #ifdef __cplusplus
15697
- } /* extern "C" */
15698
- #endif
15699
-
15700
-
15701
- #endif // UPB_MESSAGE_COMPARE_H_
15702
-
15703
- #ifndef UPB_MESSAGE_INTERNAL_COMPARE_UNKNOWN_H_
15704
- #define UPB_MESSAGE_INTERNAL_COMPARE_UNKNOWN_H_
15705
-
15706
- #include <stddef.h>
15707
-
15708
- // Must be last.
15709
-
15710
- #ifdef __cplusplus
15711
- extern "C" {
15712
- #endif
16304
+ typedef enum {
16305
+ kUpb_FindUnknown_Ok,
16306
+ kUpb_FindUnknown_NotPresent,
16307
+ kUpb_FindUnknown_ParseError,
16308
+ } upb_FindUnknown_Status;
15713
16309
 
15714
- // Returns true if unknown fields from the two messages are equal when sorted
15715
- // and varints are made canonical.
16310
+ typedef struct {
16311
+ upb_FindUnknown_Status status;
16312
+ struct upb_MessageUnknown unknown;
16313
+ uintptr_t iter;
16314
+ } upb_FindUnknownRet2;
16315
+
16316
+ // Finds first occurrence of unknown data (upb_MessageUnknown) by tag id in
16317
+ // message, including unknown upb_StringView and non-canonical extensions
16318
+ // (upb_Extension*).
15716
16319
  //
15717
- // This function is discouraged, as the comparison is inherently lossy without
15718
- // schema data:
16320
+ // If multiple matching entries exist for the same field number (e.g. both a
16321
+ // raw unknown upb_StringView and a non-canonical extension), this function
16322
+ // returns the one encountered first in internal iteration order (which follows
16323
+ // the order they were added or parsed).
15719
16324
  //
15720
- // 1. We don't know whether delimited fields are sub-messages. Unknown
15721
- // sub-messages will therefore not have their fields sorted and varints
15722
- // canonicalized.
15723
- // 2. We don't know about oneof/non-repeated fields, which should semantically
15724
- // discard every value except the last.
16325
+ // A depth_limit of zero means to just use the upb default depth limit.
16326
+ upb_FindUnknownRet2 upb_Message_FindUnknown2(const struct upb_Message* msg,
16327
+ uint32_t field_number,
16328
+ int depth_limit);
15725
16329
 
15726
- typedef enum {
15727
- kUpb_UnknownCompareResult_Equal = 0,
15728
- kUpb_UnknownCompareResult_NotEqual = 1,
15729
- kUpb_UnknownCompareResult_OutOfMemory = 2,
15730
- kUpb_UnknownCompareResult_MaxDepthExceeded = 3,
15731
- } upb_UnknownCompareResult;
15732
-
15733
- upb_UnknownCompareResult UPB_PRIVATE(_upb_Message_UnknownFieldsAreEqual)(
15734
- const upb_Message* msg1, const upb_Message* msg2, int max_depth);
16330
+ // Removes a segment of unknown data from the message, advancing to the next
16331
+ // segment. Returns false if the removed segment was at the end of the last
16332
+ // chunk.
16333
+ //
16334
+ // This must be done while iterating:
16335
+ //
16336
+ // uintptr_t iter = kUpb_Message_UnknownBegin;
16337
+ // upb_MessageUnknown data;
16338
+ // // Iterate chunks
16339
+ // while (upb_Message_NextUnknown2(msg, &data, &iter)) {
16340
+ // // Iterate within a chunk, deleting ranges
16341
+ // while (ShouldDeleteSubSegment(&data)) {
16342
+ // // Data now points to the region to be deleted
16343
+ // switch (upb_Message_DeleteUnknown2(msg, &data, &iter)) {
16344
+ // case kUpb_Message_DeleteUnknown_DeletedLast: return ok;
16345
+ // case kUpb_Message_DeleteUnknown_IterUpdated: break;
16346
+ // // If DeleteUnknown returned kUpb_Message_DeleteUnknown_IterUpdated,
16347
+ // // then data now points to the remaining unknown fields after the
16348
+ // // region that was just deleted.
16349
+ // case kUpb_Message_DeleteUnknown_AllocFail: return err;
16350
+ // }
16351
+ // }
16352
+ // }
16353
+ //
16354
+ // The range given in `data` must be contained inside the most recently
16355
+ // returned region.
16356
+ //
16357
+ // Support deletion of unknown (upb_MessageUnknown*), including unknown
16358
+ // upb_StringView and non-canonical extensions (upb_Extension*).
16359
+ UPB_NODISCARD upb_Message_DeleteUnknownStatus upb_Message_DeleteUnknown2(
16360
+ struct upb_Message* msg, struct upb_MessageUnknown* data, uintptr_t* iter,
16361
+ struct upb_Arena* arena);
15735
16362
 
15736
16363
  #ifdef __cplusplus
15737
16364
  } /* extern "C" */
15738
16365
  #endif
15739
16366
 
15740
16367
 
15741
- #endif /* UPB_MESSAGE_INTERNAL_COMPARE_UNKNOWN_H_ */
15742
-
15743
- #ifndef GOOGLE_UPB_UPB_MESSAGE_INTERNAL_ITERATOR_H__
15744
- #define GOOGLE_UPB_UPB_MESSAGE_INTERNAL_ITERATOR_H__
15745
-
15746
- #include <stddef.h>
15747
- #include <stdint.h>
15748
-
15749
-
15750
- // Must be last.
15751
-
15752
- #define kUpb_BaseField_Begin ((size_t)-1)
15753
- bool UPB_PRIVATE(_upb_Message_NextBaseField)(const upb_Message* msg,
15754
- const upb_MiniTable* m,
15755
- const upb_MiniTableField** out_f,
15756
- upb_MessageValue* out_v,
15757
- uintptr_t* iter);
15758
-
15759
- #endif // GOOGLE_UPB_UPB_MESSAGE_INTERNAL_ITERATOR_H__
16368
+ #endif /* UPB_MESSAGE_UNKNOWN_FIELDS_H_ */
15760
16369
 
15761
16370
  #ifndef UPB_WIRE_EPS_COPY_INPUT_STREAM_H_
15762
16371
  #define UPB_WIRE_EPS_COPY_INPUT_STREAM_H_
@@ -15765,77 +16374,6 @@ bool UPB_PRIVATE(_upb_Message_NextBaseField)(const upb_Message* msg,
15765
16374
  #include <stdint.h>
15766
16375
 
15767
16376
 
15768
- #ifndef GOOGLE_UPB_UPB_BASE_ERROR_HANDLER_H__
15769
- #define GOOGLE_UPB_UPB_BASE_ERROR_HANDLER_H__
15770
-
15771
- #include <setjmp.h>
15772
-
15773
- // Must be last.
15774
-
15775
- // upb_ErrorHandler is a standard longjmp()-based exception handler for UPB.
15776
- // It is used for efficient error handling in cases where longjmp() is safe to
15777
- // use, such as in highly performance-sensitive C parsing code.
15778
- //
15779
- // This structure contains both a jmp_buf and an error code; the error code is
15780
- // stored in the structure prior to calling longjmp(). This is necessary because
15781
- // per the C standard, it is not possible to store the result of setjmp(), so
15782
- // the error code must be passed out-of-band.
15783
- //
15784
- // upb_ErrorHandler is generally not C++-compatible, because longjmp() does not
15785
- // run C++ destructors. So any library that supports upb_ErrorHandler should
15786
- // also support a regular return-based error handling mechanism. (Note: we
15787
- // could conceivably extend this to take a callback, which could either call
15788
- // longjmp() or throw a C++ exception. But since C++ exceptions are forbidden
15789
- // by the C++ style guide, there's not likely to be a demand for this.)
15790
- //
15791
- // To support both cases (longjmp() or return-based status) efficiently, code
15792
- // can be written like this:
15793
- //
15794
- // UPB_ATTR_CONST bool upb_Arena_HasErrHandler(const upb_Arena* a);
15795
- //
15796
- // INLINE void* upb_Arena_Malloc(upb_Arena* a, size_t size) {
15797
- // if (UPB_UNLIKELY(a->end - a->ptr < size)) {
15798
- // void* ret = upb_Arena_MallocFallback(a, size);
15799
- // UPB_MAYBE_ASSUME(upb_Arena_HasErrHandler(a), ret != NULL);
15800
- // return ret;
15801
- // }
15802
- // void* ret = a->ptr;
15803
- // a->ptr += size;
15804
- // UPB_ASSUME(ret != NULL);
15805
- // return ret;
15806
- // }
15807
- //
15808
- // If the optimizer can prove that an error handler is present, it can assume
15809
- // that upb_Arena_Malloc() will not return NULL.
15810
-
15811
- // We need to standardize on any error code that might be thrown by an error
15812
- // handler.
15813
-
15814
- typedef enum {
15815
- kUpb_ErrorCode_Ok = 0,
15816
- kUpb_ErrorCode_OutOfMemory = 1,
15817
- kUpb_ErrorCode_Malformed = 2,
15818
- } upb_ErrorCode;
15819
-
15820
- typedef struct {
15821
- int code;
15822
- jmp_buf buf;
15823
- } upb_ErrorHandler;
15824
-
15825
- UPB_INLINE void upb_ErrorHandler_Init(upb_ErrorHandler* e) {
15826
- e->code = kUpb_ErrorCode_Ok;
15827
- }
15828
-
15829
- UPB_INLINE UPB_NORETURN void upb_ErrorHandler_ThrowError(upb_ErrorHandler* e,
15830
- int code) {
15831
- UPB_ASSERT(code != kUpb_ErrorCode_Ok);
15832
- e->code = code;
15833
- UPB_LONGJMP(e->buf, 1);
15834
- }
15835
-
15836
-
15837
- #endif // GOOGLE_UPB_UPB_BASE_ERROR_HANDLER_H__
15838
-
15839
16377
  #ifndef UPB_WIRE_INTERNAL_EPS_COPY_INPUT_STREAM_H_
15840
16378
  #define UPB_WIRE_INTERNAL_EPS_COPY_INPUT_STREAM_H_
15841
16379
 
@@ -15860,15 +16398,18 @@ extern "C" {
15860
16398
  // efficient fixed size copies.
15861
16399
  #define kUpb_EpsCopyInputStream_SlopBytes 16
15862
16400
 
16401
+ struct upb_EpsCopyCapture {
16402
+ const char* start; // Pointer to the beginning of the captured region.
16403
+ };
16404
+
15863
16405
  struct upb_EpsCopyInputStream {
15864
16406
  const char* end; // Can read up to SlopBytes bytes beyond this.
15865
16407
  const char* limit_ptr; // For bounds checks, = end + UPB_MIN(limit, 0)
15866
16408
  uintptr_t input_delta; // Diff between the original input pointer and patch
15867
- const char* buffer_start; // Pointer to the original input buffer
15868
- const char* capture_start; // If non-NULL, the start of the captured region.
15869
- ptrdiff_t limit; // Submessage limit relative to end
15870
- upb_ErrorHandler* err; // Error handler to use when things go wrong.
15871
- bool error; // To distinguish between EOF and error.
16409
+ const char* buffer_start; // Pointer to the original input buffer
16410
+ ptrdiff_t limit; // Submessage limit relative to end
16411
+ upb_ErrorHandler* err; // Error handler to use when things go wrong.
16412
+ bool error; // To distinguish between EOF and error.
15872
16413
  #ifndef NDEBUG
15873
16414
  int guaranteed_bytes;
15874
16415
  #endif
@@ -15890,7 +16431,6 @@ UPB_INLINE void upb_EpsCopyInputStream_InitWithErrorHandler(
15890
16431
  struct upb_EpsCopyInputStream* e, const char** ptr, size_t size,
15891
16432
  upb_ErrorHandler* err) {
15892
16433
  e->buffer_start = *ptr;
15893
- e->capture_start = NULL;
15894
16434
  e->err = err;
15895
16435
  if (size <= kUpb_EpsCopyInputStream_SlopBytes) {
15896
16436
  memset(&e->patch, 0, 32);
@@ -15920,11 +16460,21 @@ UPB_INLINE bool upb_EpsCopyInputStream_HasErrorHandler(
15920
16460
  return e && e->err != NULL;
15921
16461
  }
15922
16462
 
16463
+ UPB_NORETURN UPB_NOINLINE void UPB_PRIVATE(
16464
+ upb_EpsCopyInputStream_ThrowMalformed)(struct upb_EpsCopyInputStream* e);
16465
+
15923
16466
  // Call this function to signal an error. If an error handler is set, it will be
15924
16467
  // called and the function will never return. Otherwise, returns NULL to
15925
16468
  // indicate an error.
15926
- const char* UPB_PRIVATE(upb_EpsCopyInputStream_ReturnError)(
15927
- struct upb_EpsCopyInputStream* e);
16469
+ UPB_INLINE const char* UPB_PRIVATE(upb_EpsCopyInputStream_ReturnError)(
16470
+ struct upb_EpsCopyInputStream* e) {
16471
+ if (e->err) {
16472
+ UPB_PRIVATE(upb_EpsCopyInputStream_ThrowMalformed)(e);
16473
+ } else {
16474
+ e->error = true;
16475
+ }
16476
+ return NULL;
16477
+ }
15928
16478
 
15929
16479
  UPB_INLINE const char* UPB_PRIVATE(upb_EpsCopyInputStream_AssumeResult)(
15930
16480
  struct upb_EpsCopyInputStream* e, const char* ptr) {
@@ -16044,22 +16594,21 @@ UPB_INLINE const char* UPB_PRIVATE(upb_EpsCopyInputStream_GetInputPtr)(
16044
16594
  return e->buffer_start + position;
16045
16595
  }
16046
16596
 
16047
- UPB_INLINE void upb_EpsCopyInputStream_StartCapture(
16048
- struct upb_EpsCopyInputStream* e, const char* ptr) {
16049
- UPB_ASSERT(e->capture_start == NULL);
16050
- e->capture_start = UPB_PRIVATE(upb_EpsCopyInputStream_GetInputPtr)(e, ptr);
16597
+ UPB_INLINE void upb_EpsCopyCapture_Start(struct upb_EpsCopyCapture* c,
16598
+ struct upb_EpsCopyInputStream* e,
16599
+ const char* ptr) {
16600
+ c->start = UPB_PRIVATE(upb_EpsCopyInputStream_GetInputPtr)(e, ptr);
16051
16601
  }
16052
16602
 
16053
- UPB_INLINE bool upb_EpsCopyInputStream_EndCapture(
16054
- struct upb_EpsCopyInputStream* e, const char* ptr, upb_StringView* sv) {
16055
- UPB_ASSERT(e->capture_start != NULL);
16603
+ UPB_INLINE bool upb_EpsCopyCapture_End(struct upb_EpsCopyCapture* c,
16604
+ struct upb_EpsCopyInputStream* e,
16605
+ const char* ptr, upb_StringView* sv) {
16056
16606
  if (ptr - e->end > e->limit) {
16057
16607
  return UPB_PRIVATE(upb_EpsCopyInputStream_ReturnError)(e);
16058
16608
  }
16059
16609
  const char* end = UPB_PRIVATE(upb_EpsCopyInputStream_GetInputPtr)(e, ptr);
16060
- sv->data = e->capture_start;
16610
+ sv->data = c->start;
16061
16611
  sv->size = end - sv->data;
16062
- e->capture_start = NULL;
16063
16612
  return true;
16064
16613
  }
16065
16614
 
@@ -16147,7 +16696,7 @@ UPB_FORCEINLINE bool upb_EpsCopyInputStream_TryParseDelimitedFast(
16147
16696
  // Fast case: Sub-message is <128 bytes and fits in the current buffer.
16148
16697
  // This means we can preserve limit/limit_ptr verbatim.
16149
16698
  const char* saved_limit_ptr = e->limit_ptr;
16150
- int saved_limit = e->limit;
16699
+ ptrdiff_t saved_limit = e->limit;
16151
16700
  e->limit_ptr = *ptr + size;
16152
16701
  e->limit = e->limit_ptr - e->end;
16153
16702
  UPB_ASSERT(e->limit_ptr == e->end + UPB_MIN(0, e->limit));
@@ -16171,6 +16720,7 @@ UPB_FORCEINLINE bool upb_EpsCopyInputStream_TryParseDelimitedFast(
16171
16720
  extern "C" {
16172
16721
  #endif
16173
16722
 
16723
+ typedef struct upb_EpsCopyCapture upb_EpsCopyCapture;
16174
16724
  typedef struct upb_EpsCopyInputStream upb_EpsCopyInputStream;
16175
16725
 
16176
16726
  // Initializes a upb_EpsCopyInputStream using the contents of the buffer
@@ -16224,19 +16774,19 @@ UPB_INLINE bool upb_EpsCopyInputStream_IsDone(upb_EpsCopyInputStream* e,
16224
16774
  UPB_INLINE bool upb_EpsCopyInputStream_CheckSize(
16225
16775
  const upb_EpsCopyInputStream* e, const char* ptr, int size);
16226
16776
 
16227
- // Marks the start of a capture operation. Only one capture operation may be
16228
- // active at a time. The capture operation will be finalized by a call to
16229
- // upb_EpsCopyInputStream_EndCapture(). The captured string will be returned in
16230
- // sv, and will point to the original input buffer if possible.
16231
- UPB_INLINE void upb_EpsCopyInputStream_StartCapture(upb_EpsCopyInputStream* e,
16232
- const char* ptr);
16777
+ // Marks the start of a capture operation. The capture operation will be
16778
+ // finalized by a call to upb_EpsCopyCapture_End(). The captured string will
16779
+ // be returned in sv, and will point to the original input buffer if possible.
16780
+ UPB_INLINE void upb_EpsCopyCapture_Start(upb_EpsCopyCapture* c,
16781
+ upb_EpsCopyInputStream* e,
16782
+ const char* ptr);
16233
16783
 
16234
- // Ends a capture operation and returns the captured string. This may only be
16235
- // called once per capture operation. Returns false if the capture operation
16236
- // was invalid (the parsing pointer extends beyond the end of the stream).
16237
- UPB_INLINE bool upb_EpsCopyInputStream_EndCapture(upb_EpsCopyInputStream* e,
16238
- const char* ptr,
16239
- upb_StringView* sv);
16784
+ // Ends a capture operation and returns the captured string. Returns false if
16785
+ // the capture operation was invalid (the parsing pointer extends beyond the
16786
+ // end of the stream).
16787
+ UPB_INLINE bool upb_EpsCopyCapture_End(upb_EpsCopyCapture* c,
16788
+ upb_EpsCopyInputStream* e,
16789
+ const char* ptr, upb_StringView* sv);
16240
16790
 
16241
16791
  // Reads a string from the stream and advances the pointer accordingly. The
16242
16792
  // returned string view will always alias the input buffer.
@@ -16471,8 +17021,14 @@ UPB_FORCEINLINE const char* upb_WireReader_ReadVarint(
16471
17021
  // by calling upb_EpsCopyInputStream_IsDone().
16472
17022
  UPB_INLINE const char* upb_WireReader_SkipVarint(
16473
17023
  const char* ptr, upb_EpsCopyInputStream* stream) {
16474
- uint64_t val;
16475
- return upb_WireReader_ReadVarint(ptr, &val, stream);
17024
+ UPB_PRIVATE(upb_EpsCopyInputStream_ConsumeBytes)(stream, 10);
17025
+ const char* bound = ptr + 10;
17026
+ do {
17027
+ if ((*(ptr++) & 0x80) == 0) {
17028
+ return ptr;
17029
+ }
17030
+ } while (ptr != bound);
17031
+ return UPB_PRIVATE(upb_EpsCopyInputStream_ReturnError)(stream);
16476
17032
  }
16477
17033
 
16478
17034
  // Reads a varint indicating the size of a delimited field into `size`, or
@@ -16534,7 +17090,7 @@ UPB_INLINE const char* upb_WireReader_SkipGroup(
16534
17090
  return UPB_PRIVATE(upb_EpsCopyInputStream_AssumeResult)(stream, ret);
16535
17091
  }
16536
17092
 
16537
- UPB_INLINE const char* _upb_WireReader_SkipValue(
17093
+ UPB_FORCEINLINE const char* _upb_WireReader_SkipValueForceInline(
16538
17094
  const char* ptr, uint32_t tag, int depth_limit,
16539
17095
  upb_EpsCopyInputStream* stream) {
16540
17096
  switch (upb_WireReader_GetWireType(tag)) {
@@ -16566,29 +17122,160 @@ UPB_INLINE const char* _upb_WireReader_SkipValue(
16566
17122
  }
16567
17123
  }
16568
17124
 
16569
- // Skips data for a wire value of any type, returning a pointer past the end of
16570
- // the data, or NULL if there was an error parsing the group. The `tag` argument
16571
- // should be the tag that was just parsed. The `depth_limit` argument indicates
16572
- // how many levels of recursion a group is allowed to have before reporting a
16573
- // parse error (this limit exists to protect against stack overflow).
17125
+ UPB_INLINE const char* _upb_WireReader_SkipValue(
17126
+ const char* ptr, uint32_t tag, int depth_limit,
17127
+ upb_EpsCopyInputStream* stream) {
17128
+ return _upb_WireReader_SkipValueForceInline(ptr, tag, depth_limit, stream);
17129
+ }
17130
+
17131
+ // Skips data for a wire value of any type, returning a pointer past the end of
17132
+ // the data, or NULL if there was an error parsing the group. The `tag` argument
17133
+ // should be the tag that was just parsed. The `depth_limit` argument indicates
17134
+ // how many levels of recursion a group is allowed to have before reporting a
17135
+ // parse error (this limit exists to protect against stack overflow).
17136
+ //
17137
+ // REQUIRES: there must be at least 10 bytes of data available at `ptr`.
17138
+ // Bounds checks must be performed before calling this function, preferably
17139
+ // by calling upb_EpsCopyInputStream_IsDone().
17140
+ //
17141
+ // TODO: evaluate how the depth_limit should be specified. Do users need
17142
+ // control over this?
17143
+ UPB_INLINE const char* upb_WireReader_SkipValue(
17144
+ const char* ptr, uint32_t tag, upb_EpsCopyInputStream* stream) {
17145
+ return _upb_WireReader_SkipValue(ptr, tag, 100, stream);
17146
+ }
17147
+
17148
+ #ifdef __cplusplus
17149
+ } /* extern "C" */
17150
+ #endif
17151
+
17152
+
17153
+ #endif // UPB_WIRE_READER_H_
17154
+
17155
+ #ifndef UPB_MESSAGE_COMPARE_H_
17156
+ #define UPB_MESSAGE_COMPARE_H_
17157
+
17158
+ #include <stddef.h>
17159
+
17160
+
17161
+ // Must be last.
17162
+
17163
+ enum {
17164
+ // If set, upb_Message_IsEqual() will attempt to compare unknown fields.
17165
+ // By its very nature this comparison is inexact.
17166
+ kUpb_CompareOption_IncludeUnknownFields = (1 << 0)
17167
+ };
17168
+
17169
+ #ifdef __cplusplus
17170
+ extern "C" {
17171
+ #endif
17172
+
17173
+ // Returns true if no known fields or extensions are set in the message.
17174
+ UPB_API bool upb_Message_IsEmpty(const upb_Message* msg,
17175
+ const upb_MiniTable* m);
17176
+
17177
+ UPB_API bool upb_Message_IsEqual(const upb_Message* msg1,
17178
+ const upb_Message* msg2,
17179
+ const upb_MiniTable* m, int options);
17180
+
17181
+ // If |ctype| is a message then |m| must point to its minitable.
17182
+ UPB_API_INLINE bool upb_MessageValue_IsEqual(upb_MessageValue val1,
17183
+ upb_MessageValue val2,
17184
+ upb_CType ctype,
17185
+ const upb_MiniTable* m,
17186
+ int options) {
17187
+ switch (ctype) {
17188
+ case kUpb_CType_Bool:
17189
+ return val1.bool_val == val2.bool_val;
17190
+
17191
+ case kUpb_CType_Float:
17192
+ case kUpb_CType_Int32:
17193
+ case kUpb_CType_UInt32:
17194
+ case kUpb_CType_Enum:
17195
+ return val1.int32_val == val2.int32_val;
17196
+
17197
+ case kUpb_CType_Double:
17198
+ case kUpb_CType_Int64:
17199
+ case kUpb_CType_UInt64:
17200
+ return val1.int64_val == val2.int64_val;
17201
+
17202
+ case kUpb_CType_String:
17203
+ case kUpb_CType_Bytes:
17204
+ return upb_StringView_IsEqual(val1.str_val, val2.str_val);
17205
+
17206
+ case kUpb_CType_Message:
17207
+ return upb_Message_IsEqual(val1.msg_val, val2.msg_val, m, options);
17208
+
17209
+ default:
17210
+ UPB_UNREACHABLE();
17211
+ return false;
17212
+ }
17213
+ }
17214
+
17215
+ #ifdef __cplusplus
17216
+ } /* extern "C" */
17217
+ #endif
17218
+
17219
+
17220
+ #endif // UPB_MESSAGE_COMPARE_H_
17221
+
17222
+ #ifndef UPB_MESSAGE_INTERNAL_COMPARE_UNKNOWN_H_
17223
+ #define UPB_MESSAGE_INTERNAL_COMPARE_UNKNOWN_H_
17224
+
17225
+ #include <stddef.h>
17226
+
17227
+ // Must be last.
17228
+
17229
+ #ifdef __cplusplus
17230
+ extern "C" {
17231
+ #endif
17232
+
17233
+ // Returns true if unknown fields from the two messages are equal when sorted
17234
+ // and varints are made canonical.
16574
17235
  //
16575
- // REQUIRES: there must be at least 10 bytes of data available at `ptr`.
16576
- // Bounds checks must be performed before calling this function, preferably
16577
- // by calling upb_EpsCopyInputStream_IsDone().
17236
+ // This function is discouraged, as the comparison is inherently lossy without
17237
+ // schema data:
16578
17238
  //
16579
- // TODO: evaluate how the depth_limit should be specified. Do users need
16580
- // control over this?
16581
- UPB_INLINE const char* upb_WireReader_SkipValue(
16582
- const char* ptr, uint32_t tag, upb_EpsCopyInputStream* stream) {
16583
- return _upb_WireReader_SkipValue(ptr, tag, 100, stream);
16584
- }
17239
+ // 1. We don't know whether delimited fields are sub-messages. Unknown
17240
+ // sub-messages will therefore not have their fields sorted and varints
17241
+ // canonicalized.
17242
+ // 2. We don't know about oneof/non-repeated fields, which should semantically
17243
+ // discard every value except the last.
17244
+
17245
+ typedef enum {
17246
+ kUpb_UnknownCompareResult_Equal = 0,
17247
+ kUpb_UnknownCompareResult_NotEqual = 1,
17248
+ kUpb_UnknownCompareResult_OutOfMemory = 2,
17249
+ kUpb_UnknownCompareResult_MaxDepthExceeded = 3,
17250
+ } upb_UnknownCompareResult;
17251
+
17252
+ upb_UnknownCompareResult UPB_PRIVATE(_upb_Message_UnknownFieldsAreEqual)(
17253
+ const upb_Message* msg1, const upb_Message* msg2, int max_depth);
16585
17254
 
16586
17255
  #ifdef __cplusplus
16587
17256
  } /* extern "C" */
16588
17257
  #endif
16589
17258
 
16590
17259
 
16591
- #endif // UPB_WIRE_READER_H_
17260
+ #endif /* UPB_MESSAGE_INTERNAL_COMPARE_UNKNOWN_H_ */
17261
+
17262
+ #ifndef GOOGLE_UPB_UPB_MESSAGE_INTERNAL_ITERATOR_H__
17263
+ #define GOOGLE_UPB_UPB_MESSAGE_INTERNAL_ITERATOR_H__
17264
+
17265
+ #include <stddef.h>
17266
+ #include <stdint.h>
17267
+
17268
+
17269
+ // Must be last.
17270
+
17271
+ #define kUpb_BaseField_Begin ((size_t)-1)
17272
+ bool UPB_PRIVATE(_upb_Message_NextBaseField)(const upb_Message* msg,
17273
+ const upb_MiniTable* m,
17274
+ const upb_MiniTableField** out_f,
17275
+ upb_MessageValue* out_v,
17276
+ uintptr_t* iter);
17277
+
17278
+ #endif // GOOGLE_UPB_UPB_MESSAGE_INTERNAL_ITERATOR_H__
16592
17279
 
16593
17280
  #ifndef UPB_MESSAGE_COPY_H_
16594
17281
  #define UPB_MESSAGE_COPY_H_
@@ -16601,30 +17288,42 @@ extern "C" {
16601
17288
  #endif
16602
17289
 
16603
17290
  // Deep clones a message using the provided target arena.
16604
- upb_Message* upb_Message_DeepClone(const upb_Message* msg,
16605
- const upb_MiniTable* m, upb_Arena* arena);
17291
+ UPB_NODISCARD upb_Message* upb_Message_DeepClone(const upb_Message* msg,
17292
+ const upb_MiniTable* m,
17293
+ upb_Arena* arena);
16606
17294
 
16607
17295
  // Shallow clones a message using the provided target arena.
16608
- upb_Message* upb_Message_ShallowClone(const upb_Message* msg,
16609
- const upb_MiniTable* m, upb_Arena* arena);
17296
+ // `msg` must outlive the returned message since all strings, repeated fields,
17297
+ // maps, and unknown fields will alias the original message.
17298
+ UPB_NODISCARD upb_Message* upb_Message_ShallowClone(const upb_Message* msg,
17299
+ const upb_MiniTable* m,
17300
+ upb_Arena* arena);
16610
17301
 
16611
17302
  // Deep clones array contents.
16612
- upb_Array* upb_Array_DeepClone(const upb_Array* array, upb_CType value_type,
16613
- const upb_MiniTable* sub, upb_Arena* arena);
17303
+ UPB_NODISCARD upb_Array* upb_Array_DeepClone(const upb_Array* array,
17304
+ upb_CType value_type,
17305
+ const upb_MiniTable* sub,
17306
+ upb_Arena* arena);
16614
17307
 
16615
17308
  // Deep clones map contents.
16616
- upb_Map* upb_Map_DeepClone(const upb_Map* map, upb_CType key_type,
16617
- upb_CType value_type,
16618
- const upb_MiniTable* map_entry_table,
16619
- upb_Arena* arena);
17309
+ UPB_NODISCARD upb_Map* upb_Map_DeepClone(const upb_Map* map, upb_CType key_type,
17310
+ upb_CType value_type,
17311
+ const upb_MiniTable* map_entry_table,
17312
+ upb_Arena* arena);
16620
17313
 
16621
17314
  // Deep copies the message from src to dst.
16622
- bool upb_Message_DeepCopy(upb_Message* dst, const upb_Message* src,
16623
- const upb_MiniTable* m, upb_Arena* arena);
17315
+ UPB_NODISCARD bool upb_Message_DeepCopy(upb_Message* dst,
17316
+ const upb_Message* src,
17317
+ const upb_MiniTable* m,
17318
+ upb_Arena* arena);
16624
17319
 
16625
17320
  // Shallow copies the message from src to dst.
16626
- void upb_Message_ShallowCopy(upb_Message* dst, const upb_Message* src,
16627
- const upb_MiniTable* m);
17321
+ // `src` must outlive `dst` since all strings, repeated fields, maps, and
17322
+ // unknown fields will alias the original message.
17323
+ UPB_NODISCARD UPB_API bool upb_Message_ShallowCopy(upb_Message* dst,
17324
+ const upb_Message* src,
17325
+ const upb_MiniTable* m,
17326
+ upb_Arena* arena);
16628
17327
 
16629
17328
  #ifdef __cplusplus
16630
17329
  } /* extern "C" */
@@ -16642,10 +17341,9 @@ void upb_Message_ShallowCopy(upb_Message* dst, const upb_Message* src,
16642
17341
  extern "C" {
16643
17342
  #endif
16644
17343
 
16645
- UPB_API bool upb_Message_MergeFrom(upb_Message* dst, const upb_Message* src,
16646
- const upb_MiniTable* mt,
16647
- const upb_ExtensionRegistry* extreg,
16648
- upb_Arena* arena);
17344
+ UPB_NODISCARD UPB_API bool upb_Message_MergeFrom(
17345
+ upb_Message* dst, const upb_Message* src, const upb_MiniTable* mt,
17346
+ const upb_ExtensionRegistry* extreg, upb_Arena* arena);
16649
17347
 
16650
17348
  #ifdef __cplusplus
16651
17349
  } /* extern "C" */
@@ -17026,6 +17724,60 @@ const upb_ExtensionRegistry* _upb_DefPool_GeneratedExtensionRegistry(
17026
17724
 
17027
17725
  #endif /* UPB_REFLECTION_DEF_POOL_INTERNAL_H_ */
17028
17726
 
17727
+ #ifndef UPB_REFLECTION_DEF_TYPE_H_
17728
+ #define UPB_REFLECTION_DEF_TYPE_H_
17729
+
17730
+
17731
+ // Must be last.
17732
+
17733
+ // Inside a symtab we store tagged pointers to specific def types.
17734
+ typedef enum {
17735
+ UPB_DEFTYPE_MASK = 7,
17736
+
17737
+ // Only inside symtab table.
17738
+ UPB_DEFTYPE_EXT = 0,
17739
+ UPB_DEFTYPE_MSG = 1,
17740
+ UPB_DEFTYPE_ENUM = 2,
17741
+ UPB_DEFTYPE_ENUMVAL = 3,
17742
+ UPB_DEFTYPE_SERVICE = 4,
17743
+
17744
+ // Only inside message table.
17745
+ UPB_DEFTYPE_FIELD = 0,
17746
+ UPB_DEFTYPE_ONEOF = 1,
17747
+
17748
+ // Only inside service table.
17749
+ UPB_DEFTYPE_METHOD = 0,
17750
+ } upb_deftype_t;
17751
+
17752
+ #ifdef __cplusplus
17753
+ extern "C" {
17754
+ #endif
17755
+
17756
+ // Our 3-bit pointer tagging requires all pointers to be multiples of 8.
17757
+ // The arena will always yield 8-byte-aligned addresses, however we put
17758
+ // the defs into arrays. For each element in the array to be 8-byte-aligned,
17759
+ // the sizes of each def type must also be a multiple of 8.
17760
+ //
17761
+ // If any of these asserts fail, we need to add or remove padding on 32-bit
17762
+ // machines (64-bit machines will have 8-byte alignment already due to
17763
+ // pointers, which all of these structs have).
17764
+ UPB_INLINE void _upb_DefType_CheckPadding(size_t size) {
17765
+ UPB_ASSERT((size & UPB_DEFTYPE_MASK) == 0);
17766
+ }
17767
+
17768
+ upb_deftype_t _upb_DefType_Type(upb_value v);
17769
+
17770
+ upb_value _upb_DefType_Pack(const void* ptr, upb_deftype_t type);
17771
+
17772
+ const void* _upb_DefType_Unpack(upb_value v, upb_deftype_t type);
17773
+
17774
+ #ifdef __cplusplus
17775
+ } /* extern "C" */
17776
+ #endif
17777
+
17778
+
17779
+ #endif /* UPB_REFLECTION_DEF_TYPE_H_ */
17780
+
17029
17781
  #ifndef UPB_REFLECTION_DEF_BUILDER_INTERNAL_H_
17030
17782
  #define UPB_REFLECTION_DEF_BUILDER_INTERNAL_H_
17031
17783
 
@@ -17039,6 +17791,9 @@ const upb_ExtensionRegistry* _upb_DefPool_GeneratedExtensionRegistry(
17039
17791
 
17040
17792
  // We want to copy the options verbatim into the destination options proto.
17041
17793
  // We use serialize+parse as our deep copy.
17794
+ #define _UPB_FREEZE_OPTIONS(target, options_type) \
17795
+ upb_Message_Freeze((upb_Message*)target, UPB_DESC_MINITABLE(options_type))
17796
+
17042
17797
  #define UPB_DEF_SET_OPTIONS(target, desc_type, options_type, proto) \
17043
17798
  if (google_protobuf_##desc_type##_has_options(proto)) { \
17044
17799
  size_t size; \
@@ -17049,6 +17804,7 @@ const upb_ExtensionRegistry* _upb_DefPool_GeneratedExtensionRegistry(
17049
17804
  pb, size, _upb_DefPool_GeneratedExtensionRegistry(ctx->symtab), 0, \
17050
17805
  _upb_DefBuilder_Arena(ctx)); \
17051
17806
  if (!target) _upb_DefBuilder_OomErr(ctx); \
17807
+ _UPB_FREEZE_OPTIONS(target, options_type); \
17052
17808
  } else { \
17053
17809
  target = (const google_protobuf_##options_type*)kUpbDefOptDefault; \
17054
17810
  }
@@ -17275,7 +18031,7 @@ upb_MessageDef* _upb_MessageDefs_New(
17275
18031
  // features. This is used for feature resolution under Editions.
17276
18032
  // NOLINTBEGIN
17277
18033
  // clang-format off
17278
- #define UPB_INTERNAL_UPB_EDITION_DEFAULTS "\n\027\030\204\007\"\000*\020\010\001\020\002\030\002 \003(\0010\0028\002@\001\n\027\030\347\007\"\000*\020\010\002\020\001\030\001 \002(\0010\0018\002@\001\n\027\030\350\007\"\014\010\001\020\001\030\001 \002(\0010\001*\0048\002@\001\n\027\030\351\007\"\020\010\001\020\001\030\001 \002(\0010\0018\001@\002*\000\n\027\030\217N\"\020\010\001\020\001\030\001 \002(\0010\0018\003@\002*\000 \346\007(\351\007"
18034
+ #define UPB_INTERNAL_UPB_EDITION_DEFAULTS "\n\031\030\204\007\"\000*\022\010\001\020\002\030\002 \003(\0010\0028\002@\001H\001\n\031\030\347\007\"\000*\022\010\002\020\001\030\001 \002(\0010\0018\002@\001H\001\n\031\030\350\007\"\014\010\001\020\001\030\001 \002(\0010\001*\0068\002@\001H\001\n\031\030\351\007\"\020\010\001\020\001\030\001 \002(\0010\0018\001@\002*\002H\001\n\031\030\352\007\"\022\010\001\020\001\030\001 \002(\0010\0018\003@\004H\002*\000 \346\007(\352\007"
17279
18035
  // clang-format on
17280
18036
  // NOLINTEND
17281
18037
 
@@ -17633,27 +18389,30 @@ upb_MethodDef* _upb_MethodDefs_New(
17633
18389
  extern "C" {
17634
18390
  #endif
17635
18391
 
18392
+ // Must be last
18393
+
17636
18394
  // Functions for converting defs back to the equivalent descriptor proto.
17637
18395
  // Ultimately the goal is that a round-trip proto->def->proto is lossless. Each
17638
18396
  // function returns a new proto created in arena `a`, or NULL if memory
17639
18397
  // allocation failed.
17640
- google_protobuf_DescriptorProto* upb_MessageDef_ToProto(const upb_MessageDef* m,
17641
- upb_Arena* a);
17642
- google_protobuf_EnumDescriptorProto* upb_EnumDef_ToProto(const upb_EnumDef* e,
17643
- upb_Arena* a);
17644
- google_protobuf_EnumValueDescriptorProto* upb_EnumValueDef_ToProto(
18398
+ UPB_NODISCARD google_protobuf_DescriptorProto* upb_MessageDef_ToProto(
18399
+ const upb_MessageDef* m, upb_Arena* a);
18400
+ UPB_NODISCARD google_protobuf_EnumDescriptorProto* upb_EnumDef_ToProto(
18401
+ const upb_EnumDef* e, upb_Arena* a);
18402
+ UPB_NODISCARD google_protobuf_EnumValueDescriptorProto* upb_EnumValueDef_ToProto(
17645
18403
  const upb_EnumValueDef* e, upb_Arena* a);
17646
- google_protobuf_FieldDescriptorProto* upb_FieldDef_ToProto(
18404
+ UPB_NODISCARD google_protobuf_FieldDescriptorProto* upb_FieldDef_ToProto(
17647
18405
  const upb_FieldDef* f, upb_Arena* a);
17648
- google_protobuf_OneofDescriptorProto* upb_OneofDef_ToProto(
18406
+ UPB_NODISCARD google_protobuf_OneofDescriptorProto* upb_OneofDef_ToProto(
17649
18407
  const upb_OneofDef* o, upb_Arena* a);
17650
- google_protobuf_FileDescriptorProto* upb_FileDef_ToProto(const upb_FileDef* f,
17651
- upb_Arena* a);
17652
- google_protobuf_MethodDescriptorProto* upb_MethodDef_ToProto(
18408
+ UPB_NODISCARD google_protobuf_FileDescriptorProto* upb_FileDef_ToProto(
18409
+ const upb_FileDef* f, upb_Arena* a);
18410
+ UPB_NODISCARD google_protobuf_MethodDescriptorProto* upb_MethodDef_ToProto(
17653
18411
  const upb_MethodDef* m, upb_Arena* a);
17654
- google_protobuf_ServiceDescriptorProto* upb_ServiceDef_ToProto(
18412
+ UPB_NODISCARD google_protobuf_ServiceDescriptorProto* upb_ServiceDef_ToProto(
17655
18413
  const upb_ServiceDef* s, upb_Arena* a);
17656
18414
 
18415
+
17657
18416
  #ifdef __cplusplus
17658
18417
  } /* extern "C" */
17659
18418
  #endif
@@ -17682,27 +18441,6 @@ int32_t upb_EnumReservedRange_End(const upb_EnumReservedRange* r);
17682
18441
 
17683
18442
  #endif /* UPB_REFLECTION_ENUM_RESERVED_RANGE_H_ */
17684
18443
 
17685
- #ifndef UPB_WIRE_INTERNAL_CONSTANTS_H_
17686
- #define UPB_WIRE_INTERNAL_CONSTANTS_H_
17687
-
17688
- #define kUpb_WireFormat_DefaultDepthLimit 100
17689
-
17690
- // MessageSet wire format is:
17691
- // message MessageSet {
17692
- // repeated group Item = 1 {
17693
- // required int32 type_id = 2;
17694
- // required bytes message = 3;
17695
- // }
17696
- // }
17697
-
17698
- enum {
17699
- kUpb_MsgSet_Item = 1,
17700
- kUpb_MsgSet_TypeId = 2,
17701
- kUpb_MsgSet_Message = 3,
17702
- };
17703
-
17704
- #endif /* UPB_WIRE_INTERNAL_CONSTANTS_H_ */
17705
-
17706
18444
  /*
17707
18445
  * Internal implementation details of the decoder that are shared between
17708
18446
  * decode.c and decode_fast.c.
@@ -17711,7 +18449,6 @@ enum {
17711
18449
  #ifndef UPB_WIRE_INTERNAL_DECODER_H_
17712
18450
  #define UPB_WIRE_INTERNAL_DECODER_H_
17713
18451
 
17714
- #include <setjmp.h>
17715
18452
  #include <stddef.h>
17716
18453
  #include <stdint.h>
17717
18454
  #include <string.h>
@@ -17721,6 +18458,14 @@ enum {
17721
18458
  // Must be last.
17722
18459
 
17723
18460
  #define DECODE_NOGROUP (uint32_t)-1
18461
+ #define kUpb_Decoder_EncodeVarint32MaxSize 5
18462
+
18463
+ typedef union {
18464
+ bool bool_val;
18465
+ uint32_t uint32_val;
18466
+ uint64_t uint64_val;
18467
+ uint32_t size;
18468
+ } wireval;
17724
18469
 
17725
18470
  typedef struct upb_Decoder {
17726
18471
  upb_EpsCopyInputStream input;
@@ -17735,7 +18480,7 @@ typedef struct upb_Decoder {
17735
18480
  upb_Arena arena;
17736
18481
  void* foo[UPB_ARENA_SIZE_HACK / sizeof(void*)];
17737
18482
  };
17738
- upb_ErrorHandler err;
18483
+ upb_ErrorHandler* err;
17739
18484
 
17740
18485
  #ifndef NDEBUG
17741
18486
  char* trace_buf;
@@ -17744,13 +18489,20 @@ typedef struct upb_Decoder {
17744
18489
  #endif
17745
18490
  } upb_Decoder;
17746
18491
 
18492
+ UPB_INLINE void _upb_Decoder_AssumeEpsHasErrorHandler(upb_Decoder* d) {
18493
+ UPB_ASSUME(upb_EpsCopyInputStream_HasErrorHandler(&d->input));
18494
+ }
18495
+
18496
+ #define EPS(d) (_upb_Decoder_AssumeEpsHasErrorHandler(d), &(d)->input)
18497
+
17747
18498
  UPB_INLINE const char* upb_Decoder_Init(upb_Decoder* d, const char* buf,
17748
18499
  size_t size,
17749
18500
  const upb_ExtensionRegistry* extreg,
17750
18501
  int options, upb_Arena* arena,
17751
- char* trace_buf, size_t trace_size) {
17752
- upb_ErrorHandler_Init(&d->err);
17753
- upb_EpsCopyInputStream_InitWithErrorHandler(&d->input, &buf, size, &d->err);
18502
+ upb_ErrorHandler* err, char* trace_buf,
18503
+ size_t trace_size) {
18504
+ d->err = err;
18505
+ upb_EpsCopyInputStream_InitWithErrorHandler(&d->input, &buf, size, d->err);
17754
18506
 
17755
18507
  UPB_STATIC_ASSERT((int)kUpb_DecodeStatus_Ok == (int)kUpb_ErrorCode_Ok,
17756
18508
  "mismatched error codes");
@@ -17791,22 +18543,36 @@ UPB_INLINE const char* upb_Decoder_Init(upb_Decoder* d, const char* buf,
17791
18543
  UPB_INLINE upb_DecodeStatus upb_Decoder_Destroy(upb_Decoder* d,
17792
18544
  upb_Arena* arena) {
17793
18545
  UPB_PRIVATE(_upb_Arena_SwapOut)(arena, &d->arena);
17794
- return (upb_DecodeStatus)d->err.code;
18546
+ return (upb_DecodeStatus)d->err->code;
17795
18547
  }
17796
18548
 
17797
- #ifndef NDEBUG
17798
- UPB_INLINE bool _upb_Decoder_TraceBufferFull(upb_Decoder* d) {
17799
- return d->trace_ptr == d->trace_end - 1;
18549
+ // Resets decoder fields in preparation for decoding a new message.
18550
+ //
18551
+ // Some decoder fields (arena, extreg, err) are preserved so they can be
18552
+ // reused across messages.
18553
+ // NOTE: The input stream is NOT reset. If a new input buffer is being used,
18554
+ // upb_EpsCopyInputStream_InitWithErrorHandler() must be called separately.
18555
+ UPB_INLINE void upb_Decoder_Reset(upb_Decoder* d, int options,
18556
+ upb_Message* msg) {
18557
+ d->depth = upb_DecodeOptions_GetEffectiveMaxDepth(options);
18558
+ d->options = options;
18559
+ d->end_group = DECODE_NOGROUP;
18560
+ d->missing_required = false;
18561
+ d->message_is_done = false;
18562
+ d->original_msg = msg;
17800
18563
  }
17801
18564
 
17802
- UPB_INLINE bool _upb_Decoder_TraceBufferAlmostFull(upb_Decoder* d) {
17803
- return d->trace_ptr == d->trace_end - 2;
18565
+ #ifndef NDEBUG
18566
+ UPB_INLINE bool _upb_Decoder_TraceBufferHasBytesAvailable(upb_Decoder* d,
18567
+ int n) {
18568
+ return d->trace_ptr && d->trace_end && d->trace_end - d->trace_ptr > n;
17804
18569
  }
17805
18570
  #endif
17806
18571
 
17807
18572
  UPB_INLINE char* _upb_Decoder_TraceNext(upb_Decoder* d) {
17808
18573
  #ifndef NDEBUG
17809
- return _upb_Decoder_TraceBufferAlmostFull(d) ? NULL : d->trace_ptr + 1;
18574
+ return _upb_Decoder_TraceBufferHasBytesAvailable(d, 2) ? d->trace_ptr + 1
18575
+ : NULL;
17810
18576
  #else
17811
18577
  return NULL;
17812
18578
  #endif
@@ -17827,10 +18593,20 @@ UPB_INLINE char* _upb_Decoder_TracePtr(upb_Decoder* d) {
17827
18593
  // '<' Fallback to MiniTable parser.
17828
18594
  // 'M' Field successfully parsed with MiniTable.
17829
18595
  // 'X' Truncated -- trace buffer is full, further events were discarded.
18596
+ // 'U' Unknown field parsed fast
18597
+ //
18598
+ // Lower-case letters indicate events that are more subtle and therefore
18599
+ // difficult to assert on, but may be useful information for debugging:
18600
+ // 'r' Refresh buffer.
18601
+ // 's' Fall back to unknown fast path
18602
+ // 'm' Fall back to minitable lookup fast path
17830
18603
  UPB_INLINE void _upb_Decoder_Trace(upb_Decoder* d, char event) {
17831
18604
  #ifndef NDEBUG
18605
+ #ifdef UPB_TRACE_FASTDECODER
18606
+ fprintf(stderr, "Fasttable trace event: %c\n", event);
18607
+ #endif
17832
18608
  if (d->trace_ptr == NULL) return;
17833
- if (_upb_Decoder_TraceBufferFull(d)) {
18609
+ if (!_upb_Decoder_TraceBufferHasBytesAvailable(d, 1)) {
17834
18610
  d->trace_ptr[-1] = 'X'; // Truncated.
17835
18611
  return;
17836
18612
  }
@@ -17845,20 +18621,29 @@ bool _upb_Decoder_VerifyUtf8Inline(const char* ptr, int len) {
17845
18621
  return utf8_range_IsValid(ptr, len);
17846
18622
  }
17847
18623
 
18624
+ UPB_INLINE void _upb_Decoder_VerifyOneofUnlinked(
18625
+ const upb_MiniTable* mt, const upb_MiniTableField* field) {
18626
+ #ifndef NDEBUG
18627
+ const upb_MiniTableField* oneof = upb_MiniTable_GetOneof(mt, field);
18628
+ if (oneof) {
18629
+ // All other members of the oneof must be message fields that are also
18630
+ // unlinked.
18631
+ do {
18632
+ UPB_ASSERT(upb_MiniTableField_CType(oneof) == kUpb_CType_Message);
18633
+ const upb_MiniTable* oneof_sub = upb_MiniTable_GetSubMessageTable(oneof);
18634
+ UPB_ASSERT(!oneof_sub);
18635
+ } while (upb_MiniTable_NextOneofField(mt, &oneof));
18636
+ }
18637
+ #endif // NDEBUG
18638
+ }
18639
+
17848
18640
  const char* _upb_Decoder_CheckRequired(upb_Decoder* d, const char* ptr,
17849
18641
  const upb_Message* msg,
17850
18642
  const upb_MiniTable* m);
17851
18643
 
17852
- /* x86-64 pointers always have the high 16 bits matching. So we can shift
17853
- * left 8 and right 8 without loss of information. */
17854
- UPB_INLINE intptr_t decode_totable(const upb_MiniTable* tablep) {
17855
- return ((intptr_t)tablep << 8) | tablep->UPB_PRIVATE(table_mask);
17856
- }
17857
-
17858
- UPB_INLINE const upb_MiniTable* decode_totablep(intptr_t table) {
17859
- return (const upb_MiniTable*)(table >> 8);
17860
- }
17861
-
18644
+ #if UPB_FASTTABLE
18645
+ UPB_PRESERVE_NONE
18646
+ #endif
17862
18647
  const char* _upb_Decoder_DecodeMessage(upb_Decoder* d, const char* ptr,
17863
18648
  upb_Message* msg,
17864
18649
  const upb_MiniTable* layout);
@@ -17884,7 +18669,7 @@ UPB_INLINE bool _upb_Decoder_ReadString(upb_Decoder* d, const char** ptr,
17884
18669
  upb_EpsCopyInputStream_ReadStringAlwaysAlias(&d->input, *ptr, size, &tmp);
17885
18670
  if (*ptr == NULL) return false;
17886
18671
  if (validate_utf8 && !utf8_range_IsValid(tmp.data, tmp.size)) {
17887
- upb_ErrorHandler_ThrowError(&d->err, kUpb_DecodeStatus_BadUtf8);
18672
+ upb_ErrorHandler_ThrowError(d->err, kUpb_DecodeStatus_BadUtf8);
17888
18673
  return false;
17889
18674
  }
17890
18675
  if ((d->options & kUpb_DecodeOption_AliasString) == 0) {
@@ -17897,8 +18682,236 @@ UPB_INLINE bool _upb_Decoder_ReadString(upb_Decoder* d, const char** ptr,
17897
18682
  return true;
17898
18683
  }
17899
18684
 
18685
+ UPB_INLINE char* upb_Decoder_EncodeVarint32(uint32_t val, char* ptr) {
18686
+ do {
18687
+ uint8_t byte = val & 0x7fU;
18688
+ val >>= 7;
18689
+ if (val) byte |= 0x80U;
18690
+ *(ptr++) = byte;
18691
+ } while (val);
18692
+ return ptr;
18693
+ }
18694
+
18695
+ UPB_FORCEINLINE
18696
+ void _upb_Decoder_AddEnumValueToUnknown(upb_Decoder* d, upb_Message* msg,
18697
+ const upb_MiniTableField* field,
18698
+ uint64_t val) {
18699
+ // Unrecognized enum goes into unknown fields.
18700
+ // For packed fields the tag could be arbitrarily far in the past,
18701
+ // so we just re-encode the tag and value here.
18702
+ const uint32_t tag =
18703
+ ((uint32_t)field->UPB_PRIVATE(number) << 3) | kUpb_WireType_Varint;
18704
+ upb_Message* unknown_msg =
18705
+ field->UPB_PRIVATE(mode) & kUpb_LabelFlags_IsExtension ? d->original_msg
18706
+ : msg;
18707
+ char buf[2 * kUpb_Decoder_EncodeVarint32MaxSize];
18708
+ char* end = buf;
18709
+ end = upb_Decoder_EncodeVarint32(tag, end);
18710
+ end = upb_Decoder_EncodeVarint32(val, end);
18711
+
18712
+ if (!UPB_PRIVATE(_upb_Message_AddUnknown)(unknown_msg, buf, end - buf,
18713
+ &d->arena, kUpb_AddUnknown_Copy)) {
18714
+ upb_ErrorHandler_ThrowError(d->err, kUpb_DecodeStatus_OutOfMemory);
18715
+ }
18716
+ }
18717
+
17900
18718
 
17901
18719
  #endif /* UPB_WIRE_INTERNAL_DECODER_H_ */
18720
+
18721
+ #ifndef UPB_WIRE_INTERNAL_ENCODE_H_
18722
+ #define UPB_WIRE_INTERNAL_ENCODE_H_
18723
+
18724
+ #include <setjmp.h>
18725
+ #include <stddef.h>
18726
+ #include <stdint.h>
18727
+
18728
+
18729
+ #ifndef GOOGLE_UPB_UPB_WIRE_INTERNAL_BACK_ALLOC_H__
18730
+ #define GOOGLE_UPB_UPB_WIRE_INTERNAL_BACK_ALLOC_H__
18731
+
18732
+ #include <stddef.h>
18733
+
18734
+
18735
+ // Must be last.
18736
+
18737
+ #ifdef __cplusplus
18738
+ extern "C" {
18739
+ #endif
18740
+
18741
+ // Allocates memory from the back of the arena.
18742
+ typedef struct {
18743
+ upb_Arena* arena;
18744
+ char *buf, *limit;
18745
+ bool standalone;
18746
+ } upb_BackAlloc;
18747
+
18748
+ // Needed because C doesn't allow NULL - NULL.
18749
+ extern char upb_BackAlloc_sentinel;
18750
+
18751
+ char* upb_BackAlloc_Grow(upb_BackAlloc* a, char* ptr, size_t need);
18752
+
18753
+ UPB_INLINE char* upb_BackAlloc_Init(upb_BackAlloc* a, upb_Arena* arena) {
18754
+ a->arena = arena;
18755
+ // This could eagerly steal whatever's in the arena, since stealing with a
18756
+ // minimum of 0 can't fail.
18757
+ a->buf = &upb_BackAlloc_sentinel;
18758
+ a->limit = &upb_BackAlloc_sentinel;
18759
+ a->standalone = false;
18760
+ return a->limit;
18761
+ }
18762
+
18763
+ UPB_INLINE void upb_BackAlloc_Abort(upb_BackAlloc* a) {
18764
+ if (a->standalone) {
18765
+ UPB_PRIVATE(_upb_Arena_FreeBlock)(a->arena, a->buf);
18766
+ } else if (a->limit != a->buf) {
18767
+ UPB_PRIVATE(_upb_Arena_UseBlock)(a->arena, a->buf, a->limit - a->buf);
18768
+ }
18769
+ }
18770
+
18771
+ UPB_INLINE size_t upb_BackAlloc_Finish(upb_BackAlloc* a, const char* ptr) {
18772
+ if (a->standalone) {
18773
+ UPB_PRIVATE(_upb_Arena_AddBlock)(a->arena, a->buf);
18774
+ }
18775
+ if (ptr != a->buf) {
18776
+ UPB_PRIVATE(_upb_Arena_UseBlock)(a->arena, a->buf, ptr - a->buf);
18777
+ }
18778
+ return a->limit - ptr;
18779
+ }
18780
+
18781
+ UPB_FORCEINLINE bool upb_BackAlloc_HasBytes(const upb_BackAlloc* a,
18782
+ const char* ptr, size_t need) {
18783
+ size_t have = ptr - a->buf;
18784
+ return have >= need;
18785
+ }
18786
+
18787
+ UPB_FORCEINLINE char* upb_BackAlloc_Reserve(upb_BackAlloc* a, char* ptr,
18788
+ size_t need) {
18789
+ return upb_BackAlloc_HasBytes(a, ptr, need)
18790
+ ? ptr - need
18791
+ : upb_BackAlloc_Grow(a, ptr, need);
18792
+ }
18793
+
18794
+ UPB_INLINE size_t upb_BackAlloc_Size(const upb_BackAlloc* a, const char* ptr) {
18795
+ return a->limit - ptr;
18796
+ }
18797
+
18798
+ #ifdef __cplusplus
18799
+ } /* extern "C" */
18800
+ #endif
18801
+
18802
+
18803
+ #endif // GOOGLE_UPB_UPB_WIRE_INTERNAL_BACK_ALLOC_H__
18804
+
18805
+ // Must be last.
18806
+
18807
+ #ifdef __cplusplus
18808
+ extern "C" {
18809
+ #endif
18810
+
18811
+ typedef struct {
18812
+ upb_BackAlloc alloc;
18813
+ int options;
18814
+ int depth;
18815
+ upb_EncodeStatus status;
18816
+ _upb_mapsorter sorter;
18817
+ jmp_buf* err;
18818
+ } upb_encstate;
18819
+
18820
+ UPB_INLINE char* UPB_PRIVATE(_upb_encstate_init)(upb_encstate* e, jmp_buf* err,
18821
+ upb_Arena* arena) {
18822
+ e->status = kUpb_EncodeStatus_Ok;
18823
+ char* ptr = upb_BackAlloc_Init(&e->alloc, arena);
18824
+ e->options = 0;
18825
+ e->depth = 0;
18826
+ e->err = err;
18827
+ _upb_mapsorter_init(&e->sorter);
18828
+ return ptr;
18829
+ }
18830
+
18831
+ UPB_INLINE void UPB_PRIVATE(_upb_encstate_destroy)(upb_encstate* e) {
18832
+ _upb_mapsorter_destroy(&e->sorter);
18833
+ }
18834
+
18835
+ // Internal version of upb_Encode that encodes a single field.
18836
+ //
18837
+ // The caller must clean up the `upb_encstate` by calling
18838
+ // `_upb_encstate_destroy(e)` when done.
18839
+ upb_EncodeStatus UPB_PRIVATE(_upb_Encode_Field)(upb_encstate* e,
18840
+ const upb_Message* msg,
18841
+ const upb_MiniTableField* field,
18842
+ char** buf, size_t* size,
18843
+ int options);
18844
+
18845
+ // Internal version of upb_Encode that encodes a single extension.
18846
+ //
18847
+ // The caller must clean up the `upb_encstate` by calling
18848
+ // `_upb_encstate_destroy(e)` when done.
18849
+ upb_EncodeStatus UPB_PRIVATE(_upb_Encode_Extension)(
18850
+ upb_encstate* e, const upb_MiniTableExtension* ext,
18851
+ upb_MessageValue ext_val, bool is_message_set, char** buf, size_t* size,
18852
+ int options);
18853
+
18854
+ char* encode_message(char* ptr, upb_encstate* e, const upb_Message* msg,
18855
+ const upb_MiniTable* m, size_t* size);
18856
+
18857
+ #define kUpb_Encoder_EncodeVarint32MaxSize 5
18858
+ #define kUpb_Encoder_EncodeVarint64MaxSize 10
18859
+
18860
+ static char* upb_Encoder_EncodeVarint32(uint32_t val, char* ptr) {
18861
+ do {
18862
+ uint8_t byte = val & 0x7fU;
18863
+ val >>= 7;
18864
+ if (val) byte |= 0x80U;
18865
+ *(ptr++) = byte;
18866
+ } while (val);
18867
+ return ptr;
18868
+ }
18869
+
18870
+ static char* upb_Encoder_EncodeVarint64(uint64_t val, char* ptr) {
18871
+ do {
18872
+ uint8_t byte = val & 0x7fU;
18873
+ val >>= 7;
18874
+ if (val) byte |= 0x80U;
18875
+ *(ptr++) = byte;
18876
+ } while (val);
18877
+ return ptr;
18878
+ }
18879
+
18880
+ UPB_INLINE
18881
+ bool _upb_Encoder_AddEnumValueToUnknown(upb_Message* msg,
18882
+ const upb_MiniTableField* field,
18883
+ uint64_t val, upb_Arena* arena) {
18884
+ // Unrecognized enum goes into unknown fields.
18885
+ // For packed fields the tag could be arbitrarily far in the past,
18886
+ // so we just re-encode the tag and value here.
18887
+ const uint32_t tag =
18888
+ ((uint32_t)field->UPB_PRIVATE(number) << 3) | kUpb_WireType_Varint;
18889
+ char buf[kUpb_Encoder_EncodeVarint32MaxSize +
18890
+ kUpb_Encoder_EncodeVarint64MaxSize];
18891
+ char* end = buf;
18892
+ end = upb_Encoder_EncodeVarint32(tag, end);
18893
+ end = upb_Encoder_EncodeVarint64(val, end);
18894
+
18895
+ return UPB_PRIVATE(_upb_Message_AddUnknown)(msg, buf, end - buf, arena,
18896
+ kUpb_AddUnknown_Copy);
18897
+ }
18898
+
18899
+ bool _upb_Encoder_AddMapEntryUnknown(upb_Message* msg,
18900
+ const upb_MiniTableField* field,
18901
+ upb_Message* ent_msg,
18902
+ const upb_MiniTable* entry,
18903
+ upb_Arena* arena);
18904
+
18905
+ upb_EncodeStatus _upb_Encode(const upb_Message* msg, const upb_MiniTable* l,
18906
+ int options, upb_Arena* arena, char** buf,
18907
+ size_t* size, bool prepend_len);
18908
+
18909
+ #ifdef __cplusplus
18910
+ } /* extern "C" */
18911
+ #endif
18912
+
18913
+
18914
+ #endif /* UPB_WIRE_INTERNAL_ENCODE_H_ */
17902
18915
  #ifndef GOOGLE_UPB_UPB_WIRE_WRITER_H__
17903
18916
  #define GOOGLE_UPB_UPB_WIRE_WRITER_H__
17904
18917
 
@@ -17947,12 +18960,15 @@ UPB_PRIVATE(upb_WireWriter_VarintUnusedSizeFromLeadingZeros64)(uint64_t clz) {
17947
18960
  #undef UPB_NORETURN
17948
18961
  #undef UPB_PRINTF
17949
18962
  #undef UPB_NODEREF
18963
+ #undef UPB_NODISCARD
17950
18964
  #undef UPB_MAX
17951
18965
  #undef UPB_MIN
17952
18966
  #undef UPB_UNUSED
17953
18967
  #undef UPB_ASSUME
17954
18968
  #undef UPB_ASSERT
17955
18969
  #undef UPB_UNREACHABLE
18970
+ #undef UPB_UNREACHABLE_FAILURE
18971
+ #undef UPB_PRETTY_FUNCTION
17956
18972
  #undef UPB_DEFAULT_MAX_BLOCK_SIZE
17957
18973
  #undef UPB_SETJMP
17958
18974
  #undef UPB_LONGJMP
@@ -17986,7 +19002,6 @@ UPB_PRIVATE(upb_WireWriter_VarintUnusedSizeFromLeadingZeros64)(uint64_t clz) {
17986
19002
  #undef UPB_LINKARR_APPEND
17987
19003
  #undef UPB_LINKARR_START
17988
19004
  #undef UPB_LINKARR_STOP
17989
- #undef UPB_FUTURE_BREAKING_CHANGES
17990
19005
  #undef UPB_HAS_ATTRIBUTE
17991
19006
  #undef UPB_HAS_CPP_ATTRIBUTE
17992
19007
  #undef UPB_HAS_BUILTIN