For iPhone development, we use instruments when detecting all of them during execution, but sometimes we can eliminate these in the cradle. Static analysise.
You can run build and analyze directly for the build check. You can also check that the build option is checked in getinfo, and each build is executed. However, you will see that it will waste the analysis time during build, resulting in a long build time. You can refer to the following.
The xcode static analyzer is a great complement to other techniques for finding bugs in software, such as unit testing. you shoshould always use these in conjunction with the static analyzer to ensure your code contains as few bugs as possible before shipping the final product to your MERs.
The following are three important issues with static analysis:
Static analysis doesn' t find every code flaw. just like most software, static analysis tools go through constant improvement. therefore, it may not find all flaws in your code. you shouldn't rely on static analysis alone to ensure that your code is free of problems.
Static Analysis produces false positives. False positives are unlikely problems in source code that the analyzer identifies as problems. source-code annotations help reduce false positives.
Static analysis increases build time. static analysis takes more time than compilation because of the deep code analyses and policy adherence checks completed MED. using a build configuration tailored for static analysis lets you perform static analysis at times when fast build times are not critical.
Memory-management checks
In the cocoa reference-counting model, when your code obtains an object through a method whose name starts with alloc or new, or contains copy, your code inherently has ownership of the object. when your code when es an object from a method that doesn't return an object owned by the caller, you claim ownership of the object by invoking its retain method. at some point, the owner of the object (or a proxy for the owner) must relinquish ownership by invoking its release method. otherwise, your code leaks the object and the memory it uses. A number of such leaks can cause your application and, potentially, the operation system to become memory starved. the static analyzer checks that your code releases the objects that it owns to avoid memory leaks.
Note:
The static analyzer's ability to detect memory leaks does not preclude you from memory Ming leak checking on the running applications, using tools such as instruments.
The following are the attributes of different framwork.
In cases where it wocould be inconvenient to rename you methods, you can use source-code annotations (in the form of macros) that specify that the object a method returns is owned by the caller. these macros are ns_returns_retained and cf_returns_retained for cocoa-based and core Foundation-based code, respectively.
In the header file, you can see
# If defined (_ clang __)
# Define ns_returns_retained _ attribute _ (ns_returns_retained ))
# Else
# Define ns_returns_retained
# Endif
We can use this
-(ID) obtainanobject :( nsstring *) objectid ns_returns_retained
;
In this way, the caller can be told to count the release. In analyze, if your code calls this function and you do not release it yourself, the analyze prompt will be displayed.
Suppressing static analyzer messages
This is simple and you can directly paste the code...
Listing 9-3 analyzer message from a false Flow Path
Void loop_at_least_once (){
Char * P = NULL;
For (unsigned I = 0, n = iterations (); I <n; I ++ ){
P = get_buffer (I );
}
* P = 1 ;=> dereference of NULL pointer
}
Because the analyzer analyses one method as a single entity (it doesn't analyze called methods), it has limited information about the value of N; therefore, it has to consider the case where n = 0. to suppress the "dereference of a null pointer" analyzer message, the Code must contain an assertion that P cannot be null after the loop, as shown in listing 9-4.
Listing 9-4 suppressing a false analyzer Flow Path
Void loop_at_least_once (){
Char * P = NULL;
For (unsigned I = 0, n = iterations (); I <n; I ++ ){
P = get_buffer (I );
}
Assert (P! = NULL );
* P = 1;
}
Note: If you use custom assertion handlers, you must let the analyzer know about them using the noreturn and analyzer_noreturn attributes. For details, visit http://clang-analyzer.llvm.org/annotations.
Dead stores are a category of dead-code bugs: A value stored in a variable is never read. to have the analyzer ignore dead stores, use Pragma directives or API attributes. listing 9-5, listing 9-6, and listing 9-7 show a dead store, and how to use the unused API attribute to suppress the "value stored to 'X' during its initialization is never read" message.
Listing 9-5 a dead-store message
Int unused (int z ){
Int x = Foo (); => value stored to 'X' during its initialization is never read
Int y = 6;
Return y * z;
}
Listing 9-6 suppressing a dead-store message with the # pragma (unused) Directive
Int unused (int z ){
Int x = Foo ();
Int y = 6;
Return y * z;
# Pragma unused (X)
}
Listing 9-7 suppressing a dead-store message with the _ attribute _ (unused) API attribute
Int unused (int z ){
Int X _ attribute _ (unused ));
X = Foo ();
Int y = 6;
Return y * z;
}