| Daniel Dunbar | a572887 | 2009-12-15 20:14:24 +0000 | [diff] [blame] | 1 | // RUN: %clang_cc1 -triple x86_64-apple-darwin10 -analyze -checker-cfref -analyzer-store=basic -fblocks -verify %s | 
 | 2 | // RUN: %clang_cc1 -triple x86_64-apple-darwin10 -analyze -checker-cfref -analyzer-store=region -fblocks -verify %s | 
| Ted Kremenek | 0964a06 | 2009-01-21 06:57:53 +0000 | [diff] [blame] | 3 |  | 
| Ted Kremenek | 71ef5d6 | 2009-07-17 00:19:33 +0000 | [diff] [blame] | 4 | #if __has_feature(attribute_ns_returns_retained) | 
 | 5 | #define NS_RETURNS_RETAINED __attribute__((ns_returns_retained)) | 
 | 6 | #endif | 
 | 7 | #if __has_feature(attribute_cf_returns_retained) | 
 | 8 | #define CF_RETURNS_RETAINED __attribute__((cf_returns_retained)) | 
 | 9 | #endif | 
 | 10 |  | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 11 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 12 | // The following code is reduced using delta-debugging from Mac OS X headers: | 
 | 13 | // | 
 | 14 | // #include <Cocoa/Cocoa.h> | 
 | 15 | // #include <CoreFoundation/CoreFoundation.h> | 
 | 16 | // #include <DiskArbitration/DiskArbitration.h> | 
 | 17 | // #include <QuartzCore/QuartzCore.h> | 
 | 18 | // #include <Quartz/Quartz.h> | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 19 | // #include <IOKit/IOKitLib.h> | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 20 | // | 
 | 21 | // It includes the basic definitions for the test cases below. | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 22 | //===----------------------------------------------------------------------===// | 
 | 23 |  | 
 | 24 | typedef unsigned int __darwin_natural_t; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 25 | typedef unsigned long uintptr_t; | 
 | 26 | typedef unsigned int uint32_t; | 
 | 27 | typedef unsigned long long uint64_t; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 28 | typedef unsigned int UInt32; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 29 | typedef signed long CFIndex; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 30 | typedef struct { | 
 | 31 |     CFIndex location; | 
 | 32 |     CFIndex length; | 
 | 33 | } CFRange; | 
 | 34 | static __inline__ __attribute__((always_inline)) CFRange CFRangeMake(CFIndex loc, CFIndex len) { | 
 | 35 |     CFRange range; | 
 | 36 |     range.location = loc; | 
 | 37 |     range.length = len; | 
 | 38 |     return range; | 
 | 39 | } | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 40 | typedef const void * CFTypeRef; | 
 | 41 | typedef const struct __CFString * CFStringRef; | 
 | 42 | typedef const struct __CFAllocator * CFAllocatorRef; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 43 | extern const CFAllocatorRef kCFAllocatorDefault; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 44 | extern CFTypeRef CFRetain(CFTypeRef cf); | 
 | 45 | extern void CFRelease(CFTypeRef cf); | 
 | 46 | typedef struct { | 
 | 47 | } | 
 | 48 | CFArrayCallBacks; | 
 | 49 | extern const CFArrayCallBacks kCFTypeArrayCallBacks; | 
 | 50 | typedef const struct __CFArray * CFArrayRef; | 
 | 51 | typedef struct __CFArray * CFMutableArrayRef; | 
 | 52 | extern CFMutableArrayRef CFArrayCreateMutable(CFAllocatorRef allocator, CFIndex capacity, const CFArrayCallBacks *callBacks); | 
 | 53 | extern const void *CFArrayGetValueAtIndex(CFArrayRef theArray, CFIndex idx); | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 54 | extern void CFArrayAppendValue(CFMutableArrayRef theArray, const void *value); | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 55 | typedef struct { | 
 | 56 | } | 
 | 57 | CFDictionaryKeyCallBacks; | 
 | 58 | extern const CFDictionaryKeyCallBacks kCFTypeDictionaryKeyCallBacks; | 
 | 59 | typedef struct { | 
 | 60 | } | 
 | 61 | CFDictionaryValueCallBacks; | 
 | 62 | extern const CFDictionaryValueCallBacks kCFTypeDictionaryValueCallBacks; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 63 | typedef const struct __CFDictionary * CFDictionaryRef; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 64 | typedef struct __CFDictionary * CFMutableDictionaryRef; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 65 | extern CFMutableDictionaryRef CFDictionaryCreateMutable(CFAllocatorRef allocator, CFIndex capacity, const CFDictionaryKeyCallBacks *keyCallBacks, const CFDictionaryValueCallBacks *valueCallBacks); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 66 | typedef UInt32 CFStringEncoding; | 
 | 67 | enum { | 
 | 68 | kCFStringEncodingMacRoman = 0,     kCFStringEncodingWindowsLatin1 = 0x0500,     kCFStringEncodingISOLatin1 = 0x0201,     kCFStringEncodingNextStepLatin = 0x0B01,     kCFStringEncodingASCII = 0x0600,     kCFStringEncodingUnicode = 0x0100,     kCFStringEncodingUTF8 = 0x08000100,     kCFStringEncodingNonLossyASCII = 0x0BFF      ,     kCFStringEncodingUTF16 = 0x0100,     kCFStringEncodingUTF16BE = 0x10000100,     kCFStringEncodingUTF16LE = 0x14000100,      kCFStringEncodingUTF32 = 0x0c000100,     kCFStringEncodingUTF32BE = 0x18000100,     kCFStringEncodingUTF32LE = 0x1c000100  }; | 
 | 69 | extern CFStringRef CFStringCreateWithCString(CFAllocatorRef alloc, const char *cStr, CFStringEncoding encoding); | 
 | 70 | typedef double CFTimeInterval; | 
 | 71 | typedef CFTimeInterval CFAbsoluteTime; | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 72 | extern CFAbsoluteTime CFAbsoluteTimeGetCurrent(void); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 73 | typedef const struct __CFDate * CFDateRef; | 
 | 74 | extern CFDateRef CFDateCreate(CFAllocatorRef allocator, CFAbsoluteTime at); | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 75 | extern CFAbsoluteTime CFDateGetAbsoluteTime(CFDateRef theDate); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 76 | typedef __darwin_natural_t natural_t; | 
 | 77 | typedef natural_t mach_port_name_t; | 
 | 78 | typedef mach_port_name_t mach_port_t; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 79 | typedef int kern_return_t; | 
 | 80 | typedef kern_return_t mach_error_t; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 81 | enum { | 
 | 82 | kCFNumberSInt8Type = 1,     kCFNumberSInt16Type = 2,     kCFNumberSInt32Type = 3,     kCFNumberSInt64Type = 4,     kCFNumberFloat32Type = 5,     kCFNumberFloat64Type = 6,      kCFNumberCharType = 7,     kCFNumberShortType = 8,     kCFNumberIntType = 9,     kCFNumberLongType = 10,     kCFNumberLongLongType = 11,     kCFNumberFloatType = 12,     kCFNumberDoubleType = 13,      kCFNumberCFIndexType = 14,      kCFNumberNSIntegerType = 15,     kCFNumberCGFloatType = 16,     kCFNumberMaxType = 16    }; | 
 | 83 | typedef CFIndex CFNumberType; | 
 | 84 | typedef const struct __CFNumber * CFNumberRef; | 
 | 85 | extern CFNumberRef CFNumberCreate(CFAllocatorRef allocator, CFNumberType theType, const void *valuePtr); | 
 | 86 | typedef const struct __CFAttributedString *CFAttributedStringRef; | 
 | 87 | typedef struct __CFAttributedString *CFMutableAttributedStringRef; | 
 | 88 | extern CFAttributedStringRef CFAttributedStringCreate(CFAllocatorRef alloc, CFStringRef str, CFDictionaryRef attributes) ; | 
 | 89 | extern CFMutableAttributedStringRef CFAttributedStringCreateMutableCopy(CFAllocatorRef alloc, CFIndex maxLength, CFAttributedStringRef aStr) ; | 
 | 90 | extern void CFAttributedStringSetAttribute(CFMutableAttributedStringRef aStr, CFRange range, CFStringRef attrName, CFTypeRef value) ; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 91 | typedef signed char BOOL; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 92 | typedef unsigned long NSUInteger; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 93 | @class NSString, Protocol; | 
 | 94 | extern void NSLog(NSString *format, ...) __attribute__((format(__NSString__, 1, 2))); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 95 | typedef struct _NSZone NSZone; | 
 | 96 | @class NSInvocation, NSMethodSignature, NSCoder, NSString, NSEnumerator; | 
| Ted Kremenek | ac02f20 | 2009-08-20 05:13:36 +0000 | [diff] [blame] | 97 | @protocol NSObject | 
 | 98 | - (BOOL)isEqual:(id)object; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 99 | - (id)retain; | 
 | 100 | - (oneway void)release; | 
| Ted Kremenek | a7ecc37 | 2009-01-28 21:20:48 +0000 | [diff] [blame] | 101 | - (id)autorelease; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 102 | @end  @protocol NSCopying  - (id)copyWithZone:(NSZone *)zone; | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 103 | @end  @protocol NSMutableCopying  - (id)mutableCopyWithZone:(NSZone *)zone; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 104 | @end  @protocol NSCoding  - (void)encodeWithCoder:(NSCoder *)aCoder; | 
| Ted Kremenek | ac02f20 | 2009-08-20 05:13:36 +0000 | [diff] [blame] | 105 | @end | 
 | 106 | @interface NSObject <NSObject> {} | 
| Ted Kremenek | 8be2a67 | 2009-03-13 20:27:06 +0000 | [diff] [blame] | 107 | + (id)allocWithZone:(NSZone *)zone; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 108 | + (id)alloc; | 
 | 109 | - (void)dealloc; | 
