WPILibC++ 2027.0.0-alpha-3
Loading...
Searching...
No Matches
decode.h
Go to the documentation of this file.
1// Protocol Buffers - Google's data interchange format
2// Copyright 2023 Google LLC. All rights reserved.
3//
4// Use of this source code is governed by a BSD-style
5// license that can be found in the LICENSE file or at
6// https://developers.google.com/open-source/licenses/bsd
7
8// upb_decode: parsing into a upb_Message using a upb_MiniTable.
9
10#ifndef UPB_WIRE_DECODE_H_
11#define UPB_WIRE_DECODE_H_
12
13#include <stddef.h>
14#include <stdint.h>
15
16#include "upb/mem/arena.h"
17#include "upb/message/message.h"
20
21// Must be last.
22#include "upb/port/def.inc"
23
24#ifdef __cplusplus
25extern "C" {
26#endif
27
28// LINT.IfChange
29enum {
30 /* If set, strings and unknown fields will alias the input buffer instead of
31 * copying into the arena. */
33
34 /* If set, the parse will return failure if any message is missing any
35 * required fields when the message data ends. The parse will still continue,
36 * and the failure will only be reported at the end.
37 *
38 * IMPORTANT CAVEATS:
39 *
40 * 1. This can throw a false positive failure if an incomplete message is seen
41 * on the wire but is later completed when the sub-message occurs again.
42 * For this reason, a second pass is required to verify a failure, to be
43 * truly robust.
44 *
45 * 2. This can return a false success if you are decoding into a message that
46 * already has some sub-message fields present. If the sub-message does
47 * not occur in the binary payload, we will never visit it and discover the
48 * incomplete sub-message. For this reason, this check is only useful for
49 * implementing ParseFromString() semantics. For MergeFromString(), a
50 * post-parse validation step will always be necessary. */
52
53 /* EXPERIMENTAL:
54 *
55 * If set, the parser will allow parsing of sub-message fields that were not
56 * previously linked using upb_MiniTable_SetSubMessage(). The data will be
57 * parsed into an internal "empty" message type that cannot be accessed
58 * directly, but can be later promoted into the true message type if the
59 * sub-message fields are linked at a later time.
60 *
61 * Users should set this option if they intend to perform dynamic tree shaking
62 * and promoting using the interfaces in message/promote.h. If this option is
63 * enabled, it is important that the resulting messages are only accessed by
64 * code that is aware of promotion rules:
65 *
66 * 1. Message pointers in upb_Message, upb_Array, and upb_Map are represented
67 * by a tagged pointer upb_TaggedMessagePointer. The tag indicates whether
68 * the message uses the internal "empty" type.
69 *
70 * 2. Any code *reading* these message pointers must test whether the "empty"
71 * tag bit is set, using the interfaces in mini_table/types.h. However
72 * writing of message pointers should always use plain upb_Message*, since
73 * users are not allowed to create "empty" messages.
74 *
75 * 3. It is always safe to test whether a field is present or test the array
76 * length; these interfaces will reflect that empty messages are present,
77 * even though their data cannot be accessed without promoting first.
78 *
79 * 4. If a message pointer is indeed tagged as empty, the message may not be
80 * accessed directly, only promoted through the interfaces in
81 * message/promote.h.
82 *
83 * 5. Tagged/empty messages may never be created by the user. They may only
84 * be created by the parser or the message-copying logic in message/copy.h.
85 */
87
88 /* EXPERIMENTAL:
89 *
90 * If set, decoding will enforce UTF-8 validation for string fields, even for
91 * proto2 or fields with `features.utf8_validation = NONE`. Normally, only
92 * proto3 string fields will be validated for UTF-8. Decoding will return
93 * kUpb_DecodeStatus_BadUtf8 for non-UTF-8 strings, which is the same behavior
94 * as non-UTF-8 proto3 string fields.
95 */
97
98 /* EXPERIMENTAL:
99 *
100 * If set, the fasttable decoder will not be used. */
102};
103// LINT.ThenChange(//depot/google3/third_party/protobuf/rust/upb.rs:decode_status)
104
105UPB_INLINE uint32_t upb_DecodeOptions_MaxDepth(uint16_t depth) {
106 return (uint32_t)depth << 16;
107}
108
109uint16_t upb_DecodeOptions_GetEffectiveMaxDepth(uint32_t options);
110
111// Enforce an upper bound on recursion depth.
112UPB_INLINE int upb_Decode_LimitDepth(uint32_t decode_options, uint32_t limit) {
113 uint32_t max_depth = upb_DecodeOptions_GetEffectiveMaxDepth(decode_options);
114 if (max_depth > limit) max_depth = limit;
115 return upb_DecodeOptions_MaxDepth(max_depth) | (decode_options & 0xffff);
116}
117
118// LINT.IfChange
119typedef enum {
121 kUpb_DecodeStatus_Malformed = 1, // Wire format was corrupt
122 kUpb_DecodeStatus_OutOfMemory = 2, // Arena alloc failed
123 kUpb_DecodeStatus_BadUtf8 = 3, // String field had bad UTF-8
125 4, // Exceeded upb_DecodeOptions_MaxDepth
126
127 // kUpb_DecodeOption_CheckRequired failed (see above), but the parse otherwise
128 // succeeded.
130
131 // Unlinked sub-message field was present, but
132 // kUpb_DecodeOptions_ExperimentalAllowUnlinked was not specified in the list
133 // of options.
136// LINT.ThenChange(//depot/google3/third_party/protobuf/rust/upb.rs:decode_status)
137
138UPB_API upb_DecodeStatus upb_Decode(const char* buf, size_t size,
139 upb_Message* msg, const upb_MiniTable* mt,
140 const upb_ExtensionRegistry* extreg,
141 int options, upb_Arena* arena);
142
143// Same as upb_Decode but with a varint-encoded length prepended.
144// On success 'num_bytes_read' will be set to the how many bytes were read,
145// on failure the contents of num_bytes_read is undefined.
147 const char* buf, size_t size, upb_Message* msg, size_t* num_bytes_read,
148 const upb_MiniTable* mt, const upb_ExtensionRegistry* extreg, int options,
149 upb_Arena* arena);
150
151// For testing: decode with tracing.
153 const char* buf, size_t size, upb_Message* msg, const upb_MiniTable* mt,
154 const upb_ExtensionRegistry* extreg, int options, upb_Arena* arena,
155 char* trace_buf, size_t trace_size);
156
157// Utility function for wrapper languages to get an error string from a
158// upb_DecodeStatus.
160#ifdef __cplusplus
161} /* extern "C" */
162#endif
163
164#include "upb/port/undef.inc"
165
166#endif /* UPB_WIRE_DECODE_H_ */
#define UPB_INLINE
Definition def.inc:144
#define UPB_API
Definition def.inc:162
struct upb_ExtensionRegistry upb_ExtensionRegistry
Definition extension_registry.h:59
Definition arena.h:29
Definition types.h:18
Definition message.h:54
UPB_INLINE int upb_Decode_LimitDepth(uint32_t decode_options, uint32_t limit)
Definition decode.h:112
upb_DecodeStatus
Definition decode.h:119
@ kUpb_DecodeStatus_MaxDepthExceeded
Definition decode.h:124
@ kUpb_DecodeStatus_MissingRequired
Definition decode.h:129
@ kUpb_DecodeStatus_Ok
Definition decode.h:120
@ kUpb_DecodeStatus_Malformed
Definition decode.h:121
@ kUpb_DecodeStatus_BadUtf8
Definition decode.h:123
@ kUpb_DecodeStatus_UnlinkedSubMessage
Definition decode.h:134
@ kUpb_DecodeStatus_OutOfMemory
Definition decode.h:122
UPB_API upb_DecodeStatus upb_Decode(const char *buf, size_t size, upb_Message *msg, const upb_MiniTable *mt, const upb_ExtensionRegistry *extreg, int options, upb_Arena *arena)
UPB_INLINE uint32_t upb_DecodeOptions_MaxDepth(uint16_t depth)
Definition decode.h:105
@ kUpb_DecodeOption_AlwaysValidateUtf8
Definition decode.h:96
@ kUpb_DecodeOption_DisableFastTable
Definition decode.h:101
@ kUpb_DecodeOption_CheckRequired
Definition decode.h:51
@ kUpb_DecodeOption_ExperimentalAllowUnlinked
Definition decode.h:86
@ kUpb_DecodeOption_AliasString
Definition decode.h:32
uint16_t upb_DecodeOptions_GetEffectiveMaxDepth(uint32_t options)
UPB_API upb_DecodeStatus upb_DecodeLengthPrefixed(const char *buf, size_t size, upb_Message *msg, size_t *num_bytes_read, const upb_MiniTable *mt, const upb_ExtensionRegistry *extreg, int options, upb_Arena *arena)
UPB_API upb_DecodeStatus upb_DecodeWithTrace(const char *buf, size_t size, upb_Message *msg, const upb_MiniTable *mt, const upb_ExtensionRegistry *extreg, int options, upb_Arena *arena, char *trace_buf, size_t trace_size)
UPB_API const char * upb_DecodeStatus_String(upb_DecodeStatus status)