Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 1 | <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" |
| 2 | "http://www.w3.org/TR/html4/strict.dtd"> |
| 3 | <html> |
| 4 | <head> |
| 5 | <title>Source Annotations</title> |
| 6 | <link type="text/css" rel="stylesheet" href="menu.css" /> |
| 7 | <link type="text/css" rel="stylesheet" href="content.css" /> |
| 8 | </head> |
| 9 | <body> |
| 10 | |
| 11 | <!--#include virtual="menu.html.incl"--> |
| 12 | |
| 13 | <div id="content"> |
| 14 | |
| 15 | <h1>Source Annotations</h1> |
| 16 | |
| 17 | <p>The Clang frontend supports several source-level annotations in the form of |
| 18 | <a href="http://gcc.gnu.org/onlinedocs/gcc/Attribute-Syntax.html">GCC-style |
| 19 | attributes</a> and pragmas that can help make using the Clang Static Analyzer |
| 20 | more useful. These annotations can both help suppress false positives as well as |
| 21 | enhance the analyzer's ability to find bugs.</p> |
| 22 | |
| 23 | <p>This page gives a practical overview of such annotations. For more technical |
| 24 | specifics regarding Clang-specific annotations please see the Clang's list of <a |
| 25 | href="http://clang.llvm.org/docs/LanguageExtensions.html">language |
| 26 | extensions</a>. Details of "standard" GCC attributes (that Clang also |
| 27 | supports) can be found in the <a href="http://gcc.gnu.org/onlinedocs/gcc/">GCC |
| 28 | manual</a>, with the majority of the relevant attributes being in the section on |
| 29 | <a href="http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html">function |
| 30 | attributes</a>.</p> |
| 31 | |
| 32 | <p>Note that attributes that are labeled <b>Clang-specific</b> are not |
| 33 | recognized by GCC. Their use can be conditioned using preprocessor macros |
| 34 | (examples included on this page).</p> |
| 35 | |
| 36 | <ul> |
| 37 | <li><a href="#generic">Annotations to Enhance Generic Checks</a></li> |
| 38 | <ul> |
| 39 | <li><a href="#null_checking">Null Pointer Checking</a></li> |
| 40 | <ul> |
| 41 | <li><a href="#attr_nonnull">Attribute 'nonnull'</a></li> |
| 42 | </ul> |
| 43 | </ul> |
| 44 | <li><a href="#macosx">Mac OS X API Annotations</a></li> |
| 45 | <ul> |
| 46 | <li><a href="#cocoa_mem">Cocoa & Core Foundation Memory Management |
| 47 | Annotations</a></li> |
| 48 | <ul> |
| 49 | <li><a href="#attr_ns_returns_retained">Attribute |
| 50 | 'ns_returns_retained'</a></li> |
| 51 | <li><a href="#attr_cf_returns_retained">Attribute |
| 52 | 'cf_returns_retained'</a></li> |
| 53 | </ul> |
| 54 | </ul> |
| 55 | <li><a href="#custom_assertions">Custom Assertion Handlers</a></li> |
| 56 | <ul> |
| 57 | <li><a href="#attr_noreturn">Attribute 'noreturn'</a></li> |
| 58 | <li><a href="#attr_analyzer_noreturn">Attribute 'analyzer_noreturn'</a></li> |
| 59 | </ul> |
| 60 | </ul> |
| 61 | |
| 62 | <!-- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - --> |
| 63 | <h2 id="generic">Annotations to Enhance Generic Checks</h2> |
| 64 | <!-- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - --> |
| 65 | |
| 66 | <h3 id="null_checking">Null Pointer Checking</h3> |
| 67 | |
| 68 | <h4 id="attr_nonnull">Attribute 'nonnull'</h4> |
| 69 | |
| 70 | <p>The analyzer recognizes the GCC attribute 'nonnull', which indicates that a |
| 71 | function expects that a given function parameter is not a null pointer. Specific |
| 72 | details of the syntax of using the 'nonnull' attribute can be found in <a |
| 73 | href="http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html#index-g_t_0040code_007bnonnull_007d-function-attribute-2263">GCC's |
| 74 | documentation</a>.</p> |
| 75 | |
| 76 | <p>Both the Clang compiler and GCC will flag warnings for simple cases where a |
| 77 | null pointer is directly being passed to a function with a 'nonnull' parameter |
| 78 | (e.g., as a constant). The analyzer extends this checking by using its deeper |
| 79 | symbolic analysis to track what pointer values are potentially null and then |
| 80 | flag warnings when they are passed in a function call via a 'nonnull' |
| 81 | parameter.</p> |
| 82 | |
| 83 | <p><b>Example</b></p> |
| 84 | |
| 85 | <pre class="code_example"> |
| 86 | <span class="command">$ cat test.m</span> |
| 87 | int bar(int*p, int q, int *r) __attribute__((nonnull(1,3))); |
| 88 | |
| 89 | int foo(int *p, int *q) { |
| 90 | return !p ? bar(q, 2, p) |
| 91 | : bar(p, 2, q); |
| 92 | } |
Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 93 | </pre> |
| 94 | |
Ted Kremenek | 42291dd | 2009-06-24 19:17:54 +0000 | [diff] [blame] | 95 | <p>Running <tt>scan-build</tt> over this source produces the following |
| 96 | output:</p> |
| 97 | |
Ted Kremenek | 5ceab86 | 2009-06-24 19:20:24 +0000 | [diff] [blame^] | 98 | <img src="images/example_attribute_nonnull.png"> |
Ted Kremenek | 42291dd | 2009-06-24 19:17:54 +0000 | [diff] [blame] | 99 | |
Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 100 | <!-- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - --> |
| 101 | <h2 id="macosx">Mac OS X API Annotations</h2> |
| 102 | <!-- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - --> |
| 103 | |
| 104 | <h3 id="cocoa_mem">Cocoa & Core Foundation Memory Management |
| 105 | Annotations</h3> |
| 106 | |
Ted Kremenek | cb41f3e | 2009-06-09 01:32:41 +0000 | [diff] [blame] | 107 | <!-- |
Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 108 | <p>As described in <a href="/available_checks.html#retain_release">Available |
Ted Kremenek | cb41f3e | 2009-06-09 01:32:41 +0000 | [diff] [blame] | 109 | Checks</a>, |
| 110 | --> |
| 111 | <p>The analyzer supports the proper management of retain counts for |
Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 112 | both Cocoa and Core Foundation objects. This checking is largely based on |
| 113 | enforcing Cocoa and Core Foundation naming conventions for Objective-C methods |
| 114 | (Cocoa) and C functions (Core Foundation). Not strictly following these |
| 115 | conventions can cause the analyzer to miss bugs or flag false positives.</p> |
| 116 | |
| 117 | <p>One can educate the analyzer (and others who read your code) about methods or |
| 118 | functions that deviate from the Cocoa and Core Foundation conventions using the |
| 119 | attributes described here.</p> |
| 120 | |
| 121 | <h4 id="attr_ns_returns_retained">Attribute 'ns_returns_retained' |
| 122 | (Clang-specific)</h4> |
| 123 | |
| 124 | <p>The GCC-style (Clang-specific) attribute 'ns_returns_retained' allows one to |
| 125 | annotate an Objective-C method or C function as returning a retained Cocoa |
| 126 | object that the caller is responsible for releasing (via sending a |
| 127 | <tt>release</tt> message to the object).</p> |
| 128 | |
| 129 | <p><b>Placing on Objective-C methods</b>: For Objective-C methods, this |
| 130 | annotation essentially tells the analyzer to treat the method as if its name |
| 131 | begins with "alloc" or "new" or contais the word |
| 132 | "copy".</p> |
| 133 | |
| 134 | <p><b>Placing on C functions</b>: For C functions returning Cocoa objects, the |
| 135 | analyzer typically does not make any assumptions about whether or not the object |
| 136 | is returned retained. Explicitly adding the 'ns_returns_retained' attribute to C |
| 137 | functions allows the analyzer to perform extra checking.</p> |
| 138 | |
| 139 | <p><b>Important note when using Garbage Collection</b>: Note that the analyzer |
| 140 | interprets this attribute slightly differently when using Objective-C garbage |
| 141 | collection (available on Mac OS 10.5+). When analyzing Cocoa code that uses |
| 142 | garbage collection, "alloc" methods are assumed to return an object |
| 143 | that is managed by the garbage collector (and thus doesn't have a retain count |
| 144 | the caller must balance). These same assumptions are applied to methods or |
| 145 | functions annotated with 'ns_returns_retained'. If you are returning a Core |
| 146 | Foundation object (which may not be managed by the garbage collector) you should |
| 147 | use 'cf_returns_retained'.</p> |
| 148 | |
| 149 | <p><b>Example</b></p> |
| 150 | |
| 151 | <pre class="code_example"> |
| 152 | <span class="command">$ cat test.m</span> |
| 153 | #import <Foundation/Foundation.h> |
| 154 | |
| 155 | #ifndef NS_RETURNS_RETAINED |
| 156 | #if __clang__ |
| 157 | <span class="code_highlight">#define NS_RETURNS_RETAINED __attribute__((ns_returns_retained))</span> |
| 158 | #else |
| 159 | #define NS_RETURNS_RETAINED |
| 160 | #endif |
| 161 | #endif |
| 162 | |
| 163 | @interface MyClass : NSObject {} |
| 164 | - (NSString*) returnsRetained <span class="code_highlight">NS_RETURNS_RETAINED</span>; |
| 165 | - (NSString*) alsoReturnsRetained; |
| 166 | @end |
| 167 | |
| 168 | @implementation MyClass |
| 169 | - (NSString*) returnsRetained { |
| 170 | return [[NSString alloc] initWithCString:"no leak here"]; |
| 171 | } |
| 172 | - (NSString*) alsoReturnsRetained { |
| 173 | return [[NSString alloc] initWithCString:"flag a leak"]; |
| 174 | } |
| 175 | @end |
Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 176 | </pre> |
| 177 | |
Ted Kremenek | 7d277e2 | 2009-06-24 18:50:14 +0000 | [diff] [blame] | 178 | <p>Running <tt>scan-build</tt> on this source file produces the following output:</p> |
| 179 | |
| 180 | <img src="images/example_ns_returns_retained.png"> |
| 181 | |
Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 182 | <h4 id="attr_cf_returns_retained">Attribute 'cf_returns_retained' |
| 183 | (Clang-specific)</h4> |
| 184 | |
| 185 | <p>The GCC-style (Clang-specific) attribute 'cf_returns_retained' allows one to |
| 186 | annotate an Objective-C method or C function as returning a retained Core |
| 187 | Foundation object that the caller is responsible for releasing. |
| 188 | |
| 189 | <p><b>Placing on Objective-C methods</b>: With respect to Objective-C methods., |
| 190 | this attribute is identical in its behavior and usage to 'ns_returns_retained' |
| 191 | except for the distinction of returning a Core Foundation object instead of a |
| 192 | Cocoa object. This distinction is important for two reasons:</p> |
| 193 | |
| 194 | <ul> |
| 195 | <li>Core Foundation objects are not automatically managed by the Objective-C |
| 196 | garbage collector.</li> |
| 197 | <li>Because Core Foundation is a C API, the analyzer cannot always tell that a |
| 198 | pointer return value refers to a Core Foundation object. In contrast, it is |
| 199 | trivial for the analyzer to recognize if a pointer refers to a Cocoa object |
| 200 | (given the Objective-C type system).</p> |
| 201 | </ul> |
| 202 | |
| 203 | <p><b>Placing on C functions</b>: When placing the attribute |
| 204 | 'cf_returns_retained' on the declarations of C functions, the analyzer |
| 205 | interprets the function as:</p> |
| 206 | |
| 207 | <ol> |
| 208 | <li>Returning a Core Foundation Object</li> |
| 209 | <li>Treating the function as if it its name |
| 210 | contained the keywords "create" or "copy". This means the |
| 211 | returned object as a +1 retain count that must be released by the caller, either |
| 212 | by sending a <tt>release</tt> message (via toll-free bridging to an Objective-C |
| 213 | object pointer), calling <tt>CFRelease</tt> (or similar function), or using |
| 214 | <tt>CFMakeCollectable</tt> to register the object with the Objective-C garbage |
| 215 | collector.</li> |
| 216 | </ol> |
| 217 | |
| 218 | <p><b>Example</b></p> |
| 219 | |
| 220 | <p>In this example, observe the difference in output when the code is compiled |
| 221 | to not use garbage collection versus when it is compiled to only use garbage |
| 222 | collection (<tt>-fobjc-gc-only</tt>).</p> |
| 223 | |
| 224 | <pre class="code_example"> |
| 225 | <span class="command">$ cat test.m</span> |
| 226 | $ cat test.m |
| 227 | #import <Cocoa/Cocoa.h> |
| 228 | |
| 229 | #ifndef CF_RETURNS_RETAINED |
| 230 | #if __clang__ |
| 231 | <span class="code_highlight">#define CF_RETURNS_RETAINED __attribute__((cf_returns_retained))</span> |
| 232 | #else |
| 233 | #define CF_RETURNS_RETAINED |
| 234 | #endif |
| 235 | #endif |
| 236 | |
| 237 | @interface MyClass : NSObject {} |
| 238 | - (NSDate*) returnsCFRetained <span class="code_highlight">CF_RETURNS_RETAINED</span>; |
| 239 | - (NSDate*) alsoReturnsRetained; |
| 240 | - (NSDate*) returnsNSRetained <span class="code_highlight">NS_RETURNS_RETAINED</span>; |
| 241 | @end |
| 242 | |
| 243 | <span class="code_highlight">CF_RETURNS_RETAINED</span> |
| 244 | CFDateRef returnsRetainedCFDate() { |
| 245 | return CFDateCreate(0, CFAbsoluteTimeGetCurrent()); |
| 246 | } |
| 247 | |
| 248 | @implementation MyClass |
| 249 | - (NSDate*) returnsCFRetained { |
| 250 | return (NSDate*) returnsRetainedCFDate(); // No leak. |
| 251 | } |
| 252 | |
| 253 | - (NSDate*) alsoReturnsRetained { |
| 254 | return (NSDate*) returnsRetainedCFDate(); // Always report a leak. |
| 255 | } |
| 256 | |
| 257 | - (NSDate*) returnsNSRetained { |
| 258 | return (NSDate*) returnsRetainedCFDate(); // Report a leak when using GC. |
| 259 | } |
| 260 | @end |
Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 261 | </pre> |
| 262 | |
Ted Kremenek | 6fe1ef2 | 2009-06-24 19:04:37 +0000 | [diff] [blame] | 263 | <p>Running <tt>scan-build</tt> on this example produces the following output:</p> |
| 264 | |
| 265 | <img src="images/example_cf_returns_retained.png"> |
| 266 | |
| 267 | </p>When the above code is compiled using Objective-C garbage collection (i.e., |
| 268 | code is compiled with the flag <tt>-fobjc-gc</tt> or <tt>-fobjc-gc-only</tt>), |
| 269 | <tt>scan-build</tt> produces both the above error (with slightly different text |
| 270 | to indicate the code uses garbage collection) as well as the following warning, |
| 271 | which indicates a leak that occurs <em>only</em> when using garbage |
| 272 | collection:</p> |
| 273 | |
| 274 | <img src="images/example_cf_returns_retained_gc.png"> |
| 275 | |
Ted Kremenek | 591b907 | 2009-06-08 21:21:24 +0000 | [diff] [blame] | 276 | <!-- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - --> |
| 277 | <h2 id="custom_assertions">Custom Assertion Handlers</h2> |
| 278 | <!-- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - --> |
| 279 | |
| 280 | <p>The analyzer exploits code assertions by pruning off paths where the |
| 281 | assertion condition is false. The idea is capture any program invariants |
| 282 | specified in the assertion that the developer may know but is not immediately |
| 283 | apparent in the code itself. In this way assertions make implicit assumptions |
| 284 | explicit in the code, which not only makes the analyzer more accurate when |
| 285 | finding bugs, but can help others better able to understand your code as well. |
| 286 | It can also help remove certain kinds of analyzer false positives by pruning off |
| 287 | false paths.</p> |
| 288 | |
| 289 | <p>In order to exploit assertions, however, the analyzer must understand when it |
| 290 | encounters an "assertion handler." Typically assertions are |
| 291 | implemented with a macro, with the macro performing a check for the assertion |
| 292 | condition and, when the check fails, calling an assertion handler. For example, consider the following code |
| 293 | fragment:</p> |
| 294 | |
| 295 | <pre class="code_example"> |
| 296 | void foo(int *p) { |
| 297 | assert(p != NULL); |
| 298 | } |
| 299 | </pre> |
| 300 | |
| 301 | <p>When this code is preprocessed on Mac OS X it expands to the following:</p> |
| 302 | |
| 303 | <pre class="code_example"> |
| 304 | void foo(int *p) { |
| 305 | (__builtin_expect(!(p != NULL), 0) ? __assert_rtn(__func__, "t.c", 4, "p != NULL") : (void)0); |
| 306 | } |
| 307 | </pre> |
| 308 | |
| 309 | <p>In this example, the assertion handler is <tt>__assert_rtn</tt>. When called, |
| 310 | most assertion handlers typically print an error and terminate the program. The |
| 311 | analyzer can exploit such semantics by ending the analysis of a path once it |
| 312 | hits a call to an assertion handler.</p> |
| 313 | |
| 314 | <p>The trick, however, is that the analyzer needs to know that a called function |
| 315 | is an assertion handler; otherwise the analyzer might assume the function call |
| 316 | returns and it will continue analyzing the path where the assertion condition |
| 317 | failed. This can lead to false positives, as the assertion condition usually |
| 318 | implies a safety condition (e.g., a pointer is not null) prior to performing |
| 319 | some action that depends on that condition (e.g., dereferencing a pointer).</p> |
| 320 | |
| 321 | <p>The analyzer knows about several well-known assertion handlers, but can |
| 322 | automatically infer if a function should be treated as an assertion handler if |
| 323 | it is annotated with the 'noreturn' attribute or the (Clang-specific) |
| 324 | 'analyzer_noreturn' attribute.</p> |
| 325 | |
| 326 | <h4 id="attr_noreturn">Attribute 'noreturn'</h4> |
| 327 | |
| 328 | <p>The 'noreturn' attribute is a GCC-attribute that can be placed on the |
| 329 | declarations of functions. It means exactly what its name implies: a function |
| 330 | with a 'noreturn' attribute should never return.</p> |
| 331 | |
| 332 | <p>Specific details of the syntax of using the 'noreturn' attribute can be found |
| 333 | in <a |
| 334 | href="http://gcc.gnu.org/onlinedocs/gcc/Function-Attributes.html#index-g_t_0040code_007bnoreturn_007d-function-attribute-2264">GCC's |
| 335 | documentation</a>.</p> |
| 336 | |
| 337 | <p>Not only does the analyzer exploit this information when pruning false paths, |
| 338 | but the compiler also takes it seriously and will generate different code (and |
| 339 | possibly better optimized) under the assumption that the function does not |
| 340 | return.</p> |
| 341 | |
| 342 | <p><b>Example</b></p> |
| 343 | |
| 344 | <p>On Mac OS X, the function prototype for <tt>__assert_rtn</tt> (declared in |
| 345 | <tt>assert.h</tt>) is specifically annotated with the 'noreturn' attribute:</p> |
| 346 | |
| 347 | <pre class="code_example"> |
| 348 | void __assert_rtn(const char *, const char *, int, const char *) <span class="code_highlight">__attribute__((__noreturn__))</span>; |
| 349 | </pre> |
| 350 | |
| 351 | <h4 id="attr_analyzer_noreturn">Attribute 'analyzer_noreturn' (Clang-specific)</h4> |
| 352 | |
| 353 | <p>The Clang-specific 'analyzer_noreturn' attribute is almost identical to |
| 354 | 'noreturn' except that it is ignored by the compiler for the purposes of code |
| 355 | generation.</p> |
| 356 | |
| 357 | <p>This attribute is useful for annotating assertion handlers that actually |
| 358 | <em>can</em> return, but for the purpose of using the analyzer we want to |
| 359 | pretend that such functions do not return.</p> |
| 360 | |
| 361 | <p>Because this attribute is Clang-specific, its use should be conditioned with |
| 362 | the use of preprocessor macros.</p> |
| 363 | |
| 364 | <p><b>Example</b> |
| 365 | |
| 366 | <pre class="code_example"> |
| 367 | #ifndef CLANG_ANALYZER_NORETURN |
| 368 | #if __clang__ |
| 369 | <span class="code_highlight">#define CLANG_ANALYZER_NORETURN __attribute__((analyzer_noreturn))</span> |
| 370 | #else |
| 371 | #define CLANG_ANALYZER_NORETURN |
| 372 | #endif |
| 373 | |
| 374 | void my_assert_rtn(const char *, const char *, int, const char *) <span class="code_highlight">CLANG_ANALYZER_NORETURN</span>; |
| 375 | </pre> |
| 376 | |
| 377 | </div> |
| 378 | </body> |
| 379 | </html> |
| 380 | |