| Ted Kremenek | ac02f20 | 2009-08-20 05:13:36 +0000 | [diff] [blame] | 110 | @end | 
 | 111 | @interface NSObject (NSCoderMethods) | 
 | 112 | - (id)awakeAfterUsingCoder:(NSCoder *)aDecoder; | 
 | 113 | @end | 
 | 114 | extern id NSAllocateObject(Class aClass, NSUInteger extraBytes, NSZone *zone); | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 115 | typedef struct { | 
 | 116 | } | 
 | 117 | NSFastEnumerationState; | 
 | 118 | @protocol NSFastEnumeration  - (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state objects:(id *)stackbuf count:(NSUInteger)len; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 119 | @end           @class NSString, NSDictionary; | 
 | 120 | @interface NSValue : NSObject <NSCopying, NSCoding>  - (void)getValue:(void *)value; | 
 | 121 | @end  @interface NSNumber : NSValue  - (char)charValue; | 
 | 122 | - (id)initWithInt:(int)value; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 123 | @end   @class NSString; | 
 | 124 | @interface NSArray : NSObject <NSCopying, NSMutableCopying, NSCoding, NSFastEnumeration>  - (NSUInteger)count; | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 125 | @end  @interface NSArray (NSArrayCreation)  + (id)array; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 126 | @end       @interface NSAutoreleasePool : NSObject { | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 127 | } | 
 | 128 | - (void)drain; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 129 | @end extern NSString * const NSBundleDidLoadNotification; | 
 | 130 | typedef double NSTimeInterval; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 131 | @interface NSDate : NSObject <NSCopying, NSCoding>  - (NSTimeInterval)timeIntervalSinceReferenceDate; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 132 | @end            typedef unsigned short unichar; | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 133 | @interface NSString : NSObject <NSCopying, NSMutableCopying, NSCoding>    - (NSUInteger)length; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 134 | - ( const char *)UTF8String; | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 135 | - (id)initWithUTF8String:(const char *)nullTerminatedCString; | 
 | 136 | + (id)stringWithUTF8String:(const char *)nullTerminatedCString; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 137 | @end        @class NSString, NSURL, NSError; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 138 | @interface NSData : NSObject <NSCopying, NSMutableCopying, NSCoding>  - (NSUInteger)length; | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 139 | + (id)dataWithBytesNoCopy:(void *)bytes length:(NSUInteger)length; | 
 | 140 | + (id)dataWithBytesNoCopy:(void *)bytes length:(NSUInteger)length freeWhenDone:(BOOL)b; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 141 | @end   @class NSLocale, NSDate, NSCalendar, NSTimeZone, NSError, NSArray, NSMutableDictionary; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 142 | @interface NSDictionary : NSObject <NSCopying, NSMutableCopying, NSCoding, NSFastEnumeration>  - (NSUInteger)count; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 143 | @end    @interface NSMutableDictionary : NSDictionary  - (void)removeObjectForKey:(id)aKey; | 
 | 144 | - (void)setObject:(id)anObject forKey:(id)aKey; | 
 | 145 | @end  @interface NSMutableDictionary (NSMutableDictionaryCreation)  + (id)dictionaryWithCapacity:(NSUInteger)numItems; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 146 | @end  typedef double CGFloat; | 
 | 147 | struct CGSize { | 
 | 148 | }; | 
 | 149 | typedef struct CGSize CGSize; | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 150 | struct CGRect { | 
 | 151 | }; | 
 | 152 | typedef struct CGRect CGRect; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 153 | typedef mach_port_t io_object_t; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 154 | typedef char io_name_t[128]; | 
 | 155 | typedef io_object_t io_iterator_t; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 156 | typedef io_object_t io_service_t; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 157 | typedef struct IONotificationPort * IONotificationPortRef; | 
 | 158 | typedef void (*IOServiceMatchingCallback)(  void * refcon,  io_iterator_t iterator ); | 
 | 159 | io_service_t IOServiceGetMatchingService(  mach_port_t masterPort,  CFDictionaryRef matching ); | 
 | 160 | kern_return_t IOServiceGetMatchingServices(  mach_port_t masterPort,  CFDictionaryRef matching,  io_iterator_t * existing ); | 
 | 161 | kern_return_t IOServiceAddNotification(  mach_port_t masterPort,  const io_name_t notificationType,  CFDictionaryRef matching,  mach_port_t wakePort,  uintptr_t reference,  io_iterator_t * notification ) __attribute__((deprecated)); | 
 | 162 | kern_return_t IOServiceAddMatchingNotification(  IONotificationPortRef notifyPort,  const io_name_t notificationType,  CFDictionaryRef matching,         IOServiceMatchingCallback callback,         void * refCon,  io_iterator_t * notification ); | 
 | 163 | CFMutableDictionaryRef IOServiceMatching(  const char * name ); | 
 | 164 | CFMutableDictionaryRef IOServiceNameMatching(  const char * name ); | 
 | 165 | CFMutableDictionaryRef IOBSDNameMatching(  mach_port_t masterPort,  uint32_t options,  const char * bsdName ); | 
 | 166 | CFMutableDictionaryRef IOOpenFirmwarePathMatching(  mach_port_t masterPort,  uint32_t options,  const char * path ); | 
 | 167 | CFMutableDictionaryRef IORegistryEntryIDMatching(  uint64_t entryID ); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 168 | typedef struct __DASession * DASessionRef; | 
 | 169 | extern DASessionRef DASessionCreate( CFAllocatorRef allocator ); | 
 | 170 | typedef struct __DADisk * DADiskRef; | 
 | 171 | extern DADiskRef DADiskCreateFromBSDName( CFAllocatorRef allocator, DASessionRef session, const char * name ); | 
 | 172 | extern DADiskRef DADiskCreateFromIOMedia( CFAllocatorRef allocator, DASessionRef session, io_service_t media ); | 
 | 173 | extern CFDictionaryRef DADiskCopyDescription( DADiskRef disk ); | 
 | 174 | extern DADiskRef DADiskCopyWholeDisk( DADiskRef disk ); | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 175 | @interface NSTask : NSObject - (id)init; | 
 | 176 | @end                    typedef struct CGColorSpace *CGColorSpaceRef; | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 177 | typedef struct CGImage *CGImageRef; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 178 | typedef struct CGLayer *CGLayerRef; | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 179 | @interface NSResponder : NSObject <NSCoding> { | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 180 | } | 
 | 181 | @end    @protocol NSAnimatablePropertyContainer      - (id)animator; | 
 | 182 | @end  extern NSString *NSAnimationTriggerOrderIn ; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 183 | @interface NSView : NSResponder  <NSAnimatablePropertyContainer>  { | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 184 | } | 
 | 185 | @end @protocol NSValidatedUserInterfaceItem - (SEL)action; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 186 | @end   @protocol NSUserInterfaceValidations - (BOOL)validateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)anItem; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 187 | @end  @class NSDate, NSDictionary, NSError, NSException, NSNotification; | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 188 | @interface NSApplication : NSResponder <NSUserInterfaceValidations> { | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 189 | } | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 190 | @end   enum { | 
 | 191 | NSTerminateCancel = 0,         NSTerminateNow = 1,         NSTerminateLater = 2 }; | 
 | 192 | typedef NSUInteger NSApplicationTerminateReply; | 
 | 193 | @protocol NSApplicationDelegate <NSObject> @optional        - (NSApplicationTerminateReply)applicationShouldTerminate:(NSApplication *)sender; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 194 | @end  @class NSAttributedString, NSEvent, NSFont, NSFormatter, NSImage, NSMenu, NSText, NSView, NSTextView; | 
 | 195 | @interface NSCell : NSObject <NSCopying, NSCoding> { | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 196 | } | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 197 | @end @class NSTextField, NSPanel, NSArray, NSWindow, NSImage, NSButton, NSError; | 
 | 198 | typedef struct { | 
 | 199 | } | 
 | 200 | CVTimeStamp; | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 201 | @interface CIImage : NSObject <NSCoding, NSCopying> { | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 202 | } | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 203 | typedef int CIFormat; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 204 | @end  enum { | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 205 | kDAReturnSuccess = 0,     kDAReturnError = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x01,     kDAReturnBusy = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x02,     kDAReturnBadArgument = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x03,     kDAReturnExclusiveAccess = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x04,     kDAReturnNoResources = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x05,     kDAReturnNotFound = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x06,     kDAReturnNotMounted = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x07,     kDAReturnNotPermitted = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x08,     kDAReturnNotPrivileged = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x09,     kDAReturnNotReady = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x0A,     kDAReturnNotWritable = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x0B,     kDAReturnUnsupported = (((0x3e)&0x3f)<<26) | (((0x368)&0xfff)<<14) | 0x0C }; | 
 | 206 | typedef mach_error_t DAReturn; | 
 | 207 | typedef const struct __DADissenter * DADissenterRef; | 
 | 208 | extern DADissenterRef DADissenterCreate( CFAllocatorRef allocator, DAReturn status, CFStringRef string ); | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 209 | @interface CIContext: NSObject { | 
 | 210 | } | 
 | 211 | - (CGImageRef)createCGImage:(CIImage *)im fromRect:(CGRect)r; | 
 | 212 | - (CGImageRef)createCGImage:(CIImage *)im fromRect:(CGRect)r     format:(CIFormat)f colorSpace:(CGColorSpaceRef)cs; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 213 | - (CGLayerRef)createCGLayerWithSize:(CGSize)size info:(CFDictionaryRef)d; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 214 | @end extern NSString* const QCRendererEventKey; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 215 | @protocol QCCompositionRenderer - (NSDictionary*) attributes; | 
 | 216 | @end   @interface QCRenderer : NSObject <QCCompositionRenderer> { | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 217 | } | 
 | 218 | - (id) createSnapshotImageOfType:(NSString*)type; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 219 | @end  extern NSString* const QCViewDidStartRenderingNotification; | 
 | 220 | @interface QCView : NSView <QCCompositionRenderer> { | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 221 | } | 
 | 222 | - (id) createSnapshotImageOfType:(NSString*)type; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 223 | @end    enum { | 
 | 224 | ICEXIFOrientation1 = 1,     ICEXIFOrientation2 = 2,     ICEXIFOrientation3 = 3,     ICEXIFOrientation4 = 4,     ICEXIFOrientation5 = 5,     ICEXIFOrientation6 = 6,     ICEXIFOrientation7 = 7,     ICEXIFOrientation8 = 8, }; | 
 | 225 | @class ICDevice; | 
 | 226 | @protocol ICDeviceDelegate <NSObject>  @required      - (void)didRemoveDevice:(ICDevice*)device; | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 227 | @end extern NSString *const ICScannerStatusWarmingUp; | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 228 | @class ICScannerDevice; | 
 | 229 | @protocol ICScannerDeviceDelegate <ICDeviceDelegate>  @optional       - (void)scannerDeviceDidBecomeAvailable:(ICScannerDevice*)scanner; | 
| Ted Kremenek | a0cc00d | 2009-05-11 17:45:06 +0000 | [diff] [blame] | 230 | @end | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 231 |  | 
| Ted Kremenek | cc58eae | 2009-09-01 18:33:16 +0000 | [diff] [blame] | 232 | typedef long unsigned int __darwin_size_t; | 
 | 233 | typedef __darwin_size_t size_t; | 
 | 234 | typedef unsigned long CFTypeID; | 
 | 235 | struct CGPoint { | 
 | 236 |   CGFloat x; | 
 | 237 |   CGFloat y; | 
 | 238 | }; | 
 | 239 | typedef struct CGPoint CGPoint; | 
 | 240 | typedef struct CGGradient *CGGradientRef; | 
 | 241 | typedef uint32_t CGGradientDrawingOptions; | 
 | 242 | extern CFTypeID CGGradientGetTypeID(void); | 
 | 243 | extern CGGradientRef CGGradientCreateWithColorComponents(CGColorSpaceRef | 
 | 244 |   space, const CGFloat components[], const CGFloat locations[], size_t count); | 
 | 245 | extern CGGradientRef CGGradientCreateWithColors(CGColorSpaceRef space, | 
 | 246 |   CFArrayRef colors, const CGFloat locations[]); | 
 | 247 | extern CGGradientRef CGGradientRetain(CGGradientRef gradient); | 
 | 248 | extern void CGGradientRelease(CGGradientRef gradient); | 
 | 249 | typedef struct CGContext *CGContextRef; | 
 | 250 | extern void CGContextDrawLinearGradient(CGContextRef context, | 
 | 251 |     CGGradientRef gradient, CGPoint startPoint, CGPoint endPoint, | 
 | 252 |     CGGradientDrawingOptions options); | 
 | 253 | extern CGColorSpaceRef CGColorSpaceCreateDeviceRGB(void); | 
 | 254 |  | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 255 | //===----------------------------------------------------------------------===// | 
 | 256 | // Test cases. | 
 | 257 | //===----------------------------------------------------------------------===// | 
 | 258 |  | 
 | 259 | CFAbsoluteTime f1() { | 
 | 260 |   CFAbsoluteTime t = CFAbsoluteTimeGetCurrent(); | 
 | 261 |   CFDateRef date = CFDateCreate(0, t); | 
 | 262 |   CFRetain(date); | 
 | 263 |   CFRelease(date); | 
 | 264 |   CFDateGetAbsoluteTime(date); // no-warning | 
 | 265 |   CFRelease(date); | 
 | 266 |   t = CFDateGetAbsoluteTime(date);   // expected-warning{{Reference-counted object is used after it is released.}} | 
 | 267 |   return t; | 
 | 268 | } | 
 | 269 |  | 
 | 270 | CFAbsoluteTime f2() { | 
 | 271 |   CFAbsoluteTime t = CFAbsoluteTimeGetCurrent(); | 
 | 272 |   CFDateRef date = CFDateCreate(0, t);   | 
 | 273 |   [((NSDate*) date) retain]; | 
 | 274 |   CFRelease(date); | 
 | 275 |   CFDateGetAbsoluteTime(date); // no-warning | 
 | 276 |   [((NSDate*) date) release]; | 
 | 277 |   t = CFDateGetAbsoluteTime(date);   // expected-warning{{Reference-counted object is used after it is released.}} | 
 | 278 |   return t; | 
 | 279 | } | 
 | 280 |  | 
 | 281 |  | 
 | 282 | NSDate* global_x; | 
 | 283 |  | 
 | 284 | // Test to see if we supresss an error when we store the pointer | 
 | 285 | // to a global. | 
 | 286 |  | 
 | 287 | CFAbsoluteTime f3() { | 
 | 288 |   CFAbsoluteTime t = CFAbsoluteTimeGetCurrent(); | 
 | 289 |   CFDateRef date = CFDateCreate(0, t);   | 
 | 290 |   [((NSDate*) date) retain]; | 
 | 291 |   CFRelease(date); | 
 | 292 |   CFDateGetAbsoluteTime(date); // no-warning | 
 | 293 |   global_x = (NSDate*) date;   | 
 | 294 |   [((NSDate*) date) release]; | 
 | 295 |   t = CFDateGetAbsoluteTime(date);   // no-warning | 
 | 296 |   return t; | 
 | 297 | } | 
 | 298 |  | 
