summaryrefslogtreecommitdiffstats
path: root/clang/lib/StaticAnalyzer/Checkers/BasicObjCFoundationChecks.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'clang/lib/StaticAnalyzer/Checkers/BasicObjCFoundationChecks.cpp')
-rw-r--r--clang/lib/StaticAnalyzer/Checkers/BasicObjCFoundationChecks.cpp15
1 files changed, 14 insertions, 1 deletions
diff --git a/clang/lib/StaticAnalyzer/Checkers/BasicObjCFoundationChecks.cpp b/clang/lib/StaticAnalyzer/Checkers/BasicObjCFoundationChecks.cpp
index fba14a0fc49..6388a8df648 100644
--- a/clang/lib/StaticAnalyzer/Checkers/BasicObjCFoundationChecks.cpp
+++ b/clang/lib/StaticAnalyzer/Checkers/BasicObjCFoundationChecks.cpp
@@ -58,6 +58,7 @@ enum FoundationClass {
FC_NSArray,
FC_NSDictionary,
FC_NSEnumerator,
+ FC_NSNull,
FC_NSOrderedSet,
FC_NSSet,
FC_NSString
@@ -69,6 +70,7 @@ static FoundationClass findKnownClass(const ObjCInterfaceDecl *ID) {
Classes["NSArray"] = FC_NSArray;
Classes["NSDictionary"] = FC_NSDictionary;
Classes["NSEnumerator"] = FC_NSEnumerator;
+ Classes["NSNull"] = FC_NSNull;
Classes["NSOrderedSet"] = FC_NSOrderedSet;
Classes["NSSet"] = FC_NSSet;
Classes["NSString"] = FC_NSString;
@@ -845,6 +847,7 @@ class ObjCNonNilReturnValueChecker
mutable bool Initialized;
mutable Selector ObjectAtIndex;
mutable Selector ObjectAtIndexedSubscript;
+ mutable Selector NullSelector;
public:
ObjCNonNilReturnValueChecker() : Initialized(false) {}
@@ -870,6 +873,7 @@ void ObjCNonNilReturnValueChecker::checkPostObjCMessage(const ObjCMethodCall &M,
ASTContext &Ctx = C.getASTContext();
ObjectAtIndex = GetUnarySelector("objectAtIndex", Ctx);
ObjectAtIndexedSubscript = GetUnarySelector("objectAtIndexedSubscript", Ctx);
+ NullSelector = GetNullarySelector("null", Ctx);
}
// Check the receiver type.
@@ -889,10 +893,11 @@ void ObjCNonNilReturnValueChecker::checkPostObjCMessage(const ObjCMethodCall &M,
State = assumeExprIsNonNull(M.getOriginExpr(), State, C);
}
+ FoundationClass Cl = findKnownClass(Interface);
+
// Objects returned from
// [NSArray|NSOrderedSet]::[ObjectAtIndex|ObjectAtIndexedSubscript]
// are never 'nil'.
- FoundationClass Cl = findKnownClass(Interface);
if (Cl == FC_NSArray || Cl == FC_NSOrderedSet) {
Selector Sel = M.getSelector();
if (Sel == ObjectAtIndex || Sel == ObjectAtIndexedSubscript) {
@@ -900,6 +905,14 @@ void ObjCNonNilReturnValueChecker::checkPostObjCMessage(const ObjCMethodCall &M,
State = assumeExprIsNonNull(M.getOriginExpr(), State, C);
}
}
+
+ // Objects returned from [NSNull null] are not nil.
+ if (Cl == FC_NSNull) {
+ if (M.getSelector() == NullSelector) {
+ // Go ahead and assume the value is non-nil.
+ State = assumeExprIsNonNull(M.getOriginExpr(), State, C);
+ }
+ }
}
C.addTransition(State);
}
OpenPOWER on IntegriCloud