Commit 2b3aa1c2 authored by dmaclach's avatar dmaclach Committed by Thomas Van Lenten

Add Setter/Getter type verification. (#3880)

Add runtime asserts (that can be disabled in release) that verify
that the types being get/set for messages using the C Api match
the type in the descriptor for the field being get/set.
parent 8537f1e6
...@@ -49,6 +49,19 @@ static void AppendTextFormatForMessage(GPBMessage *message, ...@@ -49,6 +49,19 @@ static void AppendTextFormatForMessage(GPBMessage *message,
NSMutableString *toStr, NSMutableString *toStr,
NSString *lineIndent); NSString *lineIndent);
// Are two datatypes the same basic type representation (ex Int32 and SInt32).
// Marked unused because currently only called from asserts/debug.
static BOOL DataTypesEquivalent(GPBDataType type1,
GPBDataType type2) __attribute__ ((unused));
// Basic type representation for a type (ex: for SInt32 it is Int32).
// Marked unused because currently only called from asserts/debug.
static GPBDataType BaseDataType(GPBDataType type) __attribute__ ((unused));
// String name for a data type.
// Marked unused because currently only called from asserts/debug.
static NSString *TypeToString(GPBDataType dataType) __attribute__ ((unused));
NSData *GPBEmptyNSData(void) { NSData *GPBEmptyNSData(void) {
static dispatch_once_t onceToken; static dispatch_once_t onceToken;
static NSData *defaultNSData = nil; static NSData *defaultNSData = nil;
...@@ -342,6 +355,14 @@ void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof, ...@@ -342,6 +355,14 @@ void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof,
//%PDDM-DEFINE IVAR_POD_ACCESSORS_DEFN(NAME, TYPE) //%PDDM-DEFINE IVAR_POD_ACCESSORS_DEFN(NAME, TYPE)
//%TYPE GPBGetMessage##NAME##Field(GPBMessage *self, //%TYPE GPBGetMessage##NAME##Field(GPBMessage *self,
//% TYPE$S NAME$S GPBFieldDescriptor *field) { //% TYPE$S NAME$S GPBFieldDescriptor *field) {
//%#if defined(DEBUG) && DEBUG
//% NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
//% GPBDataType##NAME),
//% @"Attempting to get value of TYPE from field %@ "
//% @"of %@ which is of type %@.",
//% [self class], field.name,
//% TypeToString(GPBGetFieldDataType(field)));
//%#endif
//% if (GPBGetHasIvarField(self, field)) { //% if (GPBGetHasIvarField(self, field)) {
//% uint8_t *storage = (uint8_t *)self->messageStorage_; //% uint8_t *storage = (uint8_t *)self->messageStorage_;
//% TYPE *typePtr = (TYPE *)&storage[field->description_->offset]; //% TYPE *typePtr = (TYPE *)&storage[field->description_->offset];
...@@ -364,14 +385,24 @@ void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof, ...@@ -364,14 +385,24 @@ void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof,
//% NAME$S GPBFieldDescriptor *field, //% NAME$S GPBFieldDescriptor *field,
//% NAME$S TYPE value, //% NAME$S TYPE value,
//% NAME$S GPBFileSyntax syntax) { //% NAME$S GPBFileSyntax syntax) {
//%#if defined(DEBUG) && DEBUG
//% NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
//% GPBDataType##NAME),
//% @"Attempting to set field %@ of %@ which is of type %@ with "
//% @"value of type TYPE.",
//% [self class], field.name,
//% TypeToString(GPBGetFieldDataType(field)));
//%#endif
//% GPBOneofDescriptor *oneof = field->containingOneof_; //% GPBOneofDescriptor *oneof = field->containingOneof_;
//% if (oneof) { //% if (oneof) {
//% GPBMessageFieldDescription *fieldDesc = field->description_; //% GPBMessageFieldDescription *fieldDesc = field->description_;
//% GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number); //% GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number);
//% } //% }
//%#if defined(DEBUG) && DEBUG
//% NSCAssert(self->messageStorage_ != NULL, //% NSCAssert(self->messageStorage_ != NULL,
//% @"%@: All messages should have storage (from init)", //% @"%@: All messages should have storage (from init)",
//% [self class]); //% [self class]);
//%#endif
//%#if defined(__clang_analyzer__) //%#if defined(__clang_analyzer__)
//% if (self->messageStorage_ == NULL) return; //% if (self->messageStorage_ == NULL) return;
//%#endif //%#endif
...@@ -391,6 +422,14 @@ void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof, ...@@ -391,6 +422,14 @@ void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof,
//%// Only exists for public api, no core code should use this. //%// Only exists for public api, no core code should use this.
//%TYPE *GPBGetMessage##NAME##Field(GPBMessage *self, //%TYPE *GPBGetMessage##NAME##Field(GPBMessage *self,
//% TYPE$S NAME$S GPBFieldDescriptor *field) { //% TYPE$S NAME$S GPBFieldDescriptor *field) {
//%#if defined(DEBUG) && DEBUG
//% NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
//% GPBDataType##NAME),
//% @"Attempting to get value of TYPE from field %@ "
//% @"of %@ which is of type %@.",
//% [self class], field.name,
//% TypeToString(GPBGetFieldDataType(field)));
//%#endif
//% return (TYPE *)GPBGetObjectIvarWithField(self, field); //% return (TYPE *)GPBGetObjectIvarWithField(self, field);
//%} //%}
//% //%
...@@ -398,6 +437,14 @@ void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof, ...@@ -398,6 +437,14 @@ void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof,
//%void GPBSetMessage##NAME##Field(GPBMessage *self, //%void GPBSetMessage##NAME##Field(GPBMessage *self,
//% NAME$S GPBFieldDescriptor *field, //% NAME$S GPBFieldDescriptor *field,
//% NAME$S TYPE *value) { //% NAME$S TYPE *value) {
//%#if defined(DEBUG) && DEBUG
//% NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
//% GPBDataType##NAME),
//% @"Attempting to set field %@ of %@ which is of type %@ with "
//% @"value of type TYPE.",
//% [self class], field.name,
//% TypeToString(GPBGetFieldDataType(field)));
//%#endif
//% GPBSetObjectIvarWithField(self, field, (id)value); //% GPBSetObjectIvarWithField(self, field, (id)value);
//%} //%}
//% //%
...@@ -455,7 +502,7 @@ void GPBSetRetainedObjectIvarWithFieldInternal(GPBMessage *self, ...@@ -455,7 +502,7 @@ void GPBSetRetainedObjectIvarWithFieldInternal(GPBMessage *self,
GPBDataType fieldType = GPBGetFieldDataType(field); GPBDataType fieldType = GPBGetFieldDataType(field);
BOOL isMapOrArray = GPBFieldIsMapOrArray(field); BOOL isMapOrArray = GPBFieldIsMapOrArray(field);
BOOL fieldIsMessage = GPBDataTypeIsMessage(fieldType); BOOL fieldIsMessage = GPBDataTypeIsMessage(fieldType);
#ifdef DEBUG #if defined(DEBUG) && DEBUG
if (value == nil && !isMapOrArray && !fieldIsMessage && if (value == nil && !isMapOrArray && !fieldIsMessage &&
field.hasDefaultValue) { field.hasDefaultValue) {
// Setting a message to nil is an obvious way to "clear" the value // Setting a message to nil is an obvious way to "clear" the value
...@@ -618,6 +665,13 @@ int32_t GPBGetMessageEnumField(GPBMessage *self, GPBFieldDescriptor *field) { ...@@ -618,6 +665,13 @@ int32_t GPBGetMessageEnumField(GPBMessage *self, GPBFieldDescriptor *field) {
int32_t GPBGetEnumIvarWithFieldInternal(GPBMessage *self, int32_t GPBGetEnumIvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(GPBGetFieldDataType(field) == GPBDataTypeEnum,
@"Attempting to get value of type Enum from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
int32_t result = GPBGetMessageInt32Field(self, field); int32_t result = GPBGetMessageInt32Field(self, field);
// If this is presevering unknown enums, make sure the value is valid before // If this is presevering unknown enums, make sure the value is valid before
// returning it. // returning it.
...@@ -638,6 +692,13 @@ void GPBSetMessageEnumField(GPBMessage *self, GPBFieldDescriptor *field, ...@@ -638,6 +692,13 @@ void GPBSetMessageEnumField(GPBMessage *self, GPBFieldDescriptor *field,
void GPBSetEnumIvarWithFieldInternal(GPBMessage *self, void GPBSetEnumIvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, int32_t value, GPBFieldDescriptor *field, int32_t value,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(GPBGetFieldDataType(field) == GPBDataTypeEnum,
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type Enum.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
// Don't allow in unknown values. Proto3 can use the Raw method. // Don't allow in unknown values. Proto3 can use the Raw method.
if (![field isValidEnumValue:value]) { if (![field isValidEnumValue:value]) {
[NSException raise:NSInvalidArgumentException [NSException raise:NSInvalidArgumentException
...@@ -663,6 +724,13 @@ void GPBSetMessageRawEnumField(GPBMessage *self, GPBFieldDescriptor *field, ...@@ -663,6 +724,13 @@ void GPBSetMessageRawEnumField(GPBMessage *self, GPBFieldDescriptor *field,
BOOL GPBGetMessageBoolField(GPBMessage *self, BOOL GPBGetMessageBoolField(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field), GPBDataTypeBool),
@"Attempting to get value of type bool from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
if (GPBGetHasIvarField(self, field)) { if (GPBGetHasIvarField(self, field)) {
// Bools are stored in the has bits to avoid needing explicit space in the // Bools are stored in the has bits to avoid needing explicit space in the
// storage structure. // storage structure.
...@@ -688,6 +756,13 @@ void GPBSetBoolIvarWithFieldInternal(GPBMessage *self, ...@@ -688,6 +756,13 @@ void GPBSetBoolIvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
BOOL value, BOOL value,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field), GPBDataTypeBool),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type bool.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBMessageFieldDescription *fieldDesc = field->description_; GPBMessageFieldDescription *fieldDesc = field->description_;
GPBOneofDescriptor *oneof = field->containingOneof_; GPBOneofDescriptor *oneof = field->containingOneof_;
if (oneof) { if (oneof) {
...@@ -714,6 +789,14 @@ void GPBSetBoolIvarWithFieldInternal(GPBMessage *self, ...@@ -714,6 +789,14 @@ void GPBSetBoolIvarWithFieldInternal(GPBMessage *self,
int32_t GPBGetMessageInt32Field(GPBMessage *self, int32_t GPBGetMessageInt32Field(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeInt32),
@"Attempting to get value of int32_t from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
if (GPBGetHasIvarField(self, field)) { if (GPBGetHasIvarField(self, field)) {
uint8_t *storage = (uint8_t *)self->messageStorage_; uint8_t *storage = (uint8_t *)self->messageStorage_;
int32_t *typePtr = (int32_t *)&storage[field->description_->offset]; int32_t *typePtr = (int32_t *)&storage[field->description_->offset];
...@@ -736,14 +819,24 @@ void GPBSetInt32IvarWithFieldInternal(GPBMessage *self, ...@@ -736,14 +819,24 @@ void GPBSetInt32IvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
int32_t value, int32_t value,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeInt32),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type int32_t.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBOneofDescriptor *oneof = field->containingOneof_; GPBOneofDescriptor *oneof = field->containingOneof_;
if (oneof) { if (oneof) {
GPBMessageFieldDescription *fieldDesc = field->description_; GPBMessageFieldDescription *fieldDesc = field->description_;
GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number); GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number);
} }
#if defined(DEBUG) && DEBUG
NSCAssert(self->messageStorage_ != NULL, NSCAssert(self->messageStorage_ != NULL,
@"%@: All messages should have storage (from init)", @"%@: All messages should have storage (from init)",
[self class]); [self class]);
#endif
#if defined(__clang_analyzer__) #if defined(__clang_analyzer__)
if (self->messageStorage_ == NULL) return; if (self->messageStorage_ == NULL) return;
#endif #endif
...@@ -764,6 +857,14 @@ void GPBSetInt32IvarWithFieldInternal(GPBMessage *self, ...@@ -764,6 +857,14 @@ void GPBSetInt32IvarWithFieldInternal(GPBMessage *self,
uint32_t GPBGetMessageUInt32Field(GPBMessage *self, uint32_t GPBGetMessageUInt32Field(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeUInt32),
@"Attempting to get value of uint32_t from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
if (GPBGetHasIvarField(self, field)) { if (GPBGetHasIvarField(self, field)) {
uint8_t *storage = (uint8_t *)self->messageStorage_; uint8_t *storage = (uint8_t *)self->messageStorage_;
uint32_t *typePtr = (uint32_t *)&storage[field->description_->offset]; uint32_t *typePtr = (uint32_t *)&storage[field->description_->offset];
...@@ -786,14 +887,24 @@ void GPBSetUInt32IvarWithFieldInternal(GPBMessage *self, ...@@ -786,14 +887,24 @@ void GPBSetUInt32IvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
uint32_t value, uint32_t value,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeUInt32),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type uint32_t.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBOneofDescriptor *oneof = field->containingOneof_; GPBOneofDescriptor *oneof = field->containingOneof_;
if (oneof) { if (oneof) {
GPBMessageFieldDescription *fieldDesc = field->description_; GPBMessageFieldDescription *fieldDesc = field->description_;
GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number); GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number);
} }
#if defined(DEBUG) && DEBUG
NSCAssert(self->messageStorage_ != NULL, NSCAssert(self->messageStorage_ != NULL,
@"%@: All messages should have storage (from init)", @"%@: All messages should have storage (from init)",
[self class]); [self class]);
#endif
#if defined(__clang_analyzer__) #if defined(__clang_analyzer__)
if (self->messageStorage_ == NULL) return; if (self->messageStorage_ == NULL) return;
#endif #endif
...@@ -814,6 +925,14 @@ void GPBSetUInt32IvarWithFieldInternal(GPBMessage *self, ...@@ -814,6 +925,14 @@ void GPBSetUInt32IvarWithFieldInternal(GPBMessage *self,
int64_t GPBGetMessageInt64Field(GPBMessage *self, int64_t GPBGetMessageInt64Field(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeInt64),
@"Attempting to get value of int64_t from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
if (GPBGetHasIvarField(self, field)) { if (GPBGetHasIvarField(self, field)) {
uint8_t *storage = (uint8_t *)self->messageStorage_; uint8_t *storage = (uint8_t *)self->messageStorage_;
int64_t *typePtr = (int64_t *)&storage[field->description_->offset]; int64_t *typePtr = (int64_t *)&storage[field->description_->offset];
...@@ -836,14 +955,24 @@ void GPBSetInt64IvarWithFieldInternal(GPBMessage *self, ...@@ -836,14 +955,24 @@ void GPBSetInt64IvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
int64_t value, int64_t value,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeInt64),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type int64_t.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBOneofDescriptor *oneof = field->containingOneof_; GPBOneofDescriptor *oneof = field->containingOneof_;
if (oneof) { if (oneof) {
GPBMessageFieldDescription *fieldDesc = field->description_; GPBMessageFieldDescription *fieldDesc = field->description_;
GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number); GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number);
} }
#if defined(DEBUG) && DEBUG
NSCAssert(self->messageStorage_ != NULL, NSCAssert(self->messageStorage_ != NULL,
@"%@: All messages should have storage (from init)", @"%@: All messages should have storage (from init)",
[self class]); [self class]);
#endif
#if defined(__clang_analyzer__) #if defined(__clang_analyzer__)
if (self->messageStorage_ == NULL) return; if (self->messageStorage_ == NULL) return;
#endif #endif
...@@ -864,6 +993,14 @@ void GPBSetInt64IvarWithFieldInternal(GPBMessage *self, ...@@ -864,6 +993,14 @@ void GPBSetInt64IvarWithFieldInternal(GPBMessage *self,
uint64_t GPBGetMessageUInt64Field(GPBMessage *self, uint64_t GPBGetMessageUInt64Field(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeUInt64),
@"Attempting to get value of uint64_t from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
if (GPBGetHasIvarField(self, field)) { if (GPBGetHasIvarField(self, field)) {
uint8_t *storage = (uint8_t *)self->messageStorage_; uint8_t *storage = (uint8_t *)self->messageStorage_;
uint64_t *typePtr = (uint64_t *)&storage[field->description_->offset]; uint64_t *typePtr = (uint64_t *)&storage[field->description_->offset];
...@@ -886,14 +1023,24 @@ void GPBSetUInt64IvarWithFieldInternal(GPBMessage *self, ...@@ -886,14 +1023,24 @@ void GPBSetUInt64IvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
uint64_t value, uint64_t value,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeUInt64),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type uint64_t.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBOneofDescriptor *oneof = field->containingOneof_; GPBOneofDescriptor *oneof = field->containingOneof_;
if (oneof) { if (oneof) {
GPBMessageFieldDescription *fieldDesc = field->description_; GPBMessageFieldDescription *fieldDesc = field->description_;
GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number); GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number);
} }
#if defined(DEBUG) && DEBUG
NSCAssert(self->messageStorage_ != NULL, NSCAssert(self->messageStorage_ != NULL,
@"%@: All messages should have storage (from init)", @"%@: All messages should have storage (from init)",
[self class]); [self class]);
#endif
#if defined(__clang_analyzer__) #if defined(__clang_analyzer__)
if (self->messageStorage_ == NULL) return; if (self->messageStorage_ == NULL) return;
#endif #endif
...@@ -914,6 +1061,14 @@ void GPBSetUInt64IvarWithFieldInternal(GPBMessage *self, ...@@ -914,6 +1061,14 @@ void GPBSetUInt64IvarWithFieldInternal(GPBMessage *self,
float GPBGetMessageFloatField(GPBMessage *self, float GPBGetMessageFloatField(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeFloat),
@"Attempting to get value of float from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
if (GPBGetHasIvarField(self, field)) { if (GPBGetHasIvarField(self, field)) {
uint8_t *storage = (uint8_t *)self->messageStorage_; uint8_t *storage = (uint8_t *)self->messageStorage_;
float *typePtr = (float *)&storage[field->description_->offset]; float *typePtr = (float *)&storage[field->description_->offset];
...@@ -936,14 +1091,24 @@ void GPBSetFloatIvarWithFieldInternal(GPBMessage *self, ...@@ -936,14 +1091,24 @@ void GPBSetFloatIvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
float value, float value,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeFloat),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type float.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBOneofDescriptor *oneof = field->containingOneof_; GPBOneofDescriptor *oneof = field->containingOneof_;
if (oneof) { if (oneof) {
GPBMessageFieldDescription *fieldDesc = field->description_; GPBMessageFieldDescription *fieldDesc = field->description_;
GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number); GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number);
} }
#if defined(DEBUG) && DEBUG
NSCAssert(self->messageStorage_ != NULL, NSCAssert(self->messageStorage_ != NULL,
@"%@: All messages should have storage (from init)", @"%@: All messages should have storage (from init)",
[self class]); [self class]);
#endif
#if defined(__clang_analyzer__) #if defined(__clang_analyzer__)
if (self->messageStorage_ == NULL) return; if (self->messageStorage_ == NULL) return;
#endif #endif
...@@ -964,6 +1129,14 @@ void GPBSetFloatIvarWithFieldInternal(GPBMessage *self, ...@@ -964,6 +1129,14 @@ void GPBSetFloatIvarWithFieldInternal(GPBMessage *self,
double GPBGetMessageDoubleField(GPBMessage *self, double GPBGetMessageDoubleField(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeDouble),
@"Attempting to get value of double from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
if (GPBGetHasIvarField(self, field)) { if (GPBGetHasIvarField(self, field)) {
uint8_t *storage = (uint8_t *)self->messageStorage_; uint8_t *storage = (uint8_t *)self->messageStorage_;
double *typePtr = (double *)&storage[field->description_->offset]; double *typePtr = (double *)&storage[field->description_->offset];
...@@ -986,14 +1159,24 @@ void GPBSetDoubleIvarWithFieldInternal(GPBMessage *self, ...@@ -986,14 +1159,24 @@ void GPBSetDoubleIvarWithFieldInternal(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
double value, double value,
GPBFileSyntax syntax) { GPBFileSyntax syntax) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeDouble),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type double.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBOneofDescriptor *oneof = field->containingOneof_; GPBOneofDescriptor *oneof = field->containingOneof_;
if (oneof) { if (oneof) {
GPBMessageFieldDescription *fieldDesc = field->description_; GPBMessageFieldDescription *fieldDesc = field->description_;
GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number); GPBMaybeClearOneof(self, oneof, fieldDesc->hasIndex, fieldDesc->number);
} }
#if defined(DEBUG) && DEBUG
NSCAssert(self->messageStorage_ != NULL, NSCAssert(self->messageStorage_ != NULL,
@"%@: All messages should have storage (from init)", @"%@: All messages should have storage (from init)",
[self class]); [self class]);
#endif
#if defined(__clang_analyzer__) #if defined(__clang_analyzer__)
if (self->messageStorage_ == NULL) return; if (self->messageStorage_ == NULL) return;
#endif #endif
...@@ -1019,6 +1202,14 @@ void GPBSetDoubleIvarWithFieldInternal(GPBMessage *self, ...@@ -1019,6 +1202,14 @@ void GPBSetDoubleIvarWithFieldInternal(GPBMessage *self,
// Only exists for public api, no core code should use this. // Only exists for public api, no core code should use this.
NSString *GPBGetMessageStringField(GPBMessage *self, NSString *GPBGetMessageStringField(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeString),
@"Attempting to get value of NSString from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
return (NSString *)GPBGetObjectIvarWithField(self, field); return (NSString *)GPBGetObjectIvarWithField(self, field);
} }
...@@ -1026,6 +1217,14 @@ NSString *GPBGetMessageStringField(GPBMessage *self, ...@@ -1026,6 +1217,14 @@ NSString *GPBGetMessageStringField(GPBMessage *self,
void GPBSetMessageStringField(GPBMessage *self, void GPBSetMessageStringField(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
NSString *value) { NSString *value) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeString),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type NSString.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBSetObjectIvarWithField(self, field, (id)value); GPBSetObjectIvarWithField(self, field, (id)value);
} }
...@@ -1035,6 +1234,14 @@ void GPBSetMessageStringField(GPBMessage *self, ...@@ -1035,6 +1234,14 @@ void GPBSetMessageStringField(GPBMessage *self,
// Only exists for public api, no core code should use this. // Only exists for public api, no core code should use this.
NSData *GPBGetMessageBytesField(GPBMessage *self, NSData *GPBGetMessageBytesField(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeBytes),
@"Attempting to get value of NSData from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
return (NSData *)GPBGetObjectIvarWithField(self, field); return (NSData *)GPBGetObjectIvarWithField(self, field);
} }
...@@ -1042,6 +1249,14 @@ NSData *GPBGetMessageBytesField(GPBMessage *self, ...@@ -1042,6 +1249,14 @@ NSData *GPBGetMessageBytesField(GPBMessage *self,
void GPBSetMessageBytesField(GPBMessage *self, void GPBSetMessageBytesField(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
NSData *value) { NSData *value) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeBytes),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type NSData.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBSetObjectIvarWithField(self, field, (id)value); GPBSetObjectIvarWithField(self, field, (id)value);
} }
...@@ -1051,6 +1266,14 @@ void GPBSetMessageBytesField(GPBMessage *self, ...@@ -1051,6 +1266,14 @@ void GPBSetMessageBytesField(GPBMessage *self,
// Only exists for public api, no core code should use this. // Only exists for public api, no core code should use this.
GPBMessage *GPBGetMessageMessageField(GPBMessage *self, GPBMessage *GPBGetMessageMessageField(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeMessage),
@"Attempting to get value of GPBMessage from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
return (GPBMessage *)GPBGetObjectIvarWithField(self, field); return (GPBMessage *)GPBGetObjectIvarWithField(self, field);
} }
...@@ -1058,6 +1281,14 @@ GPBMessage *GPBGetMessageMessageField(GPBMessage *self, ...@@ -1058,6 +1281,14 @@ GPBMessage *GPBGetMessageMessageField(GPBMessage *self,
void GPBSetMessageMessageField(GPBMessage *self, void GPBSetMessageMessageField(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
GPBMessage *value) { GPBMessage *value) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeMessage),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type GPBMessage.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBSetObjectIvarWithField(self, field, (id)value); GPBSetObjectIvarWithField(self, field, (id)value);
} }
...@@ -1067,6 +1298,14 @@ void GPBSetMessageMessageField(GPBMessage *self, ...@@ -1067,6 +1298,14 @@ void GPBSetMessageMessageField(GPBMessage *self,
// Only exists for public api, no core code should use this. // Only exists for public api, no core code should use this.
GPBMessage *GPBGetMessageGroupField(GPBMessage *self, GPBMessage *GPBGetMessageGroupField(GPBMessage *self,
GPBFieldDescriptor *field) { GPBFieldDescriptor *field) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeGroup),
@"Attempting to get value of GPBMessage from field %@ "
@"of %@ which is of type %@.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
return (GPBMessage *)GPBGetObjectIvarWithField(self, field); return (GPBMessage *)GPBGetObjectIvarWithField(self, field);
} }
...@@ -1074,6 +1313,14 @@ GPBMessage *GPBGetMessageGroupField(GPBMessage *self, ...@@ -1074,6 +1313,14 @@ GPBMessage *GPBGetMessageGroupField(GPBMessage *self,
void GPBSetMessageGroupField(GPBMessage *self, void GPBSetMessageGroupField(GPBMessage *self,
GPBFieldDescriptor *field, GPBFieldDescriptor *field,
GPBMessage *value) { GPBMessage *value) {
#if defined(DEBUG) && DEBUG
NSCAssert(DataTypesEquivalent(GPBGetFieldDataType(field),
GPBDataTypeGroup),
@"Attempting to set field %@ of %@ which is of type %@ with "
@"value of type GPBMessage.",
[self class], field.name,
TypeToString(GPBGetFieldDataType(field)));
#endif
GPBSetObjectIvarWithField(self, field, (id)value); GPBSetObjectIvarWithField(self, field, (id)value);
} }
...@@ -1137,8 +1384,40 @@ void GPBSetMessageRepeatedField(GPBMessage *self, GPBFieldDescriptor *field, id ...@@ -1137,8 +1384,40 @@ void GPBSetMessageRepeatedField(GPBMessage *self, GPBFieldDescriptor *field, id
GPBSetObjectIvarWithField(self, field, array); GPBSetObjectIvarWithField(self, field, array);
} }
#if defined(DEBUG) && DEBUG static GPBDataType BaseDataType(GPBDataType type) {
static NSString *TypeToStr(GPBDataType dataType) { switch (type) {
case GPBDataTypeSFixed32:
case GPBDataTypeInt32:
case GPBDataTypeSInt32:
case GPBDataTypeEnum:
return GPBDataTypeInt32;
case GPBDataTypeFixed32:
case GPBDataTypeUInt32:
return GPBDataTypeUInt32;
case GPBDataTypeSFixed64:
case GPBDataTypeInt64:
case GPBDataTypeSInt64:
return GPBDataTypeInt64;
case GPBDataTypeFixed64:
case GPBDataTypeUInt64:
return GPBDataTypeUInt64;
case GPBDataTypeMessage:
case GPBDataTypeGroup:
return GPBDataTypeMessage;
case GPBDataTypeBool:
case GPBDataTypeFloat:
case GPBDataTypeDouble:
case GPBDataTypeBytes:
case GPBDataTypeString:
return type;
}
}
static BOOL DataTypesEquivalent(GPBDataType type1, GPBDataType type2) {
return BaseDataType(type1) == BaseDataType(type2);
}
static NSString *TypeToString(GPBDataType dataType) {
switch (dataType) { switch (dataType) {
case GPBDataTypeBool: case GPBDataTypeBool:
return @"Bool"; return @"Bool";
...@@ -1166,10 +1445,9 @@ static NSString *TypeToStr(GPBDataType dataType) { ...@@ -1166,10 +1445,9 @@ static NSString *TypeToStr(GPBDataType dataType) {
case GPBDataTypeGroup: case GPBDataTypeGroup:
return @"Object"; return @"Object";
case GPBDataTypeEnum: case GPBDataTypeEnum:
return @"Bool"; return @"Enum";
} }
} }
#endif
// GPBGetMessageMapField is defined in GPBMessage.m // GPBGetMessageMapField is defined in GPBMessage.m
...@@ -1185,8 +1463,8 @@ void GPBSetMessageMapField(GPBMessage *self, GPBFieldDescriptor *field, ...@@ -1185,8 +1463,8 @@ void GPBSetMessageMapField(GPBMessage *self, GPBFieldDescriptor *field,
if (dictionary) { if (dictionary) {
GPBDataType keyDataType = field.mapKeyDataType; GPBDataType keyDataType = field.mapKeyDataType;
GPBDataType valueDataType = GPBGetFieldDataType(field); GPBDataType valueDataType = GPBGetFieldDataType(field);
NSString *keyStr = TypeToStr(keyDataType); NSString *keyStr = TypeToString(keyDataType);
NSString *valueStr = TypeToStr(valueDataType); NSString *valueStr = TypeToString(valueDataType);
if (keyDataType == GPBDataTypeString) { if (keyDataType == GPBDataTypeString) {
keyStr = @"String"; keyStr = @"String";
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment