I have custom UIView
drawing in drawRect
.
I don't know the C APIs that well so I'm not sure what memory rules they require. The Objective-C rules are pretty simple and state that you release anything you own via init
retain
or copy
but the C function CGGradientCreateWithColorComponents
is not Objective-C and the Product > Analyze reports that it is a potential leak.
Is it necessary to release the results of this function, and if so, how? And in general, when it comes to these APIs, is there any easy way to know if a function is allocating memory that you need to manually release?
UPDATE: Here is the code, thanks to the information in the answers so far. I'm getting incorrect decrement
error now:
CGGradientRef theGradient=[self makeGradient:YES];
//do something with theGradient in my drawing
CGGradientRelease(theGradient); // this line Analyze says incorrect decrement of object not owned by caller
And in makeGradient
I have:
- (CGGradientRef)makeGradient:(BOOL)red{
CGGradientRef gradient;
//create my gradient
return gradient;
}
The general rule is that if you call function whose name contains “Create” or “Copy”, you must release the object that it returns. This is called the “Create rule”.
You created the gradient using a function that has “Create” embedded in the name. That means you're responsible for releasing the gradient. You can use CGGradientRelease
or CFRelease
.
You can read about the Create rule and other memory management conventions in the Memory Management Programming Guide for Core Foundation.
You can also read Quartz 2D Programming Guide: Memory Management: Object Ownership.
Based on your new code samples, I now see that you need to learn about another memory management convention. ;^)
Objective-C methods use a slightly different naming convention than Core Foundation functions. Instead of putting “Create” or “Copy” in the name, the convention for Objective-C methods is that the name must start with “alloc”, “new”, “copy”, or “mutableCopy” if it returns an object that the caller must release. (You can read about Objective-C memory management conventions here.)
Change the name of your method from makeGradient:
to newGradient:
and the analyzer will stop complaining. I tested it! :^)