1*9356374aSAndroid Build Coastguard Worker // Copyright 2020 The Abseil Authors.
2*9356374aSAndroid Build Coastguard Worker //
3*9356374aSAndroid Build Coastguard Worker // Licensed under the Apache License, Version 2.0 (the "License");
4*9356374aSAndroid Build Coastguard Worker // you may not use this file except in compliance with the License.
5*9356374aSAndroid Build Coastguard Worker // You may obtain a copy of the License at
6*9356374aSAndroid Build Coastguard Worker //
7*9356374aSAndroid Build Coastguard Worker // https://www.apache.org/licenses/LICENSE-2.0
8*9356374aSAndroid Build Coastguard Worker //
9*9356374aSAndroid Build Coastguard Worker // Unless required by applicable law or agreed to in writing, software
10*9356374aSAndroid Build Coastguard Worker // distributed under the License is distributed on an "AS IS" BASIS,
11*9356374aSAndroid Build Coastguard Worker // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12*9356374aSAndroid Build Coastguard Worker // See the License for the specific language governing permissions and
13*9356374aSAndroid Build Coastguard Worker // limitations under the License.
14*9356374aSAndroid Build Coastguard Worker
15*9356374aSAndroid Build Coastguard Worker // -----------------------------------------------------------------------------
16*9356374aSAndroid Build Coastguard Worker // File: internal/proto.h
17*9356374aSAndroid Build Coastguard Worker // -----------------------------------------------------------------------------
18*9356374aSAndroid Build Coastguard Worker //
19*9356374aSAndroid Build Coastguard Worker // Declares functions for serializing and deserializing data to and from memory
20*9356374aSAndroid Build Coastguard Worker // buffers in protocol buffer wire format. This library takes no steps to
21*9356374aSAndroid Build Coastguard Worker // ensure that the encoded data matches with any message specification.
22*9356374aSAndroid Build Coastguard Worker
23*9356374aSAndroid Build Coastguard Worker #ifndef ABSL_LOG_INTERNAL_PROTO_H_
24*9356374aSAndroid Build Coastguard Worker #define ABSL_LOG_INTERNAL_PROTO_H_
25*9356374aSAndroid Build Coastguard Worker
26*9356374aSAndroid Build Coastguard Worker #include <cstddef>
27*9356374aSAndroid Build Coastguard Worker #include <cstdint>
28*9356374aSAndroid Build Coastguard Worker #include <limits>
29*9356374aSAndroid Build Coastguard Worker
30*9356374aSAndroid Build Coastguard Worker #include "absl/base/attributes.h"
31*9356374aSAndroid Build Coastguard Worker #include "absl/base/casts.h"
32*9356374aSAndroid Build Coastguard Worker #include "absl/base/config.h"
33*9356374aSAndroid Build Coastguard Worker #include "absl/strings/string_view.h"
34*9356374aSAndroid Build Coastguard Worker #include "absl/types/span.h"
35*9356374aSAndroid Build Coastguard Worker
36*9356374aSAndroid Build Coastguard Worker namespace absl {
37*9356374aSAndroid Build Coastguard Worker ABSL_NAMESPACE_BEGIN
38*9356374aSAndroid Build Coastguard Worker namespace log_internal {
39*9356374aSAndroid Build Coastguard Worker
40*9356374aSAndroid Build Coastguard Worker // absl::Span<char> represents a view into the available space in a mutable
41*9356374aSAndroid Build Coastguard Worker // buffer during encoding. Encoding functions shrink the span as they go so
42*9356374aSAndroid Build Coastguard Worker // that the same view can be passed to a series of Encode functions. If the
43*9356374aSAndroid Build Coastguard Worker // data do not fit, nothing is encoded, the view is set to size zero (so that
44*9356374aSAndroid Build Coastguard Worker // all subsequent encode calls fail), and false is returned. Otherwise true is
45*9356374aSAndroid Build Coastguard Worker // returned.
46*9356374aSAndroid Build Coastguard Worker
47*9356374aSAndroid Build Coastguard Worker // In particular, attempting to encode a series of data into an insufficient
48*9356374aSAndroid Build Coastguard Worker // buffer has consistent and efficient behavior without any caller-side error
49*9356374aSAndroid Build Coastguard Worker // checking. Individual values will be encoded in their entirety or not at all
50*9356374aSAndroid Build Coastguard Worker // (unless one of the `Truncate` functions is used). Once a value is omitted
51*9356374aSAndroid Build Coastguard Worker // because it does not fit, no subsequent values will be encoded to preserve
52*9356374aSAndroid Build Coastguard Worker // ordering; the decoded sequence will be a prefix of the original sequence.
53*9356374aSAndroid Build Coastguard Worker
54*9356374aSAndroid Build Coastguard Worker // There are two ways to encode a message-typed field:
55*9356374aSAndroid Build Coastguard Worker //
56*9356374aSAndroid Build Coastguard Worker // * Construct its contents in a separate buffer and use `EncodeBytes` to copy
57*9356374aSAndroid Build Coastguard Worker // it into the primary buffer with type, tag, and length.
58*9356374aSAndroid Build Coastguard Worker // * Use `EncodeMessageStart` to write type and tag fields and reserve space for
59*9356374aSAndroid Build Coastguard Worker // the length field, then encode the contents directly into the buffer, then
60*9356374aSAndroid Build Coastguard Worker // use `EncodeMessageLength` to write the actual length into the reserved
61*9356374aSAndroid Build Coastguard Worker // bytes. This works fine if the actual length takes fewer bytes to encode
62*9356374aSAndroid Build Coastguard Worker // than were reserved, although you don't get your extra bytes back.
63*9356374aSAndroid Build Coastguard Worker // This approach will always produce a valid encoding, but your protocol may
64*9356374aSAndroid Build Coastguard Worker // require that the whole message field by omitted if the buffer is too small
65*9356374aSAndroid Build Coastguard Worker // to contain all desired subfields. In this case, operate on a copy of the
66*9356374aSAndroid Build Coastguard Worker // buffer view and assign back only if everything fit, i.e. if the last
67*9356374aSAndroid Build Coastguard Worker // `Encode` call returned true.
68*9356374aSAndroid Build Coastguard Worker
69*9356374aSAndroid Build Coastguard Worker // Encodes the specified integer as a varint field and returns true if it fits.
70*9356374aSAndroid Build Coastguard Worker // Used for int32_t, int64_t, uint32_t, uint64_t, bool, and enum field types.
71*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize * 2 bytes (20).
72*9356374aSAndroid Build Coastguard Worker bool EncodeVarint(uint64_t tag, uint64_t value, absl::Span<char> *buf);
EncodeVarint(uint64_t tag,int64_t value,absl::Span<char> * buf)73*9356374aSAndroid Build Coastguard Worker inline bool EncodeVarint(uint64_t tag, int64_t value, absl::Span<char> *buf) {
74*9356374aSAndroid Build Coastguard Worker return EncodeVarint(tag, static_cast<uint64_t>(value), buf);
75*9356374aSAndroid Build Coastguard Worker }
EncodeVarint(uint64_t tag,uint32_t value,absl::Span<char> * buf)76*9356374aSAndroid Build Coastguard Worker inline bool EncodeVarint(uint64_t tag, uint32_t value, absl::Span<char> *buf) {
77*9356374aSAndroid Build Coastguard Worker return EncodeVarint(tag, static_cast<uint64_t>(value), buf);
78*9356374aSAndroid Build Coastguard Worker }
EncodeVarint(uint64_t tag,int32_t value,absl::Span<char> * buf)79*9356374aSAndroid Build Coastguard Worker inline bool EncodeVarint(uint64_t tag, int32_t value, absl::Span<char> *buf) {
80*9356374aSAndroid Build Coastguard Worker return EncodeVarint(tag, static_cast<uint64_t>(value), buf);
81*9356374aSAndroid Build Coastguard Worker }
82*9356374aSAndroid Build Coastguard Worker
83*9356374aSAndroid Build Coastguard Worker // Encodes the specified integer as a varint field using ZigZag encoding and
84*9356374aSAndroid Build Coastguard Worker // returns true if it fits.
85*9356374aSAndroid Build Coastguard Worker // Used for sint32 and sint64 field types.
86*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize * 2 bytes (20).
EncodeVarintZigZag(uint64_t tag,int64_t value,absl::Span<char> * buf)87*9356374aSAndroid Build Coastguard Worker inline bool EncodeVarintZigZag(uint64_t tag, int64_t value,
88*9356374aSAndroid Build Coastguard Worker absl::Span<char> *buf) {
89*9356374aSAndroid Build Coastguard Worker if (value < 0)
90*9356374aSAndroid Build Coastguard Worker return EncodeVarint(tag, 2 * static_cast<uint64_t>(-(value + 1)) + 1, buf);
91*9356374aSAndroid Build Coastguard Worker return EncodeVarint(tag, 2 * static_cast<uint64_t>(value), buf);
92*9356374aSAndroid Build Coastguard Worker }
93*9356374aSAndroid Build Coastguard Worker
94*9356374aSAndroid Build Coastguard Worker // Encodes the specified integer as a 64-bit field and returns true if it fits.
95*9356374aSAndroid Build Coastguard Worker // Used for fixed64 and sfixed64 field types.
96*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize + 8 bytes (18).
97*9356374aSAndroid Build Coastguard Worker bool Encode64Bit(uint64_t tag, uint64_t value, absl::Span<char> *buf);
Encode64Bit(uint64_t tag,int64_t value,absl::Span<char> * buf)98*9356374aSAndroid Build Coastguard Worker inline bool Encode64Bit(uint64_t tag, int64_t value, absl::Span<char> *buf) {
99*9356374aSAndroid Build Coastguard Worker return Encode64Bit(tag, static_cast<uint64_t>(value), buf);
100*9356374aSAndroid Build Coastguard Worker }
Encode64Bit(uint64_t tag,uint32_t value,absl::Span<char> * buf)101*9356374aSAndroid Build Coastguard Worker inline bool Encode64Bit(uint64_t tag, uint32_t value, absl::Span<char> *buf) {
102*9356374aSAndroid Build Coastguard Worker return Encode64Bit(tag, static_cast<uint64_t>(value), buf);
103*9356374aSAndroid Build Coastguard Worker }
Encode64Bit(uint64_t tag,int32_t value,absl::Span<char> * buf)104*9356374aSAndroid Build Coastguard Worker inline bool Encode64Bit(uint64_t tag, int32_t value, absl::Span<char> *buf) {
105*9356374aSAndroid Build Coastguard Worker return Encode64Bit(tag, static_cast<uint64_t>(value), buf);
106*9356374aSAndroid Build Coastguard Worker }
107*9356374aSAndroid Build Coastguard Worker
108*9356374aSAndroid Build Coastguard Worker // Encodes the specified double as a 64-bit field and returns true if it fits.
109*9356374aSAndroid Build Coastguard Worker // Used for double field type.
110*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize + 8 bytes (18).
EncodeDouble(uint64_t tag,double value,absl::Span<char> * buf)111*9356374aSAndroid Build Coastguard Worker inline bool EncodeDouble(uint64_t tag, double value, absl::Span<char> *buf) {
112*9356374aSAndroid Build Coastguard Worker return Encode64Bit(tag, absl::bit_cast<uint64_t>(value), buf);
113*9356374aSAndroid Build Coastguard Worker }
114*9356374aSAndroid Build Coastguard Worker
115*9356374aSAndroid Build Coastguard Worker // Encodes the specified integer as a 32-bit field and returns true if it fits.
116*9356374aSAndroid Build Coastguard Worker // Used for fixed32 and sfixed32 field types.
117*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize + 4 bytes (14).
118*9356374aSAndroid Build Coastguard Worker bool Encode32Bit(uint64_t tag, uint32_t value, absl::Span<char> *buf);
Encode32Bit(uint64_t tag,int32_t value,absl::Span<char> * buf)119*9356374aSAndroid Build Coastguard Worker inline bool Encode32Bit(uint64_t tag, int32_t value, absl::Span<char> *buf) {
120*9356374aSAndroid Build Coastguard Worker return Encode32Bit(tag, static_cast<uint32_t>(value), buf);
121*9356374aSAndroid Build Coastguard Worker }
122*9356374aSAndroid Build Coastguard Worker
123*9356374aSAndroid Build Coastguard Worker // Encodes the specified float as a 32-bit field and returns true if it fits.
124*9356374aSAndroid Build Coastguard Worker // Used for float field type.
125*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize + 4 bytes (14).
EncodeFloat(uint64_t tag,float value,absl::Span<char> * buf)126*9356374aSAndroid Build Coastguard Worker inline bool EncodeFloat(uint64_t tag, float value, absl::Span<char> *buf) {
127*9356374aSAndroid Build Coastguard Worker return Encode32Bit(tag, absl::bit_cast<uint32_t>(value), buf);
128*9356374aSAndroid Build Coastguard Worker }
129*9356374aSAndroid Build Coastguard Worker
130*9356374aSAndroid Build Coastguard Worker // Encodes the specified bytes as a length-delimited field and returns true if
131*9356374aSAndroid Build Coastguard Worker // they fit.
132*9356374aSAndroid Build Coastguard Worker // Used for string, bytes, message, and packed-repeated field type.
133*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize * 2 + value.size() bytes (20 + value.size()).
134*9356374aSAndroid Build Coastguard Worker bool EncodeBytes(uint64_t tag, absl::Span<const char> value,
135*9356374aSAndroid Build Coastguard Worker absl::Span<char> *buf);
136*9356374aSAndroid Build Coastguard Worker
137*9356374aSAndroid Build Coastguard Worker // Encodes as many of the specified bytes as will fit as a length-delimited
138*9356374aSAndroid Build Coastguard Worker // field and returns true as long as the field header (`tag_type` and `length`)
139*9356374aSAndroid Build Coastguard Worker // fits.
140*9356374aSAndroid Build Coastguard Worker // Used for string, bytes, message, and packed-repeated field type.
141*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize * 2 + value.size() bytes (20 + value.size()).
142*9356374aSAndroid Build Coastguard Worker bool EncodeBytesTruncate(uint64_t tag, absl::Span<const char> value,
143*9356374aSAndroid Build Coastguard Worker absl::Span<char> *buf);
144*9356374aSAndroid Build Coastguard Worker
145*9356374aSAndroid Build Coastguard Worker // Encodes the specified string as a length-delimited field and returns true if
146*9356374aSAndroid Build Coastguard Worker // it fits.
147*9356374aSAndroid Build Coastguard Worker // Used for string, bytes, message, and packed-repeated field type.
148*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize * 2 + value.size() bytes (20 + value.size()).
EncodeString(uint64_t tag,absl::string_view value,absl::Span<char> * buf)149*9356374aSAndroid Build Coastguard Worker inline bool EncodeString(uint64_t tag, absl::string_view value,
150*9356374aSAndroid Build Coastguard Worker absl::Span<char> *buf) {
151*9356374aSAndroid Build Coastguard Worker return EncodeBytes(tag, value, buf);
152*9356374aSAndroid Build Coastguard Worker }
153*9356374aSAndroid Build Coastguard Worker
154*9356374aSAndroid Build Coastguard Worker // Encodes as much of the specified string as will fit as a length-delimited
155*9356374aSAndroid Build Coastguard Worker // field and returns true as long as the field header (`tag_type` and `length`)
156*9356374aSAndroid Build Coastguard Worker // fits.
157*9356374aSAndroid Build Coastguard Worker // Used for string, bytes, message, and packed-repeated field type.
158*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize * 2 + value.size() bytes (20 + value.size()).
EncodeStringTruncate(uint64_t tag,absl::string_view value,absl::Span<char> * buf)159*9356374aSAndroid Build Coastguard Worker inline bool EncodeStringTruncate(uint64_t tag, absl::string_view value,
160*9356374aSAndroid Build Coastguard Worker absl::Span<char> *buf) {
161*9356374aSAndroid Build Coastguard Worker return EncodeBytesTruncate(tag, value, buf);
162*9356374aSAndroid Build Coastguard Worker }
163*9356374aSAndroid Build Coastguard Worker
164*9356374aSAndroid Build Coastguard Worker // Encodes the header for a length-delimited field containing up to `max_size`
165*9356374aSAndroid Build Coastguard Worker // bytes or the number remaining in the buffer, whichever is less. If the
166*9356374aSAndroid Build Coastguard Worker // header fits, a non-nullptr `Span` is returned; this must be passed to
167*9356374aSAndroid Build Coastguard Worker // `EncodeMessageLength` after all contents are encoded to finalize the length
168*9356374aSAndroid Build Coastguard Worker // field. If the header does not fit, a nullptr `Span` is returned which is
169*9356374aSAndroid Build Coastguard Worker // safe to pass to `EncodeMessageLength` but need not be.
170*9356374aSAndroid Build Coastguard Worker // Used for string, bytes, message, and packed-repeated field type.
171*9356374aSAndroid Build Coastguard Worker // Consumes up to kMaxVarintSize * 2 bytes (20).
172*9356374aSAndroid Build Coastguard Worker ABSL_MUST_USE_RESULT absl::Span<char> EncodeMessageStart(uint64_t tag,
173*9356374aSAndroid Build Coastguard Worker uint64_t max_size,
174*9356374aSAndroid Build Coastguard Worker absl::Span<char> *buf);
175*9356374aSAndroid Build Coastguard Worker
176*9356374aSAndroid Build Coastguard Worker // Finalizes the length field in `msg` so that it encompasses all data encoded
177*9356374aSAndroid Build Coastguard Worker // since the call to `EncodeMessageStart` which returned `msg`. Does nothing if
178*9356374aSAndroid Build Coastguard Worker // `msg` is a `nullptr` `Span`.
179*9356374aSAndroid Build Coastguard Worker void EncodeMessageLength(absl::Span<char> msg, const absl::Span<char> *buf);
180*9356374aSAndroid Build Coastguard Worker
181*9356374aSAndroid Build Coastguard Worker enum class WireType : uint64_t {
182*9356374aSAndroid Build Coastguard Worker kVarint = 0,
183*9356374aSAndroid Build Coastguard Worker k64Bit = 1,
184*9356374aSAndroid Build Coastguard Worker kLengthDelimited = 2,
185*9356374aSAndroid Build Coastguard Worker k32Bit = 5,
186*9356374aSAndroid Build Coastguard Worker };
187*9356374aSAndroid Build Coastguard Worker
VarintSize(uint64_t value)188*9356374aSAndroid Build Coastguard Worker constexpr size_t VarintSize(uint64_t value) {
189*9356374aSAndroid Build Coastguard Worker return value < 128 ? 1 : 1 + VarintSize(value >> 7);
190*9356374aSAndroid Build Coastguard Worker }
MinVarintSize()191*9356374aSAndroid Build Coastguard Worker constexpr size_t MinVarintSize() {
192*9356374aSAndroid Build Coastguard Worker return VarintSize((std::numeric_limits<uint64_t>::min)());
193*9356374aSAndroid Build Coastguard Worker }
MaxVarintSize()194*9356374aSAndroid Build Coastguard Worker constexpr size_t MaxVarintSize() {
195*9356374aSAndroid Build Coastguard Worker return VarintSize((std::numeric_limits<uint64_t>::max)());
196*9356374aSAndroid Build Coastguard Worker }
197*9356374aSAndroid Build Coastguard Worker
MaxVarintForSize(size_t size)198*9356374aSAndroid Build Coastguard Worker constexpr uint64_t MaxVarintForSize(size_t size) {
199*9356374aSAndroid Build Coastguard Worker return size >= 10 ? (std::numeric_limits<uint64_t>::max)()
200*9356374aSAndroid Build Coastguard Worker : (static_cast<uint64_t>(1) << size * 7) - 1;
201*9356374aSAndroid Build Coastguard Worker }
202*9356374aSAndroid Build Coastguard Worker
203*9356374aSAndroid Build Coastguard Worker // `BufferSizeFor` returns a number of bytes guaranteed to be sufficient to
204*9356374aSAndroid Build Coastguard Worker // store encoded fields of the specified WireTypes regardless of tag numbers and
205*9356374aSAndroid Build Coastguard Worker // data values. This only makes sense for `WireType::kLengthDelimited` if you
206*9356374aSAndroid Build Coastguard Worker // add in the length of the contents yourself, e.g. for string and bytes fields
207*9356374aSAndroid Build Coastguard Worker // by adding the lengths of any encoded strings to the return value or for
208*9356374aSAndroid Build Coastguard Worker // submessage fields by enumerating the fields you may encode into their
209*9356374aSAndroid Build Coastguard Worker // contents.
BufferSizeFor()210*9356374aSAndroid Build Coastguard Worker constexpr size_t BufferSizeFor() { return 0; }
211*9356374aSAndroid Build Coastguard Worker template <typename... T>
BufferSizeFor(WireType type,T...tail)212*9356374aSAndroid Build Coastguard Worker constexpr size_t BufferSizeFor(WireType type, T... tail) {
213*9356374aSAndroid Build Coastguard Worker // tag_type + data + ...
214*9356374aSAndroid Build Coastguard Worker return MaxVarintSize() +
215*9356374aSAndroid Build Coastguard Worker (type == WireType::kVarint ? MaxVarintSize() : //
216*9356374aSAndroid Build Coastguard Worker type == WireType::k64Bit ? 8 : //
217*9356374aSAndroid Build Coastguard Worker type == WireType::k32Bit ? 4 : MaxVarintSize()) + //
218*9356374aSAndroid Build Coastguard Worker BufferSizeFor(tail...);
219*9356374aSAndroid Build Coastguard Worker }
220*9356374aSAndroid Build Coastguard Worker
221*9356374aSAndroid Build Coastguard Worker // absl::Span<const char> represents a view into the un-processed space in a
222*9356374aSAndroid Build Coastguard Worker // buffer during decoding. Decoding functions shrink the span as they go so
223*9356374aSAndroid Build Coastguard Worker // that the same view can be decoded iteratively until all data are processed.
224*9356374aSAndroid Build Coastguard Worker // In general, if the buffer is exhausted but additional bytes are expected by
225*9356374aSAndroid Build Coastguard Worker // the decoder, it will return values as if the additional bytes were zeros.
226*9356374aSAndroid Build Coastguard Worker // Length-delimited fields are an exception - if the encoded length field
227*9356374aSAndroid Build Coastguard Worker // indicates more data bytes than are available in the buffer, the `bytes_value`
228*9356374aSAndroid Build Coastguard Worker // and `string_value` accessors will return truncated views.
229*9356374aSAndroid Build Coastguard Worker
230*9356374aSAndroid Build Coastguard Worker class ProtoField final {
231*9356374aSAndroid Build Coastguard Worker public:
232*9356374aSAndroid Build Coastguard Worker // Consumes bytes from `data` and returns true if there were any bytes to
233*9356374aSAndroid Build Coastguard Worker // decode.
234*9356374aSAndroid Build Coastguard Worker bool DecodeFrom(absl::Span<const char> *data);
tag()235*9356374aSAndroid Build Coastguard Worker uint64_t tag() const { return tag_; }
type()236*9356374aSAndroid Build Coastguard Worker WireType type() const { return type_; }
237*9356374aSAndroid Build Coastguard Worker
238*9356374aSAndroid Build Coastguard Worker // These value accessors will return nonsense if the data were not encoded in
239*9356374aSAndroid Build Coastguard Worker // the corresponding wiretype from the corresponding C++ (or other language)
240*9356374aSAndroid Build Coastguard Worker // type.
241*9356374aSAndroid Build Coastguard Worker
double_value()242*9356374aSAndroid Build Coastguard Worker double double_value() const { return absl::bit_cast<double>(value_); }
float_value()243*9356374aSAndroid Build Coastguard Worker float float_value() const {
244*9356374aSAndroid Build Coastguard Worker return absl::bit_cast<float>(static_cast<uint32_t>(value_));
245*9356374aSAndroid Build Coastguard Worker }
int32_value()246*9356374aSAndroid Build Coastguard Worker int32_t int32_value() const { return static_cast<int32_t>(value_); }
int64_value()247*9356374aSAndroid Build Coastguard Worker int64_t int64_value() const { return static_cast<int64_t>(value_); }
sint32_value()248*9356374aSAndroid Build Coastguard Worker int32_t sint32_value() const {
249*9356374aSAndroid Build Coastguard Worker if (value_ % 2) return static_cast<int32_t>(0 - ((value_ - 1) / 2) - 1);
250*9356374aSAndroid Build Coastguard Worker return static_cast<int32_t>(value_ / 2);
251*9356374aSAndroid Build Coastguard Worker }
sint64_value()252*9356374aSAndroid Build Coastguard Worker int64_t sint64_value() const {
253*9356374aSAndroid Build Coastguard Worker if (value_ % 2) return 0 - ((value_ - 1) / 2) - 1;
254*9356374aSAndroid Build Coastguard Worker return value_ / 2;
255*9356374aSAndroid Build Coastguard Worker }
uint32_value()256*9356374aSAndroid Build Coastguard Worker uint32_t uint32_value() const { return static_cast<uint32_t>(value_); }
uint64_value()257*9356374aSAndroid Build Coastguard Worker uint64_t uint64_value() const { return value_; }
bool_value()258*9356374aSAndroid Build Coastguard Worker bool bool_value() const { return value_ != 0; }
259*9356374aSAndroid Build Coastguard Worker // To decode an enum, call int32_value() and cast to the appropriate type.
260*9356374aSAndroid Build Coastguard Worker // Note that the official C++ proto compiler treats enum fields with values
261*9356374aSAndroid Build Coastguard Worker // that do not correspond to a defined enumerator as unknown fields.
262*9356374aSAndroid Build Coastguard Worker
263*9356374aSAndroid Build Coastguard Worker // To decode fields within a submessage field, call
264*9356374aSAndroid Build Coastguard Worker // `DecodeNextField(field.BytesValue())`.
bytes_value()265*9356374aSAndroid Build Coastguard Worker absl::Span<const char> bytes_value() const { return data_; }
string_value()266*9356374aSAndroid Build Coastguard Worker absl::string_view string_value() const {
267*9356374aSAndroid Build Coastguard Worker const auto data = bytes_value();
268*9356374aSAndroid Build Coastguard Worker return absl::string_view(data.data(), data.size());
269*9356374aSAndroid Build Coastguard Worker }
270*9356374aSAndroid Build Coastguard Worker // Returns the encoded length of a length-delimited field. This equals
271*9356374aSAndroid Build Coastguard Worker // `bytes_value().size()` except when the latter has been truncated due to
272*9356374aSAndroid Build Coastguard Worker // buffer underrun.
encoded_length()273*9356374aSAndroid Build Coastguard Worker uint64_t encoded_length() const { return value_; }
274*9356374aSAndroid Build Coastguard Worker
275*9356374aSAndroid Build Coastguard Worker private:
276*9356374aSAndroid Build Coastguard Worker uint64_t tag_;
277*9356374aSAndroid Build Coastguard Worker WireType type_;
278*9356374aSAndroid Build Coastguard Worker // For `kTypeVarint`, `kType64Bit`, and `kType32Bit`, holds the decoded value.
279*9356374aSAndroid Build Coastguard Worker // For `kTypeLengthDelimited`, holds the decoded length.
280*9356374aSAndroid Build Coastguard Worker uint64_t value_;
281*9356374aSAndroid Build Coastguard Worker absl::Span<const char> data_;
282*9356374aSAndroid Build Coastguard Worker };
283*9356374aSAndroid Build Coastguard Worker
284*9356374aSAndroid Build Coastguard Worker } // namespace log_internal
285*9356374aSAndroid Build Coastguard Worker ABSL_NAMESPACE_END
286*9356374aSAndroid Build Coastguard Worker } // namespace absl
287*9356374aSAndroid Build Coastguard Worker
288*9356374aSAndroid Build Coastguard Worker #endif // ABSL_LOG_INTERNAL_PROTO_H_
289