Line data Source code
1 : #ifndef HEADER_fd_src_ballet_pb_fd_pb_gen_h
2 : #define HEADER_fd_src_ballet_pb_fd_pb_gen_h
3 :
4 : /* fd_pb_gen.h is the runtime for C code generated by fd_pb_gen.py.
5 : Provides schema-driven Protobuf encode and decode of generated
6 : message structs.
7 :
8 : Decoding allocates memory for variable-size fields (bytes, strings,
9 : repeated fields) from a caller provided spad. A decoded message is
10 : valid until the caller pops the spad frame it was decoded in. */
11 :
12 : #include "fd_pb_encode.h"
13 : #include "fd_pb_tokenize.h"
14 : #include "../../util/spad/fd_spad.h"
15 : #include <stdbool.h>
16 : #include <stddef.h>
17 :
18 : /* fd_pb_bytes_array_t is a heap allocated byte array */
19 :
20 : struct fd_pb_bytes_array {
21 : uint size;
22 : uchar bytes[];
23 : };
24 :
25 : typedef struct fd_pb_bytes_array fd_pb_bytes_array_t;
26 :
27 : #define FD_PB_BYTES_ARRAY_T(n) struct { uint size; uchar bytes[ n ]; }
28 0 : #define FD_PB_BYTES_ARRAY_T_ALLOCSIZE(n) ((ulong)(n) + offsetof(fd_pb_bytes_array_t, bytes))
29 :
30 : /* fd_pb_msgdesc_t describes a generated message type. */
31 :
32 : struct fd_pb_msgdesc {
33 : int (* encode)( fd_pb_encoder_t * enc, void const * msg );
34 : int (* decode)( fd_pb_inbuf_t * in, void * msg, fd_spad_t * spad );
35 : };
36 :
37 : typedef struct fd_pb_msgdesc fd_pb_msgdesc_t;
38 :
39 : /* Scalar types for repeated field handling */
40 :
41 0 : #define FD_PB_GEN_BOOL (0)
42 0 : #define FD_PB_GEN_INT32 (1) /* also enums */
43 0 : #define FD_PB_GEN_UINT32 (2)
44 0 : #define FD_PB_GEN_SINT32 (3)
45 0 : #define FD_PB_GEN_INT64 (4)
46 0 : #define FD_PB_GEN_UINT64 (5)
47 0 : #define FD_PB_GEN_SINT64 (6)
48 0 : #define FD_PB_GEN_FIXED32 (7) /* also sfixed32, float */
49 0 : #define FD_PB_GEN_FIXED64 (8) /* also sfixed64, double */
50 :
51 : FD_PROTOTYPES_BEGIN
52 :
53 : /* fd_pb_encode serializes msg (of type desc) to the buffer at out.
54 : On entry, *out_sz is the buffer size. On success, sets *out_sz to
55 : the number of bytes written and returns out. On failure (out of
56 : space, invalid message), returns NULL. */
57 :
58 : uchar *
59 : fd_pb_encode( fd_pb_msgdesc_t const * desc,
60 : void const * msg,
61 : uchar * out,
62 : ulong * out_sz );
63 :
64 : /* fd_pb_decode deserializes the Protobuf message at [in,in+in_sz) into
65 : msg, allocating variable-size fields from spad. msg must be zero
66 : initialized. Returns msg on success and NULL on failure (malformed
67 : input, spad exhausted). Partial allocations are left in the spad
68 : frame either way. */
69 :
70 : void *
71 : fd_pb_decode( fd_pb_msgdesc_t const * desc,
72 : void * msg,
73 : void const * in,
74 : ulong in_sz,
75 : fd_spad_t * spad );
76 :
77 : /* Generated code helpers. Decode helpers return 1 on success and 0 on
78 : failure (malformed input, spad exhausted). */
79 :
80 : static inline int
81 : fd_pb_dec_tlv( fd_pb_inbuf_t * in,
82 0 : fd_pb_tlv_t * tlv ) {
83 0 : if( FD_UNLIKELY( !fd_pb_tlv_read( in, tlv ) ) ) return 0;
84 0 : return tlv->field_id!=0U;
85 0 : }
86 :
87 : static inline int
88 : fd_pb_dec_skip( fd_pb_inbuf_t * in,
89 0 : fd_pb_tlv_t const * tlv ) {
90 0 : return !!fd_pb_tlv_skip( in, tlv );
91 0 : }
92 :
93 : int fd_pb_dec_bool ( fd_pb_tlv_t const * tlv, bool * out );
94 : int fd_pb_dec_int32 ( fd_pb_tlv_t const * tlv, int * out );
95 : int fd_pb_dec_uint32 ( fd_pb_tlv_t const * tlv, uint * out );
96 : int fd_pb_dec_sint32 ( fd_pb_tlv_t const * tlv, int * out );
97 : int fd_pb_dec_int64 ( fd_pb_tlv_t const * tlv, long * out );
98 : int fd_pb_dec_uint64 ( fd_pb_tlv_t const * tlv, ulong * out );
99 : int fd_pb_dec_sint64 ( fd_pb_tlv_t const * tlv, long * out );
100 : int fd_pb_dec_fixed32( fd_pb_tlv_t const * tlv, uint * out );
101 : int fd_pb_dec_fixed64( fd_pb_tlv_t const * tlv, ulong * out );
102 : int fd_pb_dec_float ( fd_pb_tlv_t const * tlv, float * out );
103 : int fd_pb_dec_double ( fd_pb_tlv_t const * tlv, double * out );
104 :
105 : /* fd_pb_dec_repeated decodes a repeated scalar field element (unpacked)
106 : or elements (packed) and appends them to the array. arr points to
107 : the array pointer (a T * field, passed as void * to avoid aliasing
108 : casts in generated code). */
109 :
110 : int
111 : fd_pb_dec_repeated( fd_pb_inbuf_t * in,
112 : fd_pb_tlv_t const * tlv,
113 : fd_spad_t * spad,
114 : int type,
115 : void * arr,
116 : uint * cnt );
117 :
118 : /* fd_pb_dec_grow appends a zero initialized element to the array whose
119 : pointer is at arr. Capacity grows geometrically; outgrown arrays
120 : are abandoned in the spad frame. Returns a pointer to the new
121 : element, or NULL if the spad is exhausted. */
122 :
123 : void *
124 : fd_pb_dec_grow( fd_spad_t * spad,
125 : void * arr,
126 : uint * cnt,
127 : ulong ele_align,
128 : ulong ele_sz );
129 :
130 : int
131 : fd_pb_dec_submsg( fd_pb_inbuf_t * in,
132 : fd_pb_tlv_t const * tlv,
133 : fd_spad_t * spad,
134 : fd_pb_msgdesc_t const * desc,
135 : void * msg );
136 :
137 : int
138 : fd_pb_dec_bytes_ptr( fd_pb_inbuf_t * in,
139 : fd_pb_tlv_t const * tlv,
140 : fd_spad_t * spad,
141 : fd_pb_bytes_array_t ** out );
142 :
143 : int
144 : fd_pb_dec_bytes_fixed( fd_pb_inbuf_t * in,
145 : fd_pb_tlv_t const * tlv,
146 : uchar * out,
147 : ulong sz );
148 :
149 : int
150 : fd_pb_dec_bytes_static( fd_pb_inbuf_t * in,
151 : fd_pb_tlv_t const * tlv,
152 : uchar * out,
153 : uint * out_sz,
154 : ulong max );
155 :
156 : int
157 : fd_pb_dec_string_static( fd_pb_inbuf_t * in,
158 : fd_pb_tlv_t const * tlv,
159 : char * out,
160 : ulong max ); /* incl NUL */
161 :
162 : /* Encode helpers return 1 on success and 0 on failure (out of space). */
163 :
164 : int
165 : fd_pb_enc_submsg( fd_pb_encoder_t * enc,
166 : uint field_id,
167 : fd_pb_msgdesc_t const * desc,
168 : void const * msg );
169 :
170 : int
171 : fd_pb_enc_bytes_ptr( fd_pb_encoder_t * enc,
172 : uint field_id,
173 : fd_pb_bytes_array_t const * bytes );
174 :
175 : int
176 : fd_pb_enc_packed( fd_pb_encoder_t * enc,
177 : uint field_id,
178 : int type,
179 : void const * arr,
180 : ulong cnt );
181 :
182 : static inline int
183 : fd_pb_enc_nonzero( void const * p,
184 0 : ulong sz ) {
185 0 : uchar const * b = p;
186 0 : for( ulong i=0UL; i<sz; i++ ) if( b[i] ) return 1;
187 0 : return 0;
188 0 : }
189 :
190 : FD_PROTOTYPES_END
191 :
192 : #endif /* HEADER_fd_src_ballet_pb_fd_pb_gen_h */
|