[cfe-commits] r75870 - in /cfe/trunk: lib/Sema/SemaExpr.cpp test/SemaObjC/id-isa-ref.m
Steve Naroff
snaroff at apple.com
Wed Jul 15 17:25:07 PDT 2009
Author: snaroff
Date: Wed Jul 15 19:25:06 2009
New Revision: 75870
URL: http://llvm.org/viewvc/llvm-project?rev=75870&view=rev
Log:
Avoid crashing for the enclosed test case.
This is fallout from the recent ObjCObjectPointerType rework. I'll work on fixing this tomorrow.
Added:
cfe/trunk/test/SemaObjC/id-isa-ref.m
Modified:
cfe/trunk/lib/Sema/SemaExpr.cpp
Modified: cfe/trunk/lib/Sema/SemaExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=75870&r1=75869&r2=75870&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaExpr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExpr.cpp Wed Jul 15 19:25:06 2009
@@ -2285,58 +2285,64 @@
const ObjCObjectPointerType *OPT = BaseType->getAsObjCObjectPointerType();
const ObjCInterfaceType *IFaceT =
OPT ? OPT->getInterfaceType() : BaseType->getAsObjCInterfaceType();
- ObjCInterfaceDecl *IDecl = IFaceT->getDecl();
- ObjCInterfaceDecl *ClassDeclared;
- if (ObjCIvarDecl *IV = IDecl->lookupInstanceVariable(&Member,
- ClassDeclared)) {
- // If the decl being referenced had an error, return an error for this
- // sub-expr without emitting another error, in order to avoid cascading
- // error cases.
- if (IV->isInvalidDecl())
- return ExprError();
+ if (IFaceT) {
+ ObjCInterfaceDecl *IDecl = IFaceT->getDecl();
+ ObjCInterfaceDecl *ClassDeclared;
+ ObjCIvarDecl *IV = IDecl->lookupInstanceVariable(&Member, ClassDeclared);
+
+ if (IV) {
+ // If the decl being referenced had an error, return an error for this
+ // sub-expr without emitting another error, in order to avoid cascading
+ // error cases.
+ if (IV->isInvalidDecl())
+ return ExprError();
- // Check whether we can reference this field.
- if (DiagnoseUseOfDecl(IV, MemberLoc))
- return ExprError();
- if (IV->getAccessControl() != ObjCIvarDecl::Public &&
- IV->getAccessControl() != ObjCIvarDecl::Package) {
- ObjCInterfaceDecl *ClassOfMethodDecl = 0;
- if (ObjCMethodDecl *MD = getCurMethodDecl())
- ClassOfMethodDecl = MD->getClassInterface();
- else if (ObjCImpDecl && getCurFunctionDecl()) {
- // Case of a c-function declared inside an objc implementation.
- // FIXME: For a c-style function nested inside an objc implementation
- // class, there is no implementation context available, so we pass
- // down the context as argument to this routine. Ideally, this context
- // need be passed down in the AST node and somehow calculated from the
- // AST for a function decl.
- Decl *ImplDecl = ObjCImpDecl.getAs<Decl>();
- if (ObjCImplementationDecl *IMPD =
- dyn_cast<ObjCImplementationDecl>(ImplDecl))
- ClassOfMethodDecl = IMPD->getClassInterface();
- else if (ObjCCategoryImplDecl* CatImplClass =
- dyn_cast<ObjCCategoryImplDecl>(ImplDecl))
- ClassOfMethodDecl = CatImplClass->getClassInterface();
- }
-
- if (IV->getAccessControl() == ObjCIvarDecl::Private) {
- if (ClassDeclared != IDecl ||
- ClassOfMethodDecl != ClassDeclared)
- Diag(MemberLoc, diag::error_private_ivar_access) << IV->getDeclName();
+ // Check whether we can reference this field.
+ if (DiagnoseUseOfDecl(IV, MemberLoc))
+ return ExprError();
+ if (IV->getAccessControl() != ObjCIvarDecl::Public &&
+ IV->getAccessControl() != ObjCIvarDecl::Package) {
+ ObjCInterfaceDecl *ClassOfMethodDecl = 0;
+ if (ObjCMethodDecl *MD = getCurMethodDecl())
+ ClassOfMethodDecl = MD->getClassInterface();
+ else if (ObjCImpDecl && getCurFunctionDecl()) {
+ // Case of a c-function declared inside an objc implementation.
+ // FIXME: For a c-style function nested inside an objc implementation
+ // class, there is no implementation context available, so we pass
+ // down the context as argument to this routine. Ideally, this context
+ // need be passed down in the AST node and somehow calculated from the
+ // AST for a function decl.
+ Decl *ImplDecl = ObjCImpDecl.getAs<Decl>();
+ if (ObjCImplementationDecl *IMPD =
+ dyn_cast<ObjCImplementationDecl>(ImplDecl))
+ ClassOfMethodDecl = IMPD->getClassInterface();
+ else if (ObjCCategoryImplDecl* CatImplClass =
+ dyn_cast<ObjCCategoryImplDecl>(ImplDecl))
+ ClassOfMethodDecl = CatImplClass->getClassInterface();
+ }
+
+ if (IV->getAccessControl() == ObjCIvarDecl::Private) {
+ if (ClassDeclared != IDecl ||
+ ClassOfMethodDecl != ClassDeclared)
+ Diag(MemberLoc, diag::error_private_ivar_access)
+ << IV->getDeclName();
+ }
+ // @protected
+ else if (!IDecl->isSuperClassOf(ClassOfMethodDecl))
+ Diag(MemberLoc, diag::error_protected_ivar_access)
+ << IV->getDeclName();
}
- // @protected
- else if (!IDecl->isSuperClassOf(ClassOfMethodDecl))
- Diag(MemberLoc, diag::error_protected_ivar_access) << IV->getDeclName();
- }
- return Owned(new (Context) ObjCIvarRefExpr(IV, IV->getType(),
- MemberLoc, BaseExpr,
- OpKind == tok::arrow));
- }
- return ExprError(Diag(MemberLoc, diag::err_typecheck_member_reference_ivar)
- << IDecl->getDeclName() << &Member
- << BaseExpr->getSourceRange());
+ return Owned(new (Context) ObjCIvarRefExpr(IV, IV->getType(),
+ MemberLoc, BaseExpr,
+ OpKind == tok::arrow));
+ }
+ return ExprError(Diag(MemberLoc, diag::err_typecheck_member_reference_ivar)
+ << IDecl->getDeclName() << &Member
+ << BaseExpr->getSourceRange());
+ }
+ // We don't have an interface. FIXME: deal with ObjC builtin 'id' type.
}
// Handle properties on 'id' and qualified "id".
if (OpKind == tok::period && (BaseType->isObjCIdType() ||
Added: cfe/trunk/test/SemaObjC/id-isa-ref.m
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjC/id-isa-ref.m?rev=75870&view=auto
==============================================================================
--- cfe/trunk/test/SemaObjC/id-isa-ref.m (added)
+++ cfe/trunk/test/SemaObjC/id-isa-ref.m Wed Jul 15 19:25:06 2009
@@ -0,0 +1,17 @@
+// RUN: clang-cc -fsyntax-only -verify %s
+
+typedef struct objc_object {
+ struct objc_class *isa;
+} *id;
+
+ at interface Whatever
++self;
+ at end
+
+static void func() {
+
+ id x;
+
+ // FIXME: The following needs to compile without error. I will fix this tomorrow (7/15/09). Until I do, we will produce an error.
+ [x->isa self]; // expected-error {{member reference base type 'id' is not a structure or union}}
+}
More information about the cfe-commits
mailing list