Wednesday, April 29, 2009

Static Code Analysis with 'clang'

On Leopard, all Cocoa objects are garbage collected, the developer has the luxury of not having to worry about memory management and can let the system take care of it. There is no such luxury on iPhone since garbage collection can be a performance intensive process. So, it is possible for memory leaks (and other nasty bugs to creep into the code during development). There are a bunch of tools at the developer's disposal to identify such problems and fix them. One such tool is the 'clang' analyzer.

I have found static code analysis to be an indispensable tool when it comes to discovering some very common bugs early in the development cycle. I first heard of the LLVM/Clang static code analyzer command line tool for Mac/iPhone late last year but started using it only recently.

The best way to understand how this works is to look at an example. The following is a sample code containing some obvious (and some not so obvious) memory leaks and bugs:

- (void)viewDidLoad {
// Uninitialized object
NSString *string1;

if (NO) {
string1 = [NSString stringWithString:@"Foo"];
}

NSUInteger counter = 0;

NSNumber *number = [[NSNumber alloc] initWithInt:0];
if (YES) {
// Memory leak
return;
}
[number release];
}

- (IBAction)createString:(id)sender {
// Memory leak
NSString *foo = [[NSString alloc] initWithString:@"Foo"];
}

- (NSString *)dummy {
NSString *string2;
return string2; // Returning an uninitialized object.
}

The analyzer can now be invoked simply by executing the following from the command line:
scan-build -k -V xcodebuild -configuration Debug -sdk iphonesimulator2.2.1
scan-build is the script for running the analyzer over a project build. The above example assumes that scan-build is in the path. The '-k' flag forces the script to keep going even if there are problems in compiling some source files and '-V' flag runs a small web server and opens up the results file in a browser. Running the analyzer against the above code, detected 5 bugs.







The analyzer works best with 'Debug' builds. The tool is not perfect and does throw up false positives, but in most cases it is bang on target. The tool also does not catch some slightly more difficult to detect leaks, but more about that in another post.

LLVM/Clang Mac binaries are available on the home page.

2 comments:

Ted Kremenek said...

Thanks for blogging about the static analyzer. If you know about specific cases of leaks that it doesn't find, please feel free to file bug reports (i.e., feature requests) at clang-analyzer.llvm.org. Besides false positives, it is also good for us to know what major classes of leaks the analyzer is missing. Note that the analyzer is only currently looking for leaks of Cocoa/Core Foundation objects; general checking for malloc-free related leaks is something that will hopefully get addressed in the future.

Natural gas said...

Very well written blog. This blog is full of information about static code analyzers. Thanks for providing script.