| Ted Kremenek | 0964a06 | 2009-01-21 06:57:53 +0000 | [diff] [blame] | 299 | //--------------------------------------------------------------------------- | 
 | 300 | // Test case 'f4' differs for region store and basic store.  See | 
 | 301 | // retain-release-region-store.m and retain-release-basic-store.m. | 
 | 302 | //--------------------------------------------------------------------------- | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 303 |  | 
 | 304 | // Test a leak. | 
 | 305 |  | 
 | 306 | CFAbsoluteTime f5(int x) {   | 
 | 307 |   CFAbsoluteTime t = CFAbsoluteTimeGetCurrent(); | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 308 |   CFDateRef date = CFDateCreate(0, t); // expected-warning{{leak}} | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 309 |    | 
 | 310 |   if (x) | 
 | 311 |     CFRelease(date); | 
 | 312 |    | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 313 |   return t; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 314 | } | 
 | 315 |  | 
 | 316 | // Test a leak involving the return. | 
 | 317 |  | 
 | 318 | CFDateRef f6(int x) {   | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 319 |   CFDateRef date = CFDateCreate(0, CFAbsoluteTimeGetCurrent());  // expected-warning{{leak}} | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 320 |   CFRetain(date); | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 321 |   return date; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 322 | } | 
 | 323 |  | 
 | 324 | // Test a leak involving an overwrite. | 
 | 325 |  | 
 | 326 | CFDateRef f7() { | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 327 |   CFDateRef date = CFDateCreate(0, CFAbsoluteTimeGetCurrent());  //expected-warning{{leak}} | 
| Ted Kremenek | 3148eb4 | 2009-01-24 00:55:43 +0000 | [diff] [blame] | 328 |   CFRetain(date); | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 329 |   date = CFDateCreate(0, CFAbsoluteTimeGetCurrent()); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 330 |   return date; | 
 | 331 | } | 
 | 332 |  | 
 | 333 | // Generalization of Create rule.  MyDateCreate returns a CFXXXTypeRef, and | 
 | 334 | // has the word create. | 
 | 335 | CFDateRef MyDateCreate(); | 
 | 336 |  | 
 | 337 | CFDateRef f8() { | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 338 |   CFDateRef date = MyDateCreate(); // expected-warning{{leak}} | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 339 |   CFRetain(date);   | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 340 |   return date; | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 341 | } | 
 | 342 |  | 
 | 343 | CFDateRef f9() { | 
 | 344 |   CFDateRef date = CFDateCreate(0, CFAbsoluteTimeGetCurrent()); | 
 | 345 |   int *p = 0; | 
| Ted Kremenek | 25d01ba | 2009-03-09 22:46:49 +0000 | [diff] [blame] | 346 |   // When allocations fail, CFDateCreate can return null. | 
 | 347 |   if (!date) *p = 1; // expected-warning{{null}} | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 348 |   return date; | 
 | 349 | } | 
 | 350 |  | 
 | 351 | // Handle DiskArbitration API: | 
 | 352 | // | 
 | 353 | // http://developer.apple.com/DOCUMENTATION/DARWIN/Reference/DiscArbitrationFramework/ | 
 | 354 | // | 
 | 355 | void f10(io_service_t media, DADiskRef d, CFStringRef s) { | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 356 |   DADiskRef disk = DADiskCreateFromBSDName(kCFAllocatorDefault, 0, "hello"); // expected-warning{{leak}} | 
 | 357 |   if (disk) NSLog(@"ok"); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 358 |    | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 359 |   disk = DADiskCreateFromIOMedia(kCFAllocatorDefault, 0, media); // expected-warning{{leak}} | 
 | 360 |   if (disk) NSLog(@"ok"); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 361 |  | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 362 |   CFDictionaryRef dict = DADiskCopyDescription(d);  // expected-warning{{leak}} | 
 | 363 |   if (dict) NSLog(@"ok");  | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 364 |    | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 365 |   disk = DADiskCopyWholeDisk(d); // expected-warning{{leak}} | 
 | 366 |   if (disk) NSLog(@"ok"); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 367 |      | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 368 |   DADissenterRef dissenter = DADissenterCreate(kCFAllocatorDefault,   // expected-warning{{leak}} | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 369 |                                                 kDAReturnSuccess, s); | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 370 |   if (dissenter) NSLog(@"ok"); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 371 |    | 
| Ted Kremenek | cf118d4 | 2009-02-04 23:49:09 +0000 | [diff] [blame] | 372 |   DASessionRef session = DASessionCreate(kCFAllocatorDefault);  // expected-warning{{leak}} | 
 | 373 |   if (session) NSLog(@"ok"); | 
| Ted Kremenek | 1261938 | 2009-01-12 21:45:02 +0000 | [diff] [blame] | 374 | } | 
 | 375 |  | 
 | 376 | // Test retain/release checker with CFString and CFMutableArray. | 
 | 377 | void f11() { | 
 | 378 |   // Create the array. | 
 | 379 |   CFMutableArrayRef A = CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); | 
 | 380 |  | 
 | 381 |   // Create a string. | 
 | 382 |   CFStringRef s1 = CFStringCreateWithCString(0, "hello world", | 
 | 383 |                                              kCFStringEncodingUTF8); | 
 | 384 |  | 
 | 385 |   // Add the string to the array. | 
 | 386 |   CFArrayAppendValue(A, s1); | 
 | 387 |    | 
 | 388 |   // Decrement the reference count. | 
 | 389 |   CFRelease(s1); // no-warning | 
 | 390 |    | 
 | 391 |   // Get the string.  We don't own it. | 
 | 392 |   s1 = (CFStringRef) CFArrayGetValueAtIndex(A, 0); | 
 | 393 |    | 
 | 394 |   // Release the array. | 
 | 395 |   CFRelease(A); // no-warning | 
 | 396 |    | 
 | 397 |   // Release the string.  This is a bug. | 
 | 398 |   CFRelease(s1); // expected-warning{{Incorrect decrement of the reference count}} | 
 | 399 | } | 
 | 400 |  | 
| Ted Kremenek | 9989065 | 2009-01-16 18:40:33 +0000 | [diff] [blame] | 401 | // PR 3337: Handle functions declared using typedefs. | 
 | 402 | typedef CFTypeRef CREATEFUN(); | 
 | 403 | CREATEFUN MyCreateFun; | 
 | 404 |  | 
 | 405 | void f12() { | 
 | 406 |   CFTypeRef o = MyCreateFun(); // expected-warning {{leak}} | 
 | 407 | } | 
| Ted Kremenek | a7ecc37 | 2009-01-28 21:20:48 +0000 | [diff] [blame] | 408 |  | 
 | 409 | void f13_autorelease() { | 
| Ted Kremenek | 6b62ec9 | 2009-05-09 01:50:57 +0000 | [diff] [blame] | 410 |   CFMutableArrayRef A = CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); // no-warning | 
| Ted Kremenek | a7ecc37 | 2009-01-28 21:20:48 +0000 | [diff] [blame] | 411 |   [(id) A autorelease]; // no-warning | 
 | 412 | } | 
| Ted Kremenek | 79f7f8a | 2009-02-19 18:20:28 +0000 | [diff] [blame] | 413 |  | 
| Ted Kremenek | 6b62ec9 | 2009-05-09 01:50:57 +0000 | [diff] [blame] | 414 | void f13_autorelease_b() { | 
 | 415 |   CFMutableArrayRef A = CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); | 
 | 416 |   [(id) A autorelease]; | 
| Ted Kremenek | eaedfea | 2009-05-10 05:11:21 +0000 | [diff] [blame] | 417 |   [(id) A autorelease]; // expected-warning{{Object sent -autorelease too many times}} | 
| Ted Kremenek | 6b62ec9 | 2009-05-09 01:50:57 +0000 | [diff] [blame] | 418 | } | 
 | 419 |  | 
 | 420 | CFMutableArrayRef f13_autorelease_c() { | 
 | 421 |   CFMutableArrayRef A = CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); | 
 | 422 |   [(id) A autorelease]; | 
 | 423 |   [(id) A autorelease];  | 
| Ted Kremenek | eaedfea | 2009-05-10 05:11:21 +0000 | [diff] [blame] | 424 |   return A; // expected-warning{{Object sent -autorelease too many times}} | 
| Ted Kremenek | 6b62ec9 | 2009-05-09 01:50:57 +0000 | [diff] [blame] | 425 | } | 
 | 426 |  | 
 | 427 | CFMutableArrayRef f13_autorelease_d() { | 
 | 428 |   CFMutableArrayRef A = CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); | 
 | 429 |   [(id) A autorelease]; | 
 | 430 |   [(id) A autorelease];  | 
| Ted Kremenek | eaedfea | 2009-05-10 05:11:21 +0000 | [diff] [blame] | 431 |   CFMutableArrayRef B = CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); // expected-warning{{Object sent -autorelease too many times}} | 
| Ted Kremenek | 6b62ec9 | 2009-05-09 01:50:57 +0000 | [diff] [blame] | 432 |   CFRelease(B); // no-warning | 
| Mike Stump | 08631d1 | 2009-07-21 18:58:15 +0000 | [diff] [blame] | 433 |   while (1) {} | 
| Ted Kremenek | 6b62ec9 | 2009-05-09 01:50:57 +0000 | [diff] [blame] | 434 | } | 
 | 435 |  | 
 | 436 |  | 
