From 74b2756bc1f1f5f7c189996fe7e4cd3efef70263 Mon Sep 17 00:00:00 2001 From: Fariborz Jahanian Date: Fri, 3 Dec 2010 23:37:08 +0000 Subject: [PATCH] Diagnose when accessing property in a class method and no property accessor class method to be found, instead of crashing in IRGen. // rdar://8703553 git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@120855 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/clang/AST/DeclObjC.h | 2 +- lib/AST/DeclObjC.cpp | 10 ++++++---- lib/Sema/SemaExpr.cpp | 5 +++-- lib/Sema/SemaExprObjC.cpp | 4 ++-- test/SemaObjC/property-impl-misuse.m | 20 ++++++++++++++++++++ 5 files changed, 32 insertions(+), 9 deletions(-) diff --git a/include/clang/AST/DeclObjC.h b/include/clang/AST/DeclObjC.h index 16d3a10359..8282e0aab5 100644 --- a/include/clang/AST/DeclObjC.h +++ b/include/clang/AST/DeclObjC.h @@ -639,7 +639,7 @@ public: ObjCInterfaceDecl *lookupInheritedClass(const IdentifierInfo *ICName); // Lookup a method in the classes implementation hierarchy. - ObjCMethodDecl *lookupPrivateInstanceMethod(const Selector &Sel); + ObjCMethodDecl *lookupPrivateMethod(const Selector &Sel, bool Instance=true); // Location information, modeled after the Stmt API. SourceLocation getLocStart() const { return getLocation(); } // '@'interface diff --git a/lib/AST/DeclObjC.cpp b/lib/AST/DeclObjC.cpp index ea8fd4ae89..45f5188d40 100644 --- a/lib/AST/DeclObjC.cpp +++ b/lib/AST/DeclObjC.cpp @@ -311,14 +311,16 @@ ObjCMethodDecl *ObjCInterfaceDecl::lookupMethod(Selector Sel, return NULL; } -ObjCMethodDecl *ObjCInterfaceDecl::lookupPrivateInstanceMethod( - const Selector &Sel) { +ObjCMethodDecl *ObjCInterfaceDecl::lookupPrivateMethod( + const Selector &Sel, + bool Instance) { ObjCMethodDecl *Method = 0; if (ObjCImplementationDecl *ImpDecl = getImplementation()) - Method = ImpDecl->getInstanceMethod(Sel); + Method = Instance ? ImpDecl->getInstanceMethod(Sel) + : ImpDecl->getClassMethod(Sel); if (!Method && getSuperClass()) - return getSuperClass()->lookupPrivateInstanceMethod(Sel); + return getSuperClass()->lookupPrivateMethod(Sel, Instance); return Method; } diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp index 9102cac879..270aa3e06b 100644 --- a/lib/Sema/SemaExpr.cpp +++ b/lib/Sema/SemaExpr.cpp @@ -3498,12 +3498,13 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, if (ObjCMethodDecl *MD = getCurMethodDecl()) { ObjCInterfaceDecl *IFace = MD->getClassInterface(); ObjCMethodDecl *Getter; - // FIXME: need to also look locally in the implementation. if ((Getter = IFace->lookupClassMethod(Sel))) { // Check the use of this method. if (DiagnoseUseOfDecl(Getter, MemberLoc)) return ExprError(); } + else + Getter = IFace->lookupPrivateMethod(Sel, false); // If we found a getter then this may be a valid dot-reference, we // will look for the matching setter, in case it is needed. Selector SetterSel = @@ -3513,7 +3514,7 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, if (!Setter) { // If this reference is in an @implementation, also check for 'private' // methods. - Setter = IFace->lookupPrivateInstanceMethod(SetterSel); + Setter = IFace->lookupPrivateMethod(SetterSel, false); } // Look through local category implementations associated with the class. if (!Setter) diff --git a/lib/Sema/SemaExprObjC.cpp b/lib/Sema/SemaExprObjC.cpp index 46a834a487..e60aa071e2 100644 --- a/lib/Sema/SemaExprObjC.cpp +++ b/lib/Sema/SemaExprObjC.cpp @@ -402,7 +402,7 @@ HandleExprPropertyRefExpr(const ObjCObjectPointerType *OPT, // If this reference is in an @implementation, check for 'private' methods. if (!Getter) - Getter = IFace->lookupPrivateInstanceMethod(Sel); + Getter = IFace->lookupPrivateMethod(Sel); // Look through local category implementations associated with the class. if (!Getter) @@ -421,7 +421,7 @@ HandleExprPropertyRefExpr(const ObjCObjectPointerType *OPT, if (!Setter) { // If this reference is in an @implementation, also check for 'private' // methods. - Setter = IFace->lookupPrivateInstanceMethod(SetterSel); + Setter = IFace->lookupPrivateMethod(SetterSel); } // Look through local category implementations associated with the class. if (!Setter) diff --git a/test/SemaObjC/property-impl-misuse.m b/test/SemaObjC/property-impl-misuse.m index 58c91c59d0..122afc1d4b 100644 --- a/test/SemaObjC/property-impl-misuse.m +++ b/test/SemaObjC/property-impl-misuse.m @@ -14,3 +14,23 @@ @synthesize Y; // expected-note {{previous use is here}} @synthesize Z=Y; // expected-error {{synthesized properties 'Z' and 'Y' both claim ivar 'Y'}} @end + +// rdar://8703553 +@interface IDEPathCell +{ +@private + id _gradientStyle; +} + +@property (readwrite, assign, nonatomic) id gradientStyle; +@end + +@implementation IDEPathCell + +@synthesize gradientStyle = _gradientStyle; +- (void)setGradientStyle:(id)value { } + ++ (void)_componentCellWithRepresentedObject { + self.gradientStyle; // expected-error {{property 'gradientStyle' not found on object of type 'Class'}} +} +@end -- 2.40.0