1 // Protocol Buffers - Google's data interchange format
2 // Copyright 2008 Google Inc. All rights reserved.
3 // http://code.google.com/p/protobuf/
5 // Redistribution and use in source and binary forms, with or without
6 // modification, are permitted provided that the following conditions are
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
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.
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.
31 // Author: kenton@google.com (Kenton Varda)
32 // Based on original Protocol Buffers design by
33 // Sanjay Ghemawat, Jeff Dean, and others.
36 #include <google/protobuf/descriptor.pb.h>
37 #include <google/protobuf/generated_message_reflection.h>
38 #include <google/protobuf/descriptor.h>
39 #include <google/protobuf/repeated_field.h>
40 #include <google/protobuf/extension_set.h>
41 #include <google/protobuf/generated_message_util.h>
42 #include <google/protobuf/stubs/common.h>
48 bool ParseNamedEnum(const EnumDescriptor* descriptor,
51 const EnumValueDescriptor* d = descriptor->FindValueByName(name);
52 if (d == NULL) return false;
57 const string& NameOfEnum(const EnumDescriptor* descriptor, int value) {
58 const EnumValueDescriptor* d = descriptor->FindValueByNumber(value);
59 return (d == NULL ? kEmptyString : d->name());
62 // ===================================================================
63 // Helpers for reporting usage errors (e.g. trying to use GetInt32() on
68 void ReportReflectionUsageError(
69 const Descriptor* descriptor, const FieldDescriptor* field,
70 const char* method, const char* description) {
72 << "Protocol Buffer reflection usage error:\n"
73 " Method : google::protobuf::Reflection::" << method << "\n"
74 " Message type: " << descriptor->full_name() << "\n"
75 " Field : " << field->full_name() << "\n"
76 " Problem : " << description;
79 const char* cpptype_names_[FieldDescriptor::MAX_CPPTYPE + 1] = {
93 static void ReportReflectionUsageTypeError(
94 const Descriptor* descriptor, const FieldDescriptor* field,
96 FieldDescriptor::CppType expected_type) {
98 << "Protocol Buffer reflection usage error:\n"
99 " Method : google::protobuf::Reflection::" << method << "\n"
100 " Message type: " << descriptor->full_name() << "\n"
101 " Field : " << field->full_name() << "\n"
102 " Problem : Field is not the right type for this message:\n"
103 " Expected : " << cpptype_names_[expected_type] << "\n"
104 " Field type: " << cpptype_names_[field->cpp_type()];
107 static void ReportReflectionUsageEnumTypeError(
108 const Descriptor* descriptor, const FieldDescriptor* field,
109 const char* method, const EnumValueDescriptor* value) {
111 << "Protocol Buffer reflection usage error:\n"
112 " Method : google::protobuf::Reflection::" << method << "\n"
113 " Message type: " << descriptor->full_name() << "\n"
114 " Field : " << field->full_name() << "\n"
115 " Problem : Enum value did not match field type:\n"
116 " Expected : " << field->enum_type()->full_name() << "\n"
117 " Actual : " << value->full_name();
120 #define USAGE_CHECK(CONDITION, METHOD, ERROR_DESCRIPTION) \
122 ReportReflectionUsageError(descriptor_, field, #METHOD, ERROR_DESCRIPTION)
123 #define USAGE_CHECK_EQ(A, B, METHOD, ERROR_DESCRIPTION) \
124 USAGE_CHECK((A) == (B), METHOD, ERROR_DESCRIPTION)
125 #define USAGE_CHECK_NE(A, B, METHOD, ERROR_DESCRIPTION) \
126 USAGE_CHECK((A) != (B), METHOD, ERROR_DESCRIPTION)
128 #define USAGE_CHECK_TYPE(METHOD, CPPTYPE) \
129 if (field->cpp_type() != FieldDescriptor::CPPTYPE_##CPPTYPE) \
130 ReportReflectionUsageTypeError(descriptor_, field, #METHOD, \
131 FieldDescriptor::CPPTYPE_##CPPTYPE)
133 #define USAGE_CHECK_ENUM_VALUE(METHOD) \
134 if (value->type() != field->enum_type()) \
135 ReportReflectionUsageEnumTypeError(descriptor_, field, #METHOD, value)
137 #define USAGE_CHECK_MESSAGE_TYPE(METHOD) \
138 USAGE_CHECK_EQ(field->containing_type(), descriptor_, \
139 METHOD, "Field does not match message type.");
140 #define USAGE_CHECK_SINGULAR(METHOD) \
141 USAGE_CHECK_NE(field->label(), FieldDescriptor::LABEL_REPEATED, METHOD, \
142 "Field is repeated; the method requires a singular field.")
143 #define USAGE_CHECK_REPEATED(METHOD) \
144 USAGE_CHECK_EQ(field->label(), FieldDescriptor::LABEL_REPEATED, METHOD, \
145 "Field is singular; the method requires a repeated field.")
147 #define USAGE_CHECK_ALL(METHOD, LABEL, CPPTYPE) \
148 USAGE_CHECK_MESSAGE_TYPE(METHOD); \
149 USAGE_CHECK_##LABEL(METHOD); \
150 USAGE_CHECK_TYPE(METHOD, CPPTYPE)
154 // ===================================================================
156 GeneratedMessageReflection::GeneratedMessageReflection(
157 const Descriptor* descriptor,
158 const Message* default_instance,
161 int unknown_fields_offset,
162 int extensions_offset,
163 const DescriptorPool* descriptor_pool,
164 MessageFactory* factory,
166 : descriptor_ (descriptor),
167 default_instance_ (default_instance),
169 has_bits_offset_ (has_bits_offset),
170 unknown_fields_offset_(unknown_fields_offset),
171 extensions_offset_(extensions_offset),
172 object_size_ (object_size),
173 descriptor_pool_ ((descriptor_pool == NULL) ?
174 DescriptorPool::generated_pool() :
176 message_factory_ (factory) {
179 GeneratedMessageReflection::~GeneratedMessageReflection() {}
181 const UnknownFieldSet& GeneratedMessageReflection::GetUnknownFields(
182 const Message& message) const {
183 const void* ptr = reinterpret_cast<const uint8*>(&message) +
184 unknown_fields_offset_;
185 return *reinterpret_cast<const UnknownFieldSet*>(ptr);
187 UnknownFieldSet* GeneratedMessageReflection::MutableUnknownFields(
188 Message* message) const {
189 void* ptr = reinterpret_cast<uint8*>(message) + unknown_fields_offset_;
190 return reinterpret_cast<UnknownFieldSet*>(ptr);
193 int GeneratedMessageReflection::SpaceUsed(const Message& message) const {
194 // object_size_ already includes the in-memory representation of each field
195 // in the message, so we only need to account for additional memory used by
197 int total_size = object_size_;
199 total_size += GetUnknownFields(message).SpaceUsedExcludingSelf();
201 if (extensions_offset_ != -1) {
202 total_size += GetExtensionSet(message).SpaceUsedExcludingSelf();
205 for (int i = 0; i < descriptor_->field_count(); i++) {
206 const FieldDescriptor* field = descriptor_->field(i);
208 if (field->is_repeated()) {
209 switch (field->cpp_type()) {
210 #define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
211 case FieldDescriptor::CPPTYPE_##UPPERCASE : \
212 total_size += GetRaw<RepeatedField<LOWERCASE> >(message, field) \
213 .SpaceUsedExcludingSelf(); \
216 HANDLE_TYPE( INT32, int32);
217 HANDLE_TYPE( INT64, int64);
218 HANDLE_TYPE(UINT32, uint32);
219 HANDLE_TYPE(UINT64, uint64);
220 HANDLE_TYPE(DOUBLE, double);
221 HANDLE_TYPE( FLOAT, float);
222 HANDLE_TYPE( BOOL, bool);
223 HANDLE_TYPE( ENUM, int);
226 case FieldDescriptor::CPPTYPE_STRING:
227 switch (field->options().ctype()) {
228 default: // TODO(kenton): Support other string reps.
229 case FieldOptions::STRING:
230 total_size += GetRaw<RepeatedPtrField<string> >(message, field)
231 .SpaceUsedExcludingSelf();
236 case FieldDescriptor::CPPTYPE_MESSAGE:
237 // We don't know which subclass of RepeatedPtrFieldBase the type is,
238 // so we use RepeatedPtrFieldBase directly.
240 GetRaw<RepeatedPtrFieldBase>(message, field)
241 .SpaceUsedExcludingSelf<GenericTypeHandler<Message> >();
245 switch (field->cpp_type()) {
246 case FieldDescriptor::CPPTYPE_INT32 :
247 case FieldDescriptor::CPPTYPE_INT64 :
248 case FieldDescriptor::CPPTYPE_UINT32:
249 case FieldDescriptor::CPPTYPE_UINT64:
250 case FieldDescriptor::CPPTYPE_DOUBLE:
251 case FieldDescriptor::CPPTYPE_FLOAT :
252 case FieldDescriptor::CPPTYPE_BOOL :
253 case FieldDescriptor::CPPTYPE_ENUM :
254 // Field is inline, so we've already counted it.
257 case FieldDescriptor::CPPTYPE_STRING: {
258 switch (field->options().ctype()) {
259 default: // TODO(kenton): Support other string reps.
260 case FieldOptions::STRING: {
261 const string* ptr = GetField<const string*>(message, field);
263 // Initially, the string points to the default value stored in
264 // the prototype. Only count the string if it has been changed
265 // from the default value.
266 const string* default_ptr = DefaultRaw<const string*>(field);
268 if (ptr != default_ptr) {
269 // string fields are represented by just a pointer, so also
270 // include sizeof(string) as well.
271 total_size += sizeof(*ptr) + StringSpaceUsedExcludingSelf(*ptr);
279 case FieldDescriptor::CPPTYPE_MESSAGE:
280 if (&message == default_instance_) {
281 // For singular fields, the prototype just stores a pointer to the
282 // external type's prototype, so there is no extra memory usage.
284 const Message* sub_message = GetRaw<const Message*>(message, field);
285 if (sub_message != NULL) {
286 total_size += sub_message->SpaceUsed();
297 void GeneratedMessageReflection::Swap(
299 Message* message2) const {
300 if (message1 == message2) return;
302 // TODO(kenton): Other Reflection methods should probably check this too.
303 GOOGLE_CHECK_EQ(message1->GetReflection(), this)
304 << "First argument to Swap() (of type \""
305 << message1->GetDescriptor()->full_name()
306 << "\") is not compatible with this reflection object (which is for type \""
307 << descriptor_->full_name()
308 << "\"). Note that the exact same class is required; not just the same "
310 GOOGLE_CHECK_EQ(message2->GetReflection(), this)
311 << "Second argument to Swap() (of type \""
312 << message2->GetDescriptor()->full_name()
313 << "\") is not compatible with this reflection object (which is for type \""
314 << descriptor_->full_name()
315 << "\"). Note that the exact same class is required; not just the same "
318 uint32* has_bits1 = MutableHasBits(message1);
319 uint32* has_bits2 = MutableHasBits(message2);
320 int has_bits_size = (descriptor_->field_count() + 31) / 32;
322 for (int i = 0; i < has_bits_size; i++) {
323 std::swap(has_bits1[i], has_bits2[i]);
326 for (int i = 0; i < descriptor_->field_count(); i++) {
327 const FieldDescriptor* field = descriptor_->field(i);
328 if (field->is_repeated()) {
329 switch (field->cpp_type()) {
330 #define SWAP_ARRAYS(CPPTYPE, TYPE) \
331 case FieldDescriptor::CPPTYPE_##CPPTYPE: \
332 MutableRaw<RepeatedField<TYPE> >(message1, field)->Swap( \
333 MutableRaw<RepeatedField<TYPE> >(message2, field)); \
336 SWAP_ARRAYS(INT32 , int32 );
337 SWAP_ARRAYS(INT64 , int64 );
338 SWAP_ARRAYS(UINT32, uint32);
339 SWAP_ARRAYS(UINT64, uint64);
340 SWAP_ARRAYS(FLOAT , float );
341 SWAP_ARRAYS(DOUBLE, double);
342 SWAP_ARRAYS(BOOL , bool );
343 SWAP_ARRAYS(ENUM , int );
346 case FieldDescriptor::CPPTYPE_STRING:
347 case FieldDescriptor::CPPTYPE_MESSAGE:
348 MutableRaw<RepeatedPtrFieldBase>(message1, field)->Swap(
349 MutableRaw<RepeatedPtrFieldBase>(message2, field));
353 GOOGLE_LOG(FATAL) << "Unimplemented type: " << field->cpp_type();
356 switch (field->cpp_type()) {
357 #define SWAP_VALUES(CPPTYPE, TYPE) \
358 case FieldDescriptor::CPPTYPE_##CPPTYPE: \
359 std::swap(*MutableRaw<TYPE>(message1, field), \
360 *MutableRaw<TYPE>(message2, field)); \
363 SWAP_VALUES(INT32 , int32 );
364 SWAP_VALUES(INT64 , int64 );
365 SWAP_VALUES(UINT32, uint32);
366 SWAP_VALUES(UINT64, uint64);
367 SWAP_VALUES(FLOAT , float );
368 SWAP_VALUES(DOUBLE, double);
369 SWAP_VALUES(BOOL , bool );
370 SWAP_VALUES(ENUM , int );
372 case FieldDescriptor::CPPTYPE_MESSAGE:
373 std::swap(*MutableRaw<Message*>(message1, field),
374 *MutableRaw<Message*>(message2, field));
377 case FieldDescriptor::CPPTYPE_STRING:
378 switch (field->options().ctype()) {
379 default: // TODO(kenton): Support other string reps.
380 case FieldOptions::STRING:
381 std::swap(*MutableRaw<string*>(message1, field),
382 *MutableRaw<string*>(message2, field));
388 GOOGLE_LOG(FATAL) << "Unimplemented type: " << field->cpp_type();
393 if (extensions_offset_ != -1) {
394 MutableExtensionSet(message1)->Swap(MutableExtensionSet(message2));
397 MutableUnknownFields(message1)->Swap(MutableUnknownFields(message2));
400 // -------------------------------------------------------------------
402 bool GeneratedMessageReflection::HasField(const Message& message,
403 const FieldDescriptor* field) const {
404 USAGE_CHECK_MESSAGE_TYPE(HasField);
405 USAGE_CHECK_SINGULAR(HasField);
407 if (field->is_extension()) {
408 return GetExtensionSet(message).Has(field->number());
410 return HasBit(message, field);
414 int GeneratedMessageReflection::FieldSize(const Message& message,
415 const FieldDescriptor* field) const {
416 USAGE_CHECK_MESSAGE_TYPE(FieldSize);
417 USAGE_CHECK_REPEATED(FieldSize);
419 if (field->is_extension()) {
420 return GetExtensionSet(message).ExtensionSize(field->number());
422 switch (field->cpp_type()) {
423 #define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
424 case FieldDescriptor::CPPTYPE_##UPPERCASE : \
425 return GetRaw<RepeatedField<LOWERCASE> >(message, field).size()
427 HANDLE_TYPE( INT32, int32);
428 HANDLE_TYPE( INT64, int64);
429 HANDLE_TYPE(UINT32, uint32);
430 HANDLE_TYPE(UINT64, uint64);
431 HANDLE_TYPE(DOUBLE, double);
432 HANDLE_TYPE( FLOAT, float);
433 HANDLE_TYPE( BOOL, bool);
434 HANDLE_TYPE( ENUM, int);
437 case FieldDescriptor::CPPTYPE_STRING:
438 case FieldDescriptor::CPPTYPE_MESSAGE:
439 return GetRaw<RepeatedPtrFieldBase>(message, field).size();
442 GOOGLE_LOG(FATAL) << "Can't get here.";
447 void GeneratedMessageReflection::ClearField(
448 Message* message, const FieldDescriptor* field) const {
449 USAGE_CHECK_MESSAGE_TYPE(ClearField);
451 if (field->is_extension()) {
452 MutableExtensionSet(message)->ClearExtension(field->number());
453 } else if (!field->is_repeated()) {
454 if (HasBit(*message, field)) {
455 ClearBit(message, field);
457 // We need to set the field back to its default value.
458 switch (field->cpp_type()) {
459 #define CLEAR_TYPE(CPPTYPE, TYPE) \
460 case FieldDescriptor::CPPTYPE_##CPPTYPE: \
461 *MutableRaw<TYPE>(message, field) = \
462 field->default_value_##TYPE(); \
465 CLEAR_TYPE(INT32 , int32 );
466 CLEAR_TYPE(INT64 , int64 );
467 CLEAR_TYPE(UINT32, uint32);
468 CLEAR_TYPE(UINT64, uint64);
469 CLEAR_TYPE(FLOAT , float );
470 CLEAR_TYPE(DOUBLE, double);
471 CLEAR_TYPE(BOOL , bool );
474 case FieldDescriptor::CPPTYPE_ENUM:
475 *MutableRaw<int>(message, field) =
476 field->default_value_enum()->number();
479 case FieldDescriptor::CPPTYPE_STRING: {
480 switch (field->options().ctype()) {
481 default: // TODO(kenton): Support other string reps.
482 case FieldOptions::STRING:
483 const string* default_ptr = DefaultRaw<const string*>(field);
484 string** value = MutableRaw<string*>(message, field);
485 if (*value != default_ptr) {
486 if (field->has_default_value()) {
487 (*value)->assign(field->default_value_string());
497 case FieldDescriptor::CPPTYPE_MESSAGE:
498 (*MutableRaw<Message*>(message, field))->Clear();
503 switch (field->cpp_type()) {
504 #define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
505 case FieldDescriptor::CPPTYPE_##UPPERCASE : \
506 MutableRaw<RepeatedField<LOWERCASE> >(message, field)->Clear(); \
509 HANDLE_TYPE( INT32, int32);
510 HANDLE_TYPE( INT64, int64);
511 HANDLE_TYPE(UINT32, uint32);
512 HANDLE_TYPE(UINT64, uint64);
513 HANDLE_TYPE(DOUBLE, double);
514 HANDLE_TYPE( FLOAT, float);
515 HANDLE_TYPE( BOOL, bool);
516 HANDLE_TYPE( ENUM, int);
519 case FieldDescriptor::CPPTYPE_STRING: {
520 switch (field->options().ctype()) {
521 default: // TODO(kenton): Support other string reps.
522 case FieldOptions::STRING:
523 MutableRaw<RepeatedPtrField<string> >(message, field)->Clear();
529 case FieldDescriptor::CPPTYPE_MESSAGE: {
530 // We don't know which subclass of RepeatedPtrFieldBase the type is,
531 // so we use RepeatedPtrFieldBase directly.
532 MutableRaw<RepeatedPtrFieldBase>(message, field)
533 ->Clear<GenericTypeHandler<Message> >();
540 void GeneratedMessageReflection::RemoveLast(
542 const FieldDescriptor* field) const {
543 USAGE_CHECK_MESSAGE_TYPE(RemoveLast);
544 USAGE_CHECK_REPEATED(RemoveLast);
546 if (field->is_extension()) {
547 MutableExtensionSet(message)->RemoveLast(field->number());
549 switch (field->cpp_type()) {
550 #define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
551 case FieldDescriptor::CPPTYPE_##UPPERCASE : \
552 MutableRaw<RepeatedField<LOWERCASE> >(message, field)->RemoveLast(); \
555 HANDLE_TYPE( INT32, int32);
556 HANDLE_TYPE( INT64, int64);
557 HANDLE_TYPE(UINT32, uint32);
558 HANDLE_TYPE(UINT64, uint64);
559 HANDLE_TYPE(DOUBLE, double);
560 HANDLE_TYPE( FLOAT, float);
561 HANDLE_TYPE( BOOL, bool);
562 HANDLE_TYPE( ENUM, int);
565 case FieldDescriptor::CPPTYPE_STRING:
566 switch (field->options().ctype()) {
567 default: // TODO(kenton): Support other string reps.
568 case FieldOptions::STRING:
569 MutableRaw<RepeatedPtrField<string> >(message, field)->RemoveLast();
574 case FieldDescriptor::CPPTYPE_MESSAGE:
575 MutableRaw<RepeatedPtrFieldBase>(message, field)
576 ->RemoveLast<GenericTypeHandler<Message> >();
582 Message* GeneratedMessageReflection::ReleaseLast(
584 const FieldDescriptor* field) const {
585 USAGE_CHECK_ALL(ReleaseLast, REPEATED, MESSAGE);
587 if (field->is_extension()) {
588 return static_cast<Message*>(
589 MutableExtensionSet(message)->ReleaseLast(field->number()));
591 return MutableRaw<RepeatedPtrFieldBase>(message, field)
592 ->ReleaseLast<GenericTypeHandler<Message> >();
596 void GeneratedMessageReflection::SwapElements(
598 const FieldDescriptor* field,
601 USAGE_CHECK_MESSAGE_TYPE(Swap);
602 USAGE_CHECK_REPEATED(Swap);
604 if (field->is_extension()) {
605 MutableExtensionSet(message)->SwapElements(field->number(), index1, index2);
607 switch (field->cpp_type()) {
608 #define HANDLE_TYPE(UPPERCASE, LOWERCASE) \
609 case FieldDescriptor::CPPTYPE_##UPPERCASE : \
610 MutableRaw<RepeatedField<LOWERCASE> >(message, field) \
611 ->SwapElements(index1, index2); \
614 HANDLE_TYPE( INT32, int32);
615 HANDLE_TYPE( INT64, int64);
616 HANDLE_TYPE(UINT32, uint32);
617 HANDLE_TYPE(UINT64, uint64);
618 HANDLE_TYPE(DOUBLE, double);
619 HANDLE_TYPE( FLOAT, float);
620 HANDLE_TYPE( BOOL, bool);
621 HANDLE_TYPE( ENUM, int);
624 case FieldDescriptor::CPPTYPE_STRING:
625 case FieldDescriptor::CPPTYPE_MESSAGE:
626 MutableRaw<RepeatedPtrFieldBase>(message, field)
627 ->SwapElements(index1, index2);
634 // Comparison functor for sorting FieldDescriptors by field number.
635 struct FieldNumberSorter {
636 bool operator()(const FieldDescriptor* left,
637 const FieldDescriptor* right) const {
638 return left->number() < right->number();
643 void GeneratedMessageReflection::ListFields(
644 const Message& message,
645 vector<const FieldDescriptor*>* output) const {
648 // Optimization: The default instance never has any fields set.
649 if (&message == default_instance_) return;
651 for (int i = 0; i < descriptor_->field_count(); i++) {
652 const FieldDescriptor* field = descriptor_->field(i);
653 if (field->is_repeated()) {
654 if (FieldSize(message, field) > 0) {
655 output->push_back(field);
658 if (HasBit(message, field)) {
659 output->push_back(field);
664 if (extensions_offset_ != -1) {
665 GetExtensionSet(message).AppendToList(descriptor_, descriptor_pool_,
669 // ListFields() must sort output by field number.
670 sort(output->begin(), output->end(), FieldNumberSorter());
673 // -------------------------------------------------------------------
675 #undef DEFINE_PRIMITIVE_ACCESSORS
676 #define DEFINE_PRIMITIVE_ACCESSORS(TYPENAME, TYPE, PASSTYPE, CPPTYPE) \
677 PASSTYPE GeneratedMessageReflection::Get##TYPENAME( \
678 const Message& message, const FieldDescriptor* field) const { \
679 USAGE_CHECK_ALL(Get##TYPENAME, SINGULAR, CPPTYPE); \
680 if (field->is_extension()) { \
681 return GetExtensionSet(message).Get##TYPENAME( \
682 field->number(), field->default_value_##PASSTYPE()); \
684 return GetField<TYPE>(message, field); \
688 void GeneratedMessageReflection::Set##TYPENAME( \
689 Message* message, const FieldDescriptor* field, \
690 PASSTYPE value) const { \
691 USAGE_CHECK_ALL(Set##TYPENAME, SINGULAR, CPPTYPE); \
692 if (field->is_extension()) { \
693 return MutableExtensionSet(message)->Set##TYPENAME( \
694 field->number(), field->type(), value, field); \
696 SetField<TYPE>(message, field, value); \
700 PASSTYPE GeneratedMessageReflection::GetRepeated##TYPENAME( \
701 const Message& message, \
702 const FieldDescriptor* field, int index) const { \
703 USAGE_CHECK_ALL(GetRepeated##TYPENAME, REPEATED, CPPTYPE); \
704 if (field->is_extension()) { \
705 return GetExtensionSet(message).GetRepeated##TYPENAME( \
706 field->number(), index); \
708 return GetRepeatedField<TYPE>(message, field, index); \
712 void GeneratedMessageReflection::SetRepeated##TYPENAME( \
713 Message* message, const FieldDescriptor* field, \
714 int index, PASSTYPE value) const { \
715 USAGE_CHECK_ALL(SetRepeated##TYPENAME, REPEATED, CPPTYPE); \
716 if (field->is_extension()) { \
717 MutableExtensionSet(message)->SetRepeated##TYPENAME( \
718 field->number(), index, value); \
720 SetRepeatedField<TYPE>(message, field, index, value); \
724 void GeneratedMessageReflection::Add##TYPENAME( \
725 Message* message, const FieldDescriptor* field, \
726 PASSTYPE value) const { \
727 USAGE_CHECK_ALL(Add##TYPENAME, REPEATED, CPPTYPE); \
728 if (field->is_extension()) { \
729 MutableExtensionSet(message)->Add##TYPENAME( \
730 field->number(), field->type(), field->options().packed(), value, \
733 AddField<TYPE>(message, field, value); \
737 DEFINE_PRIMITIVE_ACCESSORS(Int32 , int32 , int32 , INT32 )
738 DEFINE_PRIMITIVE_ACCESSORS(Int64 , int64 , int64 , INT64 )
739 DEFINE_PRIMITIVE_ACCESSORS(UInt32, uint32, uint32, UINT32)
740 DEFINE_PRIMITIVE_ACCESSORS(UInt64, uint64, uint64, UINT64)
741 DEFINE_PRIMITIVE_ACCESSORS(Float , float , float , FLOAT )
742 DEFINE_PRIMITIVE_ACCESSORS(Double, double, double, DOUBLE)
743 DEFINE_PRIMITIVE_ACCESSORS(Bool , bool , bool , BOOL )
744 #undef DEFINE_PRIMITIVE_ACCESSORS
746 // -------------------------------------------------------------------
748 string GeneratedMessageReflection::GetString(
749 const Message& message, const FieldDescriptor* field) const {
750 USAGE_CHECK_ALL(GetString, SINGULAR, STRING);
751 if (field->is_extension()) {
752 return GetExtensionSet(message).GetString(field->number(),
753 field->default_value_string());
755 switch (field->options().ctype()) {
756 default: // TODO(kenton): Support other string reps.
757 case FieldOptions::STRING:
758 return *GetField<const string*>(message, field);
761 GOOGLE_LOG(FATAL) << "Can't get here.";
762 return kEmptyString; // Make compiler happy.
766 const string& GeneratedMessageReflection::GetStringReference(
767 const Message& message,
768 const FieldDescriptor* field, string* scratch) const {
769 USAGE_CHECK_ALL(GetStringReference, SINGULAR, STRING);
770 if (field->is_extension()) {
771 return GetExtensionSet(message).GetString(field->number(),
772 field->default_value_string());
774 switch (field->options().ctype()) {
775 default: // TODO(kenton): Support other string reps.
776 case FieldOptions::STRING:
777 return *GetField<const string*>(message, field);
780 GOOGLE_LOG(FATAL) << "Can't get here.";
781 return kEmptyString; // Make compiler happy.
786 void GeneratedMessageReflection::SetString(
787 Message* message, const FieldDescriptor* field,
788 const string& value) const {
789 USAGE_CHECK_ALL(SetString, SINGULAR, STRING);
790 if (field->is_extension()) {
791 return MutableExtensionSet(message)->SetString(field->number(),
792 field->type(), value, field);
794 switch (field->options().ctype()) {
795 default: // TODO(kenton): Support other string reps.
796 case FieldOptions::STRING: {
797 string** ptr = MutableField<string*>(message, field);
798 if (*ptr == DefaultRaw<const string*>(field)) {
799 *ptr = new string(value);
801 (*ptr)->assign(value);
810 string GeneratedMessageReflection::GetRepeatedString(
811 const Message& message, const FieldDescriptor* field, int index) const {
812 USAGE_CHECK_ALL(GetRepeatedString, REPEATED, STRING);
813 if (field->is_extension()) {
814 return GetExtensionSet(message).GetRepeatedString(field->number(), index);
816 switch (field->options().ctype()) {
817 default: // TODO(kenton): Support other string reps.
818 case FieldOptions::STRING:
819 return GetRepeatedPtrField<string>(message, field, index);
822 GOOGLE_LOG(FATAL) << "Can't get here.";
823 return kEmptyString; // Make compiler happy.
827 const string& GeneratedMessageReflection::GetRepeatedStringReference(
828 const Message& message, const FieldDescriptor* field,
829 int index, string* scratch) const {
830 USAGE_CHECK_ALL(GetRepeatedStringReference, REPEATED, STRING);
831 if (field->is_extension()) {
832 return GetExtensionSet(message).GetRepeatedString(field->number(), index);
834 switch (field->options().ctype()) {
835 default: // TODO(kenton): Support other string reps.
836 case FieldOptions::STRING:
837 return GetRepeatedPtrField<string>(message, field, index);
840 GOOGLE_LOG(FATAL) << "Can't get here.";
841 return kEmptyString; // Make compiler happy.
846 void GeneratedMessageReflection::SetRepeatedString(
847 Message* message, const FieldDescriptor* field,
848 int index, const string& value) const {
849 USAGE_CHECK_ALL(SetRepeatedString, REPEATED, STRING);
850 if (field->is_extension()) {
851 MutableExtensionSet(message)->SetRepeatedString(
852 field->number(), index, value);
854 switch (field->options().ctype()) {
855 default: // TODO(kenton): Support other string reps.
856 case FieldOptions::STRING:
857 *MutableRepeatedField<string>(message, field, index) = value;
864 void GeneratedMessageReflection::AddString(
865 Message* message, const FieldDescriptor* field,
866 const string& value) const {
867 USAGE_CHECK_ALL(AddString, REPEATED, STRING);
868 if (field->is_extension()) {
869 MutableExtensionSet(message)->AddString(field->number(),
870 field->type(), value, field);
872 switch (field->options().ctype()) {
873 default: // TODO(kenton): Support other string reps.
874 case FieldOptions::STRING:
875 *AddField<string>(message, field) = value;
882 // -------------------------------------------------------------------
884 const EnumValueDescriptor* GeneratedMessageReflection::GetEnum(
885 const Message& message, const FieldDescriptor* field) const {
886 USAGE_CHECK_ALL(GetEnum, SINGULAR, ENUM);
889 if (field->is_extension()) {
890 value = GetExtensionSet(message).GetEnum(
891 field->number(), field->default_value_enum()->number());
893 value = GetField<int>(message, field);
895 const EnumValueDescriptor* result =
896 field->enum_type()->FindValueByNumber(value);
897 GOOGLE_CHECK(result != NULL) << "Value " << value << " is not valid for field "
898 << field->full_name() << " of type "
899 << field->enum_type()->full_name() << ".";
903 void GeneratedMessageReflection::SetEnum(
904 Message* message, const FieldDescriptor* field,
905 const EnumValueDescriptor* value) const {
906 USAGE_CHECK_ALL(SetEnum, SINGULAR, ENUM);
907 USAGE_CHECK_ENUM_VALUE(SetEnum);
909 if (field->is_extension()) {
910 MutableExtensionSet(message)->SetEnum(field->number(), field->type(),
911 value->number(), field);
913 SetField<int>(message, field, value->number());
917 const EnumValueDescriptor* GeneratedMessageReflection::GetRepeatedEnum(
918 const Message& message, const FieldDescriptor* field, int index) const {
919 USAGE_CHECK_ALL(GetRepeatedEnum, REPEATED, ENUM);
922 if (field->is_extension()) {
923 value = GetExtensionSet(message).GetRepeatedEnum(field->number(), index);
925 value = GetRepeatedField<int>(message, field, index);
927 const EnumValueDescriptor* result =
928 field->enum_type()->FindValueByNumber(value);
929 GOOGLE_CHECK(result != NULL) << "Value " << value << " is not valid for field "
930 << field->full_name() << " of type "
931 << field->enum_type()->full_name() << ".";
935 void GeneratedMessageReflection::SetRepeatedEnum(
937 const FieldDescriptor* field, int index,
938 const EnumValueDescriptor* value) const {
939 USAGE_CHECK_ALL(SetRepeatedEnum, REPEATED, ENUM);
940 USAGE_CHECK_ENUM_VALUE(SetRepeatedEnum);
942 if (field->is_extension()) {
943 MutableExtensionSet(message)->SetRepeatedEnum(
944 field->number(), index, value->number());
946 SetRepeatedField<int>(message, field, index, value->number());
950 void GeneratedMessageReflection::AddEnum(
951 Message* message, const FieldDescriptor* field,
952 const EnumValueDescriptor* value) const {
953 USAGE_CHECK_ALL(AddEnum, REPEATED, ENUM);
954 USAGE_CHECK_ENUM_VALUE(AddEnum);
956 if (field->is_extension()) {
957 MutableExtensionSet(message)->AddEnum(field->number(), field->type(),
958 field->options().packed(),
959 value->number(), field);
961 AddField<int>(message, field, value->number());
965 // -------------------------------------------------------------------
967 const Message& GeneratedMessageReflection::GetMessage(
968 const Message& message, const FieldDescriptor* field,
969 MessageFactory* factory) const {
970 USAGE_CHECK_ALL(GetMessage, SINGULAR, MESSAGE);
972 if (factory == NULL) factory = message_factory_;
974 if (field->is_extension()) {
975 return static_cast<const Message&>(
976 GetExtensionSet(message).GetMessage(
977 field->number(), field->message_type(), factory));
979 const Message* result;
980 result = GetRaw<const Message*>(message, field);
981 if (result == NULL) {
982 result = DefaultRaw<const Message*>(field);
988 Message* GeneratedMessageReflection::MutableMessage(
989 Message* message, const FieldDescriptor* field,
990 MessageFactory* factory) const {
991 USAGE_CHECK_ALL(MutableMessage, SINGULAR, MESSAGE);
993 if (factory == NULL) factory = message_factory_;
995 if (field->is_extension()) {
996 return static_cast<Message*>(
997 MutableExtensionSet(message)->MutableMessage(field, factory));
1000 Message** result_holder = MutableField<Message*>(message, field);
1001 if (*result_holder == NULL) {
1002 const Message* default_message = DefaultRaw<const Message*>(field);
1003 *result_holder = default_message->New();
1005 result = *result_holder;
1010 Message* GeneratedMessageReflection::ReleaseMessage(
1012 const FieldDescriptor* field,
1013 MessageFactory* factory) const {
1014 USAGE_CHECK_ALL(ReleaseMessage, SINGULAR, MESSAGE);
1016 if (factory == NULL) factory = message_factory_;
1018 if (field->is_extension()) {
1019 return static_cast<Message*>(
1020 MutableExtensionSet(message)->ReleaseMessage(field, factory));
1022 ClearBit(message, field);
1023 Message** result = MutableRaw<Message*>(message, field);
1024 Message* ret = *result;
1030 const Message& GeneratedMessageReflection::GetRepeatedMessage(
1031 const Message& message, const FieldDescriptor* field, int index) const {
1032 USAGE_CHECK_ALL(GetRepeatedMessage, REPEATED, MESSAGE);
1034 if (field->is_extension()) {
1035 return static_cast<const Message&>(
1036 GetExtensionSet(message).GetRepeatedMessage(field->number(), index));
1038 return GetRaw<RepeatedPtrFieldBase>(message, field)
1039 .Get<GenericTypeHandler<Message> >(index);
1043 Message* GeneratedMessageReflection::MutableRepeatedMessage(
1044 Message* message, const FieldDescriptor* field, int index) const {
1045 USAGE_CHECK_ALL(MutableRepeatedMessage, REPEATED, MESSAGE);
1047 if (field->is_extension()) {
1048 return static_cast<Message*>(
1049 MutableExtensionSet(message)->MutableRepeatedMessage(
1050 field->number(), index));
1052 return MutableRaw<RepeatedPtrFieldBase>(message, field)
1053 ->Mutable<GenericTypeHandler<Message> >(index);
1057 Message* GeneratedMessageReflection::AddMessage(
1058 Message* message, const FieldDescriptor* field,
1059 MessageFactory* factory) const {
1060 USAGE_CHECK_ALL(AddMessage, REPEATED, MESSAGE);
1062 if (factory == NULL) factory = message_factory_;
1064 if (field->is_extension()) {
1065 return static_cast<Message*>(
1066 MutableExtensionSet(message)->AddMessage(field, factory));
1068 // We can't use AddField<Message>() because RepeatedPtrFieldBase doesn't
1069 // know how to allocate one.
1070 RepeatedPtrFieldBase* repeated =
1071 MutableRaw<RepeatedPtrFieldBase>(message, field);
1072 Message* result = repeated->AddFromCleared<GenericTypeHandler<Message> >();
1073 if (result == NULL) {
1074 // We must allocate a new object.
1075 const Message* prototype;
1076 if (repeated->size() == 0) {
1077 prototype = factory->GetPrototype(field->message_type());
1079 prototype = &repeated->Get<GenericTypeHandler<Message> >(0);
1081 result = prototype->New();
1082 repeated->AddAllocated<GenericTypeHandler<Message> >(result);
1088 void* GeneratedMessageReflection::MutableRawRepeatedField(
1089 Message* message, const FieldDescriptor* field,
1090 FieldDescriptor::CppType cpptype,
1091 int ctype, const Descriptor* desc) const {
1092 USAGE_CHECK_REPEATED("MutableRawRepeatedField");
1093 if (field->cpp_type() != cpptype)
1094 ReportReflectionUsageTypeError(descriptor_,
1095 field, "MutableRawRepeatedField", cpptype);
1097 GOOGLE_CHECK_EQ(field->options().ctype(), ctype) << "subtype mismatch";
1099 GOOGLE_CHECK_EQ(field->message_type(), desc) << "wrong submessage type";
1100 if (field->is_extension())
1101 return MutableExtensionSet(message)->MutableRawRepeatedField(
1104 return reinterpret_cast<uint8*>(message) + offsets_[field->index()];
1107 // -----------------------------------------------------------------------------
1109 const FieldDescriptor* GeneratedMessageReflection::FindKnownExtensionByName(
1110 const string& name) const {
1111 if (extensions_offset_ == -1) return NULL;
1113 const FieldDescriptor* result = descriptor_pool_->FindExtensionByName(name);
1114 if (result != NULL && result->containing_type() == descriptor_) {
1118 if (descriptor_->options().message_set_wire_format()) {
1119 // MessageSet extensions may be identified by type name.
1120 const Descriptor* type = descriptor_pool_->FindMessageTypeByName(name);
1122 // Look for a matching extension in the foreign type's scope.
1123 for (int i = 0; i < type->extension_count(); i++) {
1124 const FieldDescriptor* extension = type->extension(i);
1125 if (extension->containing_type() == descriptor_ &&
1126 extension->type() == FieldDescriptor::TYPE_MESSAGE &&
1127 extension->is_optional() &&
1128 extension->message_type() == type) {
1139 const FieldDescriptor* GeneratedMessageReflection::FindKnownExtensionByNumber(
1141 if (extensions_offset_ == -1) return NULL;
1142 return descriptor_pool_->FindExtensionByNumber(descriptor_, number);
1145 // ===================================================================
1146 // Some private helpers.
1148 // These simple template accessors obtain pointers (or references) to
1150 template <typename Type>
1151 inline const Type& GeneratedMessageReflection::GetRaw(
1152 const Message& message, const FieldDescriptor* field) const {
1153 const void* ptr = reinterpret_cast<const uint8*>(&message) +
1154 offsets_[field->index()];
1155 return *reinterpret_cast<const Type*>(ptr);
1158 template <typename Type>
1159 inline Type* GeneratedMessageReflection::MutableRaw(
1160 Message* message, const FieldDescriptor* field) const {
1161 void* ptr = reinterpret_cast<uint8*>(message) + offsets_[field->index()];
1162 return reinterpret_cast<Type*>(ptr);
1165 template <typename Type>
1166 inline const Type& GeneratedMessageReflection::DefaultRaw(
1167 const FieldDescriptor* field) const {
1168 const void* ptr = reinterpret_cast<const uint8*>(default_instance_) +
1169 offsets_[field->index()];
1170 return *reinterpret_cast<const Type*>(ptr);
1173 inline const uint32* GeneratedMessageReflection::GetHasBits(
1174 const Message& message) const {
1175 const void* ptr = reinterpret_cast<const uint8*>(&message) + has_bits_offset_;
1176 return reinterpret_cast<const uint32*>(ptr);
1178 inline uint32* GeneratedMessageReflection::MutableHasBits(
1179 Message* message) const {
1180 void* ptr = reinterpret_cast<uint8*>(message) + has_bits_offset_;
1181 return reinterpret_cast<uint32*>(ptr);
1184 inline const ExtensionSet& GeneratedMessageReflection::GetExtensionSet(
1185 const Message& message) const {
1186 GOOGLE_DCHECK_NE(extensions_offset_, -1);
1187 const void* ptr = reinterpret_cast<const uint8*>(&message) +
1189 return *reinterpret_cast<const ExtensionSet*>(ptr);
1191 inline ExtensionSet* GeneratedMessageReflection::MutableExtensionSet(
1192 Message* message) const {
1193 GOOGLE_DCHECK_NE(extensions_offset_, -1);
1194 void* ptr = reinterpret_cast<uint8*>(message) + extensions_offset_;
1195 return reinterpret_cast<ExtensionSet*>(ptr);
1198 // Simple accessors for manipulating has_bits_.
1199 inline bool GeneratedMessageReflection::HasBit(
1200 const Message& message, const FieldDescriptor* field) const {
1201 return GetHasBits(message)[field->index() / 32] &
1202 (1 << (field->index() % 32));
1205 inline void GeneratedMessageReflection::SetBit(
1206 Message* message, const FieldDescriptor* field) const {
1207 MutableHasBits(message)[field->index() / 32] |= (1 << (field->index() % 32));
1210 inline void GeneratedMessageReflection::ClearBit(
1211 Message* message, const FieldDescriptor* field) const {
1212 MutableHasBits(message)[field->index() / 32] &= ~(1 << (field->index() % 32));
1215 // Template implementations of basic accessors. Inline because each
1216 // template instance is only called from one location. These are
1217 // used for all types except messages.
1218 template <typename Type>
1219 inline const Type& GeneratedMessageReflection::GetField(
1220 const Message& message, const FieldDescriptor* field) const {
1221 return GetRaw<Type>(message, field);
1224 template <typename Type>
1225 inline void GeneratedMessageReflection::SetField(
1226 Message* message, const FieldDescriptor* field, const Type& value) const {
1227 *MutableRaw<Type>(message, field) = value;
1228 SetBit(message, field);
1231 template <typename Type>
1232 inline Type* GeneratedMessageReflection::MutableField(
1233 Message* message, const FieldDescriptor* field) const {
1234 SetBit(message, field);
1235 return MutableRaw<Type>(message, field);
1238 template <typename Type>
1239 inline const Type& GeneratedMessageReflection::GetRepeatedField(
1240 const Message& message, const FieldDescriptor* field, int index) const {
1241 return GetRaw<RepeatedField<Type> >(message, field).Get(index);
1244 template <typename Type>
1245 inline const Type& GeneratedMessageReflection::GetRepeatedPtrField(
1246 const Message& message, const FieldDescriptor* field, int index) const {
1247 return GetRaw<RepeatedPtrField<Type> >(message, field).Get(index);
1250 template <typename Type>
1251 inline void GeneratedMessageReflection::SetRepeatedField(
1252 Message* message, const FieldDescriptor* field,
1253 int index, Type value) const {
1254 MutableRaw<RepeatedField<Type> >(message, field)->Set(index, value);
1257 template <typename Type>
1258 inline Type* GeneratedMessageReflection::MutableRepeatedField(
1259 Message* message, const FieldDescriptor* field, int index) const {
1260 RepeatedPtrField<Type>* repeated =
1261 MutableRaw<RepeatedPtrField<Type> >(message, field);
1262 return repeated->Mutable(index);
1265 template <typename Type>
1266 inline void GeneratedMessageReflection::AddField(
1267 Message* message, const FieldDescriptor* field, const Type& value) const {
1268 MutableRaw<RepeatedField<Type> >(message, field)->Add(value);
1271 template <typename Type>
1272 inline Type* GeneratedMessageReflection::AddField(
1273 Message* message, const FieldDescriptor* field) const {
1274 RepeatedPtrField<Type>* repeated =
1275 MutableRaw<RepeatedPtrField<Type> >(message, field);
1276 return repeated->Add();
1279 } // namespace internal
1280 } // namespace protobuf
1281 } // namespace google