| Ted Kremenek | 79f7f8a | 2009-02-19 18:20:28 +0000 | [diff] [blame] | 437 | // This case exercises the logic where the leak site is the same as the allocation site. | 
 | 438 | void f14_leakimmediately() { | 
 | 439 |   CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); // expected-warning{{leak}} | 
 | 440 | } | 
| Ted Kremenek | 9f45d28 | 2009-03-05 18:15:02 +0000 | [diff] [blame] | 441 |  | 
| Ted Kremenek | e82e13a | 2009-04-07 05:33:18 +0000 | [diff] [blame] | 442 | // Test that we track an allocated object beyond the point where the *name* | 
 | 443 | // of the variable storing the reference is no longer live. | 
 | 444 | void f15() { | 
 | 445 |   // Create the array. | 
 | 446 |   CFMutableArrayRef A = CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); | 
 | 447 |   CFMutableArrayRef *B = &A; | 
 | 448 |   // At this point, the name 'A' is no longer live. | 
 | 449 |   CFRelease(*B);  // no-warning | 
 | 450 | } | 
 | 451 |  | 
| Ted Kremenek | 79b4f7d | 2009-07-14 00:43:42 +0000 | [diff] [blame] | 452 | // Test when we pass NULL to CFRetain/CFRelease. | 
 | 453 | void f16(int x, CFTypeRef p) { | 
 | 454 |   if (p) | 
 | 455 |     return; | 
 | 456 |  | 
 | 457 |   if (x) { | 
 | 458 |     CFRelease(p); // expected-warning{{Null pointer argument in call to CFRelease}} | 
 | 459 |   } | 
 | 460 |   else { | 
 | 461 |     CFRetain(p); // expected-warning{{Null pointer argument in call to CFRetain}} | 
 | 462 |   } | 
 | 463 | } | 
| Ted Kremenek | e82e13a | 2009-04-07 05:33:18 +0000 | [diff] [blame] | 464 |  | 
| Ted Kremenek | 9f45d28 | 2009-03-05 18:15:02 +0000 | [diff] [blame] | 465 | // Test basic tracking of ivars associated with 'self'.  For the retain/release | 
 | 466 | // checker we currently do not want to flag leaks associated with stores | 
 | 467 | // of tracked objects to ivars. | 
 | 468 | @interface SelfIvarTest : NSObject { | 
 | 469 |   id myObj; | 
 | 470 | } | 
 | 471 | - (void)test_self_tracking; | 
 | 472 | @end | 
 | 473 |  | 
 | 474 | @implementation SelfIvarTest | 
 | 475 | - (void)test_self_tracking { | 
 | 476 |   myObj = (id) CFArrayCreateMutable(0, 10, &kCFTypeArrayCallBacks); // no-warning | 
 | 477 | } | 
 | 478 | @end | 
 | 479 |  | 
| Ted Kremenek | e8720ce | 2009-05-10 06:25:57 +0000 | [diff] [blame] | 480 | // Test return of non-owned objects in contexts where an owned object | 
 | 481 | // is expected. | 
 | 482 | @interface TestReturnNotOwnedWhenExpectedOwned | 
 | 483 | - (NSString*)newString; | 
 | 484 | @end | 
 | 485 |  | 
 | 486 | @implementation TestReturnNotOwnedWhenExpectedOwned | 
 | 487 | - (NSString*)newString { | 
 | 488 |   NSString *s = [NSString stringWithUTF8String:"hello"]; | 
 | 489 |   return s; // expected-warning{{Object with +0 retain counts returned to caller where a +1 (owning) retain count is expected}} | 
 | 490 | } | 
 | 491 | @end | 
 | 492 |  | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 493 | // <rdar://problem/6659160> | 
 | 494 | int isFoo(char c); | 
 | 495 |  | 
 | 496 | static void rdar_6659160(char *inkind, char *inname) | 
 | 497 | { | 
 | 498 |   // We currently expect that [NSObject alloc] cannot fail.  This | 
 | 499 |   // will be a toggled flag in the future.  It can indeed return null, but | 
 | 500 |   // Cocoa programmers generally aren't expected to reason about out-of-memory | 
 | 501 |   // conditions. | 
 | 502 |   NSString *kind = [[NSString alloc] initWithUTF8String:inkind];  // expected-warning{{leak}} | 
 | 503 |    | 
 | 504 |   // We do allow stringWithUTF8String to fail.  This isn't really correct, as | 
| Ted Kremenek | 68ac94a | 2009-03-23 17:10:25 +0000 | [diff] [blame] | 505 |   // far as returning 0.  In most error conditions it will throw an exception. | 
 | 506 |   // If allocation fails it could return 0, but again this | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 507 |   // isn't expected. | 
 | 508 |   NSString *name = [NSString stringWithUTF8String:inname]; | 
 | 509 |   if(!name) | 
 | 510 |     return; | 
 | 511 |  | 
 | 512 |   const char *kindC = 0; | 
 | 513 |   const char *nameC = 0; | 
 | 514 |    | 
 | 515 |   // In both cases, we cannot reach a point down below where we | 
 | 516 |   // dereference kindC or nameC with either being null.  This is because | 
 | 517 |   // we assume that [NSObject alloc] doesn't fail and that we have the guard | 
 | 518 |   // up above. | 
 | 519 |    | 
 | 520 |   if(kind) | 
 | 521 |     kindC = [kind UTF8String]; | 
 | 522 |   if(name) | 
 | 523 |     nameC = [name UTF8String]; | 
| Ted Kremenek | 25d01ba | 2009-03-09 22:46:49 +0000 | [diff] [blame] | 524 |   if(!isFoo(kindC[0])) // expected-warning{{null}} | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 525 |     return; | 
 | 526 |   if(!isFoo(nameC[0])) // no-warning | 
 | 527 |     return; | 
 | 528 |  | 
 | 529 |   [kind release]; | 
| Ted Kremenek | f9df136 | 2009-04-23 21:25:57 +0000 | [diff] [blame] | 530 |   [name release]; // expected-warning{{Incorrect decrement of the reference count}} | 
| Ted Kremenek | cd57fce | 2009-03-09 22:28:18 +0000 | [diff] [blame] | 531 | } | 
| Ted Kremenek | 9f45d28 | 2009-03-05 18:15:02 +0000 | [diff] [blame] | 532 |  | 
| Ted Kremenek | 8be2a67 | 2009-03-13 20:27:06 +0000 | [diff] [blame] | 533 | // PR 3677 - 'allocWithZone' should be treated as following the Cocoa naming | 
 | 534 | //  conventions with respect to 'return'ing ownership. | 
 | 535 | @interface PR3677: NSObject @end | 
 | 536 | @implementation PR3677 | 
 | 537 | + (id)allocWithZone:(NSZone *)inZone { | 
 | 538 |   return [super allocWithZone:inZone];  // no-warning | 
 | 539 | } | 
 | 540 | @end | 
 | 541 |  | 
| Ted Kremenek | c505d4f | 2009-03-19 19:50:58 +0000 | [diff] [blame] | 542 | // PR 3820 - Reason about calls to -dealloc | 
 | 543 | void pr3820_DeallocInsteadOfRelease(void) | 
 | 544 | { | 
 | 545 |   id foo = [[NSString alloc] init]; // no-warning | 
 | 546 |   [foo dealloc]; | 
 | 547 |   // foo is not leaked, since it has been deallocated. | 
 | 548 | } | 
 | 549 |  | 
 | 550 | void pr3820_ReleaseAfterDealloc(void) | 
 | 551 | { | 
 | 552 |   id foo = [[NSString alloc] init]; | 
 | 553 |   [foo dealloc]; | 
 | 554 |   [foo release];  // expected-warning{{used after it is release}} | 
 | 555 |   // NSInternalInconsistencyException: message sent to deallocated object | 
 | 556 | } | 
 | 557 |  | 
 | 558 | void pr3820_DeallocAfterRelease(void) | 
 | 559 | { | 
 | 560 |   NSLog(@"\n\n[%s]", __FUNCTION__); | 
 | 561 |   id foo = [[NSString alloc] init]; | 
 | 562 |   [foo release]; | 
 | 563 |   [foo dealloc]; // expected-warning{{used after it is released}} | 
 | 564 |   // message sent to released object | 
 | 565 | } | 
| Ted Kremenek | 68ac94a | 2009-03-23 17:10:25 +0000 | [diff] [blame] | 566 |  | 
 | 567 | // From <rdar://problem/6704930>.  The problem here is that 'length' binds to | 
 | 568 | // '($0 - 1)' after '--length', but SimpleConstraintManager doesn't know how to | 
 | 569 | // reason about '($0 - 1) > constant'.  As a temporary hack, we drop the value | 
 | 570 | // of '($0 - 1)' and conjure a new symbol. | 
 | 571 | void rdar6704930(unsigned char *s, unsigned int length) { | 
 | 572 |   NSString* name = 0; | 
 | 573 |   if (s != 0) { | 
 | 574 |     if (length > 0) { | 
 | 575 |       while (length > 0) { | 
 | 576 |         if (*s == ':') { | 
 | 577 |           ++s; | 
 | 578 |           --length; | 
 | 579 |           name = [[NSString alloc] init]; // no-warning | 
 | 580 |           break; | 
 | 581 |         } | 
 | 582 |         ++s; | 
 | 583 |         --length; | 
 | 584 |       } | 
 | 585 |       if ((length == 0) && (name != 0)) { | 
 | 586 |         [name release]; | 
 | 587 |         name = 0; | 
 | 588 |       } | 
 | 589 |       if (length == 0) { // no ':' found -> use it all as name | 
 | 590 |         name = [[NSString alloc] init]; // no-warning | 
 | 591 |       } | 
 | 592 |     } | 
 | 593 |   } | 
 | 594 |  | 
 | 595 |   if (name != 0) { | 
 | 596 |     [name release]; | 
 | 597 |   } | 
 | 598 | } | 
 | 599 |  | 
| Ted Kremenek | 0fc169e | 2009-04-24 23:09:54 +0000 | [diff] [blame] | 600 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 601 | // <rdar://problem/6833332> | 
 | 602 | // One build of the analyzer accidentally stopped tracking the allocated | 
 | 603 | // object after the 'retain'. | 
| Ted Kremenek | ebd5a2d | 2009-05-11 18:30:24 +0000 | [diff] [blame] | 604 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | fde52c9 | 2009-04-29 00:41:31 +0000 | [diff] [blame] | 605 |  | 
 | 606 | @interface rdar_6833332 : NSObject <NSApplicationDelegate> { | 
 | 607 |     NSWindow *window; | 
 | 608 | } | 
 | 609 | @property (nonatomic, retain) NSWindow *window; | 
 | 610 | @end | 
 | 611 |  | 
 | 612 | @implementation rdar_6833332 | 
 | 613 | @synthesize window; | 
 | 614 | - (void)applicationDidFinishLaunching:(NSNotification *)aNotification { | 
 | 615 |  NSMutableDictionary *dict = [[NSMutableDictionary dictionaryWithCapacity:4] retain]; // expected-warning{{leak}} | 
 | 616 |  | 
 | 617 |  [dict setObject:@"foo" forKey:@"bar"]; | 
 | 618 |  | 
 | 619 |  NSLog(@"%@", dict); | 
 | 620 | } | 
 | 621 | - (void)dealloc { | 
 | 622 |     [window release]; | 
 | 623 |     [super dealloc]; | 
 | 624 | } | 
 | 625 | @end | 
 | 626 |  | 
