Line data Source code
1 : // Protocol Buffers - Google's data interchange format
2 : // Copyright 2008 Google Inc. All rights reserved.
3 : // https://developers.google.com/protocol-buffers/
4 : //
5 : // Redistribution and use in source and binary forms, with or without
6 : // modification, are permitted provided that the following conditions are
7 : // met:
8 : //
9 : // * Redistributions of source code must retain the above copyright
10 : // notice, this list of conditions and the following disclaimer.
11 : // * Redistributions in binary form must reproduce the above
12 : // copyright notice, this list of conditions and the following disclaimer
13 : // in the documentation and/or other materials provided with the
14 : // distribution.
15 : // * Neither the name of Google Inc. nor the names of its
16 : // contributors may be used to endorse or promote products derived from
17 : // this software without specific prior written permission.
18 : //
19 : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20 : // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21 : // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22 : // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
23 : // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
24 : // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
25 : // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 : // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 : // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 : // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
29 : // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 :
31 : // Author: kenton@google.com (Kenton Varda)
32 : // wink@google.com (Wink Saville) (refactored from wire_format.h)
33 : // Based on original Protocol Buffers design by
34 : // Sanjay Ghemawat, Jeff Dean, and others.
35 :
36 : #ifndef GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_INL_H__
37 : #define GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_INL_H__
38 :
39 : #ifdef _MSC_VER
40 : // This is required for min/max on VS2013 only.
41 : #include <algorithm>
42 : #endif
43 :
44 : #include <string>
45 : #include <google/protobuf/stubs/common.h>
46 : #include <google/protobuf/stubs/logging.h>
47 : #include <google/protobuf/message_lite.h>
48 : #include <google/protobuf/repeated_field.h>
49 : #include <google/protobuf/wire_format_lite.h>
50 : #include <google/protobuf/io/coded_stream.h>
51 : #include <google/protobuf/arenastring.h>
52 :
53 :
54 : namespace google {
55 : namespace protobuf {
56 : namespace internal {
57 :
58 : // Implementation details of ReadPrimitive.
59 :
60 : template <>
61 : inline bool WireFormatLite::ReadPrimitive<int32, WireFormatLite::TYPE_INT32>(
62 : io::CodedInputStream* input,
63 : int32* value) {
64 : uint32 temp;
65 1297828 : if (!input->ReadVarint32(&temp)) return false;
66 1298809 : *value = static_cast<int32>(temp);
67 1277964 : return true;
68 : }
69 : template <>
70 : inline bool WireFormatLite::ReadPrimitive<int64, WireFormatLite::TYPE_INT64>(
71 : io::CodedInputStream* input,
72 : int64* value) {
73 : uint64 temp;
74 24 : if (!input->ReadVarint64(&temp)) return false;
75 24 : *value = static_cast<int64>(temp);
76 12 : return true;
77 : }
78 : template <>
79 : inline bool WireFormatLite::ReadPrimitive<uint32, WireFormatLite::TYPE_UINT32>(
80 : io::CodedInputStream* input,
81 : uint32* value) {
82 29940 : return input->ReadVarint32(value);
83 : }
84 : template <>
85 : inline bool WireFormatLite::ReadPrimitive<uint64, WireFormatLite::TYPE_UINT64>(
86 : io::CodedInputStream* input,
87 : uint64* value) {
88 42 : return input->ReadVarint64(value);
89 : }
90 : template <>
91 : inline bool WireFormatLite::ReadPrimitive<int32, WireFormatLite::TYPE_SINT32>(
92 : io::CodedInputStream* input,
93 : int32* value) {
94 : uint32 temp;
95 0 : if (!input->ReadVarint32(&temp)) return false;
96 0 : *value = ZigZagDecode32(temp);
97 : return true;
98 : }
99 : template <>
100 : inline bool WireFormatLite::ReadPrimitive<int64, WireFormatLite::TYPE_SINT64>(
101 : io::CodedInputStream* input,
102 : int64* value) {
103 : uint64 temp;
104 0 : if (!input->ReadVarint64(&temp)) return false;
105 0 : *value = ZigZagDecode64(temp);
106 : return true;
107 : }
108 : template <>
109 : inline bool WireFormatLite::ReadPrimitive<uint32, WireFormatLite::TYPE_FIXED32>(
110 : io::CodedInputStream* input,
111 : uint32* value) {
112 0 : return input->ReadLittleEndian32(value);
113 : }
114 : template <>
115 : inline bool WireFormatLite::ReadPrimitive<uint64, WireFormatLite::TYPE_FIXED64>(
116 : io::CodedInputStream* input,
117 : uint64* value) {
118 0 : return input->ReadLittleEndian64(value);
119 : }
120 : template <>
121 : inline bool WireFormatLite::ReadPrimitive<int32, WireFormatLite::TYPE_SFIXED32>(
122 : io::CodedInputStream* input,
123 : int32* value) {
124 : uint32 temp;
125 0 : if (!input->ReadLittleEndian32(&temp)) return false;
126 0 : *value = static_cast<int32>(temp);
127 : return true;
128 : }
129 : template <>
130 : inline bool WireFormatLite::ReadPrimitive<int64, WireFormatLite::TYPE_SFIXED64>(
131 : io::CodedInputStream* input,
132 : int64* value) {
133 : uint64 temp;
134 0 : if (!input->ReadLittleEndian64(&temp)) return false;
135 0 : *value = static_cast<int64>(temp);
136 : return true;
137 : }
138 : template <>
139 : inline bool WireFormatLite::ReadPrimitive<float, WireFormatLite::TYPE_FLOAT>(
140 : io::CodedInputStream* input,
141 : float* value) {
142 : uint32 temp;
143 0 : if (!input->ReadLittleEndian32(&temp)) return false;
144 0 : *value = DecodeFloat(temp);
145 : return true;
146 : }
147 : template <>
148 : inline bool WireFormatLite::ReadPrimitive<double, WireFormatLite::TYPE_DOUBLE>(
149 : io::CodedInputStream* input,
150 : double* value) {
151 : uint64 temp;
152 135 : if (!input->ReadLittleEndian64(&temp)) return false;
153 135 : *value = DecodeDouble(temp);
154 133 : return true;
155 : }
156 : template <>
157 : inline bool WireFormatLite::ReadPrimitive<bool, WireFormatLite::TYPE_BOOL>(
158 : io::CodedInputStream* input,
159 : bool* value) {
160 : uint64 temp;
161 952 : if (!input->ReadVarint64(&temp)) return false;
162 952 : *value = temp != 0;
163 23 : return true;
164 : }
165 : template <>
166 : inline bool WireFormatLite::ReadPrimitive<int, WireFormatLite::TYPE_ENUM>(
167 : io::CodedInputStream* input,
168 : int* value) {
169 : uint32 temp;
170 12983 : if (!input->ReadVarint32(&temp)) return false;
171 12983 : *value = static_cast<int>(temp);
172 11 : return true;
173 : }
174 :
175 : template <>
176 : inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
177 : uint32, WireFormatLite::TYPE_FIXED32>(
178 : const uint8* buffer,
179 : uint32* value) {
180 : return io::CodedInputStream::ReadLittleEndian32FromArray(buffer, value);
181 : }
182 : template <>
183 : inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
184 : uint64, WireFormatLite::TYPE_FIXED64>(
185 : const uint8* buffer,
186 : uint64* value) {
187 : return io::CodedInputStream::ReadLittleEndian64FromArray(buffer, value);
188 : }
189 : template <>
190 : inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
191 : int32, WireFormatLite::TYPE_SFIXED32>(
192 : const uint8* buffer,
193 : int32* value) {
194 : uint32 temp;
195 : buffer = io::CodedInputStream::ReadLittleEndian32FromArray(buffer, &temp);
196 : *value = static_cast<int32>(temp);
197 : return buffer;
198 : }
199 : template <>
200 : inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
201 : int64, WireFormatLite::TYPE_SFIXED64>(
202 : const uint8* buffer,
203 : int64* value) {
204 : uint64 temp;
205 : buffer = io::CodedInputStream::ReadLittleEndian64FromArray(buffer, &temp);
206 : *value = static_cast<int64>(temp);
207 : return buffer;
208 : }
209 : template <>
210 : inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
211 : float, WireFormatLite::TYPE_FLOAT>(
212 : const uint8* buffer,
213 : float* value) {
214 : uint32 temp;
215 : buffer = io::CodedInputStream::ReadLittleEndian32FromArray(buffer, &temp);
216 : *value = DecodeFloat(temp);
217 : return buffer;
218 : }
219 : template <>
220 : inline const uint8* WireFormatLite::ReadPrimitiveFromArray<
221 : double, WireFormatLite::TYPE_DOUBLE>(
222 : const uint8* buffer,
223 : double* value) {
224 : uint64 temp;
225 : buffer = io::CodedInputStream::ReadLittleEndian64FromArray(buffer, &temp);
226 : *value = DecodeDouble(temp);
227 : return buffer;
228 : }
229 :
230 : template <typename CType, enum WireFormatLite::FieldType DeclaredType>
231 : inline bool WireFormatLite::ReadRepeatedPrimitive(
232 : int, // tag_size, unused.
233 : uint32 tag,
234 : io::CodedInputStream* input,
235 0 : RepeatedField<CType>* values) {
236 : CType value;
237 0 : if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
238 0 : values->Add(value);
239 0 : int elements_already_reserved = values->Capacity() - values->size();
240 0 : while (elements_already_reserved > 0 && input->ExpectTag(tag)) {
241 0 : if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
242 0 : values->AddAlreadyReserved(value);
243 0 : elements_already_reserved--;
244 : }
245 0 : return true;
246 : }
247 :
248 : template <typename CType, enum WireFormatLite::FieldType DeclaredType>
249 : inline bool WireFormatLite::ReadRepeatedFixedSizePrimitive(
250 : int tag_size,
251 : uint32 tag,
252 : io::CodedInputStream* input,
253 : RepeatedField<CType>* values) {
254 : GOOGLE_DCHECK_EQ(UInt32Size(tag), tag_size);
255 : CType value;
256 : if (!ReadPrimitive<CType, DeclaredType>(input, &value))
257 : return false;
258 : values->Add(value);
259 :
260 : // For fixed size values, repeated values can be read more quickly by
261 : // reading directly from a raw array.
262 : //
263 : // We can get a tight loop by only reading as many elements as can be
264 : // added to the RepeatedField without having to do any resizing. Additionally,
265 : // we only try to read as many elements as are available from the current
266 : // buffer space. Doing so avoids having to perform boundary checks when
267 : // reading the value: the maximum number of elements that can be read is
268 : // known outside of the loop.
269 : const void* void_pointer;
270 : int size;
271 : input->GetDirectBufferPointerInline(&void_pointer, &size);
272 : if (size > 0) {
273 : const uint8* buffer = reinterpret_cast<const uint8*>(void_pointer);
274 : // The number of bytes each type occupies on the wire.
275 : const int per_value_size = tag_size + sizeof(value);
276 :
277 : int elements_available = min(values->Capacity() - values->size(),
278 : size / per_value_size);
279 : int num_read = 0;
280 : while (num_read < elements_available &&
281 : (buffer = io::CodedInputStream::ExpectTagFromArray(
282 : buffer, tag)) != NULL) {
283 : buffer = ReadPrimitiveFromArray<CType, DeclaredType>(buffer, &value);
284 : values->AddAlreadyReserved(value);
285 : ++num_read;
286 : }
287 : const int read_bytes = num_read * per_value_size;
288 : if (read_bytes > 0) {
289 : input->Skip(read_bytes);
290 : }
291 : }
292 : return true;
293 : }
294 :
295 : // Specializations of ReadRepeatedPrimitive for the fixed size types, which use
296 : // the optimized code path.
297 : #define READ_REPEATED_FIXED_SIZE_PRIMITIVE(CPPTYPE, DECLARED_TYPE) \
298 : template <> \
299 : inline bool WireFormatLite::ReadRepeatedPrimitive< \
300 : CPPTYPE, WireFormatLite::DECLARED_TYPE>( \
301 : int tag_size, \
302 : uint32 tag, \
303 : io::CodedInputStream* input, \
304 : RepeatedField<CPPTYPE>* values) { \
305 : return ReadRepeatedFixedSizePrimitive< \
306 : CPPTYPE, WireFormatLite::DECLARED_TYPE>( \
307 : tag_size, tag, input, values); \
308 : }
309 :
310 : READ_REPEATED_FIXED_SIZE_PRIMITIVE(uint32, TYPE_FIXED32)
311 : READ_REPEATED_FIXED_SIZE_PRIMITIVE(uint64, TYPE_FIXED64)
312 : READ_REPEATED_FIXED_SIZE_PRIMITIVE(int32, TYPE_SFIXED32)
313 : READ_REPEATED_FIXED_SIZE_PRIMITIVE(int64, TYPE_SFIXED64)
314 : READ_REPEATED_FIXED_SIZE_PRIMITIVE(float, TYPE_FLOAT)
315 : READ_REPEATED_FIXED_SIZE_PRIMITIVE(double, TYPE_DOUBLE)
316 :
317 : #undef READ_REPEATED_FIXED_SIZE_PRIMITIVE
318 :
319 : template <typename CType, enum WireFormatLite::FieldType DeclaredType>
320 0 : bool WireFormatLite::ReadRepeatedPrimitiveNoInline(
321 : int tag_size,
322 : uint32 tag,
323 : io::CodedInputStream* input,
324 : RepeatedField<CType>* value) {
325 : return ReadRepeatedPrimitive<CType, DeclaredType>(
326 0 : tag_size, tag, input, value);
327 : }
328 :
329 : template <typename CType, enum WireFormatLite::FieldType DeclaredType>
330 : inline bool WireFormatLite::ReadPackedPrimitive(io::CodedInputStream* input,
331 : RepeatedField<CType>* values) {
332 : uint32 length;
333 3153 : if (!input->ReadVarint32(&length)) return false;
334 3153 : io::CodedInputStream::Limit limit = input->PushLimit(length);
335 45053 : while (input->BytesUntilLimit() > 0) {
336 : CType value;
337 41900 : if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
338 41900 : values->Add(value);
339 : }
340 3153 : input->PopLimit(limit);
341 12 : return true;
342 : }
343 :
344 : template <typename CType, enum WireFormatLite::FieldType DeclaredType>
345 : inline bool WireFormatLite::ReadPackedFixedSizePrimitive(
346 : io::CodedInputStream* input, RepeatedField<CType>* values) {
347 : uint32 length;
348 : if (!input->ReadVarint32(&length)) return false;
349 : const uint32 old_entries = values->size();
350 : const uint32 new_entries = length / sizeof(CType);
351 : const uint32 new_bytes = new_entries * sizeof(CType);
352 : if (new_bytes != length) return false;
353 : // We would *like* to pre-allocate the buffer to write into (for
354 : // speed), but *must* avoid performing a very large allocation due
355 : // to a malicious user-supplied "length" above. So we have a fast
356 : // path that pre-allocates when the "length" is less than a bound.
357 : // We determine the bound by calling BytesUntilTotalBytesLimit() and
358 : // BytesUntilLimit(). These return -1 to mean "no limit set".
359 : // There are four cases:
360 : // TotalBytesLimit Limit
361 : // -1 -1 Use slow path.
362 : // -1 >= 0 Use fast path if length <= Limit.
363 : // >= 0 -1 Use slow path.
364 : // >= 0 >= 0 Use fast path if length <= min(both limits).
365 : int64 bytes_limit = input->BytesUntilTotalBytesLimit();
366 : if (bytes_limit == -1) {
367 : bytes_limit = input->BytesUntilLimit();
368 : } else {
369 : bytes_limit =
370 : min(bytes_limit, static_cast<int64>(input->BytesUntilLimit()));
371 : }
372 : if (bytes_limit >= new_bytes) {
373 : // Fast-path that pre-allocates *values to the final size.
374 : #if defined(PROTOBUF_LITTLE_ENDIAN)
375 : values->Resize(old_entries + new_entries, 0);
376 : // values->mutable_data() may change after Resize(), so do this after:
377 : void* dest = reinterpret_cast<void*>(values->mutable_data() + old_entries);
378 : if (!input->ReadRaw(dest, new_bytes)) {
379 : values->Truncate(old_entries);
380 : return false;
381 : }
382 : #else
383 : values->Reserve(old_entries + new_entries);
384 : CType value;
385 : for (uint32 i = 0; i < new_entries; ++i) {
386 : if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
387 : values->AddAlreadyReserved(value);
388 : }
389 : #endif
390 : } else {
391 : // This is the slow-path case where "length" may be too large to
392 : // safely allocate. We read as much as we can into *values
393 : // without pre-allocating "length" bytes.
394 : CType value;
395 : for (uint32 i = 0; i < new_entries; ++i) {
396 : if (!ReadPrimitive<CType, DeclaredType>(input, &value)) return false;
397 : values->Add(value);
398 : }
399 : }
400 : return true;
401 : }
402 :
403 : // Specializations of ReadPackedPrimitive for the fixed size types, which use
404 : // an optimized code path.
405 : #define READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(CPPTYPE, DECLARED_TYPE) \
406 : template <> \
407 : inline bool WireFormatLite::ReadPackedPrimitive< \
408 : CPPTYPE, WireFormatLite::DECLARED_TYPE>( \
409 : io::CodedInputStream* input, \
410 : RepeatedField<CPPTYPE>* values) { \
411 : return ReadPackedFixedSizePrimitive< \
412 : CPPTYPE, WireFormatLite::DECLARED_TYPE>(input, values); \
413 : }
414 :
415 : READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(uint32, TYPE_FIXED32);
416 : READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(uint64, TYPE_FIXED64);
417 : READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(int32, TYPE_SFIXED32);
418 : READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(int64, TYPE_SFIXED64);
419 : READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(float, TYPE_FLOAT);
420 : READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE(double, TYPE_DOUBLE);
421 :
422 : #undef READ_REPEATED_PACKED_FIXED_SIZE_PRIMITIVE
423 :
424 : template <typename CType, enum WireFormatLite::FieldType DeclaredType>
425 0 : bool WireFormatLite::ReadPackedPrimitiveNoInline(io::CodedInputStream* input,
426 : RepeatedField<CType>* values) {
427 0 : return ReadPackedPrimitive<CType, DeclaredType>(input, values);
428 : }
429 :
430 :
431 :
432 0 : inline bool WireFormatLite::ReadGroup(int field_number,
433 0 : io::CodedInputStream* input,
434 : MessageLite* value) {
435 0 : if (!input->IncrementRecursionDepth()) return false;
436 0 : if (!value->MergePartialFromCodedStream(input)) return false;
437 0 : input->DecrementRecursionDepth();
438 : // Make sure the last thing read was an end tag for this group.
439 0 : if (!input->LastTagWas(MakeTag(field_number, WIRETYPE_END_GROUP))) {
440 : return false;
441 : }
442 0 : return true;
443 : }
444 0 : inline bool WireFormatLite::ReadMessage(io::CodedInputStream* input,
445 : MessageLite* value) {
446 : uint32 length;
447 0 : if (!input->ReadVarint32(&length)) return false;
448 : std::pair<io::CodedInputStream::Limit, int> p =
449 0 : input->IncrementRecursionDepthAndPushLimit(length);
450 0 : if (p.second < 0 || !value->MergePartialFromCodedStream(input)) return false;
451 : // Make sure that parsing stopped when the limit was hit, not at an endgroup
452 : // tag.
453 0 : return input->DecrementRecursionDepthAndPopLimit(p.first);
454 : }
455 :
456 : // We name the template parameter something long and extremely unlikely to occur
457 : // elsewhere because a *qualified* member access expression designed to avoid
458 : // virtual dispatch, C++03 [basic.lookup.classref] 3.4.5/4 requires that the
459 : // name of the qualifying class to be looked up both in the context of the full
460 : // expression (finding the template parameter) and in the context of the object
461 : // whose member we are accessing. This could potentially find a nested type
462 : // within that object. The standard goes on to require these names to refer to
463 : // the same entity, which this collision would violate. The lack of a safe way
464 : // to avoid this collision appears to be a defect in the standard, but until it
465 : // is corrected, we choose the name to avoid accidental collisions.
466 : template<typename MessageType_WorkAroundCppLookupDefect>
467 : inline bool WireFormatLite::ReadGroupNoVirtual(
468 : int field_number, io::CodedInputStream* input,
469 : MessageType_WorkAroundCppLookupDefect* value) {
470 : if (!input->IncrementRecursionDepth()) return false;
471 : if (!value->
472 : MessageType_WorkAroundCppLookupDefect::MergePartialFromCodedStream(input))
473 : return false;
474 : input->UnsafeDecrementRecursionDepth();
475 : // Make sure the last thing read was an end tag for this group.
476 : if (!input->LastTagWas(MakeTag(field_number, WIRETYPE_END_GROUP))) {
477 : return false;
478 : }
479 : return true;
480 : }
481 : template<typename MessageType_WorkAroundCppLookupDefect>
482 : inline bool WireFormatLite::ReadGroupNoVirtualNoRecursionDepth(
483 : int field_number, io::CodedInputStream* input,
484 : MessageType_WorkAroundCppLookupDefect* value) {
485 : return value->MessageType_WorkAroundCppLookupDefect::
486 : MergePartialFromCodedStream(input) &&
487 : input->LastTagWas(MakeTag(field_number, WIRETYPE_END_GROUP));
488 : }
489 : template<typename MessageType_WorkAroundCppLookupDefect>
490 1277696 : inline bool WireFormatLite::ReadMessageNoVirtual(
491 : io::CodedInputStream* input, MessageType_WorkAroundCppLookupDefect* value) {
492 : uint32 length;
493 1277696 : if (!input->ReadVarint32(&length)) return false;
494 : std::pair<io::CodedInputStream::Limit, int> p =
495 1278321 : input->IncrementRecursionDepthAndPushLimit(length);
496 1277080 : if (p.second < 0 || !value->
497 : MessageType_WorkAroundCppLookupDefect::MergePartialFromCodedStream(input))
498 0 : return false;
499 : // Make sure that parsing stopped when the limit was hit, not at an endgroup
500 : // tag.
501 1276737 : return input->DecrementRecursionDepthAndPopLimit(p.first);
502 : }
503 : template<typename MessageType_WorkAroundCppLookupDefect>
504 12827 : inline bool WireFormatLite::ReadMessageNoVirtualNoRecursionDepth(
505 : io::CodedInputStream* input, MessageType_WorkAroundCppLookupDefect* value) {
506 12827 : io::CodedInputStream::Limit old_limit = input->ReadLengthAndPushLimit();
507 12827 : if (!value->
508 : MessageType_WorkAroundCppLookupDefect::MergePartialFromCodedStream(input))
509 0 : return false;
510 : // Make sure that parsing stopped when the limit was hit, not at an endgroup
511 : // tag.
512 12827 : return input->CheckEntireMessageConsumedAndPopLimit(old_limit);
513 : }
514 :
515 : // ===================================================================
516 :
517 : inline void WireFormatLite::WriteTag(int field_number, WireType type,
518 : io::CodedOutputStream* output) {
519 64 : output->WriteTag(MakeTag(field_number, type));
520 : }
521 :
522 : inline void WireFormatLite::WriteInt32NoTag(int32 value,
523 : io::CodedOutputStream* output) {
524 8 : output->WriteVarint32SignExtended(value);
525 : }
526 : inline void WireFormatLite::WriteInt64NoTag(int64 value,
527 : io::CodedOutputStream* output) {
528 0 : output->WriteVarint64(static_cast<uint64>(value));
529 : }
530 : inline void WireFormatLite::WriteUInt32NoTag(uint32 value,
531 : io::CodedOutputStream* output) {
532 0 : output->WriteVarint32(value);
533 : }
534 : inline void WireFormatLite::WriteUInt64NoTag(uint64 value,
535 : io::CodedOutputStream* output) {
536 0 : output->WriteVarint64(value);
537 : }
538 : inline void WireFormatLite::WriteSInt32NoTag(int32 value,
539 : io::CodedOutputStream* output) {
540 0 : output->WriteVarint32(ZigZagEncode32(value));
541 : }
542 : inline void WireFormatLite::WriteSInt64NoTag(int64 value,
543 : io::CodedOutputStream* output) {
544 0 : output->WriteVarint64(ZigZagEncode64(value));
545 : }
546 : inline void WireFormatLite::WriteFixed32NoTag(uint32 value,
547 : io::CodedOutputStream* output) {
548 0 : output->WriteLittleEndian32(value);
549 : }
550 : inline void WireFormatLite::WriteFixed64NoTag(uint64 value,
551 : io::CodedOutputStream* output) {
552 0 : output->WriteLittleEndian64(value);
553 : }
554 : inline void WireFormatLite::WriteSFixed32NoTag(int32 value,
555 : io::CodedOutputStream* output) {
556 0 : output->WriteLittleEndian32(static_cast<uint32>(value));
557 : }
558 : inline void WireFormatLite::WriteSFixed64NoTag(int64 value,
559 : io::CodedOutputStream* output) {
560 0 : output->WriteLittleEndian64(static_cast<uint64>(value));
561 : }
562 : inline void WireFormatLite::WriteFloatNoTag(float value,
563 : io::CodedOutputStream* output) {
564 0 : output->WriteLittleEndian32(EncodeFloat(value));
565 : }
566 : inline void WireFormatLite::WriteDoubleNoTag(double value,
567 : io::CodedOutputStream* output) {
568 0 : output->WriteLittleEndian64(EncodeDouble(value));
569 : }
570 : inline void WireFormatLite::WriteBoolNoTag(bool value,
571 : io::CodedOutputStream* output) {
572 0 : output->WriteVarint32(value ? 1 : 0);
573 : }
574 : inline void WireFormatLite::WriteEnumNoTag(int value,
575 : io::CodedOutputStream* output) {
576 0 : output->WriteVarint32SignExtended(value);
577 : }
578 :
579 : // See comment on ReadGroupNoVirtual to understand the need for this template
580 : // parameter name.
581 : template<typename MessageType_WorkAroundCppLookupDefect>
582 : inline void WireFormatLite::WriteGroupNoVirtual(
583 : int field_number, const MessageType_WorkAroundCppLookupDefect& value,
584 : io::CodedOutputStream* output) {
585 : WriteTag(field_number, WIRETYPE_START_GROUP, output);
586 : value.MessageType_WorkAroundCppLookupDefect::SerializeWithCachedSizes(output);
587 : WriteTag(field_number, WIRETYPE_END_GROUP, output);
588 : }
589 : template<typename MessageType_WorkAroundCppLookupDefect>
590 : inline void WireFormatLite::WriteMessageNoVirtual(
591 : int field_number, const MessageType_WorkAroundCppLookupDefect& value,
592 : io::CodedOutputStream* output) {
593 : WriteTag(field_number, WIRETYPE_LENGTH_DELIMITED, output);
594 : output->WriteVarint32(
595 : value.MessageType_WorkAroundCppLookupDefect::GetCachedSize());
596 : value.MessageType_WorkAroundCppLookupDefect::SerializeWithCachedSizes(output);
597 : }
598 :
599 : // ===================================================================
600 :
601 : inline uint8* WireFormatLite::WriteTagToArray(int field_number,
602 : WireType type,
603 : uint8* target) {
604 : return io::CodedOutputStream::WriteTagToArray(MakeTag(field_number, type),
605 8173460 : target);
606 : }
607 :
608 : inline uint8* WireFormatLite::WriteInt32NoTagToArray(int32 value,
609 : uint8* target) {
610 1293076 : return io::CodedOutputStream::WriteVarint32SignExtendedToArray(value, target);
611 : }
612 : inline uint8* WireFormatLite::WriteInt64NoTagToArray(int64 value,
613 : uint8* target) {
614 : return io::CodedOutputStream::WriteVarint64ToArray(
615 343 : static_cast<uint64>(value), target);
616 : }
617 : inline uint8* WireFormatLite::WriteUInt32NoTagToArray(uint32 value,
618 : uint8* target) {
619 29940 : return io::CodedOutputStream::WriteVarint32ToArray(value, target);
620 : }
621 : inline uint8* WireFormatLite::WriteUInt64NoTagToArray(uint64 value,
622 : uint8* target) {
623 42 : return io::CodedOutputStream::WriteVarint64ToArray(value, target);
624 : }
625 : inline uint8* WireFormatLite::WriteSInt32NoTagToArray(int32 value,
626 : uint8* target) {
627 : return io::CodedOutputStream::WriteVarint32ToArray(ZigZagEncode32(value),
628 0 : target);
629 : }
630 : inline uint8* WireFormatLite::WriteSInt64NoTagToArray(int64 value,
631 : uint8* target) {
632 : return io::CodedOutputStream::WriteVarint64ToArray(ZigZagEncode64(value),
633 0 : target);
634 : }
635 : inline uint8* WireFormatLite::WriteFixed32NoTagToArray(uint32 value,
636 : uint8* target) {
637 18 : return io::CodedOutputStream::WriteLittleEndian32ToArray(value, target);
638 : }
639 : inline uint8* WireFormatLite::WriteFixed64NoTagToArray(uint64 value,
640 : uint8* target) {
641 18 : return io::CodedOutputStream::WriteLittleEndian64ToArray(value, target);
642 : }
643 : inline uint8* WireFormatLite::WriteSFixed32NoTagToArray(int32 value,
644 : uint8* target) {
645 : return io::CodedOutputStream::WriteLittleEndian32ToArray(
646 0 : static_cast<uint32>(value), target);
647 : }
648 : inline uint8* WireFormatLite::WriteSFixed64NoTagToArray(int64 value,
649 : uint8* target) {
650 : return io::CodedOutputStream::WriteLittleEndian64ToArray(
651 0 : static_cast<uint64>(value), target);
652 : }
653 : inline uint8* WireFormatLite::WriteFloatNoTagToArray(float value,
654 : uint8* target) {
655 : return io::CodedOutputStream::WriteLittleEndian32ToArray(EncodeFloat(value),
656 0 : target);
657 : }
658 : inline uint8* WireFormatLite::WriteDoubleNoTagToArray(double value,
659 : uint8* target) {
660 : return io::CodedOutputStream::WriteLittleEndian64ToArray(EncodeDouble(value),
661 135 : target);
662 : }
663 : inline uint8* WireFormatLite::WriteBoolNoTagToArray(bool value,
664 : uint8* target) {
665 856 : return io::CodedOutputStream::WriteVarint32ToArray(value ? 1 : 0, target);
666 : }
667 : inline uint8* WireFormatLite::WriteEnumNoTagToArray(int value,
668 : uint8* target) {
669 5389 : return io::CodedOutputStream::WriteVarint32SignExtendedToArray(value, target);
670 : }
671 :
672 : inline uint8* WireFormatLite::WriteInt32ToArray(int field_number,
673 : int32 value,
674 : uint8* target) {
675 1281116 : target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
676 1278146 : return WriteInt32NoTagToArray(value, target);
677 : }
678 : inline uint8* WireFormatLite::WriteInt64ToArray(int field_number,
679 : int64 value,
680 : uint8* target) {
681 343 : target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
682 12 : return WriteInt64NoTagToArray(value, target);
683 : }
684 : inline uint8* WireFormatLite::WriteUInt32ToArray(int field_number,
685 : uint32 value,
686 : uint8* target) {
687 0 : target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
688 : return WriteUInt32NoTagToArray(value, target);
689 : }
690 : inline uint8* WireFormatLite::WriteUInt64ToArray(int field_number,
691 : uint64 value,
692 : uint8* target) {
693 42 : target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
694 : return WriteUInt64NoTagToArray(value, target);
695 : }
696 : inline uint8* WireFormatLite::WriteSInt32ToArray(int field_number,
697 : int32 value,
698 : uint8* target) {
699 0 : target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
700 : return WriteSInt32NoTagToArray(value, target);
701 : }
702 : inline uint8* WireFormatLite::WriteSInt64ToArray(int field_number,
703 : int64 value,
704 : uint8* target) {
705 0 : target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
706 : return WriteSInt64NoTagToArray(value, target);
707 : }
708 : inline uint8* WireFormatLite::WriteFixed32ToArray(int field_number,
709 : uint32 value,
710 : uint8* target) {
711 18 : target = WriteTagToArray(field_number, WIRETYPE_FIXED32, target);
712 : return WriteFixed32NoTagToArray(value, target);
713 : }
714 : inline uint8* WireFormatLite::WriteFixed64ToArray(int field_number,
715 : uint64 value,
716 : uint8* target) {
717 18 : target = WriteTagToArray(field_number, WIRETYPE_FIXED64, target);
718 : return WriteFixed64NoTagToArray(value, target);
719 : }
720 : inline uint8* WireFormatLite::WriteSFixed32ToArray(int field_number,
721 : int32 value,
722 : uint8* target) {
723 0 : target = WriteTagToArray(field_number, WIRETYPE_FIXED32, target);
724 : return WriteSFixed32NoTagToArray(value, target);
725 : }
726 : inline uint8* WireFormatLite::WriteSFixed64ToArray(int field_number,
727 : int64 value,
728 : uint8* target) {
729 0 : target = WriteTagToArray(field_number, WIRETYPE_FIXED64, target);
730 : return WriteSFixed64NoTagToArray(value, target);
731 : }
732 : inline uint8* WireFormatLite::WriteFloatToArray(int field_number,
733 : float value,
734 : uint8* target) {
735 0 : target = WriteTagToArray(field_number, WIRETYPE_FIXED32, target);
736 : return WriteFloatNoTagToArray(value, target);
737 : }
738 : inline uint8* WireFormatLite::WriteDoubleToArray(int field_number,
739 : double value,
740 : uint8* target) {
741 135 : target = WriteTagToArray(field_number, WIRETYPE_FIXED64, target);
742 133 : return WriteDoubleNoTagToArray(value, target);
743 : }
744 : inline uint8* WireFormatLite::WriteBoolToArray(int field_number,
745 : bool value,
746 : uint8* target) {
747 856 : target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
748 48 : return WriteBoolNoTagToArray(value, target);
749 : }
750 : inline uint8* WireFormatLite::WriteEnumToArray(int field_number,
751 : int value,
752 : uint8* target) {
753 5389 : target = WriteTagToArray(field_number, WIRETYPE_VARINT, target);
754 11 : return WriteEnumNoTagToArray(value, target);
755 : }
756 :
757 : inline uint8* WireFormatLite::WriteStringToArray(int field_number,
758 : const string& value,
759 : uint8* target) {
760 : // String is for UTF-8 text only
761 : // WARNING: In wire_format.cc, both strings and bytes are handled by
762 : // WriteString() to avoid code duplication. If the implementations become
763 : // different, you will need to update that usage.
764 246299 : target = WriteTagToArray(field_number, WIRETYPE_LENGTH_DELIMITED, target);
765 246299 : return io::CodedOutputStream::WriteStringWithSizeToArray(value, target);
766 : }
767 : inline uint8* WireFormatLite::WriteBytesToArray(int field_number,
768 : const string& value,
769 : uint8* target) {
770 1277862 : target = WriteTagToArray(field_number, WIRETYPE_LENGTH_DELIMITED, target);
771 1277862 : return io::CodedOutputStream::WriteStringWithSizeToArray(value, target);
772 : }
773 :
774 :
775 : inline uint8* WireFormatLite::WriteGroupToArray(int field_number,
776 : const MessageLite& value,
777 : uint8* target) {
778 0 : target = WriteTagToArray(field_number, WIRETYPE_START_GROUP, target);
779 0 : target = value.SerializeWithCachedSizesToArray(target);
780 : return WriteTagToArray(field_number, WIRETYPE_END_GROUP, target);
781 : }
782 : inline uint8* WireFormatLite::WriteMessageToArray(int field_number,
783 : const MessageLite& value,
784 : uint8* target) {
785 0 : target = WriteTagToArray(field_number, WIRETYPE_LENGTH_DELIMITED, target);
786 : target = io::CodedOutputStream::WriteVarint32ToArray(
787 0 : value.GetCachedSize(), target);
788 0 : return value.SerializeWithCachedSizesToArray(target);
789 : }
790 :
791 : // See comment on ReadGroupNoVirtual to understand the need for this template
792 : // parameter name.
793 : template<typename MessageType_WorkAroundCppLookupDefect>
794 : inline uint8* WireFormatLite::WriteGroupNoVirtualToArray(
795 : int field_number, const MessageType_WorkAroundCppLookupDefect& value,
796 : uint8* target) {
797 : target = WriteTagToArray(field_number, WIRETYPE_START_GROUP, target);
798 : target = value.MessageType_WorkAroundCppLookupDefect
799 : ::SerializeWithCachedSizesToArray(target);
800 : return WriteTagToArray(field_number, WIRETYPE_END_GROUP, target);
801 : }
802 : template<typename MessageType_WorkAroundCppLookupDefect>
803 : inline uint8* WireFormatLite::WriteMessageNoVirtualToArray(
804 : int field_number, const MessageType_WorkAroundCppLookupDefect& value,
805 : uint8* target) {
806 1284370 : target = WriteTagToArray(field_number, WIRETYPE_LENGTH_DELIMITED, target);
807 1284325 : target = io::CodedOutputStream::WriteVarint32ToArray(
808 1284370 : value.MessageType_WorkAroundCppLookupDefect::GetCachedSize(), target);
809 : return value.MessageType_WorkAroundCppLookupDefect
810 1284346 : ::SerializeWithCachedSizesToArray(target);
811 : }
812 :
813 : // ===================================================================
814 :
815 1277725 : inline int WireFormatLite::Int32Size(int32 value) {
816 1277725 : return io::CodedOutputStream::VarintSize32SignExtended(value);
817 : }
818 12 : inline int WireFormatLite::Int64Size(int64 value) {
819 24 : return io::CodedOutputStream::VarintSize64(static_cast<uint64>(value));
820 : }
821 29940 : inline int WireFormatLite::UInt32Size(uint32 value) {
822 29940 : return io::CodedOutputStream::VarintSize32(value);
823 : }
824 : inline int WireFormatLite::UInt64Size(uint64 value) {
825 42 : return io::CodedOutputStream::VarintSize64(value);
826 : }
827 : inline int WireFormatLite::SInt32Size(int32 value) {
828 0 : return io::CodedOutputStream::VarintSize32(ZigZagEncode32(value));
829 : }
830 : inline int WireFormatLite::SInt64Size(int64 value) {
831 0 : return io::CodedOutputStream::VarintSize64(ZigZagEncode64(value));
832 : }
833 11 : inline int WireFormatLite::EnumSize(int value) {
834 11 : return io::CodedOutputStream::VarintSize32SignExtended(value);
835 : }
836 :
837 246145 : inline int WireFormatLite::StringSize(const string& value) {
838 246145 : return io::CodedOutputStream::VarintSize32(value.size()) +
839 252878 : value.size();
840 : }
841 1277360 : inline int WireFormatLite::BytesSize(const string& value) {
842 1277360 : return io::CodedOutputStream::VarintSize32(value.size()) +
843 1277702 : value.size();
844 : }
845 :
846 :
847 : inline int WireFormatLite::GroupSize(const MessageLite& value) {
848 0 : return value.ByteSize();
849 : }
850 4 : inline int WireFormatLite::MessageSize(const MessageLite& value) {
851 8 : return LengthDelimitedSize(value.ByteSize());
852 : }
853 :
854 : // See comment on ReadGroupNoVirtual to understand the need for this template
855 : // parameter name.
856 : template<typename MessageType_WorkAroundCppLookupDefect>
857 : inline int WireFormatLite::GroupSizeNoVirtual(
858 : const MessageType_WorkAroundCppLookupDefect& value) {
859 : return value.MessageType_WorkAroundCppLookupDefect::ByteSize();
860 : }
861 : template<typename MessageType_WorkAroundCppLookupDefect>
862 1284072 : inline int WireFormatLite::MessageSizeNoVirtual(
863 : const MessageType_WorkAroundCppLookupDefect& value) {
864 : return LengthDelimitedSize(
865 1290258 : value.MessageType_WorkAroundCppLookupDefect::ByteSize());
866 : }
867 :
868 1277710 : inline int WireFormatLite::LengthDelimitedSize(int length) {
869 1290090 : return io::CodedOutputStream::VarintSize32(length) + length;
870 : }
871 :
872 : } // namespace internal
873 : } // namespace protobuf
874 :
875 : } // namespace google
876 : #endif // GOOGLE_PROTOBUF_WIRE_FORMAT_LITE_INL_H__
|