diff options
author | Douglas Gregor <dgregor@apple.com> | 2011-11-14 22:10:01 +0000 |
---|---|---|
committer | Douglas Gregor <dgregor@apple.com> | 2011-11-14 22:10:01 +0000 |
commit | b3029960632ca8a3248e74770eda64d6c16f7246 (patch) | |
tree | 7f7653e42ae5198506c92b81f6864f57242440d8 /lib/Sema/SemaDeclObjC.cpp | |
parent | 2bbcd5ce370753c86d312d2c72a97476ac35b073 (diff) |
Use Sema::RequireCompleteType to check for the completeness of
Objective-C classes. This has two purposes: to consistently provide
"forward declaration here" notes when we hit an incomplete type, and
to give LLDB a chance to complete the type.
RequireCompleteType bits from Sean Callanan!
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@144573 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaDeclObjC.cpp')
-rw-r--r-- | lib/Sema/SemaDeclObjC.cpp | 32 |
1 files changed, 20 insertions, 12 deletions
diff --git a/lib/Sema/SemaDeclObjC.cpp b/lib/Sema/SemaDeclObjC.cpp index fe9a7841cf..f4e2fb3205 100644 --- a/lib/Sema/SemaDeclObjC.cpp +++ b/lib/Sema/SemaDeclObjC.cpp @@ -463,11 +463,12 @@ ActOnStartClassInterface(SourceLocation AtInterfaceLoc, if (!SuperClassDecl) Diag(SuperLoc, diag::err_undef_superclass) << SuperName << ClassName << SourceRange(AtInterfaceLoc, ClassLoc); - else if (SuperClassDecl->isForwardDecl()) { - Diag(SuperLoc, diag::err_forward_superclass) - << SuperClassDecl->getDeclName() << ClassName - << SourceRange(AtInterfaceLoc, ClassLoc); - Diag(SuperClassDecl->getLocation(), diag::note_forward_class); + else if (RequireCompleteType(SuperLoc, + Context.getObjCInterfaceType(SuperClassDecl), + PDiag(diag::err_forward_superclass) + << SuperClassDecl->getDeclName() + << ClassName + << SourceRange(AtInterfaceLoc, ClassLoc))) { SuperClassDecl = 0; } } @@ -746,14 +747,20 @@ ActOnStartCategoryInterface(SourceLocation AtInterfaceLoc, ObjCInterfaceDecl *IDecl = getObjCInterfaceDecl(ClassName, ClassLoc, true); /// Check that class of this category is already completely declared. - if (!IDecl || IDecl->isForwardDecl()) { + + if (!IDecl + || RequireCompleteType(ClassLoc, Context.getObjCInterfaceType(IDecl), + PDiag(diag::err_category_forward_interface) + << (CategoryName == 0))) { // Create an invalid ObjCCategoryDecl to serve as context for // the enclosing method declarations. We mark the decl invalid // to make it clear that this isn't a valid AST. CDecl = ObjCCategoryDecl::Create(Context, CurContext, AtInterfaceLoc, ClassLoc, CategoryLoc, CategoryName,IDecl); CDecl->setInvalidDecl(); - Diag(ClassLoc, diag::err_undef_interface) << ClassName; + + if (!IDecl) + Diag(ClassLoc, diag::err_undef_interface) << ClassName; return ActOnObjCContainerStartDefinition(CDecl); } @@ -820,9 +827,12 @@ Decl *Sema::ActOnStartCategoryImplementation( ObjCCategoryImplDecl::Create(Context, CurContext, CatName, IDecl, ClassLoc, AtCatImplLoc); /// Check that class of this category is already completely declared. - if (!IDecl || IDecl->isForwardDecl()) { + if (!IDecl) { Diag(ClassLoc, diag::err_undef_interface) << ClassName; CDecl->setInvalidDecl(); + } else if (RequireCompleteType(ClassLoc, Context.getObjCInterfaceType(IDecl), + diag::err_undef_interface)) { + CDecl->setInvalidDecl(); } // FIXME: PushOnScopeChains? @@ -867,11 +877,9 @@ Decl *Sema::ActOnStartClassImplementation( Diag(ClassLoc, diag::err_redefinition_different_kind) << ClassName; Diag(PrevDecl->getLocation(), diag::note_previous_definition); } else if ((IDecl = dyn_cast_or_null<ObjCInterfaceDecl>(PrevDecl))) { - // If this is a forward declaration of an interface, warn. - if (IDecl->isForwardDecl()) { - Diag(ClassLoc, diag::warn_undef_interface) << ClassName; + if (RequireCompleteType(ClassLoc, Context.getObjCInterfaceType(IDecl), + diag::warn_undef_interface)) IDecl = 0; - } } else { // We did not find anything with the name ClassName; try to correct for // typos in the class name. |