| Ted Kremenek | 8c6096e | 2009-05-09 03:10:32 +0000 | [diff] [blame] | 627 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | a0cc00d | 2009-05-11 17:45:06 +0000 | [diff] [blame] | 628 | // <rdar://problem/6257780> clang checker fails to catch use-after-release | 
 | 629 | //===----------------------------------------------------------------------===// | 
 | 630 |                                   | 
| Ted Kremenek | ebd5a2d | 2009-05-11 18:30:24 +0000 | [diff] [blame] | 631 | int rdar_6257780_Case1() { | 
| Ted Kremenek | a0cc00d | 2009-05-11 17:45:06 +0000 | [diff] [blame] | 632 |   NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; | 
 | 633 |   NSArray *array = [NSArray array]; | 
| Ted Kremenek | bb206fd | 2009-10-01 17:31:50 +0000 | [diff] [blame] | 634 |   [array release]; // expected-warning{{Incorrect decrement of the reference count of an object that is not owned at this point by the caller}} | 
| Ted Kremenek | a0cc00d | 2009-05-11 17:45:06 +0000 | [diff] [blame] | 635 |   [pool drain]; | 
 | 636 |   return 0; | 
 | 637 | } | 
 | 638 |  | 
 | 639 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | ebd5a2d | 2009-05-11 18:30:24 +0000 | [diff] [blame] | 640 | // <rdar://problem/6866843> Checker should understand new/setObject:/release constructs | 
 | 641 | //===----------------------------------------------------------------------===// | 
 | 642 |  | 
 | 643 | void rdar_6866843() { | 
 | 644 |  NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; | 
 | 645 |  NSMutableDictionary* dictionary = [[NSMutableDictionary alloc] init]; | 
 | 646 |  NSArray* array = [[NSArray alloc] init]; | 
 | 647 |  [dictionary setObject:array forKey:@"key"]; | 
 | 648 |  [array release]; | 
 | 649 |  // Using 'array' here should be fine | 
 | 650 |  NSLog(@"array = %@\n", array); // no-warning | 
 | 651 |  // Now the array is released | 
 | 652 |  [dictionary release]; | 
 | 653 |  [pool drain]; | 
 | 654 | } | 
 | 655 |  | 
| Ted Kremenek | 6738b73 | 2009-05-12 04:53:03 +0000 | [diff] [blame] | 656 |  | 
 | 657 | //===----------------------------------------------------------------------===// | 
 | 658 | // <rdar://problem/6877235> Classes typedef-ed to CF objects should get the same treatment as CF objects | 
 | 659 | //===----------------------------------------------------------------------===// | 
 | 660 |  | 
 | 661 | typedef CFTypeRef OtherRef; | 
 | 662 |  | 
 | 663 | @interface RDar6877235 : NSObject {} | 
 | 664 | - (CFTypeRef)_copyCFTypeRef; | 
 | 665 | - (OtherRef)_copyOtherRef; | 
 | 666 | @end | 
 | 667 |  | 
 | 668 | @implementation RDar6877235 | 
 | 669 | - (CFTypeRef)_copyCFTypeRef { | 
 | 670 |   return [[NSString alloc] init]; // no-warning | 
 | 671 | } | 
 | 672 | - (OtherRef)_copyOtherRef { | 
 | 673 |   return [[NSString alloc] init]; // no-warning | 
 | 674 | } | 
 | 675 | @end | 
 | 676 |  | 
| Ted Kremenek | ebd5a2d | 2009-05-11 18:30:24 +0000 | [diff] [blame] | 677 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | ac02f20 | 2009-08-20 05:13:36 +0000 | [diff] [blame] | 678 | //<rdar://problem/6320065> false positive - init method returns an object | 
 | 679 | // owned by caller | 
| Ted Kremenek | 78a35a3 | 2009-05-12 20:06:54 +0000 | [diff] [blame] | 680 | //===----------------------------------------------------------------------===// | 
 | 681 |  | 
 | 682 | @interface RDar6320065 : NSObject { | 
 | 683 |   NSString *_foo; | 
 | 684 | } | 
 | 685 | - (id)initReturningNewClass; | 
 | 686 | - (id)initReturningNewClassBad; | 
 | 687 | - (id)initReturningNewClassBad2; | 
 | 688 | @end | 
 | 689 |  | 
 | 690 | @interface RDar6320065Subclass : RDar6320065 | 
 | 691 | @end | 
 | 692 |  | 
 | 693 | @implementation RDar6320065 | 
 | 694 | - (id)initReturningNewClass { | 
 | 695 |   [self release]; | 
 | 696 |   self = [[RDar6320065Subclass alloc] init]; // no-warning | 
 | 697 |   return self; | 
 | 698 | } | 
 | 699 | - (id)initReturningNewClassBad { | 
 | 700 |   [self release]; | 
 | 701 |   [[RDar6320065Subclass alloc] init]; // expected-warning {{leak}} | 
 | 702 |   return self; | 
 | 703 | } | 
 | 704 | - (id)initReturningNewClassBad2 { | 
 | 705 |   [self release]; | 
 | 706 |   self = [[RDar6320065Subclass alloc] init]; | 
 | 707 |   return [self autorelease]; // expected-warning{{Object with +0 retain counts returned to caller where a +1 (owning) retain count is expected}} | 
 | 708 | } | 
 | 709 |  | 
 | 710 | @end | 
 | 711 |  | 
 | 712 | @implementation RDar6320065Subclass | 
 | 713 | @end | 
 | 714 |  | 
 | 715 | int RDar6320065_test() { | 
 | 716 |   RDar6320065 *test = [[RDar6320065 alloc] init]; // no-warning | 
 | 717 |   [test release]; | 
 | 718 |   return 0; | 
 | 719 | } | 
 | 720 |  | 
 | 721 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | ac02f20 | 2009-08-20 05:13:36 +0000 | [diff] [blame] | 722 | // <rdar://problem/7129086> -awakeAfterUsingCoder: returns an owned object  | 
 | 723 | //  and claims the receiver | 
 | 724 | //===----------------------------------------------------------------------===// | 
 | 725 |  | 
 | 726 | @interface RDar7129086 : NSObject {} @end | 
 | 727 | @implementation RDar7129086 | 
 | 728 | - (id)awakeAfterUsingCoder:(NSCoder *)aDecoder { | 
 | 729 |   [self release]; // no-warning | 
 | 730 |   return [NSString alloc];  // no-warning | 
 | 731 | } | 
 | 732 | @end | 
 | 733 |  | 
 | 734 | //===----------------------------------------------------------------------===// | 
 | 735 | // <rdar://problem/6859457> [NSData dataWithBytesNoCopy] does not return a | 
 | 736 | //  retained object | 
| Ted Kremenek | 3043766 | 2009-05-14 21:29:16 +0000 | [diff] [blame] | 737 | //===----------------------------------------------------------------------===// | 
 | 738 |  | 
 | 739 | @interface RDar6859457 : NSObject {} | 
 | 740 | - (NSString*) NoCopyString; | 
 | 741 | - (NSString*) noCopyString; | 
 | 742 | @end | 
 | 743 |  | 
 | 744 | @implementation RDar6859457  | 
 | 745 | - (NSString*) NoCopyString { return [[NSString alloc] init]; } // no-warning | 
 | 746 | - (NSString*) noCopyString { return [[NSString alloc] init]; } // no-warning | 
 | 747 | @end | 
 | 748 |  | 
 | 749 | void test_RDar6859457(RDar6859457 *x, void *bytes, NSUInteger dataLength) { | 
 | 750 |   [x NoCopyString]; // expected-warning{{leak}} | 
 | 751 |   [x noCopyString]; // expected-warning{{leak}} | 
 | 752 |   [NSData dataWithBytesNoCopy:bytes length:dataLength];  // no-warning | 
 | 753 |   [NSData dataWithBytesNoCopy:bytes length:dataLength freeWhenDone:1]; // no-warning | 
 | 754 | } | 
 | 755 |  | 
 | 756 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | ba67f6a | 2009-05-18 23:14:34 +0000 | [diff] [blame] | 757 | // PR 4230 - an autorelease pool is not necessarily leaked during a premature | 
 | 758 | //  return | 
 | 759 | //===----------------------------------------------------------------------===// | 
 | 760 |  | 
 | 761 | static void PR4230(void) | 
 | 762 | { | 
 | 763 |   NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; // no-warning | 
 | 764 |   NSString *object = [[[NSString alloc] init] autorelease]; // no-warning | 
 | 765 |   return; | 
 | 766 | } | 
 | 767 |  | 
 | 768 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 7db1604 | 2009-05-15 15:49:00 +0000 | [diff] [blame] | 769 | // Method name that has a null IdentifierInfo* for its first selector slot. | 
 | 770 | // This test just makes sure that we handle it. | 
 | 771 | //===----------------------------------------------------------------------===// | 
 | 772 |  | 
 | 773 | @interface TestNullIdentifier | 
 | 774 | @end | 
 | 775 |  | 
 | 776 | @implementation TestNullIdentifier | 
 | 777 | + (id):(int)x, ... { | 
 | 778 |   return [[NSString alloc] init]; // expected-warning{{leak}} | 
 | 779 | } | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 780 | @end | 
| Ted Kremenek | 7db1604 | 2009-05-15 15:49:00 +0000 | [diff] [blame] | 781 |  | 
 | 782 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | fae664a | 2009-05-16 01:38:01 +0000 | [diff] [blame] | 783 | // <rdar://problem/6893565> don't flag leaks for return types that cannot be  | 
 | 784 | //                          determined to be CF types | 
 | 785 | //===----------------------------------------------------------------------===// | 
 | 786 |  | 
 | 787 | // We don't know if 'struct s6893565' represents a Core Foundation type, so | 
 | 788 | // we shouldn't emit an error here. | 
 | 789 | typedef struct s6893565* TD6893565; | 
 | 790 |  | 
 | 791 | @interface RDar6893565 {} | 
 | 792 | -(TD6893565)newThing; | 
 | 793 | @end | 
 | 794 |  | 
 | 795 | @implementation RDar6893565 | 
 | 796 | -(TD6893565)newThing {   | 
 | 797 |   return (TD6893565) [[NSString alloc] init]; // no-warning | 
 | 798 | } | 
 | 799 | @end | 
 | 800 |  | 
 | 801 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 767d649 | 2009-05-20 22:39:57 +0000 | [diff] [blame] | 802 | // <rdar://problem/6902710> clang: false positives w/QC and CoreImage methods | 
 | 803 | //===----------------------------------------------------------------------===// | 
 | 804 |  | 
 | 805 | void rdar6902710(QCView *view, QCRenderer *renderer, CIContext *context, | 
 | 806 |                  NSString *str, CIImage *img, CGRect rect, | 
 | 807 |                  CIFormat form, CGColorSpaceRef cs) { | 
 | 808 |   [view createSnapshotImageOfType:str]; // expected-warning{{leak}} | 
 | 809 |   [renderer createSnapshotImageOfType:str]; // expected-warning{{leak}} | 
 | 810 |   [context createCGImage:img fromRect:rect]; // expected-warning{{leak}} | 
 | 811 |   [context createCGImage:img fromRect:rect format:form colorSpace:cs]; // expected-warning{{leak}} | 
 | 812 | } | 
 | 813 |  | 
 | 814 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 815 | // <rdar://problem/6945561> -[CIContext createCGLayerWithSize:info:] | 
 | 816 | //                           misinterpreted by clang scan-build | 
 | 817 | //===----------------------------------------------------------------------===// | 
 | 818 |  | 
 | 819 | void rdar6945561(CIContext *context, CGSize size, CFDictionaryRef d) { | 
 | 820 |   [context createCGLayerWithSize:size info:d]; // expected-warning{{leak}} | 
 | 821 | } | 
 | 822 |  | 
 | 823 | //===----------------------------------------------------------------------===// | 
 | 824 | // <rdar://problem/6961230> add knowledge of IOKit functions to retain/release  | 
 | 825 | //                          checker | 
 | 826 | //===----------------------------------------------------------------------===// | 
 | 827 |  | 
 | 828 | void IOBSDNameMatching_wrapper(mach_port_t masterPort, uint32_t options,  const char * bsdName) {   | 
 | 829 |   IOBSDNameMatching(masterPort, options, bsdName); // expected-warning{{leak}} | 
 | 830 | } | 
 | 831 |  | 
 | 832 | void IOServiceMatching_wrapper(const char * name) { | 
 | 833 |   IOServiceMatching(name); // expected-warning{{leak}} | 
 | 834 | } | 
 | 835 |  | 
 | 836 | void IOServiceNameMatching_wrapper(const char * name) { | 
 | 837 |   IOServiceNameMatching(name); // expected-warning{{leak}} | 
 | 838 | } | 
 | 839 |  | 
