mirror of
https://github.com/capstone-engine/llvm-capstone.git
synced 2024-12-03 19:32:35 +00:00
[analyzer] More tests for "release and stop tracking".
Under GC, a release message is ignored, so "release and stop tracking" just becomes "stop tracking". But CFRelease is still honored. This is the main difference between ns_consumed and cf_consumed. llvm-svn: 162234
This commit is contained in:
parent
6bae2a57d5
commit
eaacff4826
@ -107,9 +107,14 @@ NSFastEnumerationState;
|
||||
@end @interface NSNumber : NSValue - (char)charValue;
|
||||
- (id)initWithInt:(int)value;
|
||||
@end @class NSString;
|
||||
@interface NSArray : NSObject <NSCopying, NSMutableCopying, NSCoding, NSFastEnumeration> - (NSUInteger)count;
|
||||
@end @interface NSArray (NSArrayCreation) + (id)array;
|
||||
@end @interface NSAutoreleasePool : NSObject {
|
||||
@interface NSArray : NSObject <NSCopying, NSMutableCopying, NSCoding, NSFastEnumeration>
|
||||
- (NSUInteger)count;
|
||||
@end
|
||||
@interface NSArray (NSArrayCreation)
|
||||
+ (id)array;
|
||||
+ (id)arrayWithObjects:(const id [])objects count:(NSUInteger)cnt;
|
||||
@end
|
||||
@interface NSAutoreleasePool : NSObject {
|
||||
}
|
||||
- (void)drain;
|
||||
- (id)init;
|
||||
@ -385,3 +390,45 @@ CFDateRef returnsRetainedCFDate() {
|
||||
return (NSDate*) returnsRetainedCFDate(); // expected-warning{{leak}}
|
||||
}
|
||||
@end
|
||||
|
||||
|
||||
#if __has_feature(attribute_ns_consumed)
|
||||
#define NS_CONSUMED __attribute__((ns_consumed))
|
||||
#endif
|
||||
#if __has_feature(attribute_cf_consumed)
|
||||
#define CF_CONSUMED __attribute__((cf_consumed))
|
||||
#endif
|
||||
|
||||
void consumeAndStopTracking(id NS_CONSUMED obj, void (^callback)(void));
|
||||
void CFConsumeAndStopTracking(CFTypeRef CF_CONSUMED obj, void (^callback)(void));
|
||||
|
||||
void testConsumeAndStopTracking() {
|
||||
id retained = [@[] retain]; // +0, GC
|
||||
consumeAndStopTracking(retained, ^{}); // no-warning
|
||||
|
||||
id doubleRetained = [[@[] retain] retain]; // +0, GC
|
||||
consumeAndStopTracking(doubleRetained, ^{
|
||||
[doubleRetained release];
|
||||
}); // no-warning
|
||||
|
||||
id unretained = @[]; // +0
|
||||
consumeAndStopTracking(unretained, ^{}); // no-warning, GC
|
||||
}
|
||||
|
||||
void testCFConsumeAndStopTrackingMsg() {
|
||||
id retained = [@[] retain]; // +0, GC
|
||||
CFConsumeAndStopTracking((CFTypeRef)retained, ^{}); // expected-warning {{Incorrect decrement of the reference count of an object that is not owned at this point by the caller}}
|
||||
}
|
||||
|
||||
void testCFConsumeAndStopTracking() {
|
||||
CFTypeRef retained = returnsRetainedCFDate(); // +1
|
||||
CFConsumeAndStopTracking(retained, ^{}); // no-warning
|
||||
|
||||
CFTypeRef doubleRetained = CFRetain(returnsRetainedCFDate()); // +2
|
||||
CFConsumeAndStopTracking(doubleRetained, ^{
|
||||
CFRelease(doubleRetained);
|
||||
}); // no-warning
|
||||
|
||||
id unretained = @[]; // +0
|
||||
CFConsumeAndStopTracking((CFTypeRef)unretained, ^{}); // expected-warning {{Incorrect decrement of the reference count of an object that is not owned at this point by the caller}}
|
||||
}
|
||||
|
@ -1748,7 +1748,7 @@ extern id NSApp;
|
||||
@end
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Test returning allocated memory in a struct.
|
||||
//
|
||||
//
|
||||
// We currently don't have a general way to track pointers that "escape".
|
||||
// Here we test that RetainCountChecker doesn't get excited about returning
|
||||
// allocated CF objects in struct fields.
|
||||
@ -1856,7 +1856,10 @@ id makeCollectableNonLeak() {
|
||||
return [objCObject autorelease]; // +0
|
||||
}
|
||||
|
||||
|
||||
void consumeAndStopTracking(id NS_CONSUMED obj, void (^callback)(void));
|
||||
void CFConsumeAndStopTracking(CFTypeRef CF_CONSUMED obj, void (^callback)(void));
|
||||
|
||||
void testConsumeAndStopTracking() {
|
||||
id retained = [@[] retain]; // +1
|
||||
consumeAndStopTracking(retained, ^{}); // no-warning
|
||||
@ -1869,3 +1872,16 @@ void testConsumeAndStopTracking() {
|
||||
id unretained = @[]; // +0
|
||||
consumeAndStopTracking(unretained, ^{}); // expected-warning {{Incorrect decrement of the reference count of an object that is not owned at this point by the caller}}
|
||||
}
|
||||
|
||||
void testCFConsumeAndStopTracking() {
|
||||
id retained = [@[] retain]; // +1
|
||||
CFConsumeAndStopTracking((CFTypeRef)retained, ^{}); // no-warning
|
||||
|
||||
id doubleRetained = [[@[] retain] retain]; // +2
|
||||
CFConsumeAndStopTracking((CFTypeRef)doubleRetained, ^{
|
||||
[doubleRetained release];
|
||||
}); // no-warning
|
||||
|
||||
id unretained = @[]; // +0
|
||||
CFConsumeAndStopTracking((CFTypeRef)unretained, ^{}); // expected-warning {{Incorrect decrement of the reference count of an object that is not owned at this point by the caller}}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user