diff options
Diffstat (limited to 'test/Analysis/ObjCPropertiesSyntaxChecks.m')
-rw-r--r-- | test/Analysis/ObjCPropertiesSyntaxChecks.m | 61 |
1 files changed, 61 insertions, 0 deletions
diff --git a/test/Analysis/ObjCPropertiesSyntaxChecks.m b/test/Analysis/ObjCPropertiesSyntaxChecks.m new file mode 100644 index 000000000000..5c642c581736 --- /dev/null +++ b/test/Analysis/ObjCPropertiesSyntaxChecks.m @@ -0,0 +1,61 @@ +// RUN: %clang_cc1 -w -fblocks -analyze -analyzer-checker=osx.ObjCProperty %s -verify + +#include "Inputs/system-header-simulator-objc.h" + +@interface I : NSObject { + NSMutableString *_mutableExplicitStr; + NSMutableString *_trulyMutableStr; + NSMutableString *_trulyMutableExplicitStr; +} +@property(copy) NSString *str; // no-warning +@property(copy) NSMutableString *mutableStr; // expected-warning{{Property of mutable type 'NSMutableString' has 'copy' attribute; an immutable object will be stored instead}} +@property(copy) NSMutableString *mutableExplicitStr; // expected-warning{{Property of mutable type 'NSMutableString' has 'copy' attribute; an immutable object will be stored instead}} +@property(copy, readonly) NSMutableString *mutableReadonlyStr; // no-warning +@property(copy, readonly) NSMutableString *mutableReadonlyStrOverriddenInChild; // no-warning +@property(copy, readonly) NSMutableString *mutableReadonlyStrOverriddenInCategory; // no-warning +@property(copy) NSMutableString *trulyMutableStr; // no-warning +@property(copy) NSMutableString *trulyMutableExplicitStr; // no-warning +@property(copy) NSMutableString *trulyMutableStrWithSynthesizedStorage; // no-warning +@end + +@interface I () {} +@property(copy) NSMutableString *mutableStrInCategory; // expected-warning{{Property of mutable type 'NSMutableString' has 'copy' attribute; an immutable object will be stored instead}} +@property (copy, readwrite) NSMutableString *mutableReadonlyStrOverriddenInCategory; // expected-warning{{Property of mutable type 'NSMutableString' has 'copy' attribute; an immutable object will be stored instead}} +@end + +@implementation I +@synthesize mutableExplicitStr = _mutableExplicitStr; +- (NSMutableString *)trulyMutableStr { + return _trulyMutableStr; +} +- (void)setTrulyMutableStr: (NSMutableString *) S { + _trulyMutableStr = [S mutableCopy]; +} +@dynamic trulyMutableExplicitStr; +- (NSMutableString *)trulyMutableExplicitStr { + return _trulyMutableExplicitStr; +} +- (void)setTrulyMutableExplicitStr: (NSMutableString *) S { + _trulyMutableExplicitStr = [S mutableCopy]; +} +@synthesize trulyMutableStrWithSynthesizedStorage; +- (NSMutableString *)trulyMutableStrWithSynthesizedStorage { + return trulyMutableStrWithSynthesizedStorage; +} +- (void)setTrulyMutableStrWithSynthesizedStorage: (NSMutableString *) S { + trulyMutableStrWithSynthesizedStorage = [S mutableCopy]; +} +@end + +@interface J : I {} +@property (copy, readwrite) NSMutableString *mutableReadonlyStrOverriddenInChild; // expected-warning{{Property of mutable type 'NSMutableString' has 'copy' attribute; an immutable object will be stored instead}} +@end + +@implementation J +@end + +// If we do not see the implementation then we do not want to warn, +// because we may miss a user-defined setter that works correctly. +@interface IWithoutImpl : NSObject {} +@property(copy) NSMutableString *mutableStr; // no-warning +@end |