| Ted Kremenek | 71ef5d6 | 2009-07-17 00:19:33 +0000 | [diff] [blame] | 840 | CF_RETURNS_RETAINED CFDictionaryRef CreateDict(); | 
| Ted Kremenek | fdd8b8e | 2009-06-16 20:44:39 +0000 | [diff] [blame] | 841 |  | 
 | 842 | void IOServiceAddNotification_wrapper(mach_port_t masterPort, const io_name_t notificationType, | 
 | 843 |   mach_port_t wakePort, uintptr_t reference, io_iterator_t * notification ) { | 
 | 844 |  | 
 | 845 |   CFDictionaryRef matching = CreateDict(); | 
 | 846 |   CFRelease(matching); | 
 | 847 |   IOServiceAddNotification(masterPort, notificationType, matching, // expected-warning{{used after it is released}} expected-warning{{deprecated}} | 
 | 848 |                            wakePort, reference, notification); | 
 | 849 | } | 
 | 850 |  | 
 | 851 | void IORegistryEntryIDMatching_wrapper(uint64_t entryID ) { | 
 | 852 |   IORegistryEntryIDMatching(entryID); // expected-warning{{leak}} | 
 | 853 | } | 
 | 854 |  | 
 | 855 | void IOOpenFirmwarePathMatching_wrapper(mach_port_t masterPort, uint32_t options, | 
 | 856 |                                         const char * path) { | 
 | 857 |   IOOpenFirmwarePathMatching(masterPort, options, path); // expected-warning{{leak}} | 
 | 858 | } | 
 | 859 |  | 
 | 860 | void IOServiceGetMatchingService_wrapper(mach_port_t masterPort) { | 
 | 861 |   CFDictionaryRef matching = CreateDict(); | 
 | 862 |   IOServiceGetMatchingService(masterPort, matching); | 
 | 863 |   CFRelease(matching); // expected-warning{{used after it is released}} | 
 | 864 | } | 
 | 865 |  | 
 | 866 | void IOServiceGetMatchingServices_wrapper(mach_port_t masterPort, io_iterator_t *existing) { | 
 | 867 |   CFDictionaryRef matching = CreateDict(); | 
 | 868 |   IOServiceGetMatchingServices(masterPort, matching, existing); | 
 | 869 |   CFRelease(matching); // expected-warning{{used after it is released}} | 
 | 870 | } | 
 | 871 |  | 
 | 872 | void IOServiceAddMatchingNotification_wrapper(IONotificationPortRef notifyPort, const io_name_t notificationType,  | 
 | 873 |   IOServiceMatchingCallback callback, void * refCon, io_iterator_t * notification) { | 
 | 874 |      | 
 | 875 |   CFDictionaryRef matching = CreateDict(); | 
 | 876 |   IOServiceAddMatchingNotification(notifyPort, notificationType, matching, callback, refCon, notification); | 
 | 877 |   CFRelease(matching); // expected-warning{{used after it is released}} | 
 | 878 | } | 
 | 879 |  | 
 | 880 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | c484381 | 2009-08-20 00:57:22 +0000 | [diff] [blame] | 881 | // Test of handling objects whose references "escape" to containers. | 
 | 882 | //===----------------------------------------------------------------------===// | 
 | 883 |  | 
 | 884 | // <rdar://problem/6539791> | 
 | 885 | void rdar_6539791(CFMutableDictionaryRef y, void* key, void* val_key) { | 
 | 886 |   CFMutableDictionaryRef x = CFDictionaryCreateMutable(kCFAllocatorDefault, 1, &kCFTypeDictionaryKeyCallBacks, &kCFTypeDictionaryValueCallBacks); | 
 | 887 |   CFDictionaryAddValue(y, key, x); | 
 | 888 |   CFRelease(x); // the dictionary keeps a reference, so the object isn't deallocated yet | 
 | 889 |   signed z = 1; | 
 | 890 |   CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); | 
 | 891 |   if (value) { | 
 | 892 |     CFDictionaryAddValue(x, val_key, value); // no-warning | 
 | 893 |     CFRelease(value); | 
 | 894 |     CFDictionaryAddValue(y, val_key, value); // no-warning | 
 | 895 |   } | 
 | 896 | } | 
 | 897 |  | 
 | 898 | // <rdar://problem/6560661> | 
 | 899 | // Same issue, except with "AppendValue" functions. | 
 | 900 | void rdar_6560661(CFMutableArrayRef x) { | 
 | 901 |   signed z = 1; | 
 | 902 |   CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); | 
 | 903 |   // CFArrayAppendValue keeps a reference to value. | 
 | 904 |   CFArrayAppendValue(x, value); | 
 | 905 |   CFRelease(value); | 
 | 906 |   CFRetain(value); | 
 | 907 |   CFRelease(value); // no-warning | 
 | 908 | } | 
 | 909 |  | 
 | 910 | // <rdar://problem/7152619> | 
 | 911 | // Same issue, excwept with "CFAttributeStringSetAttribute". | 
 | 912 | void rdar_7152619(CFStringRef str) { | 
 | 913 |   CFAttributedStringRef string = CFAttributedStringCreate(kCFAllocatorDefault, str, 0); | 
 | 914 |   CFMutableAttributedStringRef attrString = CFAttributedStringCreateMutableCopy(kCFAllocatorDefault, 100, string); | 
 | 915 |   CFRelease(string); | 
 | 916 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // expected-warning{{leak}} | 
 | 917 |   CFAttributedStringSetAttribute(attrString, CFRangeMake(0, 1), str, number); | 
 | 918 |   [number release]; | 
 | 919 |   [number retain]; | 
 | 920 |   CFRelease(attrString);   | 
 | 921 | } | 
 | 922 |  | 
 | 923 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | cc58eae | 2009-09-01 18:33:16 +0000 | [diff] [blame] | 924 | // Test of handling CGGradientXXX functions. | 
 | 925 | //===----------------------------------------------------------------------===// | 
 | 926 |  | 
 | 927 | void rdar_7184450(CGContextRef myContext, CGFloat x, CGPoint myStartPoint, | 
 | 928 |                   CGPoint myEndPoint) { | 
 | 929 |   size_t num_locations = 6; | 
 | 930 |   CGFloat locations[6] = { 0.0, 0.265, 0.28, 0.31, 0.36, 1.0 }; | 
 | 931 |   CGFloat components[28] = { 239.0/256.0, 167.0/256.0, 170.0/256.0, | 
 | 932 |      x,  // Start color | 
 | 933 |     207.0/255.0, 39.0/255.0, 39.0/255.0, x, | 
 | 934 |     147.0/255.0, 21.0/255.0, 22.0/255.0, x, | 
 | 935 |     175.0/255.0, 175.0/255.0, 175.0/255.0, x, | 
 | 936 |     255.0/255.0,255.0/255.0, 255.0/255.0, x, | 
 | 937 |     255.0/255.0,255.0/255.0, 255.0/255.0, x | 
 | 938 |   }; // End color | 
 | 939 |    | 
 | 940 |   CGGradientRef myGradient = | 
 | 941 |     CGGradientCreateWithColorComponents(CGColorSpaceCreateDeviceRGB(), // expected-warning{{leak}} | 
 | 942 |       components, locations, num_locations); | 
 | 943 |  | 
 | 944 |   CGContextDrawLinearGradient(myContext, myGradient, myStartPoint, myEndPoint, | 
 | 945 |                               0); | 
 | 946 |   CGGradientRelease(myGradient); | 
 | 947 | } | 
 | 948 |  | 
 | 949 | void rdar_7184450_pos(CGContextRef myContext, CGFloat x, CGPoint myStartPoint, | 
 | 950 |                   CGPoint myEndPoint) { | 
 | 951 |   size_t num_locations = 6; | 
 | 952 |   CGFloat locations[6] = { 0.0, 0.265, 0.28, 0.31, 0.36, 1.0 }; | 
 | 953 |   CGFloat components[28] = { 239.0/256.0, 167.0/256.0, 170.0/256.0, | 
 | 954 |      x,  // Start color | 
 | 955 |     207.0/255.0, 39.0/255.0, 39.0/255.0, x, | 
 | 956 |     147.0/255.0, 21.0/255.0, 22.0/255.0, x, | 
 | 957 |     175.0/255.0, 175.0/255.0, 175.0/255.0, x, | 
 | 958 |     255.0/255.0,255.0/255.0, 255.0/255.0, x, | 
 | 959 |     255.0/255.0,255.0/255.0, 255.0/255.0, x | 
 | 960 |   }; // End color | 
 | 961 |    | 
 | 962 |   CGGradientRef myGradient = | 
 | 963 |    CGGradientCreateWithColorComponents(CGColorSpaceCreateDeviceRGB(), components, locations, num_locations); // expected-warning 2 {{leak}} | 
 | 964 |  | 
 | 965 |   CGContextDrawLinearGradient(myContext, myGradient, myStartPoint, myEndPoint, | 
 | 966 |                               0); | 
 | 967 | } | 
 | 968 |  | 
 | 969 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 6240cf1 | 2009-10-13 22:55:33 +0000 | [diff] [blame] | 970 | // <rdar://problem/7299394> clang false positive: retained instance passed to | 
 | 971 | //                          thread in pthread_create marked as leak | 
 | 972 | // | 
 | 973 | // Until we have full IPA, the analyzer should stop tracking the reference | 
 | 974 | // count of objects passed to pthread_create. | 
 | 975 | // | 
 | 976 | //===----------------------------------------------------------------------===// | 
 | 977 |  | 
 | 978 | struct _opaque_pthread_t {}; | 
 | 979 | struct _opaque_pthread_attr_t {}; | 
 | 980 | typedef struct _opaque_pthread_t *__darwin_pthread_t; | 
 | 981 | typedef struct _opaque_pthread_attr_t __darwin_pthread_attr_t; | 
 | 982 | typedef __darwin_pthread_t pthread_t; | 
 | 983 | typedef __darwin_pthread_attr_t pthread_attr_t; | 
 | 984 |  | 
 | 985 | int pthread_create(pthread_t * restrict, const pthread_attr_t * restrict, | 
 | 986 |                    void *(*)(void *), void * restrict); | 
 | 987 |  | 
 | 988 | void *rdar_7299394_start_routine(void *p) { | 
 | 989 |   [((id) p) release]; | 
 | 990 |   return 0; | 
 | 991 | } | 
 | 992 | void rdar_7299394(pthread_attr_t *attr, pthread_t *thread, void *args) { | 
 | 993 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning | 
 | 994 |   pthread_create(thread, attr, rdar_7299394_start_routine, number); | 
 | 995 | } | 
 | 996 | void rdar_7299394_positive(pthread_attr_t *attr, pthread_t *thread) { | 
 | 997 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // expected-warning{{leak}} | 
 | 998 | } | 
 | 999 |  | 
 | 1000 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 008636a | 2009-10-14 00:27:24 +0000 | [diff] [blame] | 1001 | // <rdar://problem/7283567> False leak associated with call to  | 
 | 1002 | //                          CVPixelBufferCreateWithBytes () | 
 | 1003 | // | 
 | 1004 | // According to the Core Video Reference (ADC), CVPixelBufferCreateWithBytes and | 
 | 1005 | // CVPixelBufferCreateWithPlanarBytes can release (via a callback) the | 
 | 1006 | // pixel buffer object.  These test cases show how the analyzer stops tracking | 
 | 1007 | // the reference count for the objects passed for this argument.  This | 
 | 1008 | // could be made smarter. | 
 | 1009 | //===----------------------------------------------------------------------===// | 
 | 1010 |  | 
 | 1011 | typedef int int32_t; | 
 | 1012 | typedef UInt32 FourCharCode; | 
 | 1013 | typedef FourCharCode OSType; | 
 | 1014 | typedef uint64_t CVOptionFlags; | 
 | 1015 | typedef int32_t CVReturn; | 
 | 1016 | typedef struct __CVBuffer *CVBufferRef; | 
 | 1017 | typedef CVBufferRef CVImageBufferRef; | 
 | 1018 | typedef CVImageBufferRef CVPixelBufferRef; | 
 | 1019 | typedef void (*CVPixelBufferReleaseBytesCallback)( void *releaseRefCon, const void *baseAddress ); | 
 | 1020 |  | 
 | 1021 | extern CVReturn CVPixelBufferCreateWithBytes(CFAllocatorRef allocator, | 
 | 1022 |             size_t width, | 
 | 1023 |             size_t height, | 
 | 1024 |             OSType pixelFormatType, | 
 | 1025 |             void *baseAddress, | 
 | 1026 |             size_t bytesPerRow, | 
 | 1027 |             CVPixelBufferReleaseBytesCallback releaseCallback, | 
 | 1028 |             void *releaseRefCon, | 
 | 1029 |             CFDictionaryRef pixelBufferAttributes, | 
 | 1030 |                    CVPixelBufferRef *pixelBufferOut) ; | 
 | 1031 |  | 
 | 1032 | typedef void (*CVPixelBufferReleasePlanarBytesCallback)( void *releaseRefCon, const void *dataPtr, size_t dataSize, size_t numberOfPlanes, const void *planeAddresses[] ); | 
 | 1033 |  | 
 | 1034 | extern CVReturn CVPixelBufferCreateWithPlanarBytes(CFAllocatorRef allocator, | 
 | 1035 |         size_t width, | 
 | 1036 |         size_t height, | 
 | 1037 |         OSType pixelFormatType, | 
 | 1038 |         void *dataPtr, | 
 | 1039 |         size_t dataSize, | 
 | 1040 |         size_t numberOfPlanes, | 
 | 1041 |         void *planeBaseAddress[], | 
 | 1042 |         size_t planeWidth[], | 
 | 1043 |         size_t planeHeight[], | 
 | 1044 |         size_t planeBytesPerRow[], | 
 | 1045 |         CVPixelBufferReleasePlanarBytesCallback releaseCallback, | 
 | 1046 |         void *releaseRefCon, | 
 | 1047 |         CFDictionaryRef pixelBufferAttributes, | 
 | 1048 |         CVPixelBufferRef *pixelBufferOut) ; | 
 | 1049 |  | 
 | 1050 | extern CVReturn CVPixelBufferCreateWithBytes(CFAllocatorRef allocator, | 
 | 1051 |             size_t width, | 
 | 1052 |             size_t height, | 
 | 1053 |             OSType pixelFormatType, | 
 | 1054 |             void *baseAddress, | 
 | 1055 |             size_t bytesPerRow, | 
 | 1056 |             CVPixelBufferReleaseBytesCallback releaseCallback, | 
 | 1057 |             void *releaseRefCon, | 
 | 1058 |             CFDictionaryRef pixelBufferAttributes, | 
 | 1059 |                    CVPixelBufferRef *pixelBufferOut) ; | 
 | 1060 |  | 
 | 1061 | CVReturn rdar_7283567(CFAllocatorRef allocator, size_t width, size_t height, | 
 | 1062 |                       OSType pixelFormatType, void *baseAddress, | 
 | 1063 |                       size_t bytesPerRow, | 
 | 1064 |                       CVPixelBufferReleaseBytesCallback releaseCallback, | 
 | 1065 |                       CFDictionaryRef pixelBufferAttributes, | 
 | 1066 |                       CVPixelBufferRef *pixelBufferOut) { | 
 | 1067 |  | 
 | 1068 |   // For the allocated object, it doesn't really matter what type it is | 
 | 1069 |   // for the purpose of this test.  All we want to show is that | 
 | 1070 |   // this is freed later by the callback. | 
 | 1071 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning | 
 | 1072 |    | 
 | 1073 |   return CVPixelBufferCreateWithBytes(allocator, width, height, pixelFormatType, | 
 | 1074 |                                 baseAddress, bytesPerRow, releaseCallback, | 
 | 1075 |                                 number, // potentially released by callback | 
 | 1076 |                                 pixelBufferAttributes, pixelBufferOut) ; | 
 | 1077 | } | 
 | 1078 |  | 
 | 1079 | CVReturn rdar_7283567_2(CFAllocatorRef allocator, size_t width, size_t height, | 
 | 1080 |         OSType pixelFormatType, void *dataPtr, size_t dataSize, | 
 | 1081 |         size_t numberOfPlanes, void *planeBaseAddress[], | 
 | 1082 |         size_t planeWidth[], size_t planeHeight[], size_t planeBytesPerRow[], | 
 | 1083 |         CVPixelBufferReleasePlanarBytesCallback releaseCallback, | 
 | 1084 |         CFDictionaryRef pixelBufferAttributes, | 
 | 1085 |         CVPixelBufferRef *pixelBufferOut) { | 
 | 1086 |      | 
 | 1087 |     // For the allocated object, it doesn't really matter what type it is | 
 | 1088 |     // for the purpose of this test.  All we want to show is that | 
 | 1089 |     // this is freed later by the callback. | 
 | 1090 |     NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning | 
 | 1091 |  | 
 | 1092 |     return CVPixelBufferCreateWithPlanarBytes(allocator, | 
 | 1093 |               width, height, pixelFormatType, dataPtr, dataSize, | 
 | 1094 |               numberOfPlanes, planeBaseAddress, planeWidth, | 
 | 1095 |               planeHeight, planeBytesPerRow, releaseCallback, | 
 | 1096 |               number, // potentially released by callback | 
 | 1097 |               pixelBufferAttributes, pixelBufferOut) ; | 
 | 1098 | } | 
 | 1099 |  | 
 | 1100 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 882a51e | 2009-11-03 05:34:07 +0000 | [diff] [blame] | 1101 | // <rdar://problem/7358899> False leak associated with  | 
 | 1102 | //  CGBitmapContextCreateWithData | 
 | 1103 | //===----------------------------------------------------------------------===// | 
 | 1104 | typedef uint32_t CGBitmapInfo; | 
 | 1105 | typedef void (*CGBitmapContextReleaseDataCallback)(void *releaseInfo, void *data); | 
 | 1106 |      | 
 | 1107 | CGContextRef CGBitmapContextCreateWithData(void *data, | 
 | 1108 |     size_t width, size_t height, size_t bitsPerComponent, | 
 | 1109 |     size_t bytesPerRow, CGColorSpaceRef space, CGBitmapInfo bitmapInfo, | 
 | 1110 |     CGBitmapContextReleaseDataCallback releaseCallback, void *releaseInfo); | 
 | 1111 |  | 
 | 1112 | void rdar_7358899(void *data, | 
 | 1113 |       size_t width, size_t height, size_t bitsPerComponent, | 
 | 1114 |       size_t bytesPerRow, CGColorSpaceRef space, CGBitmapInfo bitmapInfo, | 
 | 1115 |       CGBitmapContextReleaseDataCallback releaseCallback) { | 
 | 1116 |  | 
 | 1117 |     // For the allocated object, it doesn't really matter what type it is | 
 | 1118 |     // for the purpose of this test.  All we want to show is that | 
 | 1119 |     // this is freed later by the callback. | 
 | 1120 |     NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning | 
 | 1121 |  | 
| Ted Kremenek | 002174f | 2009-11-03 05:39:12 +0000 | [diff] [blame] | 1122 |   CGBitmapContextCreateWithData(data, width, height, bitsPerComponent, // expected-warning{{leak}} | 
| Ted Kremenek | 882a51e | 2009-11-03 05:34:07 +0000 | [diff] [blame] | 1123 |     bytesPerRow, space, bitmapInfo, releaseCallback, number); | 
 | 1124 | } | 
 | 1125 |  | 
 | 1126 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | e973183 | 2009-10-20 00:13:00 +0000 | [diff] [blame] | 1127 | // <rdar://problem/7265711> allow 'new', 'copy', 'alloc', 'init' prefix to | 
 | 1128 | //  start before '_' when determining Cocoa fundamental rule | 
 | 1129 | // | 
 | 1130 | // Previously the retain/release checker just skipped prefixes before the | 
 | 1131 | // first '_' entirely.  Now the checker honors the prefix if it results in a | 
 | 1132 | // recognizable naming convention (e.g., 'new', 'init'). | 
 | 1133 | //===----------------------------------------------------------------------===// | 
 | 1134 |  | 
 | 1135 | @interface RDar7265711 {} | 
 | 1136 | - (id) new_stuff; | 
 | 1137 | @end | 
 | 1138 |  | 
 | 1139 | void rdar7265711_a(RDar7265711 *x) { | 
 | 1140 |   id y = [x new_stuff]; // expected-warning{{leak}} | 
 | 1141 | } | 
 | 1142 |  | 
 | 1143 | void rdar7265711_b(RDar7265711 *x) { | 
 | 1144 |   id y = [x new_stuff]; // no-warning | 
 | 1145 |   [y release]; | 
 | 1146 | } | 
 | 1147 |  | 
 | 1148 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 6fe2b7a | 2009-10-15 22:25:12 +0000 | [diff] [blame] | 1149 | // <rdar://problem/7306898> clang thinks [NSCursor dragCopyCursor] returns a | 
 | 1150 | //                          retained reference | 
 | 1151 | //===----------------------------------------------------------------------===// | 
 | 1152 |  | 
 | 1153 | @interface NSCursor : NSObject | 
 | 1154 | + (NSCursor *)dragCopyCursor; | 
 | 1155 | @end | 
 | 1156 |  | 
 | 1157 | void rdar7306898(void) { | 
 | 1158 |   // 'dragCopyCursor' does not follow Cocoa's fundamental rule.  It is a noun, not an sentence | 
 | 1159 |   // implying a 'copy' of something. | 
 | 1160 |   NSCursor *c =  [NSCursor dragCopyCursor]; // no-warning | 
 | 1161 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // expected-warning{{leak}} | 
 | 1162 | } | 
 | 1163 |  | 
 | 1164 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 50e837b | 2009-11-20 05:27:05 +0000 | [diff] [blame] | 1165 | // <rdar://problem/7252064> sending 'release', 'retain', etc. to a Class | 
 | 1166 | // directly is not likely what the user intended | 
 | 1167 | //===----------------------------------------------------------------------===// | 
 | 1168 |  | 
 | 1169 | @interface RDar7252064 : NSObject @end | 
 | 1170 | void rdar7252064(void) { | 
 | 1171 |   [RDar7252064 release]; // expected-warning{{The 'release' message should be sent to instances of class 'RDar7252064' and not the class directly}} | 
 | 1172 |   [RDar7252064 retain]; // expected-warning{{The 'retain' message should be sent to instances of class 'RDar7252064' and not the class directly}} | 
 | 1173 |   [RDar7252064 autorelease]; // expected-warning{{The 'autorelease' message should be sent to instances of class 'RDar7252064' and not the class directly}} | 
 | 1174 |   [NSAutoreleasePool drain]; // expected-warning{{method '+drain' not found}} expected-warning{{The 'drain' message should be sent to instances of class 'NSAutoreleasePool' and not the class directly}} | 
 | 1175 | } | 
 | 1176 |  | 
 | 1177 | //===----------------------------------------------------------------------===// | 
