Author: snaroff Date: Wed Feb 4 11:14:05 2009 New Revision: 63738 URL: http://llvm.org/viewvc/llvm-project?rev=63738&view=rev Log: Fix <rdar://problem/6552648> error: redefinition of 'XCElementAnchorDelegate' as different kind of symbol.
At first glance, this looked like a recent regression (possibly created by http://llvm.org/viewvc/llvm-project?view=rev&revision=63354, which was the only recent change to this section of Sema::ActOnStartClassInterface()). After more investigation, it looks like an edge case bug that we didn't cover in our tests. Modified: cfe/trunk/lib/Sema/SemaDeclObjC.cpp cfe/trunk/test/SemaObjC/class-def-test-1.m Modified: cfe/trunk/lib/Sema/SemaDeclObjC.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclObjC.cpp?rev=63738&r1=63737&r2=63738&view=diff ============================================================================== --- cfe/trunk/lib/Sema/SemaDeclObjC.cpp (original) +++ cfe/trunk/lib/Sema/SemaDeclObjC.cpp Wed Feb 4 11:14:05 2009 @@ -105,26 +105,41 @@ } if (SuperName) { - ObjCInterfaceDecl* SuperClassEntry = 0; // Check if a different kind of symbol declared in this scope. PrevDecl = LookupName(TUScope, SuperName, LookupOrdinaryName); - if (PrevDecl && !isa<ObjCInterfaceDecl>(PrevDecl)) { - Diag(SuperLoc, diag::err_redefinition_different_kind) << SuperName; - Diag(PrevDecl->getLocation(), diag::note_previous_definition); - } - else { - // Check that super class is previously defined - SuperClassEntry = dyn_cast_or_null<ObjCInterfaceDecl>(PrevDecl); - if (!SuperClassEntry) + ObjCInterfaceDecl *SuperClassDecl = + dyn_cast_or_null<ObjCInterfaceDecl>(PrevDecl); + if (PrevDecl && SuperClassDecl == 0) { + // The previous declaration was not a class decl. Check if we have a + // typedef. If we do, get the underlying class type. + if (const TypedefDecl *TDecl = dyn_cast_or_null<TypedefDecl>(PrevDecl)) { + QualType T = TDecl->getUnderlyingType(); + if (T->isObjCInterfaceType()) { + if (NamedDecl *IDecl = T->getAsObjCInterfaceType()->getDecl()) + SuperClassDecl = dyn_cast<ObjCInterfaceDecl>(IDecl); + } + } + // This handles the following case: + // + // typedef int SuperClass; + // @interface MyClass : SuperClass {} @end + // + if (!SuperClassDecl) { + Diag(SuperLoc, diag::err_redefinition_different_kind) << SuperName; + Diag(PrevDecl->getLocation(), diag::note_previous_definition); + } + } + if (!dyn_cast_or_null<TypedefDecl>(PrevDecl)) { + if (!SuperClassDecl) Diag(SuperLoc, diag::err_undef_superclass) << SuperName << ClassName << SourceRange(AtInterfaceLoc, ClassLoc); - else if (SuperClassEntry->isForwardDecl()) + else if (SuperClassDecl->isForwardDecl()) Diag(SuperLoc, diag::err_undef_superclass) - << SuperClassEntry->getDeclName() << ClassName + << SuperClassDecl->getDeclName() << ClassName << SourceRange(AtInterfaceLoc, ClassLoc); } - IDecl->setSuperClass(SuperClassEntry); + IDecl->setSuperClass(SuperClassDecl); IDecl->setSuperClassLoc(SuperLoc); IDecl->setLocEnd(SuperLoc); } else { // we have a root class. Modified: cfe/trunk/test/SemaObjC/class-def-test-1.m URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaObjC/class-def-test-1.m?rev=63738&r1=63737&r2=63738&view=diff ============================================================================== --- cfe/trunk/test/SemaObjC/class-def-test-1.m (original) +++ cfe/trunk/test/SemaObjC/class-def-test-1.m Wed Feb 4 11:14:05 2009 @@ -24,3 +24,10 @@ @interface INTF3 : PROTO @end // expected-error {{cannot find interface declaration for 'PROTO', superclass of 'INTF3'}} +// Make sure we allow the following (for GCC compatibility). +...@interface NSObject @end +typedef NSObject TD_NSObject; +...@interface XCElementUnit : TD_NSObject {} +...@end + + _______________________________________________ cfe-commits mailing list [email protected] http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits
