OLD | NEW |
1 // Protocol Buffers - Google's data interchange format | 1 // Protocol Buffers - Google's data interchange format |
2 // Copyright 2008 Google Inc. All rights reserved. | 2 // Copyright 2008 Google Inc. All rights reserved. |
3 // http://code.google.com/p/protobuf/ | 3 // https://developers.google.com/protocol-buffers/ |
4 // | 4 // |
5 // Redistribution and use in source and binary forms, with or without | 5 // Redistribution and use in source and binary forms, with or without |
6 // modification, are permitted provided that the following conditions are | 6 // modification, are permitted provided that the following conditions are |
7 // met: | 7 // met: |
8 // | 8 // |
9 // * Redistributions of source code must retain the above copyright | 9 // * Redistributions of source code must retain the above copyright |
10 // notice, this list of conditions and the following disclaimer. | 10 // notice, this list of conditions and the following disclaimer. |
11 // * Redistributions in binary form must reproduce the above | 11 // * Redistributions in binary form must reproduce the above |
12 // copyright notice, this list of conditions and the following disclaimer | 12 // copyright notice, this list of conditions and the following disclaimer |
13 // in the documentation and/or other materials provided with the | 13 // in the documentation and/or other materials provided with the |
(...skipping 24 matching lines...) Expand all Loading... |
38 #ifndef GOOGLE_PROTOBUF_EXTENSION_SET_H__ | 38 #ifndef GOOGLE_PROTOBUF_EXTENSION_SET_H__ |
39 #define GOOGLE_PROTOBUF_EXTENSION_SET_H__ | 39 #define GOOGLE_PROTOBUF_EXTENSION_SET_H__ |
40 | 40 |
41 #include <vector> | 41 #include <vector> |
42 #include <map> | 42 #include <map> |
43 #include <utility> | 43 #include <utility> |
44 #include <string> | 44 #include <string> |
45 | 45 |
46 | 46 |
47 #include <google/protobuf/stubs/common.h> | 47 #include <google/protobuf/stubs/common.h> |
| 48 #include <google/protobuf/stubs/logging.h> |
| 49 #include <google/protobuf/stubs/once.h> |
| 50 |
| 51 #include <google/protobuf/repeated_field.h> |
48 | 52 |
49 namespace google { | 53 namespace google { |
50 | 54 |
51 namespace protobuf { | 55 namespace protobuf { |
| 56 class Arena; |
52 class Descriptor; // descriptor.h | 57 class Descriptor; // descriptor.h |
53 class FieldDescriptor; // descriptor.h | 58 class FieldDescriptor; // descriptor.h |
54 class DescriptorPool; // descriptor.h | 59 class DescriptorPool; // descriptor.h |
55 class MessageLite; // message_lite.h | 60 class MessageLite; // message_lite.h |
56 class Message; // message.h | 61 class Message; // message.h |
57 class MessageFactory; // message.h | 62 class MessageFactory; // message.h |
58 class UnknownFieldSet; // unknown_field_set.h | 63 class UnknownFieldSet; // unknown_field_set.h |
59 namespace io { | 64 namespace io { |
60 class CodedInputStream; // coded_stream.h | 65 class CodedInputStream; // coded_stream.h |
61 class CodedOutputStream; // coded_stream.h | 66 class CodedOutputStream; // coded_stream.h |
62 } | 67 } |
63 namespace internal { | 68 namespace internal { |
64 class FieldSkipper; // wire_format_lite.h | 69 class FieldSkipper; // wire_format_lite.h |
65 class RepeatedPtrFieldBase; // repeated_field.h | |
66 } | 70 } |
67 template <typename Element> class RepeatedField; // repeated_field.h | |
68 template <typename Element> class RepeatedPtrField; // repeated_field.h | |
69 } | 71 } |
70 | 72 |
71 namespace protobuf { | 73 namespace protobuf { |
72 namespace internal { | 74 namespace internal { |
73 | 75 |
74 // Used to store values of type WireFormatLite::FieldType without having to | 76 // Used to store values of type WireFormatLite::FieldType without having to |
75 // #include wire_format_lite.h. Also, ensures that we use only one byte to | 77 // #include wire_format_lite.h. Also, ensures that we use only one byte to |
76 // store these values, which is important to keep the layout of | 78 // store these values, which is important to keep the layout of |
77 // ExtensionSet::Extension small. | 79 // ExtensionSet::Extension small. |
78 typedef uint8 FieldType; | 80 typedef uint8 FieldType; |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
131 : containing_type_(containing_type) {} | 133 : containing_type_(containing_type) {} |
132 virtual ~GeneratedExtensionFinder() {} | 134 virtual ~GeneratedExtensionFinder() {} |
133 | 135 |
134 // Returns true and fills in *output if found, otherwise returns false. | 136 // Returns true and fills in *output if found, otherwise returns false. |
135 virtual bool Find(int number, ExtensionInfo* output); | 137 virtual bool Find(int number, ExtensionInfo* output); |
136 | 138 |
137 private: | 139 private: |
138 const MessageLite* containing_type_; | 140 const MessageLite* containing_type_; |
139 }; | 141 }; |
140 | 142 |
| 143 // A FieldSkipper used for parsing MessageSet. |
| 144 class MessageSetFieldSkipper; |
| 145 |
141 // Note: extension_set_heavy.cc defines DescriptorPoolExtensionFinder for | 146 // Note: extension_set_heavy.cc defines DescriptorPoolExtensionFinder for |
142 // finding extensions from a DescriptorPool. | 147 // finding extensions from a DescriptorPool. |
143 | 148 |
144 // This is an internal helper class intended for use within the protocol buffer | 149 // This is an internal helper class intended for use within the protocol buffer |
145 // library and generated classes. Clients should not use it directly. Instead, | 150 // library and generated classes. Clients should not use it directly. Instead, |
146 // use the generated accessors such as GetExtension() of the class being | 151 // use the generated accessors such as GetExtension() of the class being |
147 // extended. | 152 // extended. |
148 // | 153 // |
149 // This class manages extensions for a protocol message object. The | 154 // This class manages extensions for a protocol message object. The |
150 // message's HasExtension(), GetExtension(), MutableExtension(), and | 155 // message's HasExtension(), GetExtension(), MutableExtension(), and |
151 // ClearExtension() methods are just thin wrappers around the embedded | 156 // ClearExtension() methods are just thin wrappers around the embedded |
152 // ExtensionSet. When parsing, if a tag number is encountered which is | 157 // ExtensionSet. When parsing, if a tag number is encountered which is |
153 // inside one of the message type's extension ranges, the tag is passed | 158 // inside one of the message type's extension ranges, the tag is passed |
154 // off to the ExtensionSet for parsing. Etc. | 159 // off to the ExtensionSet for parsing. Etc. |
155 class LIBPROTOBUF_EXPORT ExtensionSet { | 160 class LIBPROTOBUF_EXPORT ExtensionSet { |
156 public: | 161 public: |
157 ExtensionSet(); | 162 ExtensionSet(); |
| 163 explicit ExtensionSet(::google::protobuf::Arena* arena); |
158 ~ExtensionSet(); | 164 ~ExtensionSet(); |
159 | 165 |
160 // These are called at startup by protocol-compiler-generated code to | 166 // These are called at startup by protocol-compiler-generated code to |
161 // register known extensions. The registrations are used by ParseField() | 167 // register known extensions. The registrations are used by ParseField() |
162 // to look up extensions for parsed field numbers. Note that dynamic parsing | 168 // to look up extensions for parsed field numbers. Note that dynamic parsing |
163 // does not use ParseField(); only protocol-compiler-generated parsing | 169 // does not use ParseField(); only protocol-compiler-generated parsing |
164 // methods do. | 170 // methods do. |
165 static void RegisterExtension(const MessageLite* containing_type, | 171 static void RegisterExtension(const MessageLite* containing_type, |
166 int number, FieldType type, | 172 int number, FieldType type, |
167 bool is_repeated, bool is_packed); | 173 bool is_repeated, bool is_packed); |
(...skipping 15 matching lines...) Expand all Loading... |
183 std::vector<const FieldDescriptor*>* output) const; | 189 std::vector<const FieldDescriptor*>* output) const; |
184 | 190 |
185 // ================================================================= | 191 // ================================================================= |
186 // Accessors | 192 // Accessors |
187 // | 193 // |
188 // Generated message classes include type-safe templated wrappers around | 194 // Generated message classes include type-safe templated wrappers around |
189 // these methods. Generally you should use those rather than call these | 195 // these methods. Generally you should use those rather than call these |
190 // directly, unless you are doing low-level memory management. | 196 // directly, unless you are doing low-level memory management. |
191 // | 197 // |
192 // When calling any of these accessors, the extension number requested | 198 // When calling any of these accessors, the extension number requested |
193 // MUST exist in the DescriptorPool provided to the constructor. Otheriwse, | 199 // MUST exist in the DescriptorPool provided to the constructor. Otherwise, |
194 // the method will fail an assert. Normally, though, you would not call | 200 // the method will fail an assert. Normally, though, you would not call |
195 // these directly; you would either call the generated accessors of your | 201 // these directly; you would either call the generated accessors of your |
196 // message class (e.g. GetExtension()) or you would call the accessors | 202 // message class (e.g. GetExtension()) or you would call the accessors |
197 // of the reflection interface. In both cases, it is impossible to | 203 // of the reflection interface. In both cases, it is impossible to |
198 // trigger this assert failure: the generated accessors only accept | 204 // trigger this assert failure: the generated accessors only accept |
199 // linked-in extension types as parameters, while the Reflection interface | 205 // linked-in extension types as parameters, while the Reflection interface |
200 // requires you to provide the FieldDescriptor describing the extension. | 206 // requires you to provide the FieldDescriptor describing the extension. |
201 // | 207 // |
202 // When calling any of these accessors, a protocol-compiler-generated | 208 // When calling any of these accessors, a protocol-compiler-generated |
203 // implementation of the extension corresponding to the number MUST | 209 // implementation of the extension corresponding to the number MUST |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
251 MessageLite* MutableMessage(int number, FieldType type, | 257 MessageLite* MutableMessage(int number, FieldType type, |
252 const MessageLite& prototype, desc); | 258 const MessageLite& prototype, desc); |
253 MessageLite* MutableMessage(const FieldDescriptor* decsriptor, | 259 MessageLite* MutableMessage(const FieldDescriptor* decsriptor, |
254 MessageFactory* factory); | 260 MessageFactory* factory); |
255 // Adds the given message to the ExtensionSet, taking ownership of the | 261 // Adds the given message to the ExtensionSet, taking ownership of the |
256 // message object. Existing message with the same number will be deleted. | 262 // message object. Existing message with the same number will be deleted. |
257 // If "message" is NULL, this is equivalent to "ClearExtension(number)". | 263 // If "message" is NULL, this is equivalent to "ClearExtension(number)". |
258 void SetAllocatedMessage(int number, FieldType type, | 264 void SetAllocatedMessage(int number, FieldType type, |
259 const FieldDescriptor* descriptor, | 265 const FieldDescriptor* descriptor, |
260 MessageLite* message); | 266 MessageLite* message); |
| 267 void UnsafeArenaSetAllocatedMessage(int number, FieldType type, |
| 268 const FieldDescriptor* descriptor, |
| 269 MessageLite* message); |
261 MessageLite* ReleaseMessage(int number, const MessageLite& prototype); | 270 MessageLite* ReleaseMessage(int number, const MessageLite& prototype); |
| 271 MessageLite* UnsafeArenaReleaseMessage( |
| 272 int number, const MessageLite& prototype); |
| 273 |
262 MessageLite* ReleaseMessage(const FieldDescriptor* descriptor, | 274 MessageLite* ReleaseMessage(const FieldDescriptor* descriptor, |
263 MessageFactory* factory); | 275 MessageFactory* factory); |
264 #undef desc | 276 #undef desc |
| 277 ::google::protobuf::Arena* GetArenaNoVirtual() const { return arena_; } |
265 | 278 |
266 // repeated fields ------------------------------------------------- | 279 // repeated fields ------------------------------------------------- |
267 | 280 |
| 281 // Fetches a RepeatedField extension by number; returns |default_value| |
| 282 // if no such extension exists. User should not touch this directly; it is |
| 283 // used by the GetRepeatedExtension() method. |
| 284 const void* GetRawRepeatedField(int number, const void* default_value) const; |
| 285 // Fetches a mutable version of a RepeatedField extension by number, |
| 286 // instantiating one if none exists. Similar to above, user should not use |
| 287 // this directly; it underlies MutableRepeatedExtension(). |
| 288 void* MutableRawRepeatedField(int number, FieldType field_type, |
| 289 bool packed, const FieldDescriptor* desc); |
| 290 |
| 291 // This is an overload of MutableRawRepeatedField to maintain compatibility |
| 292 // with old code using a previous API. This version of |
| 293 // MutableRawRepeatedField() will GOOGLE_CHECK-fail on a missing extension. |
| 294 // (E.g.: borg/clients/internal/proto1/proto2_reflection.cc.) |
268 void* MutableRawRepeatedField(int number); | 295 void* MutableRawRepeatedField(int number); |
269 | 296 |
270 int32 GetRepeatedInt32 (int number, int index) const; | 297 int32 GetRepeatedInt32 (int number, int index) const; |
271 int64 GetRepeatedInt64 (int number, int index) const; | 298 int64 GetRepeatedInt64 (int number, int index) const; |
272 uint32 GetRepeatedUInt32(int number, int index) const; | 299 uint32 GetRepeatedUInt32(int number, int index) const; |
273 uint64 GetRepeatedUInt64(int number, int index) const; | 300 uint64 GetRepeatedUInt64(int number, int index) const; |
274 float GetRepeatedFloat (int number, int index) const; | 301 float GetRepeatedFloat (int number, int index) const; |
275 double GetRepeatedDouble(int number, int index) const; | 302 double GetRepeatedDouble(int number, int index) const; |
276 bool GetRepeatedBool (int number, int index) const; | 303 bool GetRepeatedBool (int number, int index) const; |
277 int GetRepeatedEnum (int number, int index) const; | 304 int GetRepeatedEnum (int number, int index) const; |
(...skipping 20 matching lines...) Expand all Loading... |
298 void AddFloat (int number, FieldType type, bool packed, float value, desc); | 325 void AddFloat (int number, FieldType type, bool packed, float value, desc); |
299 void AddDouble(int number, FieldType type, bool packed, double value, desc); | 326 void AddDouble(int number, FieldType type, bool packed, double value, desc); |
300 void AddBool (int number, FieldType type, bool packed, bool value, desc); | 327 void AddBool (int number, FieldType type, bool packed, bool value, desc); |
301 void AddEnum (int number, FieldType type, bool packed, int value, desc); | 328 void AddEnum (int number, FieldType type, bool packed, int value, desc); |
302 void AddString(int number, FieldType type, const string& value, desc); | 329 void AddString(int number, FieldType type, const string& value, desc); |
303 string * AddString (int number, FieldType type, desc); | 330 string * AddString (int number, FieldType type, desc); |
304 MessageLite* AddMessage(int number, FieldType type, | 331 MessageLite* AddMessage(int number, FieldType type, |
305 const MessageLite& prototype, desc); | 332 const MessageLite& prototype, desc); |
306 MessageLite* AddMessage(const FieldDescriptor* descriptor, | 333 MessageLite* AddMessage(const FieldDescriptor* descriptor, |
307 MessageFactory* factory); | 334 MessageFactory* factory); |
| 335 void AddAllocatedMessage(const FieldDescriptor* descriptor, |
| 336 MessageLite* new_entry); |
308 #undef desc | 337 #undef desc |
309 | 338 |
310 void RemoveLast(int number); | 339 void RemoveLast(int number); |
311 MessageLite* ReleaseLast(int number); | 340 MessageLite* ReleaseLast(int number); |
312 void SwapElements(int number, int index1, int index2); | 341 void SwapElements(int number, int index1, int index2); |
313 | 342 |
314 // ----------------------------------------------------------------- | 343 // ----------------------------------------------------------------- |
315 // TODO(kenton): Hardcore memory management accessors | 344 // TODO(kenton): Hardcore memory management accessors |
316 | 345 |
317 // ================================================================= | 346 // ================================================================= |
318 // convenience methods for implementing methods of Message | 347 // convenience methods for implementing methods of Message |
319 // | 348 // |
320 // These could all be implemented in terms of the other methods of this | 349 // These could all be implemented in terms of the other methods of this |
321 // class, but providing them here helps keep the generated code size down. | 350 // class, but providing them here helps keep the generated code size down. |
322 | 351 |
323 void Clear(); | 352 void Clear(); |
324 void MergeFrom(const ExtensionSet& other); | 353 void MergeFrom(const ExtensionSet& other); |
325 void Swap(ExtensionSet* other); | 354 void Swap(ExtensionSet* other); |
| 355 void SwapExtension(ExtensionSet* other, int number); |
326 bool IsInitialized() const; | 356 bool IsInitialized() const; |
327 | 357 |
328 // Parses a single extension from the input. The input should start out | 358 // Parses a single extension from the input. The input should start out |
329 // positioned immediately after the tag. | 359 // positioned immediately after the tag. |
330 bool ParseField(uint32 tag, io::CodedInputStream* input, | 360 bool ParseField(uint32 tag, io::CodedInputStream* input, |
331 ExtensionFinder* extension_finder, | 361 ExtensionFinder* extension_finder, |
332 FieldSkipper* field_skipper); | 362 FieldSkipper* field_skipper); |
333 | 363 |
334 // Specific versions for lite or full messages (constructs the appropriate | 364 // Specific versions for lite or full messages (constructs the appropriate |
335 // FieldSkipper automatically). |containing_type| is the default | 365 // FieldSkipper automatically). |containing_type| is the default |
336 // instance for the containing message; it is used only to look up the | 366 // instance for the containing message; it is used only to look up the |
337 // extension by number. See RegisterExtension(), above. Unlike the other | 367 // extension by number. See RegisterExtension(), above. Unlike the other |
338 // methods of ExtensionSet, this only works for generated message types -- | 368 // methods of ExtensionSet, this only works for generated message types -- |
339 // it looks up extensions registered using RegisterExtension(). | 369 // it looks up extensions registered using RegisterExtension(). |
340 bool ParseField(uint32 tag, io::CodedInputStream* input, | 370 bool ParseField(uint32 tag, io::CodedInputStream* input, |
| 371 const MessageLite* containing_type); |
| 372 bool ParseField(uint32 tag, io::CodedInputStream* input, |
| 373 const Message* containing_type, |
| 374 UnknownFieldSet* unknown_fields); |
| 375 bool ParseField(uint32 tag, io::CodedInputStream* input, |
341 const MessageLite* containing_type, | 376 const MessageLite* containing_type, |
342 UnknownFieldSet* unknown_fields); | 377 io::CodedOutputStream* unknown_fields); |
343 bool ParseFieldHeavy(uint32 tag, io::CodedInputStream* input, | |
344 const Message* containing_type, | |
345 UnknownFieldSet* unknown_fields); | |
346 | 378 |
347 // Parse an entire message in MessageSet format. Such messages have no | 379 // Parse an entire message in MessageSet format. Such messages have no |
348 // fields, only extensions. | 380 // fields, only extensions. |
349 bool ParseMessageSet(io::CodedInputStream* input, | 381 bool ParseMessageSet(io::CodedInputStream* input, |
350 ExtensionFinder* extension_finder, | 382 ExtensionFinder* extension_finder, |
351 FieldSkipper* field_skipper); | 383 MessageSetFieldSkipper* field_skipper); |
352 | 384 |
353 // Specific versions for lite or full messages (constructs the appropriate | 385 // Specific versions for lite or full messages (constructs the appropriate |
354 // FieldSkipper automatically). | 386 // FieldSkipper automatically). |
355 bool ParseMessageSet(io::CodedInputStream* input, | 387 bool ParseMessageSet(io::CodedInputStream* input, |
356 const MessageLite* containing_type, | 388 const MessageLite* containing_type); |
| 389 bool ParseMessageSet(io::CodedInputStream* input, |
| 390 const Message* containing_type, |
357 UnknownFieldSet* unknown_fields); | 391 UnknownFieldSet* unknown_fields); |
358 bool ParseMessageSetHeavy(io::CodedInputStream* input, | |
359 const Message* containing_type, | |
360 UnknownFieldSet* unknown_fields); | |
361 | 392 |
362 // Write all extension fields with field numbers in the range | 393 // Write all extension fields with field numbers in the range |
363 // [start_field_number, end_field_number) | 394 // [start_field_number, end_field_number) |
364 // to the output stream, using the cached sizes computed when ByteSize() was | 395 // to the output stream, using the cached sizes computed when ByteSize() was |
365 // last called. Note that the range bounds are inclusive-exclusive. | 396 // last called. Note that the range bounds are inclusive-exclusive. |
366 void SerializeWithCachedSizes(int start_field_number, | 397 void SerializeWithCachedSizes(int start_field_number, |
367 int end_field_number, | 398 int end_field_number, |
368 io::CodedOutputStream* output) const; | 399 io::CodedOutputStream* output) const; |
369 | 400 |
370 // Same as SerializeWithCachedSizes, but without any bounds checking. | 401 // Same as SerializeWithCachedSizes, but without any bounds checking. |
(...skipping 25 matching lines...) Expand all Loading... |
396 int SpaceUsedExcludingSelf() const; | 427 int SpaceUsedExcludingSelf() const; |
397 | 428 |
398 private: | 429 private: |
399 | 430 |
400 // Interface of a lazily parsed singular message extension. | 431 // Interface of a lazily parsed singular message extension. |
401 class LIBPROTOBUF_EXPORT LazyMessageExtension { | 432 class LIBPROTOBUF_EXPORT LazyMessageExtension { |
402 public: | 433 public: |
403 LazyMessageExtension() {} | 434 LazyMessageExtension() {} |
404 virtual ~LazyMessageExtension() {} | 435 virtual ~LazyMessageExtension() {} |
405 | 436 |
406 virtual LazyMessageExtension* New() const = 0; | 437 virtual LazyMessageExtension* New(::google::protobuf::Arena* arena) const =
0; |
407 virtual const MessageLite& GetMessage( | 438 virtual const MessageLite& GetMessage( |
408 const MessageLite& prototype) const = 0; | 439 const MessageLite& prototype) const = 0; |
409 virtual MessageLite* MutableMessage(const MessageLite& prototype) = 0; | 440 virtual MessageLite* MutableMessage(const MessageLite& prototype) = 0; |
410 virtual void SetAllocatedMessage(MessageLite *message) = 0; | 441 virtual void SetAllocatedMessage(MessageLite *message) = 0; |
| 442 virtual void UnsafeArenaSetAllocatedMessage(MessageLite *message) = 0; |
411 virtual MessageLite* ReleaseMessage(const MessageLite& prototype) = 0; | 443 virtual MessageLite* ReleaseMessage(const MessageLite& prototype) = 0; |
| 444 virtual MessageLite* UnsafeArenaReleaseMessage( |
| 445 const MessageLite& prototype) = 0; |
412 | 446 |
413 virtual bool IsInitialized() const = 0; | 447 virtual bool IsInitialized() const = 0; |
414 virtual int ByteSize() const = 0; | 448 virtual int ByteSize() const = 0; |
415 virtual int SpaceUsed() const = 0; | 449 virtual int SpaceUsed() const = 0; |
416 | 450 |
417 virtual void MergeFrom(const LazyMessageExtension& other) = 0; | 451 virtual void MergeFrom(const LazyMessageExtension& other) = 0; |
418 virtual void Clear() = 0; | 452 virtual void Clear() = 0; |
419 | 453 |
420 virtual bool ReadMessage(const MessageLite& prototype, | 454 virtual bool ReadMessage(const MessageLite& prototype, |
421 io::CodedInputStream* input) = 0; | 455 io::CodedInputStream* input) = 0; |
(...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
499 uint8* target) const; | 533 uint8* target) const; |
500 int ByteSize(int number) const; | 534 int ByteSize(int number) const; |
501 int MessageSetItemByteSize(int number) const; | 535 int MessageSetItemByteSize(int number) const; |
502 void Clear(); | 536 void Clear(); |
503 int GetSize() const; | 537 int GetSize() const; |
504 void Free(); | 538 void Free(); |
505 int SpaceUsedExcludingSelf() const; | 539 int SpaceUsedExcludingSelf() const; |
506 }; | 540 }; |
507 | 541 |
508 | 542 |
| 543 // Merges existing Extension from other_extension |
| 544 void InternalExtensionMergeFrom(int number, const Extension& other_extension); |
| 545 |
509 // Returns true and fills field_number and extension if extension is found. | 546 // Returns true and fills field_number and extension if extension is found. |
| 547 // Note to support packed repeated field compatibility, it also fills whether |
| 548 // the tag on wire is packed, which can be different from |
| 549 // extension->is_packed (whether packed=true is specified). |
510 bool FindExtensionInfoFromTag(uint32 tag, ExtensionFinder* extension_finder, | 550 bool FindExtensionInfoFromTag(uint32 tag, ExtensionFinder* extension_finder, |
511 int* field_number, ExtensionInfo* extension); | 551 int* field_number, ExtensionInfo* extension, |
| 552 bool* was_packed_on_wire); |
| 553 |
| 554 // Returns true and fills extension if extension is found. |
| 555 // Note to support packed repeated field compatibility, it also fills whether |
| 556 // the tag on wire is packed, which can be different from |
| 557 // extension->is_packed (whether packed=true is specified). |
| 558 bool FindExtensionInfoFromFieldNumber(int wire_type, int field_number, |
| 559 ExtensionFinder* extension_finder, |
| 560 ExtensionInfo* extension, |
| 561 bool* was_packed_on_wire); |
512 | 562 |
513 // Parses a single extension from the input. The input should start out | 563 // Parses a single extension from the input. The input should start out |
514 // positioned immediately after the wire tag. This method is called in | 564 // positioned immediately after the wire tag. This method is called in |
515 // ParseField() after field number is extracted from the wire tag and | 565 // ParseField() after field number and was_packed_on_wire is extracted from |
516 // ExtensionInfo is found by the field number. | 566 // the wire tag and ExtensionInfo is found by the field number. |
517 bool ParseFieldWithExtensionInfo(int field_number, | 567 bool ParseFieldWithExtensionInfo(int field_number, |
| 568 bool was_packed_on_wire, |
518 const ExtensionInfo& extension, | 569 const ExtensionInfo& extension, |
519 io::CodedInputStream* input, | 570 io::CodedInputStream* input, |
520 FieldSkipper* field_skipper); | 571 FieldSkipper* field_skipper); |
521 | 572 |
522 // Like ParseField(), but this method may parse singular message extensions | 573 // Like ParseField(), but this method may parse singular message extensions |
523 // lazily depending on the value of FLAGS_eagerly_parse_message_sets. | 574 // lazily depending on the value of FLAGS_eagerly_parse_message_sets. |
524 bool ParseFieldMaybeLazily(uint32 tag, io::CodedInputStream* input, | 575 bool ParseFieldMaybeLazily(int wire_type, int field_number, |
| 576 io::CodedInputStream* input, |
525 ExtensionFinder* extension_finder, | 577 ExtensionFinder* extension_finder, |
526 FieldSkipper* field_skipper); | 578 MessageSetFieldSkipper* field_skipper); |
527 | 579 |
528 // Gets the extension with the given number, creating it if it does not | 580 // Gets the extension with the given number, creating it if it does not |
529 // already exist. Returns true if the extension did not already exist. | 581 // already exist. Returns true if the extension did not already exist. |
530 bool MaybeNewExtension(int number, const FieldDescriptor* descriptor, | 582 bool MaybeNewExtension(int number, const FieldDescriptor* descriptor, |
531 Extension** result); | 583 Extension** result); |
532 | 584 |
| 585 // Gets the repeated extension for the given descriptor, creating it if |
| 586 // it does not exist. |
| 587 Extension* MaybeNewRepeatedExtension(const FieldDescriptor* descriptor); |
| 588 |
533 // Parse a single MessageSet item -- called just after the item group start | 589 // Parse a single MessageSet item -- called just after the item group start |
534 // tag has been read. | 590 // tag has been read. |
535 bool ParseMessageSetItem(io::CodedInputStream* input, | 591 bool ParseMessageSetItem(io::CodedInputStream* input, |
536 ExtensionFinder* extension_finder, | 592 ExtensionFinder* extension_finder, |
537 FieldSkipper* field_skipper); | 593 MessageSetFieldSkipper* field_skipper); |
538 | |
539 | 594 |
540 // Hack: RepeatedPtrFieldBase declares ExtensionSet as a friend. This | 595 // Hack: RepeatedPtrFieldBase declares ExtensionSet as a friend. This |
541 // friendship should automatically extend to ExtensionSet::Extension, but | 596 // friendship should automatically extend to ExtensionSet::Extension, but |
542 // unfortunately some older compilers (e.g. GCC 3.4.4) do not implement this | 597 // unfortunately some older compilers (e.g. GCC 3.4.4) do not implement this |
543 // correctly. So, we must provide helpers for calling methods of that | 598 // correctly. So, we must provide helpers for calling methods of that |
544 // class. | 599 // class. |
545 | 600 |
546 // Defined in extension_set_heavy.cc. | 601 // Defined in extension_set_heavy.cc. |
547 static inline int RepeatedMessage_SpaceUsedExcludingSelf( | 602 static inline int RepeatedMessage_SpaceUsedExcludingSelf( |
548 RepeatedPtrFieldBase* field); | 603 RepeatedPtrFieldBase* field); |
549 | 604 |
550 // The Extension struct is small enough to be passed by value, so we use it | 605 // The Extension struct is small enough to be passed by value, so we use it |
551 // directly as the value type in the map rather than use pointers. We use | 606 // directly as the value type in the map rather than use pointers. We use |
552 // a map rather than hash_map here because we expect most ExtensionSets will | 607 // a map rather than hash_map here because we expect most ExtensionSets will |
553 // only contain a small number of extensions whereas hash_map is optimized | 608 // only contain a small number of extensions whereas hash_map is optimized |
554 // for 100 elements or more. Also, we want AppendToList() to order fields | 609 // for 100 elements or more. Also, we want AppendToList() to order fields |
555 // by field number. | 610 // by field number. |
556 std::map<int, Extension> extensions_; | 611 std::map<int, Extension> extensions_; |
557 | 612 ::google::protobuf::Arena* arena_; |
558 GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ExtensionSet); | 613 GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ExtensionSet); |
559 }; | 614 }; |
560 | 615 |
561 // These are just for convenience... | 616 // These are just for convenience... |
562 inline void ExtensionSet::SetString(int number, FieldType type, | 617 inline void ExtensionSet::SetString(int number, FieldType type, |
563 const string& value, | 618 const string& value, |
564 const FieldDescriptor* descriptor) { | 619 const FieldDescriptor* descriptor) { |
565 MutableString(number, type, descriptor)->assign(value); | 620 MutableString(number, type, descriptor)->assign(value); |
566 } | 621 } |
567 inline void ExtensionSet::SetRepeatedString(int number, int index, | 622 inline void ExtensionSet::SetRepeatedString(int number, int index, |
(...skipping 14 matching lines...) Expand all Loading... |
582 | 637 |
583 // First we have a set of classes representing "type traits" for different | 638 // First we have a set of classes representing "type traits" for different |
584 // field types. A type traits class knows how to implement basic accessors | 639 // field types. A type traits class knows how to implement basic accessors |
585 // for extensions of a particular type given an ExtensionSet. The signature | 640 // for extensions of a particular type given an ExtensionSet. The signature |
586 // for a type traits class looks like this: | 641 // for a type traits class looks like this: |
587 // | 642 // |
588 // class TypeTraits { | 643 // class TypeTraits { |
589 // public: | 644 // public: |
590 // typedef ? ConstType; | 645 // typedef ? ConstType; |
591 // typedef ? MutableType; | 646 // typedef ? MutableType; |
| 647 // // TypeTraits for singular fields and repeated fields will define the |
| 648 // // symbol "Singular" or "Repeated" respectively. These two symbols will |
| 649 // // be used in extension accessors to distinguish between singular |
| 650 // // extensions and repeated extensions. If the TypeTraits for the passed |
| 651 // // in extension doesn't have the expected symbol defined, it means the |
| 652 // // user is passing a repeated extension to a singular accessor, or the |
| 653 // // opposite. In that case the C++ compiler will generate an error |
| 654 // // message "no matching member function" to inform the user. |
| 655 // typedef ? Singular |
| 656 // typedef ? Repeated |
592 // | 657 // |
593 // static inline ConstType Get(int number, const ExtensionSet& set); | 658 // static inline ConstType Get(int number, const ExtensionSet& set); |
594 // static inline void Set(int number, ConstType value, ExtensionSet* set); | 659 // static inline void Set(int number, ConstType value, ExtensionSet* set); |
595 // static inline MutableType Mutable(int number, ExtensionSet* set); | 660 // static inline MutableType Mutable(int number, ExtensionSet* set); |
596 // | 661 // |
597 // // Variants for repeated fields. | 662 // // Variants for repeated fields. |
598 // static inline ConstType Get(int number, const ExtensionSet& set, | 663 // static inline ConstType Get(int number, const ExtensionSet& set, |
599 // int index); | 664 // int index); |
600 // static inline void Set(int number, int index, | 665 // static inline void Set(int number, int index, |
601 // ConstType value, ExtensionSet* set); | 666 // ConstType value, ExtensionSet* set); |
(...skipping 18 matching lines...) Expand all Loading... |
620 // ------------------------------------------------------------------- | 685 // ------------------------------------------------------------------- |
621 // PrimitiveTypeTraits | 686 // PrimitiveTypeTraits |
622 | 687 |
623 // Since the ExtensionSet has different methods for each primitive type, | 688 // Since the ExtensionSet has different methods for each primitive type, |
624 // we must explicitly define the methods of the type traits class for each | 689 // we must explicitly define the methods of the type traits class for each |
625 // known type. | 690 // known type. |
626 template <typename Type> | 691 template <typename Type> |
627 class PrimitiveTypeTraits { | 692 class PrimitiveTypeTraits { |
628 public: | 693 public: |
629 typedef Type ConstType; | 694 typedef Type ConstType; |
| 695 typedef Type MutableType; |
| 696 typedef PrimitiveTypeTraits<Type> Singular; |
630 | 697 |
631 static inline ConstType Get(int number, const ExtensionSet& set, | 698 static inline ConstType Get(int number, const ExtensionSet& set, |
632 ConstType default_value); | 699 ConstType default_value); |
633 static inline void Set(int number, FieldType field_type, | 700 static inline void Set(int number, FieldType field_type, |
634 ConstType value, ExtensionSet* set); | 701 ConstType value, ExtensionSet* set); |
635 }; | 702 }; |
636 | 703 |
637 template <typename Type> | 704 template <typename Type> |
638 class RepeatedPrimitiveTypeTraits { | 705 class RepeatedPrimitiveTypeTraits { |
639 public: | 706 public: |
640 typedef Type ConstType; | 707 typedef Type ConstType; |
| 708 typedef Type MutableType; |
| 709 typedef RepeatedPrimitiveTypeTraits<Type> Repeated; |
| 710 |
| 711 typedef RepeatedField<Type> RepeatedFieldType; |
641 | 712 |
642 static inline Type Get(int number, const ExtensionSet& set, int index); | 713 static inline Type Get(int number, const ExtensionSet& set, int index); |
643 static inline void Set(int number, int index, Type value, ExtensionSet* set); | 714 static inline void Set(int number, int index, Type value, ExtensionSet* set); |
644 static inline void Add(int number, FieldType field_type, | 715 static inline void Add(int number, FieldType field_type, |
645 bool is_packed, Type value, ExtensionSet* set); | 716 bool is_packed, Type value, ExtensionSet* set); |
| 717 |
| 718 static inline const RepeatedField<ConstType>& |
| 719 GetRepeated(int number, const ExtensionSet& set); |
| 720 static inline RepeatedField<Type>* |
| 721 MutableRepeated(int number, FieldType field_type, |
| 722 bool is_packed, ExtensionSet* set); |
| 723 |
| 724 static const RepeatedFieldType* GetDefaultRepeatedField(); |
| 725 }; |
| 726 |
| 727 LIBPROTOBUF_EXPORT extern ProtobufOnceType repeated_primitive_generic_type_trait
s_once_init_; |
| 728 |
| 729 class LIBPROTOBUF_EXPORT RepeatedPrimitiveGenericTypeTraits { |
| 730 private: |
| 731 template<typename Type> friend class RepeatedPrimitiveTypeTraits; |
| 732 static void InitializeDefaultRepeatedFields(); |
| 733 static void DestroyDefaultRepeatedFields(); |
| 734 static const RepeatedField<int32>* default_repeated_field_int32_; |
| 735 static const RepeatedField<int64>* default_repeated_field_int64_; |
| 736 static const RepeatedField<uint32>* default_repeated_field_uint32_; |
| 737 static const RepeatedField<uint64>* default_repeated_field_uint64_; |
| 738 static const RepeatedField<double>* default_repeated_field_double_; |
| 739 static const RepeatedField<float>* default_repeated_field_float_; |
| 740 static const RepeatedField<bool>* default_repeated_field_bool_; |
646 }; | 741 }; |
647 | 742 |
648 #define PROTOBUF_DEFINE_PRIMITIVE_TYPE(TYPE, METHOD) \ | 743 #define PROTOBUF_DEFINE_PRIMITIVE_TYPE(TYPE, METHOD) \ |
649 template<> inline TYPE PrimitiveTypeTraits<TYPE>::Get( \ | 744 template<> inline TYPE PrimitiveTypeTraits<TYPE>::Get( \ |
650 int number, const ExtensionSet& set, TYPE default_value) { \ | 745 int number, const ExtensionSet& set, TYPE default_value) { \ |
651 return set.Get##METHOD(number, default_value); \ | 746 return set.Get##METHOD(number, default_value); \ |
652 } \ | 747 } \ |
653 template<> inline void PrimitiveTypeTraits<TYPE>::Set( \ | 748 template<> inline void PrimitiveTypeTraits<TYPE>::Set( \ |
654 int number, FieldType field_type, TYPE value, ExtensionSet* set) { \ | 749 int number, FieldType field_type, TYPE value, ExtensionSet* set) { \ |
655 set->Set##METHOD(number, field_type, value, NULL); \ | 750 set->Set##METHOD(number, field_type, value, NULL); \ |
656 } \ | 751 } \ |
657 \ | 752 \ |
658 template<> inline TYPE RepeatedPrimitiveTypeTraits<TYPE>::Get( \ | 753 template<> inline TYPE RepeatedPrimitiveTypeTraits<TYPE>::Get( \ |
659 int number, const ExtensionSet& set, int index) { \ | 754 int number, const ExtensionSet& set, int index) { \ |
660 return set.GetRepeated##METHOD(number, index); \ | 755 return set.GetRepeated##METHOD(number, index); \ |
661 } \ | 756 } \ |
662 template<> inline void RepeatedPrimitiveTypeTraits<TYPE>::Set( \ | 757 template<> inline void RepeatedPrimitiveTypeTraits<TYPE>::Set( \ |
663 int number, int index, TYPE value, ExtensionSet* set) { \ | 758 int number, int index, TYPE value, ExtensionSet* set) { \ |
664 set->SetRepeated##METHOD(number, index, value); \ | 759 set->SetRepeated##METHOD(number, index, value); \ |
665 } \ | 760 } \ |
666 template<> inline void RepeatedPrimitiveTypeTraits<TYPE>::Add( \ | 761 template<> inline void RepeatedPrimitiveTypeTraits<TYPE>::Add( \ |
667 int number, FieldType field_type, bool is_packed, \ | 762 int number, FieldType field_type, bool is_packed, \ |
668 TYPE value, ExtensionSet* set) { \ | 763 TYPE value, ExtensionSet* set) { \ |
669 set->Add##METHOD(number, field_type, is_packed, value, NULL); \ | 764 set->Add##METHOD(number, field_type, is_packed, value, NULL); \ |
| 765 } \ |
| 766 template<> inline const RepeatedField<TYPE>* \ |
| 767 RepeatedPrimitiveTypeTraits<TYPE>::GetDefaultRepeatedField() { \ |
| 768 ::google::protobuf::GoogleOnceInit(
\ |
| 769 &repeated_primitive_generic_type_traits_once_init_, \ |
| 770 &RepeatedPrimitiveGenericTypeTraits::InitializeDefaultRepeatedFields); \ |
| 771 return RepeatedPrimitiveGenericTypeTraits:: \ |
| 772 default_repeated_field_##TYPE##_; \ |
| 773 } \ |
| 774 template<> inline const RepeatedField<TYPE>& \ |
| 775 RepeatedPrimitiveTypeTraits<TYPE>::GetRepeated(int number, \ |
| 776 const ExtensionSet& set) { \ |
| 777 return *reinterpret_cast<const RepeatedField<TYPE>*>( \ |
| 778 set.GetRawRepeatedField( \ |
| 779 number, GetDefaultRepeatedField())); \ |
| 780 } \ |
| 781 template<> inline RepeatedField<TYPE>* \ |
| 782 RepeatedPrimitiveTypeTraits<TYPE>::MutableRepeated(int number, \ |
| 783 FieldType field_type, \ |
| 784 bool is_packed, \ |
| 785 ExtensionSet* set) { \ |
| 786 return reinterpret_cast<RepeatedField<TYPE>*>( \ |
| 787 set->MutableRawRepeatedField(number, field_type, is_packed, NULL)); \ |
670 } | 788 } |
671 | 789 |
672 PROTOBUF_DEFINE_PRIMITIVE_TYPE( int32, Int32) | 790 PROTOBUF_DEFINE_PRIMITIVE_TYPE( int32, Int32) |
673 PROTOBUF_DEFINE_PRIMITIVE_TYPE( int64, Int64) | 791 PROTOBUF_DEFINE_PRIMITIVE_TYPE( int64, Int64) |
674 PROTOBUF_DEFINE_PRIMITIVE_TYPE(uint32, UInt32) | 792 PROTOBUF_DEFINE_PRIMITIVE_TYPE(uint32, UInt32) |
675 PROTOBUF_DEFINE_PRIMITIVE_TYPE(uint64, UInt64) | 793 PROTOBUF_DEFINE_PRIMITIVE_TYPE(uint64, UInt64) |
676 PROTOBUF_DEFINE_PRIMITIVE_TYPE( float, Float) | 794 PROTOBUF_DEFINE_PRIMITIVE_TYPE( float, Float) |
677 PROTOBUF_DEFINE_PRIMITIVE_TYPE(double, Double) | 795 PROTOBUF_DEFINE_PRIMITIVE_TYPE(double, Double) |
678 PROTOBUF_DEFINE_PRIMITIVE_TYPE( bool, Bool) | 796 PROTOBUF_DEFINE_PRIMITIVE_TYPE( bool, Bool) |
679 | 797 |
680 #undef PROTOBUF_DEFINE_PRIMITIVE_TYPE | 798 #undef PROTOBUF_DEFINE_PRIMITIVE_TYPE |
681 | 799 |
682 // ------------------------------------------------------------------- | 800 // ------------------------------------------------------------------- |
683 // StringTypeTraits | 801 // StringTypeTraits |
684 | 802 |
685 // Strings support both Set() and Mutable(). | 803 // Strings support both Set() and Mutable(). |
686 class LIBPROTOBUF_EXPORT StringTypeTraits { | 804 class LIBPROTOBUF_EXPORT StringTypeTraits { |
687 public: | 805 public: |
688 typedef const string& ConstType; | 806 typedef const string& ConstType; |
689 typedef string* MutableType; | 807 typedef string* MutableType; |
| 808 typedef StringTypeTraits Singular; |
690 | 809 |
691 static inline const string& Get(int number, const ExtensionSet& set, | 810 static inline const string& Get(int number, const ExtensionSet& set, |
692 ConstType default_value) { | 811 ConstType default_value) { |
693 return set.GetString(number, default_value); | 812 return set.GetString(number, default_value); |
694 } | 813 } |
695 static inline void Set(int number, FieldType field_type, | 814 static inline void Set(int number, FieldType field_type, |
696 const string& value, ExtensionSet* set) { | 815 const string& value, ExtensionSet* set) { |
697 set->SetString(number, field_type, value, NULL); | 816 set->SetString(number, field_type, value, NULL); |
698 } | 817 } |
699 static inline string* Mutable(int number, FieldType field_type, | 818 static inline string* Mutable(int number, FieldType field_type, |
700 ExtensionSet* set) { | 819 ExtensionSet* set) { |
701 return set->MutableString(number, field_type, NULL); | 820 return set->MutableString(number, field_type, NULL); |
702 } | 821 } |
703 }; | 822 }; |
704 | 823 |
| 824 LIBPROTOBUF_EXPORT extern ProtobufOnceType repeated_string_type_traits_once_init
_; |
| 825 |
705 class LIBPROTOBUF_EXPORT RepeatedStringTypeTraits { | 826 class LIBPROTOBUF_EXPORT RepeatedStringTypeTraits { |
706 public: | 827 public: |
707 typedef const string& ConstType; | 828 typedef const string& ConstType; |
708 typedef string* MutableType; | 829 typedef string* MutableType; |
| 830 typedef RepeatedStringTypeTraits Repeated; |
| 831 |
| 832 typedef RepeatedPtrField<string> RepeatedFieldType; |
709 | 833 |
710 static inline const string& Get(int number, const ExtensionSet& set, | 834 static inline const string& Get(int number, const ExtensionSet& set, |
711 int index) { | 835 int index) { |
712 return set.GetRepeatedString(number, index); | 836 return set.GetRepeatedString(number, index); |
713 } | 837 } |
714 static inline void Set(int number, int index, | 838 static inline void Set(int number, int index, |
715 const string& value, ExtensionSet* set) { | 839 const string& value, ExtensionSet* set) { |
716 set->SetRepeatedString(number, index, value); | 840 set->SetRepeatedString(number, index, value); |
717 } | 841 } |
718 static inline string* Mutable(int number, int index, ExtensionSet* set) { | 842 static inline string* Mutable(int number, int index, ExtensionSet* set) { |
719 return set->MutableRepeatedString(number, index); | 843 return set->MutableRepeatedString(number, index); |
720 } | 844 } |
721 static inline void Add(int number, FieldType field_type, | 845 static inline void Add(int number, FieldType field_type, |
722 bool /*is_packed*/, const string& value, | 846 bool /*is_packed*/, const string& value, |
723 ExtensionSet* set) { | 847 ExtensionSet* set) { |
724 set->AddString(number, field_type, value, NULL); | 848 set->AddString(number, field_type, value, NULL); |
725 } | 849 } |
726 static inline string* Add(int number, FieldType field_type, | 850 static inline string* Add(int number, FieldType field_type, |
727 ExtensionSet* set) { | 851 ExtensionSet* set) { |
728 return set->AddString(number, field_type, NULL); | 852 return set->AddString(number, field_type, NULL); |
729 } | 853 } |
| 854 static inline const RepeatedPtrField<string>& |
| 855 GetRepeated(int number, const ExtensionSet& set) { |
| 856 return *reinterpret_cast<const RepeatedPtrField<string>*>( |
| 857 set.GetRawRepeatedField(number, GetDefaultRepeatedField())); |
| 858 } |
| 859 |
| 860 static inline RepeatedPtrField<string>* |
| 861 MutableRepeated(int number, FieldType field_type, |
| 862 bool is_packed, ExtensionSet* set) { |
| 863 return reinterpret_cast<RepeatedPtrField<string>*>( |
| 864 set->MutableRawRepeatedField(number, field_type, |
| 865 is_packed, NULL)); |
| 866 } |
| 867 |
| 868 static const RepeatedFieldType* GetDefaultRepeatedField() { |
| 869 ::google::protobuf::GoogleOnceInit(&repeated_string_type_traits_once_init_, |
| 870 &InitializeDefaultRepeatedFields); |
| 871 return default_repeated_field_; |
| 872 } |
| 873 |
| 874 private: |
| 875 static void InitializeDefaultRepeatedFields(); |
| 876 static void DestroyDefaultRepeatedFields(); |
| 877 static const RepeatedFieldType *default_repeated_field_; |
730 }; | 878 }; |
731 | 879 |
732 // ------------------------------------------------------------------- | 880 // ------------------------------------------------------------------- |
733 // EnumTypeTraits | 881 // EnumTypeTraits |
734 | 882 |
735 // ExtensionSet represents enums using integers internally, so we have to | 883 // ExtensionSet represents enums using integers internally, so we have to |
736 // static_cast around. | 884 // static_cast around. |
737 template <typename Type, bool IsValid(int)> | 885 template <typename Type, bool IsValid(int)> |
738 class EnumTypeTraits { | 886 class EnumTypeTraits { |
739 public: | 887 public: |
740 typedef Type ConstType; | 888 typedef Type ConstType; |
| 889 typedef Type MutableType; |
| 890 typedef EnumTypeTraits<Type, IsValid> Singular; |
741 | 891 |
742 static inline ConstType Get(int number, const ExtensionSet& set, | 892 static inline ConstType Get(int number, const ExtensionSet& set, |
743 ConstType default_value) { | 893 ConstType default_value) { |
744 return static_cast<Type>(set.GetEnum(number, default_value)); | 894 return static_cast<Type>(set.GetEnum(number, default_value)); |
745 } | 895 } |
746 static inline void Set(int number, FieldType field_type, | 896 static inline void Set(int number, FieldType field_type, |
747 ConstType value, ExtensionSet* set) { | 897 ConstType value, ExtensionSet* set) { |
748 GOOGLE_DCHECK(IsValid(value)); | 898 GOOGLE_DCHECK(IsValid(value)); |
749 set->SetEnum(number, field_type, value, NULL); | 899 set->SetEnum(number, field_type, value, NULL); |
750 } | 900 } |
751 }; | 901 }; |
752 | 902 |
753 template <typename Type, bool IsValid(int)> | 903 template <typename Type, bool IsValid(int)> |
754 class RepeatedEnumTypeTraits { | 904 class RepeatedEnumTypeTraits { |
755 public: | 905 public: |
756 typedef Type ConstType; | 906 typedef Type ConstType; |
| 907 typedef Type MutableType; |
| 908 typedef RepeatedEnumTypeTraits<Type, IsValid> Repeated; |
| 909 |
| 910 typedef RepeatedField<Type> RepeatedFieldType; |
757 | 911 |
758 static inline ConstType Get(int number, const ExtensionSet& set, int index) { | 912 static inline ConstType Get(int number, const ExtensionSet& set, int index) { |
759 return static_cast<Type>(set.GetRepeatedEnum(number, index)); | 913 return static_cast<Type>(set.GetRepeatedEnum(number, index)); |
760 } | 914 } |
761 static inline void Set(int number, int index, | 915 static inline void Set(int number, int index, |
762 ConstType value, ExtensionSet* set) { | 916 ConstType value, ExtensionSet* set) { |
763 GOOGLE_DCHECK(IsValid(value)); | 917 GOOGLE_DCHECK(IsValid(value)); |
764 set->SetRepeatedEnum(number, index, value); | 918 set->SetRepeatedEnum(number, index, value); |
765 } | 919 } |
766 static inline void Add(int number, FieldType field_type, | 920 static inline void Add(int number, FieldType field_type, |
767 bool is_packed, ConstType value, ExtensionSet* set) { | 921 bool is_packed, ConstType value, ExtensionSet* set) { |
768 GOOGLE_DCHECK(IsValid(value)); | 922 GOOGLE_DCHECK(IsValid(value)); |
769 set->AddEnum(number, field_type, is_packed, value, NULL); | 923 set->AddEnum(number, field_type, is_packed, value, NULL); |
770 } | 924 } |
| 925 static inline const RepeatedField<Type>& GetRepeated(int number, |
| 926 const ExtensionSet& |
| 927 set) { |
| 928 // Hack: the `Extension` struct stores a RepeatedField<int> for enums. |
| 929 // RepeatedField<int> cannot implicitly convert to RepeatedField<EnumType> |
| 930 // so we need to do some casting magic. See message.h for similar |
| 931 // contortions for non-extension fields. |
| 932 return *reinterpret_cast<const RepeatedField<Type>*>( |
| 933 set.GetRawRepeatedField(number, GetDefaultRepeatedField())); |
| 934 } |
| 935 |
| 936 static inline RepeatedField<Type>* MutableRepeated(int number, |
| 937 FieldType field_type, |
| 938 bool is_packed, |
| 939 ExtensionSet* set) { |
| 940 return reinterpret_cast<RepeatedField<Type>*>( |
| 941 set->MutableRawRepeatedField(number, field_type, is_packed, NULL)); |
| 942 } |
| 943 |
| 944 static const RepeatedFieldType* GetDefaultRepeatedField() { |
| 945 // Hack: as noted above, repeated enum fields are internally stored as a |
| 946 // RepeatedField<int>. We need to be able to instantiate global static |
| 947 // objects to return as default (empty) repeated fields on non-existent |
| 948 // extensions. We would not be able to know a-priori all of the enum types |
| 949 // (values of |Type|) to instantiate all of these, so we just re-use int32's |
| 950 // default repeated field object. |
| 951 return reinterpret_cast<const RepeatedField<Type>*>( |
| 952 RepeatedPrimitiveTypeTraits<int32>::GetDefaultRepeatedField()); |
| 953 } |
771 }; | 954 }; |
772 | 955 |
773 // ------------------------------------------------------------------- | 956 // ------------------------------------------------------------------- |
774 // MessageTypeTraits | 957 // MessageTypeTraits |
775 | 958 |
776 // ExtensionSet guarantees that when manipulating extensions with message | 959 // ExtensionSet guarantees that when manipulating extensions with message |
777 // types, the implementation used will be the compiled-in class representing | 960 // types, the implementation used will be the compiled-in class representing |
778 // that type. So, we can static_cast down to the exact type we expect. | 961 // that type. So, we can static_cast down to the exact type we expect. |
779 template <typename Type> | 962 template <typename Type> |
780 class MessageTypeTraits { | 963 class MessageTypeTraits { |
781 public: | 964 public: |
782 typedef const Type& ConstType; | 965 typedef const Type& ConstType; |
783 typedef Type* MutableType; | 966 typedef Type* MutableType; |
| 967 typedef MessageTypeTraits<Type> Singular; |
784 | 968 |
785 static inline ConstType Get(int number, const ExtensionSet& set, | 969 static inline ConstType Get(int number, const ExtensionSet& set, |
786 ConstType default_value) { | 970 ConstType default_value) { |
787 return static_cast<const Type&>( | 971 return static_cast<const Type&>( |
788 set.GetMessage(number, default_value)); | 972 set.GetMessage(number, default_value)); |
789 } | 973 } |
790 static inline MutableType Mutable(int number, FieldType field_type, | 974 static inline MutableType Mutable(int number, FieldType field_type, |
791 ExtensionSet* set) { | 975 ExtensionSet* set) { |
792 return static_cast<Type*>( | 976 return static_cast<Type*>( |
793 set->MutableMessage(number, field_type, Type::default_instance(), NULL)); | 977 set->MutableMessage(number, field_type, Type::default_instance(), NULL)); |
794 } | 978 } |
795 static inline void SetAllocated(int number, FieldType field_type, | 979 static inline void SetAllocated(int number, FieldType field_type, |
796 MutableType message, ExtensionSet* set) { | 980 MutableType message, ExtensionSet* set) { |
797 set->SetAllocatedMessage(number, field_type, NULL, message); | 981 set->SetAllocatedMessage(number, field_type, NULL, message); |
798 } | 982 } |
799 static inline MutableType Release(int number, FieldType field_type, | 983 static inline MutableType Release(int number, FieldType /* field_type */, |
800 ExtensionSet* set) { | 984 ExtensionSet* set) { |
801 return static_cast<Type*>(set->ReleaseMessage( | 985 return static_cast<Type*>(set->ReleaseMessage( |
802 number, Type::default_instance())); | 986 number, Type::default_instance())); |
803 } | 987 } |
804 }; | 988 }; |
805 | 989 |
| 990 // forward declaration |
| 991 class RepeatedMessageGenericTypeTraits; |
| 992 |
806 template <typename Type> | 993 template <typename Type> |
807 class RepeatedMessageTypeTraits { | 994 class RepeatedMessageTypeTraits { |
808 public: | 995 public: |
809 typedef const Type& ConstType; | 996 typedef const Type& ConstType; |
810 typedef Type* MutableType; | 997 typedef Type* MutableType; |
| 998 typedef RepeatedMessageTypeTraits<Type> Repeated; |
| 999 |
| 1000 typedef RepeatedPtrField<Type> RepeatedFieldType; |
811 | 1001 |
812 static inline ConstType Get(int number, const ExtensionSet& set, int index) { | 1002 static inline ConstType Get(int number, const ExtensionSet& set, int index) { |
813 return static_cast<const Type&>(set.GetRepeatedMessage(number, index)); | 1003 return static_cast<const Type&>(set.GetRepeatedMessage(number, index)); |
814 } | 1004 } |
815 static inline MutableType Mutable(int number, int index, ExtensionSet* set) { | 1005 static inline MutableType Mutable(int number, int index, ExtensionSet* set) { |
816 return static_cast<Type*>(set->MutableRepeatedMessage(number, index)); | 1006 return static_cast<Type*>(set->MutableRepeatedMessage(number, index)); |
817 } | 1007 } |
818 static inline MutableType Add(int number, FieldType field_type, | 1008 static inline MutableType Add(int number, FieldType field_type, |
819 ExtensionSet* set) { | 1009 ExtensionSet* set) { |
820 return static_cast<Type*>( | 1010 return static_cast<Type*>( |
821 set->AddMessage(number, field_type, Type::default_instance(), NULL)); | 1011 set->AddMessage(number, field_type, Type::default_instance(), NULL)); |
822 } | 1012 } |
| 1013 static inline const RepeatedPtrField<Type>& GetRepeated(int number, |
| 1014 const ExtensionSet& |
| 1015 set) { |
| 1016 // See notes above in RepeatedEnumTypeTraits::GetRepeated(): same |
| 1017 // casting hack applies here, because a RepeatedPtrField<MessageLite> |
| 1018 // cannot naturally become a RepeatedPtrType<Type> even though Type is |
| 1019 // presumably a message. google::protobuf::Message goes through similar cont
ortions |
| 1020 // with a reinterpret_cast<>. |
| 1021 return *reinterpret_cast<const RepeatedPtrField<Type>*>( |
| 1022 set.GetRawRepeatedField(number, GetDefaultRepeatedField())); |
| 1023 } |
| 1024 static inline RepeatedPtrField<Type>* MutableRepeated(int number, |
| 1025 FieldType field_type, |
| 1026 bool is_packed, |
| 1027 ExtensionSet* set) { |
| 1028 return reinterpret_cast<RepeatedPtrField<Type>*>( |
| 1029 set->MutableRawRepeatedField(number, field_type, is_packed, NULL)); |
| 1030 } |
| 1031 |
| 1032 static const RepeatedFieldType* GetDefaultRepeatedField(); |
823 }; | 1033 }; |
824 | 1034 |
| 1035 LIBPROTOBUF_EXPORT extern ProtobufOnceType repeated_message_generic_type_traits_
once_init_; |
| 1036 |
| 1037 // This class exists only to hold a generic default empty repeated field for all |
| 1038 // message-type repeated field extensions. |
| 1039 class LIBPROTOBUF_EXPORT RepeatedMessageGenericTypeTraits { |
| 1040 public: |
| 1041 typedef RepeatedPtrField< ::google::protobuf::MessageLite*> RepeatedFieldType; |
| 1042 private: |
| 1043 template<typename Type> friend class RepeatedMessageTypeTraits; |
| 1044 static void InitializeDefaultRepeatedFields(); |
| 1045 static void DestroyDefaultRepeatedFields(); |
| 1046 static const RepeatedFieldType* default_repeated_field_; |
| 1047 }; |
| 1048 |
| 1049 template<typename Type> inline |
| 1050 const typename RepeatedMessageTypeTraits<Type>::RepeatedFieldType* |
| 1051 RepeatedMessageTypeTraits<Type>::GetDefaultRepeatedField() { |
| 1052 ::google::protobuf::GoogleOnceInit( |
| 1053 &repeated_message_generic_type_traits_once_init_, |
| 1054 &RepeatedMessageGenericTypeTraits::InitializeDefaultRepeatedFields); |
| 1055 return reinterpret_cast<const RepeatedFieldType*>( |
| 1056 RepeatedMessageGenericTypeTraits::default_repeated_field_); |
| 1057 } |
| 1058 |
825 // ------------------------------------------------------------------- | 1059 // ------------------------------------------------------------------- |
826 // ExtensionIdentifier | 1060 // ExtensionIdentifier |
827 | 1061 |
828 // This is the type of actual extension objects. E.g. if you have: | 1062 // This is the type of actual extension objects. E.g. if you have: |
829 // extends Foo with optional int32 bar = 1234; | 1063 // extends Foo with optional int32 bar = 1234; |
830 // then "bar" will be defined in C++ as: | 1064 // then "bar" will be defined in C++ as: |
831 // ExtensionIdentifier<Foo, PrimitiveTypeTraits<int32>, 1, false> bar(1234); | 1065 // ExtensionIdentifier<Foo, PrimitiveTypeTraits<int32>, 1, false> bar(1234); |
832 // | 1066 // |
833 // Note that we could, in theory, supply the field number as a template | 1067 // Note that we could, in theory, supply the field number as a template |
834 // parameter, and thus make an instance of ExtensionIdentifier have no | 1068 // parameter, and thus make an instance of ExtensionIdentifier have no |
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
897 inline int ExtensionSize( \ | 1131 inline int ExtensionSize( \ |
898 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1132 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
899 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) const { \ | 1133 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) const { \ |
900 return _extensions_.ExtensionSize(id.number()); \ | 1134 return _extensions_.ExtensionSize(id.number()); \ |
901 } \ | 1135 } \ |
902 \ | 1136 \ |
903 /* Singular accessors */ \ | 1137 /* Singular accessors */ \ |
904 template <typename _proto_TypeTraits, \ | 1138 template <typename _proto_TypeTraits, \ |
905 ::google::protobuf::internal::FieldType _field_type,
\ | 1139 ::google::protobuf::internal::FieldType _field_type,
\ |
906 bool _is_packed> \ | 1140 bool _is_packed> \ |
907 inline typename _proto_TypeTraits::ConstType GetExtension( \ | 1141 inline typename _proto_TypeTraits::Singular::ConstType GetExtension( \ |
908 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1142 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
909 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) const { \ | 1143 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) const { \ |
910 return _proto_TypeTraits::Get(id.number(), _extensions_, \ | 1144 return _proto_TypeTraits::Get(id.number(), _extensions_, \ |
911 id.default_value()); \ | 1145 id.default_value()); \ |
912 } \ | 1146 } \ |
913 \ | 1147 \ |
914 template <typename _proto_TypeTraits, \ | 1148 template <typename _proto_TypeTraits, \ |
915 ::google::protobuf::internal::FieldType _field_type,
\ | 1149 ::google::protobuf::internal::FieldType _field_type,
\ |
916 bool _is_packed> \ | 1150 bool _is_packed> \ |
917 inline typename _proto_TypeTraits::MutableType MutableExtension( \ | 1151 inline typename _proto_TypeTraits::Singular::MutableType MutableExtension( \ |
918 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1152 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
919 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \ | 1153 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \ |
920 return _proto_TypeTraits::Mutable(id.number(), _field_type, \ | 1154 return _proto_TypeTraits::Mutable(id.number(), _field_type, \ |
921 &_extensions_); \ | 1155 &_extensions_); \ |
922 } \ | 1156 } \ |
923 \ | 1157 \ |
924 template <typename _proto_TypeTraits, \ | 1158 template <typename _proto_TypeTraits, \ |
925 ::google::protobuf::internal::FieldType _field_type,
\ | 1159 ::google::protobuf::internal::FieldType _field_type,
\ |
926 bool _is_packed> \ | 1160 bool _is_packed> \ |
927 inline void SetExtension( \ | 1161 inline void SetExtension( \ |
928 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1162 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
929 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ | 1163 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ |
930 typename _proto_TypeTraits::ConstType value) { \ | 1164 typename _proto_TypeTraits::Singular::ConstType value) { \ |
931 _proto_TypeTraits::Set(id.number(), _field_type, value, &_extensions_); \ | 1165 _proto_TypeTraits::Set(id.number(), _field_type, value, &_extensions_); \ |
932 } \ | 1166 } \ |
933 \ | 1167 \ |
934 template <typename _proto_TypeTraits, \ | 1168 template <typename _proto_TypeTraits, \ |
935 ::google::protobuf::internal::FieldType _field_type,
\ | 1169 ::google::protobuf::internal::FieldType _field_type,
\ |
936 bool _is_packed> \ | 1170 bool _is_packed> \ |
937 inline void SetAllocatedExtension( \ | 1171 inline void SetAllocatedExtension( \ |
938 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1172 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
939 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ | 1173 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ |
940 typename _proto_TypeTraits::MutableType value) { \ | 1174 typename _proto_TypeTraits::Singular::MutableType value) { \ |
941 _proto_TypeTraits::SetAllocated(id.number(), _field_type, \ | 1175 _proto_TypeTraits::SetAllocated(id.number(), _field_type, \ |
942 value, &_extensions_); \ | 1176 value, &_extensions_); \ |
943 } \ | 1177 } \ |
944 template <typename _proto_TypeTraits, \ | 1178 template <typename _proto_TypeTraits, \ |
945 ::google::protobuf::internal::FieldType _field_type,
\ | 1179 ::google::protobuf::internal::FieldType _field_type,
\ |
946 bool _is_packed> \ | 1180 bool _is_packed> \ |
947 inline typename _proto_TypeTraits::MutableType ReleaseExtension( \ | 1181 inline typename _proto_TypeTraits::Singular::MutableType ReleaseExtension( \ |
948 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1182 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
949 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \ | 1183 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \ |
950 return _proto_TypeTraits::Release(id.number(), _field_type, \ | 1184 return _proto_TypeTraits::Release(id.number(), _field_type, \ |
951 &_extensions_); \ | 1185 &_extensions_); \ |
952 } \ | 1186 } \ |
953 \ | 1187 \ |
954 /* Repeated accessors */ \ | 1188 /* Repeated accessors */ \ |
955 template <typename _proto_TypeTraits, \ | 1189 template <typename _proto_TypeTraits, \ |
956 ::google::protobuf::internal::FieldType _field_type,
\ | 1190 ::google::protobuf::internal::FieldType _field_type,
\ |
957 bool _is_packed> \ | 1191 bool _is_packed> \ |
958 inline typename _proto_TypeTraits::ConstType GetExtension( \ | 1192 inline typename _proto_TypeTraits::Repeated::ConstType GetExtension( \ |
959 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1193 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
960 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ | 1194 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ |
961 int index) const { \ | 1195 int index) const { \ |
962 return _proto_TypeTraits::Get(id.number(), _extensions_, index); \ | 1196 return _proto_TypeTraits::Get(id.number(), _extensions_, index); \ |
963 } \ | 1197 } \ |
964 \ | 1198 \ |
965 template <typename _proto_TypeTraits, \ | 1199 template <typename _proto_TypeTraits, \ |
966 ::google::protobuf::internal::FieldType _field_type,
\ | 1200 ::google::protobuf::internal::FieldType _field_type,
\ |
967 bool _is_packed> \ | 1201 bool _is_packed> \ |
968 inline typename _proto_TypeTraits::MutableType MutableExtension( \ | 1202 inline typename _proto_TypeTraits::Repeated::MutableType MutableExtension( \ |
969 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1203 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
970 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ | 1204 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ |
971 int index) { \ | 1205 int index) { \ |
972 return _proto_TypeTraits::Mutable(id.number(), index, &_extensions_); \ | 1206 return _proto_TypeTraits::Mutable(id.number(), index, &_extensions_); \ |
973 } \ | 1207 } \ |
974 \ | 1208 \ |
975 template <typename _proto_TypeTraits, \ | 1209 template <typename _proto_TypeTraits, \ |
976 ::google::protobuf::internal::FieldType _field_type,
\ | 1210 ::google::protobuf::internal::FieldType _field_type,
\ |
977 bool _is_packed> \ | 1211 bool _is_packed> \ |
978 inline void SetExtension( \ | 1212 inline void SetExtension( \ |
979 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1213 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
980 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ | 1214 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ |
981 int index, typename _proto_TypeTraits::ConstType value) { \ | 1215 int index, typename _proto_TypeTraits::Repeated::ConstType value) { \ |
982 _proto_TypeTraits::Set(id.number(), index, value, &_extensions_); \ | 1216 _proto_TypeTraits::Set(id.number(), index, value, &_extensions_); \ |
983 } \ | 1217 } \ |
984 \ | 1218 \ |
985 template <typename _proto_TypeTraits, \ | 1219 template <typename _proto_TypeTraits, \ |
986 ::google::protobuf::internal::FieldType _field_type,
\ | 1220 ::google::protobuf::internal::FieldType _field_type,
\ |
987 bool _is_packed> \ | 1221 bool _is_packed> \ |
988 inline typename _proto_TypeTraits::MutableType AddExtension( \ | 1222 inline typename _proto_TypeTraits::Repeated::MutableType AddExtension( \ |
989 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1223 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
990 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \ | 1224 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id) { \ |
991 return _proto_TypeTraits::Add(id.number(), _field_type, &_extensions_); \ | 1225 return _proto_TypeTraits::Add(id.number(), _field_type, &_extensions_); \ |
992 } \ | 1226 } \ |
993 \ | 1227 \ |
994 template <typename _proto_TypeTraits, \ | 1228 template <typename _proto_TypeTraits, \ |
995 ::google::protobuf::internal::FieldType _field_type,
\ | 1229 ::google::protobuf::internal::FieldType _field_type,
\ |
996 bool _is_packed> \ | 1230 bool _is_packed> \ |
997 inline void AddExtension( \ | 1231 inline void AddExtension( \ |
998 const ::google::protobuf::internal::ExtensionIdentifier<
\ | 1232 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
999 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ | 1233 CLASSNAME, _proto_TypeTraits, _field_type, _is_packed>& id, \ |
1000 typename _proto_TypeTraits::ConstType value) { \ | 1234 typename _proto_TypeTraits::Repeated::ConstType value) { \ |
1001 _proto_TypeTraits::Add(id.number(), _field_type, _is_packed, \ | 1235 _proto_TypeTraits::Add(id.number(), _field_type, _is_packed, \ |
1002 value, &_extensions_); \ | 1236 value, &_extensions_); \ |
| 1237 } \ |
| 1238 \ |
| 1239 template <typename _proto_TypeTraits, \ |
| 1240 ::google::protobuf::internal::FieldType _field_type,
\ |
| 1241 bool _is_packed> \ |
| 1242 inline const typename _proto_TypeTraits::Repeated::RepeatedFieldType& \ |
| 1243 GetRepeatedExtension( \ |
| 1244 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
| 1245 CLASSNAME, _proto_TypeTraits, _field_type, \ |
| 1246 _is_packed>& id) const { \ |
| 1247 return _proto_TypeTraits::GetRepeated(id.number(), _extensions_); \ |
| 1248 } \ |
| 1249 \ |
| 1250 template <typename _proto_TypeTraits, \ |
| 1251 ::google::protobuf::internal::FieldType _field_type,
\ |
| 1252 bool _is_packed> \ |
| 1253 inline typename _proto_TypeTraits::Repeated::RepeatedFieldType* \ |
| 1254 MutableRepeatedExtension( \ |
| 1255 const ::google::protobuf::internal::ExtensionIdentifier<
\ |
| 1256 CLASSNAME, _proto_TypeTraits, _field_type, \ |
| 1257 _is_packed>& id) { \ |
| 1258 return _proto_TypeTraits::MutableRepeated(id.number(), _field_type, \ |
| 1259 _is_packed, &_extensions_); \ |
1003 } | 1260 } |
1004 | 1261 |
1005 } // namespace internal | 1262 } // namespace internal |
1006 } // namespace protobuf | 1263 } // namespace protobuf |
1007 | 1264 |
1008 } // namespace google | 1265 } // namespace google |
1009 #endif // GOOGLE_PROTOBUF_EXTENSION_SET_H__ | 1266 #endif // GOOGLE_PROTOBUF_EXTENSION_SET_H__ |
OLD | NEW |