| Ted Kremenek | 8c6096e | 2009-05-09 03:10:32 +0000 | [diff] [blame] | 1178 | // Tests of ownership attributes. | 
 | 1179 | //===----------------------------------------------------------------------===// | 
 | 1180 |  | 
| Ted Kremenek | 5dc53c9 | 2009-05-13 21:07:32 +0000 | [diff] [blame] | 1181 | typedef NSString* MyStringTy; | 
 | 1182 |  | 
| Ted Kremenek | 8b31826 | 2009-07-21 21:21:04 +0000 | [diff] [blame] | 1183 | @protocol FooP; | 
 | 1184 |  | 
| Ted Kremenek | 8c6096e | 2009-05-09 03:10:32 +0000 | [diff] [blame] | 1185 | @interface TestOwnershipAttr : NSObject | 
| Ted Kremenek | 71ef5d6 | 2009-07-17 00:19:33 +0000 | [diff] [blame] | 1186 | - (NSString*) returnsAnOwnedString  NS_RETURNS_RETAINED; // no-warning | 
 | 1187 | - (NSString*) returnsAnOwnedCFString  CF_RETURNS_RETAINED; // no-warning | 
 | 1188 | - (MyStringTy) returnsAnOwnedTypedString NS_RETURNS_RETAINED; // no-warning | 
 | 1189 | - (int) returnsAnOwnedInt NS_RETURNS_RETAINED; // expected-warning{{'ns_returns_retained' attribute only applies to functions or methods that return a pointer or Objective-C object}} | 
