From c8a440dfb68074ff310e624928cd2dd61c101728 Mon Sep 17 00:00:00 2001 From: Thomas Van Lenten Date: Wed, 25 May 2016 13:46:00 -0400 Subject: [PATCH] Add more warnings to for the ObjC runtime build Working on https://github.com/google/protobuf/issues/1599, specifically: - Turn on more warnings that the Xcode UI calls out with individual controls. - Manually add: -Wundef -Wswitch-enum - Manually add and then diable in the unittests because of XCTest's headers: -Wreserved-id-macro -Wdocumentation-unknown-command - Manually add -Wdirect-ivar-access, but disable it for the unittests and in the library code (via #pragmas to suppress it). This is done so proto users can enable the warning. --- objectivec/GPBArray.m | 8 ++++ objectivec/GPBBootstrap.h | 2 +- objectivec/GPBCodedInputStream.h | 2 +- objectivec/GPBCodedInputStream.m | 8 ++++ objectivec/GPBCodedOutputStream.m | 10 ++++- objectivec/GPBDescriptor.h | 2 +- objectivec/GPBDescriptor.m | 10 ++++- objectivec/GPBDescriptor_PackagePrivate.h | 30 +++++++++------ objectivec/GPBDictionary.m | 11 ++++++ objectivec/GPBExtensionInternals.m | 11 ++++++ objectivec/GPBExtensionRegistry.m | 8 ++++ objectivec/GPBMessage.m | 22 +++++++---- objectivec/GPBMessage_PackagePrivate.h | 3 ++ objectivec/GPBUnknownField.m | 8 ++++ objectivec/GPBUnknownFieldSet.m | 10 ++++- objectivec/GPBUtilities.m | 24 +++++++++--- objectivec/GPBUtilities_PackagePrivate.h | 8 +++- .../project.pbxproj | 38 +++++++++++++++++++ .../project.pbxproj | 38 +++++++++++++++++++ objectivec/google/protobuf/Struct.pbobjc.m | 1 + .../compiler/objectivec/objectivec_file.cc | 28 +++++++++++++- .../compiler/objectivec/objectivec_message.cc | 16 ++++++++ .../compiler/objectivec/objectivec_message.h | 3 ++ 23 files changed, 269 insertions(+), 32 deletions(-) diff --git a/objectivec/GPBArray.m b/objectivec/GPBArray.m index 426c7cbdde..dce45b6eec 100644 --- a/objectivec/GPBArray.m +++ b/objectivec/GPBArray.m @@ -32,6 +32,12 @@ #import "GPBMessage_PackagePrivate.h" +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + // Mutable arrays use an internal buffer that can always hold a multiple of this elements. #define kChunkSize 16 #define CapacityFromCount(x) (((x / kChunkSize) + 1) * kChunkSize) @@ -2532,3 +2538,5 @@ static BOOL ArrayDefault_IsValidValue(int32_t value) { } @end + +#pragma clang diagnostic pop diff --git a/objectivec/GPBBootstrap.h b/objectivec/GPBBootstrap.h index ffefa7706c..4db08e80d8 100644 --- a/objectivec/GPBBootstrap.h +++ b/objectivec/GPBBootstrap.h @@ -48,7 +48,7 @@ // doesn't allow us to forward declare. We work around this one case by // providing a local definition. The default case has to use NS_ENUM for the // magic that is Swift bridging of enums. -#if (__cplusplus && __cplusplus < 201103L) +#if (defined(__cplusplus) && __cplusplus && __cplusplus < 201103L) #define GPB_ENUM(X) enum X : int32_t X; enum X : int32_t #else #define GPB_ENUM(X) NS_ENUM(int32_t, X) diff --git a/objectivec/GPBCodedInputStream.h b/objectivec/GPBCodedInputStream.h index d64b64e3f3..44f6990677 100644 --- a/objectivec/GPBCodedInputStream.h +++ b/objectivec/GPBCodedInputStream.h @@ -93,7 +93,7 @@ NS_ASSUME_NONNULL_BEGIN /// /// @param message The message to set fields on as they are read. /// @param extensionRegistry An optional extension registry to use to lookup -/// extensions for @message. +/// extensions for @c message. - (void)readMessage:(GPBMessage *)message extensionRegistry:(nullable GPBExtensionRegistry *)extensionRegistry; diff --git a/objectivec/GPBCodedInputStream.m b/objectivec/GPBCodedInputStream.m index 319ec15ba7..402271785b 100644 --- a/objectivec/GPBCodedInputStream.m +++ b/objectivec/GPBCodedInputStream.m @@ -316,6 +316,12 @@ void GPBCodedInputStreamCheckLastTagWas(GPBCodedInputStreamState *state, [super dealloc]; } +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + - (int32_t)readTag { return GPBCodedInputStreamReadTag(&state_); } @@ -496,4 +502,6 @@ void GPBCodedInputStreamCheckLastTagWas(GPBCodedInputStreamState *state, return GPBCodedInputStreamReadSInt64(&state_); } +#pragma clang diagnostic pop + @end diff --git a/objectivec/GPBCodedOutputStream.m b/objectivec/GPBCodedOutputStream.m index fd9ed66ca2..63ba8068c7 100644 --- a/objectivec/GPBCodedOutputStream.m +++ b/objectivec/GPBCodedOutputStream.m @@ -144,7 +144,7 @@ static void GPBWriteRawLittleEndian64(GPBOutputBufferState *state, GPBWriteRawByte(state, (int32_t)(value >> 56) & 0xFF); } -#if DEBUG && !defined(NS_BLOCK_ASSERTIONS) +#if defined(DEBUG) && DEBUG && !defined(NS_BLOCK_ASSERTIONS) + (void)load { // This test exists to verify that CFStrings with embedded NULLs will work // for us. If this Assert fails, all code below that depends on @@ -203,6 +203,12 @@ static void GPBWriteRawLittleEndian64(GPBOutputBufferState *state, return [[[self alloc] initWithData:data] autorelease]; } +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + - (void)writeDoubleNoTag:(double)value { GPBWriteRawLittleEndian64(&state_, GPBConvertDoubleToInt64(value)); } @@ -981,6 +987,8 @@ static void GPBWriteRawLittleEndian64(GPBOutputBufferState *state, GPBWriteRawLittleEndian64(&state_, value); } +#pragma clang diagnostic pop + @end size_t GPBComputeDoubleSizeNoTag(Float64 value) { diff --git a/objectivec/GPBDescriptor.h b/objectivec/GPBDescriptor.h index a6eff0fb7d..c0f644c749 100644 --- a/objectivec/GPBDescriptor.h +++ b/objectivec/GPBDescriptor.h @@ -135,7 +135,7 @@ typedef NS_ENUM(uint8_t, GPBFieldType) { @property(nonatomic, readonly, assign) Class msgClass; @property(nonatomic, readonly) NSString *singletonName; @property(nonatomic, readonly, strong, nullable) GPBEnumDescriptor *enumDescriptor; -@property(nonatomic, readonly) id defaultValue; +@property(nonatomic, readonly, nullable) id defaultValue; @end NS_ASSUME_NONNULL_END diff --git a/objectivec/GPBDescriptor.m b/objectivec/GPBDescriptor.m index 2709737cad..898f231d47 100644 --- a/objectivec/GPBDescriptor.m +++ b/objectivec/GPBDescriptor.m @@ -36,6 +36,12 @@ #import "GPBWireFormat.h" #import "GPBMessage_PackagePrivate.h" +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + // The address of this variable is used as a key for obj_getAssociatedObject. static const char kTextFormatExtraValueKey = 0; @@ -803,7 +809,7 @@ uint32_t GPBFieldAlternateTag(GPBFieldDescriptor *self) { if ((self = [super init])) { description_ = description; -#if DEBUG +#if defined(DEBUG) && DEBUG const char *className = description->messageOrGroupClassName; if (className) { NSAssert(objc_lookUpClass(className) != Nil, @@ -961,3 +967,5 @@ uint32_t GPBFieldAlternateTag(GPBFieldDescriptor *self) { } @end + +#pragma clang diagnostic pop diff --git a/objectivec/GPBDescriptor_PackagePrivate.h b/objectivec/GPBDescriptor_PackagePrivate.h index e3d0a80f05..c20ff6b099 100644 --- a/objectivec/GPBDescriptor_PackagePrivate.h +++ b/objectivec/GPBDescriptor_PackagePrivate.h @@ -245,6 +245,12 @@ typedef NS_OPTIONS(uint32_t, GPBDescriptorInitializationFlags) { CF_EXTERN_C_BEGIN +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + GPB_INLINE BOOL GPBFieldIsMapOrArray(GPBFieldDescriptor *field) { return (field->description_->flags & (GPBFieldRepeated | GPBFieldMapKeyMask)) != 0; @@ -262,6 +268,8 @@ GPB_INLINE uint32_t GPBFieldNumber(GPBFieldDescriptor *field) { return field->description_->number; } +#pragma clang diagnostic pop + uint32_t GPBFieldTag(GPBFieldDescriptor *self); // For repeated fields, alternateWireType is the wireType with the opposite @@ -291,23 +299,23 @@ GPB_INLINE BOOL GPBExtensionIsWireFormat(GPBExtensionDescription *description) { } // Helper for compile time assets. -#ifndef _GPBCompileAssert +#ifndef GPBInternalCompileAssert #if __has_feature(c_static_assert) || __has_extension(c_static_assert) - #define _GPBCompileAssert(test, msg) _Static_assert((test), #msg) + #define GPBInternalCompileAssert(test, msg) _Static_assert((test), #msg) #else // Pre-Xcode 7 support. - #define _GPBCompileAssertSymbolInner(line, msg) _GPBCompileAssert ## line ## __ ## msg - #define _GPBCompileAssertSymbol(line, msg) _GPBCompileAssertSymbolInner(line, msg) - #define _GPBCompileAssert(test, msg) \ - typedef char _GPBCompileAssertSymbol(__LINE__, msg) [ ((test) ? 1 : -1) ] + #define GPBInternalCompileAssertSymbolInner(line, msg) GPBInternalCompileAssert ## line ## __ ## msg + #define GPBInternalCompileAssertSymbol(line, msg) GPBInternalCompileAssertSymbolInner(line, msg) + #define GPBInternalCompileAssert(test, msg) \ + typedef char GPBInternalCompileAssertSymbol(__LINE__, msg) [ ((test) ? 1 : -1) ] #endif // __has_feature(c_static_assert) || __has_extension(c_static_assert) -#endif // _GPBCompileAssert +#endif // GPBInternalCompileAssert // Sanity check that there isn't padding between the field description // structures with and without a default. -_GPBCompileAssert(sizeof(GPBMessageFieldDescriptionWithDefault) == - (sizeof(GPBGenericValue) + - sizeof(GPBMessageFieldDescription)), - DescriptionsWithDefault_different_size_than_expected); +GPBInternalCompileAssert(sizeof(GPBMessageFieldDescriptionWithDefault) == + (sizeof(GPBGenericValue) + + sizeof(GPBMessageFieldDescription)), + DescriptionsWithDefault_different_size_than_expected); CF_EXTERN_C_END diff --git a/objectivec/GPBDictionary.m b/objectivec/GPBDictionary.m index 3bd146e0f9..0f0241a1f7 100644 --- a/objectivec/GPBDictionary.m +++ b/objectivec/GPBDictionary.m @@ -45,6 +45,12 @@ // directly. // ------------------------------------------------------------------ +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + // Used to include code only visible to specific versions of the static // analyzer. Useful for wrapping code that only exists to silence the analyzer. // Determine the values you want to use for BEGIN_APPLE_BUILD_VERSION, @@ -484,6 +490,8 @@ void GPBDictionaryReadEntry(id mapDictionary, key.valueString = [@"" retain]; } if (GPBDataTypeIsObject(valueDataType) && value.valueString == nil) { +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wswitch-enum" switch (valueDataType) { case GPBDataTypeString: value.valueString = [@"" retain]; @@ -505,6 +513,7 @@ void GPBDictionaryReadEntry(id mapDictionary, // Nothing break; } +#pragma clang diagnostic pop } if ((keyDataType == GPBDataTypeString) && GPBDataTypeIsObject(valueDataType)) { @@ -13553,3 +13562,5 @@ void GPBDictionaryReadEntry(id mapDictionary, } @end + +#pragma clang diagnostic pop diff --git a/objectivec/GPBExtensionInternals.m b/objectivec/GPBExtensionInternals.m index 7d0dcb2ee9..290c82a1bb 100644 --- a/objectivec/GPBExtensionInternals.m +++ b/objectivec/GPBExtensionInternals.m @@ -45,6 +45,8 @@ static id NewSingleValueFromInputStream(GPBExtensionDescriptor *extension, __attribute__((ns_returns_retained)); GPB_INLINE size_t DataTypeSize(GPBDataType dataType) { +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wswitch-enum" switch (dataType) { case GPBDataTypeBool: return 1; @@ -59,6 +61,7 @@ GPB_INLINE size_t DataTypeSize(GPBDataType dataType) { default: return 0; } +#pragma clang diagnostic pop } static size_t ComputePBSerializedSizeNoTagOfObject(GPBDataType dataType, id object) { @@ -261,6 +264,12 @@ static void WriteArrayIncludingTagsToCodedOutputStream( } } +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + void GPBExtensionMergeFromInputStream(GPBExtensionDescriptor *extension, BOOL isPackedOnStream, GPBCodedInputStream *input, @@ -378,3 +387,5 @@ static id NewSingleValueFromInputStream(GPBExtensionDescriptor *extension, return nil; } + +#pragma clang diagnostic pop diff --git a/objectivec/GPBExtensionRegistry.m b/objectivec/GPBExtensionRegistry.m index df61a17b18..01eb761f35 100644 --- a/objectivec/GPBExtensionRegistry.m +++ b/objectivec/GPBExtensionRegistry.m @@ -51,6 +51,12 @@ [super dealloc]; } +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + - (instancetype)copyWithZone:(NSZone *)zone { GPBExtensionRegistry *result = [[[self class] allocWithZone:zone] init]; if (result && mutableClassMap_.count) { @@ -105,4 +111,6 @@ } } +#pragma clang diagnostic pop + @end diff --git a/objectivec/GPBMessage.m b/objectivec/GPBMessage.m index 8134e25962..77b9dbd3b5 100644 --- a/objectivec/GPBMessage.m +++ b/objectivec/GPBMessage.m @@ -44,6 +44,12 @@ #import "GPBUnknownFieldSet_PackagePrivate.h" #import "GPBUtilities_PackagePrivate.h" +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + NSString *const GPBMessageErrorDomain = GPBNSStringifySymbol(GPBMessageErrorDomain); @@ -694,7 +700,7 @@ void GPBClearMessageAutocreator(GPBMessage *self) { return; } -#if DEBUG && !defined(NS_BLOCK_ASSERTIONS) +#if defined(DEBUG) && DEBUG && !defined(NS_BLOCK_ASSERTIONS) // Either the autocreator must have its "has" flag set to YES, or it must be // NO and not equal to ourselves. BOOL autocreatorHas = @@ -1736,7 +1742,7 @@ static GPBUnknownFieldSet *GetOrMakeUnknownFields(GPBMessage *self) { } - (BOOL)hasExtension:(GPBExtensionDescriptor *)extension { -#if DEBUG +#if defined(DEBUG) && DEBUG CheckExtension(self, extension); #endif // DEBUG return nil != [extensionMap_ objectForKey:extension]; @@ -2621,7 +2627,7 @@ static void MergeRepeatedNotPackedFieldFromCodedInputStream( case GPBDataTypeFixed32: case GPBDataTypeUInt32: case GPBDataTypeFloat: { - _GPBCompileAssert(sizeof(float) == sizeof(uint32_t), float_not_32_bits); + GPBInternalCompileAssert(sizeof(float) == sizeof(uint32_t), float_not_32_bits); // These are all 32bit, signed/unsigned doesn't matter for equality. uint32_t *selfValPtr = (uint32_t *)&selfStorage[fieldOffset]; uint32_t *otherValPtr = (uint32_t *)&otherStorage[fieldOffset]; @@ -2636,7 +2642,7 @@ static void MergeRepeatedNotPackedFieldFromCodedInputStream( case GPBDataTypeFixed64: case GPBDataTypeUInt64: case GPBDataTypeDouble: { - _GPBCompileAssert(sizeof(double) == sizeof(uint64_t), double_not_64_bits); + GPBInternalCompileAssert(sizeof(double) == sizeof(uint64_t), double_not_64_bits); // These are all 64bit, signed/unsigned doesn't matter for equality. uint64_t *selfValPtr = (uint64_t *)&selfStorage[fieldOffset]; uint64_t *otherValPtr = (uint64_t *)&otherStorage[fieldOffset]; @@ -2733,7 +2739,7 @@ static void MergeRepeatedNotPackedFieldFromCodedInputStream( case GPBDataTypeFixed32: case GPBDataTypeUInt32: case GPBDataTypeFloat: { - _GPBCompileAssert(sizeof(float) == sizeof(uint32_t), float_not_32_bits); + GPBInternalCompileAssert(sizeof(float) == sizeof(uint32_t), float_not_32_bits); // These are all 32bit, just mix it in. uint32_t *valPtr = (uint32_t *)&storage[fieldOffset]; result = prime * result + *valPtr; @@ -2745,7 +2751,7 @@ static void MergeRepeatedNotPackedFieldFromCodedInputStream( case GPBDataTypeFixed64: case GPBDataTypeUInt64: case GPBDataTypeDouble: { - _GPBCompileAssert(sizeof(double) == sizeof(uint64_t), double_not_64_bits); + GPBInternalCompileAssert(sizeof(double) == sizeof(uint64_t), double_not_64_bits); // These are all 64bit, just mix what fits into an NSUInteger in. uint64_t *valPtr = (uint64_t *)&storage[fieldOffset]; result = prime * result + (NSUInteger)(*valPtr); @@ -2792,7 +2798,7 @@ static void MergeRepeatedNotPackedFieldFromCodedInputStream( return description; } -#if DEBUG +#if defined(DEBUG) && DEBUG // Xcode 5.1 added support for custom quick look info. // https://developer.apple.com/library/ios/documentation/IDEs/Conceptual/CustomClassDisplay_in_QuickLook/CH01-quick_look_for_custom_objects/CH01-quick_look_for_custom_objects.html#//apple_ref/doc/uid/TP40014001-CH2-SW1 @@ -3182,3 +3188,5 @@ static void ResolveIvarSet(GPBFieldDescriptor *field, } @end + +#pragma clang diagnostic pop diff --git a/objectivec/GPBMessage_PackagePrivate.h b/objectivec/GPBMessage_PackagePrivate.h index 478db2cf0f..ff3cd6eb08 100644 --- a/objectivec/GPBMessage_PackagePrivate.h +++ b/objectivec/GPBMessage_PackagePrivate.h @@ -110,9 +110,12 @@ CF_EXTERN_C_BEGIN // Call this before using the readOnlySemaphore_. This ensures it is created only once. NS_INLINE void GPBPrepareReadOnlySemaphore(GPBMessage *self) { +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" dispatch_once(&self->readOnlySemaphoreCreationOnce_, ^{ self->readOnlySemaphore_ = dispatch_semaphore_create(1); }); +#pragma clang diagnostic pop } // Returns a new instance that was automatically created by |autocreator| for diff --git a/objectivec/GPBUnknownField.m b/objectivec/GPBUnknownField.m index 0e29bde50f..30efe7563b 100644 --- a/objectivec/GPBUnknownField.m +++ b/objectivec/GPBUnknownField.m @@ -67,6 +67,12 @@ [super dealloc]; } +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + - (id)copyWithZone:(NSZone *)zone { GPBUnknownField *result = [[GPBUnknownField allocWithZone:zone] initWithNumber:number_]; @@ -323,4 +329,6 @@ } } +#pragma clang diagnostic pop + @end diff --git a/objectivec/GPBUnknownFieldSet.m b/objectivec/GPBUnknownFieldSet.m index 4ddc0d2a48..af08556e62 100644 --- a/objectivec/GPBUnknownFieldSet.m +++ b/objectivec/GPBUnknownFieldSet.m @@ -93,6 +93,12 @@ static void CopyWorker(const void *key, const void *value, void *context) { [copied release]; } +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + - (id)copyWithZone:(NSZone *)zone { GPBUnknownFieldSet *result = [[GPBUnknownFieldSet allocWithZone:zone] init]; if (fields_) { @@ -148,7 +154,7 @@ static void CopyWorker(const void *key, const void *value, void *context) { } - (NSArray *)sortedFields { - if (!fields_) return nil; + if (!fields_) return [NSArray array]; size_t count = CFDictionaryGetCount(fields_); ssize_t keys[count]; GPBUnknownField *values[count]; @@ -420,4 +426,6 @@ static void GPBUnknownFieldSetMergeUnknownFields(const void *key, } } +#pragma clang diagnostic pop + @end diff --git a/objectivec/GPBUtilities.m b/objectivec/GPBUtilities.m index 447c749aa7..89deb2e7e1 100644 --- a/objectivec/GPBUtilities.m +++ b/objectivec/GPBUtilities.m @@ -39,6 +39,12 @@ #import "GPBUnknownField.h" #import "GPBUnknownFieldSet.h" +// Direct access is use for speed, to avoid even internally declaring things +// read/write, etc. The warning is enabled in the project to ensure code calling +// protos can turn on -Wdirect-ivar-access without issues. +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + static void AppendTextFormatForMessage(GPBMessage *message, NSMutableString *toStr, NSString *lineIndent); @@ -891,7 +897,7 @@ void GPBSetMessageGroupField(GPBMessage *self, // Only exists for public api, no core code should use this. id GPBGetMessageRepeatedField(GPBMessage *self, GPBFieldDescriptor *field) { -#if DEBUG +#if defined(DEBUG) && DEBUG if (field.fieldType != GPBFieldTypeRepeated) { [NSException raise:NSInvalidArgumentException format:@"%@.%@ is not a repeated field.", @@ -903,7 +909,7 @@ id GPBGetMessageRepeatedField(GPBMessage *self, GPBFieldDescriptor *field) { // Only exists for public api, no core code should use this. void GPBSetMessageRepeatedField(GPBMessage *self, GPBFieldDescriptor *field, id array) { -#if DEBUG +#if defined(DEBUG) && DEBUG if (field.fieldType != GPBFieldTypeRepeated) { [NSException raise:NSInvalidArgumentException format:@"%@.%@ is not a repeated field.", @@ -957,7 +963,7 @@ void GPBSetMessageRepeatedField(GPBMessage *self, GPBFieldDescriptor *field, id GPBSetObjectIvarWithField(self, field, array); } -#if DEBUG +#if defined(DEBUG) && DEBUG static NSString *TypeToStr(GPBDataType dataType) { switch (dataType) { case GPBDataTypeBool: @@ -993,7 +999,7 @@ static NSString *TypeToStr(GPBDataType dataType) { // Only exists for public api, no core code should use this. id GPBGetMessageMapField(GPBMessage *self, GPBFieldDescriptor *field) { -#if DEBUG +#if defined(DEBUG) && DEBUG if (field.fieldType != GPBFieldTypeMap) { [NSException raise:NSInvalidArgumentException format:@"%@.%@ is not a map<> field.", @@ -1006,7 +1012,7 @@ id GPBGetMessageMapField(GPBMessage *self, GPBFieldDescriptor *field) { // Only exists for public api, no core code should use this. void GPBSetMessageMapField(GPBMessage *self, GPBFieldDescriptor *field, id dictionary) { -#if DEBUG +#if defined(DEBUG) && DEBUG if (field.fieldType != GPBFieldTypeMap) { [NSException raise:NSInvalidArgumentException format:@"%@.%@ is not a map<> field.", @@ -1133,6 +1139,8 @@ static void AppendTextFormatForMapMessageField( [toStr appendString:@"\n"]; [toStr appendString:valueLine]; +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wswitch-enum" switch (valueDataType) { case GPBDataTypeString: AppendStringEscaped(value, toStr); @@ -1153,6 +1161,7 @@ static void AppendTextFormatForMapMessageField( NSCAssert(NO, @"Can't happen"); break; } +#pragma clang diagnostic pop [toStr appendString:@"\n"]; [toStr appendString:msgEnd]; @@ -1174,6 +1183,8 @@ static void AppendTextFormatForMapMessageField( } [toStr appendString:valueLine]; +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wswitch-enum" switch (valueDataType) { case GPBDataTypeString: AppendStringEscaped(valueObj, toStr); @@ -1211,6 +1222,7 @@ static void AppendTextFormatForMapMessageField( [toStr appendString:valueObj]; break; } +#pragma clang diagnostic pop [toStr appendString:@"\n"]; [toStr appendString:msgEnd]; @@ -1706,6 +1718,8 @@ NSString *GPBDecodeTextFormatName(const uint8_t *decodeData, int32_t key, return result; } +#pragma clang diagnostic pop + #pragma mark - GPBMessageSignatureProtocol // A series of selectors that are used solely to get @encoding values diff --git a/objectivec/GPBUtilities_PackagePrivate.h b/objectivec/GPBUtilities_PackagePrivate.h index a6b6c84d98..c02493b2c7 100644 --- a/objectivec/GPBUtilities_PackagePrivate.h +++ b/objectivec/GPBUtilities_PackagePrivate.h @@ -52,7 +52,7 @@ CF_EXTERN_C_BEGIN // generated sources to make sure they are linked with a supporting runtime. void GPBCheckRuntimeVersionInternal(int32_t version); GPB_INLINE void GPBDebugCheckRuntimeVersion() { -#if DEBUG +#if defined(DEBUG) && DEBUG GPBCheckRuntimeVersionInternal(GOOGLE_PROTOBUF_OBJC_GEN_VERSION); #endif } @@ -125,6 +125,10 @@ GPB_INLINE uint64_t GPBEncodeZigZag64(int64_t n) { return (n << 1) ^ (n >> 63); } +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wswitch-enum" +#pragma clang diagnostic ignored "-Wdirect-ivar-access" + GPB_INLINE BOOL GPBDataTypeIsObject(GPBDataType type) { switch (type) { case GPBDataTypeBytes: @@ -187,6 +191,8 @@ GPB_INLINE void GPBSetHasIvarField(GPBMessage *self, GPBFieldDescriptor *field, void GPBMaybeClearOneof(GPBMessage *self, GPBOneofDescriptor *oneof, int32_t oneofHasIndex, uint32_t fieldNumberNotToClear); +#pragma clang diagnostic pop + //%PDDM-DEFINE GPB_IVAR_SET_DECL(NAME, TYPE) //%void GPBSet##NAME##IvarWithFieldInternal(GPBMessage *self, //% NAME$S GPBFieldDescriptor *field, diff --git a/objectivec/ProtocolBuffers_OSX.xcodeproj/project.pbxproj b/objectivec/ProtocolBuffers_OSX.xcodeproj/project.pbxproj index 309342543f..b2721232a4 100644 --- a/objectivec/ProtocolBuffers_OSX.xcodeproj/project.pbxproj +++ b/objectivec/ProtocolBuffers_OSX.xcodeproj/project.pbxproj @@ -749,6 +749,12 @@ PRODUCT_NAME = UnitTests; SWIFT_OBJC_BRIDGING_HEADER = "Tests/UnitTests-Bridging-Header.h"; SWIFT_OPTIMIZATION_LEVEL = "-Onone"; + WARNING_CFLAGS = ( + "$(inherited)", + "-Wno-documentation-unknown-command", + "-Wno-reserved-id-macro", + "-Wno-direct-ivar-access", + ); }; name = Debug; }; @@ -766,6 +772,12 @@ PRODUCT_BUNDLE_IDENTIFIER = "com.yourcompany.${PRODUCT_NAME:identifier}"; PRODUCT_NAME = UnitTests; SWIFT_OBJC_BRIDGING_HEADER = "Tests/UnitTests-Bridging-Header.h"; + WARNING_CFLAGS = ( + "$(inherited)", + "-Wno-documentation-unknown-command", + "-Wno-reserved-id-macro", + "-Wno-direct-ivar-access", + ); }; name = Release; }; @@ -773,15 +785,20 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = YES; + CLANG_ANALYZER_NONNULL = YES; CLANG_ANALYZER_SECURITY_FLOATLOOPCOUNTER = YES; CLANG_ANALYZER_SECURITY_INSECUREAPI_RAND = YES; CLANG_ANALYZER_SECURITY_INSECUREAPI_STRCPY = YES; CLANG_STATIC_ANALYZER_MODE = deep; CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; CLANG_WARN_NULLABLE_TO_NONNULL_CONVERSION = YES; + CLANG_WARN_OBJC_EXPLICIT_OWNERSHIP_TYPE = YES; CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; CLANG_WARN_OBJC_MISSING_PROPERTY_SYNTHESIS = YES; CLANG_WARN_SUSPICIOUS_IMPLICIT_CONVERSION = YES; + CLANG_WARN_UNREACHABLE_CODE = YES_AGGRESSIVE; CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; ENABLE_TESTABILITY = YES; GCC_C_LANGUAGE_STANDARD = c99; @@ -802,6 +819,7 @@ GCC_WARN_SHADOW = YES; GCC_WARN_SIGN_COMPARE = YES; GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNKNOWN_PRAGMAS = YES; GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_LABEL = YES; @@ -812,6 +830,13 @@ ONLY_ACTIVE_ARCH = YES; RUN_CLANG_STATIC_ANALYZER = YES; SDKROOT = macosx; + WARNING_CFLAGS = ( + "-Wdocumentation-unknown-command", + "-Wundef", + "-Wreserved-id-macro", + "-Wswitch-enum", + "-Wdirect-ivar-access", + ); }; name = Debug; }; @@ -819,15 +844,20 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = YES; + CLANG_ANALYZER_NONNULL = YES; CLANG_ANALYZER_SECURITY_FLOATLOOPCOUNTER = YES; CLANG_ANALYZER_SECURITY_INSECUREAPI_RAND = YES; CLANG_ANALYZER_SECURITY_INSECUREAPI_STRCPY = YES; CLANG_STATIC_ANALYZER_MODE = deep; CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; CLANG_WARN_NULLABLE_TO_NONNULL_CONVERSION = YES; + CLANG_WARN_OBJC_EXPLICIT_OWNERSHIP_TYPE = YES; CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; CLANG_WARN_OBJC_MISSING_PROPERTY_SYNTHESIS = YES; CLANG_WARN_SUSPICIOUS_IMPLICIT_CONVERSION = YES; + CLANG_WARN_UNREACHABLE_CODE = YES_AGGRESSIVE; CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; ENABLE_NS_ASSERTIONS = NO; GCC_C_LANGUAGE_STANDARD = c99; @@ -846,6 +876,7 @@ GCC_WARN_SHADOW = YES; GCC_WARN_SIGN_COMPARE = YES; GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNKNOWN_PRAGMAS = YES; GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_LABEL = YES; @@ -855,6 +886,13 @@ MACOSX_DEPLOYMENT_TARGET = 10.9; RUN_CLANG_STATIC_ANALYZER = YES; SDKROOT = macosx; + WARNING_CFLAGS = ( + "-Wdocumentation-unknown-command", + "-Wundef", + "-Wreserved-id-macro", + "-Wswitch-enum", + "-Wdirect-ivar-access", + ); }; name = Release; }; diff --git a/objectivec/ProtocolBuffers_iOS.xcodeproj/project.pbxproj b/objectivec/ProtocolBuffers_iOS.xcodeproj/project.pbxproj index b622181935..9ec7f9f7e6 100644 --- a/objectivec/ProtocolBuffers_iOS.xcodeproj/project.pbxproj +++ b/objectivec/ProtocolBuffers_iOS.xcodeproj/project.pbxproj @@ -901,6 +901,12 @@ SWIFT_OPTIMIZATION_LEVEL = "-Onone"; TARGETED_DEVICE_FAMILY = "1,2"; TEST_HOST = "$(BUILT_PRODUCTS_DIR)/iOSTestHarness.app/iOSTestHarness"; + WARNING_CFLAGS = ( + "$(inherited)", + "-Wno-documentation-unknown-command", + "-Wno-reserved-id-macro", + "-Wno-direct-ivar-access", + ); }; name = Debug; }; @@ -928,6 +934,12 @@ SWIFT_OBJC_BRIDGING_HEADER = "Tests/UnitTests-Bridging-Header.h"; TARGETED_DEVICE_FAMILY = "1,2"; TEST_HOST = "$(BUILT_PRODUCTS_DIR)/iOSTestHarness.app/iOSTestHarness"; + WARNING_CFLAGS = ( + "$(inherited)", + "-Wno-documentation-unknown-command", + "-Wno-reserved-id-macro", + "-Wno-direct-ivar-access", + ); }; name = Release; }; @@ -935,15 +947,20 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = YES; + CLANG_ANALYZER_NONNULL = YES; CLANG_ANALYZER_SECURITY_FLOATLOOPCOUNTER = YES; CLANG_ANALYZER_SECURITY_INSECUREAPI_RAND = YES; CLANG_ANALYZER_SECURITY_INSECUREAPI_STRCPY = YES; CLANG_STATIC_ANALYZER_MODE = deep; CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; CLANG_WARN_NULLABLE_TO_NONNULL_CONVERSION = YES; + CLANG_WARN_OBJC_EXPLICIT_OWNERSHIP_TYPE = YES; CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; CLANG_WARN_OBJC_MISSING_PROPERTY_SYNTHESIS = YES; CLANG_WARN_SUSPICIOUS_IMPLICIT_CONVERSION = YES; + CLANG_WARN_UNREACHABLE_CODE = YES_AGGRESSIVE; CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; ENABLE_TESTABILITY = YES; @@ -965,6 +982,7 @@ GCC_WARN_SHADOW = YES; GCC_WARN_SIGN_COMPARE = YES; GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNKNOWN_PRAGMAS = YES; GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_LABEL = YES; @@ -975,6 +993,13 @@ ONLY_ACTIVE_ARCH = YES; RUN_CLANG_STATIC_ANALYZER = YES; SDKROOT = iphoneos; + WARNING_CFLAGS = ( + "-Wdocumentation-unknown-command", + "-Wundef", + "-Wreserved-id-macro", + "-Wswitch-enum", + "-Wdirect-ivar-access", + ); }; name = Debug; }; @@ -982,15 +1007,20 @@ isa = XCBuildConfiguration; buildSettings = { ALWAYS_SEARCH_USER_PATHS = YES; + CLANG_ANALYZER_NONNULL = YES; CLANG_ANALYZER_SECURITY_FLOATLOOPCOUNTER = YES; CLANG_ANALYZER_SECURITY_INSECUREAPI_RAND = YES; CLANG_ANALYZER_SECURITY_INSECUREAPI_STRCPY = YES; CLANG_STATIC_ANALYZER_MODE = deep; CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES; + CLANG_WARN_DOCUMENTATION_COMMENTS = YES; CLANG_WARN_NULLABLE_TO_NONNULL_CONVERSION = YES; + CLANG_WARN_OBJC_EXPLICIT_OWNERSHIP_TYPE = YES; CLANG_WARN_OBJC_IMPLICIT_ATOMIC_PROPERTIES = YES; + CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES; CLANG_WARN_OBJC_MISSING_PROPERTY_SYNTHESIS = YES; CLANG_WARN_SUSPICIOUS_IMPLICIT_CONVERSION = YES; + CLANG_WARN_UNREACHABLE_CODE = YES_AGGRESSIVE; CLANG_WARN__DUPLICATE_METHOD_MATCH = YES; "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; ENABLE_NS_ASSERTIONS = NO; @@ -1010,6 +1040,7 @@ GCC_WARN_SHADOW = YES; GCC_WARN_SIGN_COMPARE = YES; GCC_WARN_UNDECLARED_SELECTOR = YES; + GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE; GCC_WARN_UNKNOWN_PRAGMAS = YES; GCC_WARN_UNUSED_FUNCTION = YES; GCC_WARN_UNUSED_LABEL = YES; @@ -1019,6 +1050,13 @@ IPHONEOS_DEPLOYMENT_TARGET = 6.1; RUN_CLANG_STATIC_ANALYZER = YES; SDKROOT = iphoneos; + WARNING_CFLAGS = ( + "-Wdocumentation-unknown-command", + "-Wundef", + "-Wreserved-id-macro", + "-Wswitch-enum", + "-Wdirect-ivar-access", + ); }; name = Release; }; diff --git a/objectivec/google/protobuf/Struct.pbobjc.m b/objectivec/google/protobuf/Struct.pbobjc.m index 39b1287920..538faab3a8 100644 --- a/objectivec/google/protobuf/Struct.pbobjc.m +++ b/objectivec/google/protobuf/Struct.pbobjc.m @@ -22,6 +22,7 @@ #pragma clang diagnostic push #pragma clang diagnostic ignored "-Wdeprecated-declarations" +#pragma clang diagnostic ignored "-Wdirect-ivar-access" #pragma mark - GPBStructRoot diff --git a/src/google/protobuf/compiler/objectivec/objectivec_file.cc b/src/google/protobuf/compiler/objectivec/objectivec_file.cc index ccf5fbb47b..7774058eca 100644 --- a/src/google/protobuf/compiler/objectivec/objectivec_file.cc +++ b/src/google/protobuf/compiler/objectivec/objectivec_file.cc @@ -182,6 +182,10 @@ void FileGenerator::GenerateHeader(io::Printer *printer) { import_writer.Print(printer); } + // Note: + // deprecated-declarations suppression is only needed if some place in this + // proto file is something deprecated or if it references something from + // another file that is deprecated. printer->Print( "// @@protoc_insertion_point(imports)\n" "\n" @@ -292,14 +296,34 @@ void FileGenerator::GenerateSource(io::Printer *printer) { import_writer.Print(printer); } + bool includes_oneof = false; + for (vector::iterator iter = message_generators_.begin(); + iter != message_generators_.end(); ++iter) { + if ((*iter)->IncludesOneOfDefinition()) { + includes_oneof = true; + break; + } + } + + // Note: + // deprecated-declarations suppression is only needed if some place in this + // proto file is something deprecated or if it references something from + // another file that is deprecated. printer->Print( "// @@protoc_insertion_point(imports)\n" "\n" "#pragma clang diagnostic push\n" - "#pragma clang diagnostic ignored \"-Wdeprecated-declarations\"\n" - "\n"); + "#pragma clang diagnostic ignored \"-Wdeprecated-declarations\"\n"); + if (includes_oneof) { + // The generated code for oneof's uses direct ivar access, suppress the + // warning incase developer turn that on in the context they compile the + // generated code. + printer->Print( + "#pragma clang diagnostic ignored \"-Wdirect-ivar-access\"\n"); + } printer->Print( + "\n" "#pragma mark - $root_class_name$\n" "\n" "@implementation $root_class_name$\n\n", diff --git a/src/google/protobuf/compiler/objectivec/objectivec_message.cc b/src/google/protobuf/compiler/objectivec/objectivec_message.cc index bf272596cb..e1a7861971 100644 --- a/src/google/protobuf/compiler/objectivec/objectivec_message.cc +++ b/src/google/protobuf/compiler/objectivec/objectivec_message.cc @@ -246,6 +246,22 @@ void MessageGenerator::DetermineForwardDeclarations(set* fwd_decls) { } } +bool MessageGenerator::IncludesOneOfDefinition() const { + if (!oneof_generators_.empty()) { + return true; + } + + for (vector::const_iterator iter = + nested_message_generators_.begin(); + iter != nested_message_generators_.end(); ++iter) { + if ((*iter)->IncludesOneOfDefinition()) { + return true; + } + } + + return false; +} + void MessageGenerator::GenerateEnumHeader(io::Printer* printer) { for (vector::iterator iter = enum_generators_.begin(); iter != enum_generators_.end(); ++iter) { diff --git a/src/google/protobuf/compiler/objectivec/objectivec_message.h b/src/google/protobuf/compiler/objectivec/objectivec_message.h index 8565e76ff6..910535ace3 100644 --- a/src/google/protobuf/compiler/objectivec/objectivec_message.h +++ b/src/google/protobuf/compiler/objectivec/objectivec_message.h @@ -66,6 +66,9 @@ class MessageGenerator { void GenerateExtensionRegistrationSource(io::Printer* printer); void DetermineForwardDeclarations(set* fwd_decls); + // Checks if the message or a nested message includes a oneof definition. + bool IncludesOneOfDefinition() const; + private: void GenerateParseFromMethodsHeader(io::Printer* printer);