From 3ae681eb1240f09af37936663760526ed1b324cf Mon Sep 17 00:00:00 2001 From: Argyrios Kyrtzidis Date: Tue, 25 Jan 2011 23:54:44 +0000 Subject: [PATCH] [analyzer] Do the self-init check only on NSObject subclasses. Patch by Jean-Daniel Dupas! llvm-svn: 124249 --- .../Checkers/ObjCSelfInitChecker.cpp | 16 ++++++++++++++-- clang/test/Analysis/self-init.m | 13 +++++++++++++ 2 files changed, 27 insertions(+), 2 deletions(-) diff --git a/clang/lib/StaticAnalyzer/Checkers/ObjCSelfInitChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/ObjCSelfInitChecker.cpp index c887ac86ef50..b62d2309fce7 100644 --- a/clang/lib/StaticAnalyzer/Checkers/ObjCSelfInitChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/ObjCSelfInitChecker.cpp @@ -270,11 +270,23 @@ static bool shouldRunOnFunctionOrMethod(const NamedDecl *ND) { const ObjCMethodDecl *MD = dyn_cast(ND); if (!MD) return false; - if (!MD->getClassInterface()->getSuperClass()) - return false; if (!isInitializationMethod(MD)) return false; + // self = [super init] applies only to NSObject subclasses. + // For instance, NSProxy doesn't implement -init. + ASTContext& Ctx = MD->getASTContext(); + IdentifierInfo* NSObjectII = &Ctx.Idents.get("NSObject"); + ObjCInterfaceDecl* ID = MD->getClassInterface()->getSuperClass(); + for ( ; ID ; ID = ID->getSuperClass()) { + IdentifierInfo *II = ID->getIdentifier(); + + if (II == NSObjectII) + break; + } + if (!ID) + return false; + return true; } diff --git a/clang/test/Analysis/self-init.m b/clang/test/Analysis/self-init.m index 8b2b82fabae1..9c30d26be0bb 100644 --- a/clang/test/Analysis/self-init.m +++ b/clang/test/Analysis/self-init.m @@ -17,6 +17,9 @@ -(id)init; -(id)release; @end +@interface NSProxy {} +@end + //#import "Foundation/NSObject.h" typedef unsigned NSUInteger; typedef int NSInteger; @@ -48,6 +51,10 @@ extern void *somePtr; -(void)doSomething; @end +@interface MyProxyObj : NSProxy {} +-(id)init; +@end + @implementation MyObj -(id)init { @@ -137,3 +144,9 @@ extern void *somePtr; -(void)doSomething {} @end + +@implementation MyProxyObj + +- (id)init { return self; } + +@end