| Ted Kremenek | 8c6096e | 2009-05-09 03:10:32 +0000 | [diff] [blame] | 1190 | @end | 
 | 1191 |  | 
| Ted Kremenek | 71ef5d6 | 2009-07-17 00:19:33 +0000 | [diff] [blame] | 1192 | static int ownership_attribute_doesnt_go_here NS_RETURNS_RETAINED; // expected-warning{{'ns_returns_retained' attribute only applies to function or method types}} | 
| Ted Kremenek | 5dc53c9 | 2009-05-13 21:07:32 +0000 | [diff] [blame] | 1193 |  | 
| Ted Kremenek | 8c6096e | 2009-05-09 03:10:32 +0000 | [diff] [blame] | 1194 | void test_attr_1(TestOwnershipAttr *X) { | 
 | 1195 |   NSString *str = [X returnsAnOwnedString]; // expected-warning{{leak}} | 
 | 1196 | } | 
 | 1197 |  | 
 | 1198 | void test_attr_1b(TestOwnershipAttr *X) { | 
 | 1199 |   NSString *str = [X returnsAnOwnedCFString]; // expected-warning{{leak}} | 
 | 1200 | } | 
| Ted Kremenek | b9d8db8 | 2009-06-05 23:00:33 +0000 | [diff] [blame] | 1201 |  | 
 | 1202 | @interface MyClassTestCFAttr : NSObject {} | 
| Ted Kremenek | 71ef5d6 | 2009-07-17 00:19:33 +0000 | [diff] [blame] | 1203 | - (NSDate*) returnsCFRetained CF_RETURNS_RETAINED; | 
 | 1204 | - (CFDateRef) returnsCFRetainedAsCF CF_RETURNS_RETAINED; | 
| Ted Kremenek | b9d8db8 | 2009-06-05 23:00:33 +0000 | [diff] [blame] | 1205 | - (NSDate*) alsoReturnsRetained; | 
| Ted Kremenek | 6d4b76d | 2009-07-06 18:30:43 +0000 | [diff] [blame] | 1206 | - (CFDateRef) alsoReturnsRetainedAsCF; | 
| Ted Kremenek | 71ef5d6 | 2009-07-17 00:19:33 +0000 | [diff] [blame] | 1207 | - (NSDate*) returnsNSRetained NS_RETURNS_RETAINED; | 
| Ted Kremenek | b9d8db8 | 2009-06-05 23:00:33 +0000 | [diff] [blame] | 1208 | @end | 
 | 1209 |  | 
| Ted Kremenek | 71ef5d6 | 2009-07-17 00:19:33 +0000 | [diff] [blame] | 1210 | CF_RETURNS_RETAINED | 
| Ted Kremenek | b9d8db8 | 2009-06-05 23:00:33 +0000 | [diff] [blame] | 1211 | CFDateRef returnsRetainedCFDate()  { | 
 | 1212 |   return CFDateCreate(0, CFAbsoluteTimeGetCurrent()); | 
 | 1213 | } | 
 | 1214 |  | 
 | 1215 | @implementation MyClassTestCFAttr | 
 | 1216 | - (NSDate*) returnsCFRetained { | 
 | 1217 |   return (NSDate*) returnsRetainedCFDate(); // No leak. | 
 | 1218 | } | 
 | 1219 |  | 
| Ted Kremenek | 6d4b76d | 2009-07-06 18:30:43 +0000 | [diff] [blame] | 1220 | - (CFDateRef) returnsCFRetainedAsCF { | 
 | 1221 |   return returnsRetainedCFDate(); // No leak. | 
 | 1222 | } | 
 | 1223 |  | 
 | 1224 |  | 
| Ted Kremenek | b9d8db8 | 2009-06-05 23:00:33 +0000 | [diff] [blame] | 1225 | - (NSDate*) alsoReturnsRetained { | 
 | 1226 |   return (NSDate*) returnsRetainedCFDate(); // expected-warning{{leak}} | 
 | 1227 | } | 
 | 1228 |  | 
| Ted Kremenek | 6d4b76d | 2009-07-06 18:30:43 +0000 | [diff] [blame] | 1229 | - (CFDateRef) alsoReturnsRetainedAsCF { | 
 | 1230 |   return returnsRetainedCFDate(); // expected-warning{{leak}} | 
 | 1231 | } | 
 | 1232 |  | 
 | 1233 |  | 
| Ted Kremenek | b9d8db8 | 2009-06-05 23:00:33 +0000 | [diff] [blame] | 1234 | - (NSDate*) returnsNSRetained { | 
 | 1235 |   return (NSDate*) returnsRetainedCFDate(); // no-warning | 
 | 1236 | } | 
 | 1237 | @end | 
 | 1238 |  | 
| Ted Kremenek | e2b5744 | 2009-09-15 00:40:32 +0000 | [diff] [blame] | 1239 | //===----------------------------------------------------------------------===// | 
 | 1240 | // Test that leaks post-dominated by "panic" functions are not reported. | 
 | 1241 | // | 
 | 1242 | // <rdar://problem/5905851> do not report a leak when post-dominated by a call | 
 | 1243 | // to a noreturn or panic function | 
 | 1244 | //===----------------------------------------------------------------------===// | 
 | 1245 |  | 
 | 1246 | void panic() __attribute__((noreturn)); | 
 | 1247 |  | 
 | 1248 | void test_panic_negative() { | 
 | 1249 |   signed z = 1; | 
 | 1250 |   CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z);  // expected-warning{{leak}} | 
 | 1251 | } | 
 | 1252 |  | 
 | 1253 | void test_panic_positive() { | 
 | 1254 |   signed z = 1; | 
 | 1255 |   CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); // no-warning | 
 | 1256 |   panic(); | 
 | 1257 | } | 
 | 1258 |  | 
 | 1259 | void test_panic_neg_2(int x) { | 
 | 1260 |   signed z = 1; | 
 | 1261 |   CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); // expected-warning{{leak}} | 
 | 1262 |   if (x) | 
 | 1263 |     panic(); | 
 | 1264 | } | 
 | 1265 |  | 
 | 1266 | void test_panic_pos_2(int x) { | 
 | 1267 |   signed z = 1; | 
 | 1268 |   CFNumberRef value = CFNumberCreate(kCFAllocatorDefault, kCFNumberSInt32Type, &z); // no-warning | 
 | 1269 |   if (x) | 
 | 1270 |     panic();   | 
 | 1271 |   if (!x) | 
 | 1272 |     panic(); | 
 | 1273 | } | 
 | 1274 |  | 
| Ted Kremenek | 772250c | 2009-11-25 01:35:18 +0000 | [diff] [blame] | 1275 | //===----------------------------------------------------------------------===// | 
 | 1276 | // Test uses of blocks (closures) | 
 | 1277 | //===----------------------------------------------------------------------===// | 
 | 1278 |  | 
 | 1279 | void test_blocks_1_pos(void) { | 
 | 1280 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // expected-warning{{leak}} | 
 | 1281 |   ^{}(); | 
 | 1282 | } | 
 | 1283 |  | 
| Ted Kremenek | 772250c | 2009-11-25 01:35:18 +0000 | [diff] [blame] | 1284 | void test_blocks_1_indirect_release(void) { | 
 | 1285 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning | 
 | 1286 |   ^{ [number release]; }(); | 
 | 1287 | } | 
 | 1288 |  | 
 | 1289 | void test_blocks_1_indirect_retain(void) { | 
 | 1290 |   // Eventually this should be reported as a leak. | 
 | 1291 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning | 
 | 1292 |   ^{ [number retain]; }(); | 
 | 1293 | } | 
| Ted Kremenek | 772250c | 2009-11-25 01:35:18 +0000 | [diff] [blame] | 1294 |  | 
 | 1295 | void test_blocks_1_indirect_release_via_call(void) { | 
 | 1296 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning | 
 | 1297 |   ^(NSObject *o){ [o release]; }(number); | 
 | 1298 | } | 
 | 1299 |  | 
 | 1300 | void test_blocks_1_indirect_retain_via_call(void) { | 
 | 1301 |   // Eventually this should be reported as a leak. | 
 | 1302 |   NSNumber *number = [[NSNumber alloc] initWithInt:5]; // no-warning | 
 | 1303 |   ^(NSObject *o){ [o retain]; }(number); | 
 | 1304 | } | 
 | 1305 |  |