diff options
| author | Fariborz Jahanian <fjahanian@apple.com> | 2007-09-27 18:57:03 +0000 |
|---|---|---|
| committer | Fariborz Jahanian <fjahanian@apple.com> | 2007-09-27 18:57:03 +0000 |
| commit | f6546b38b2f598aa8387ea6106392861b83c53ec (patch) | |
| tree | 1be5424b30107e517f09e943cea87f256278e9b4 /clang/Sema | |
| parent | 65ca537b5552dfbb1c74beb312d54d215a99972c (diff) | |
| download | bcm5719-llvm-f6546b38b2f598aa8387ea6106392861b83c53ec.tar.gz bcm5719-llvm-f6546b38b2f598aa8387ea6106392861b83c53ec.zip | |
Patch for method implementation. It populates ObjcImplementationDecl object with method implementation declarations .
It checks and warns on those methods declared in class interface and not implemented.
llvm-svn: 42412
Diffstat (limited to 'clang/Sema')
| -rw-r--r-- | clang/Sema/Sema.h | 2 | ||||
| -rw-r--r-- | clang/Sema/SemaDecl.cpp | 55 |
2 files changed, 56 insertions, 1 deletions
diff --git a/clang/Sema/Sema.h b/clang/Sema/Sema.h index a486d4fa73a..45d1a2dc33d 100644 --- a/clang/Sema/Sema.h +++ b/clang/Sema/Sema.h @@ -390,6 +390,8 @@ public: virtual void ActOnImpleIvarVsClassIvars(DeclTy *ClassDecl, DeclTy **Fields, unsigned NumFields); + virtual void ActOnImplMethodsVsClassMethods(DeclTy *ImplClass, DeclTy *Class); + virtual DeclTy *ObjcBuildMethodDeclaration(SourceLocation MethodLoc, tok::TokenKind MethodType, TypeTy *ReturnType, SelectorInfo *Sel, // optional arguments. The number of types/arguments is obtained diff --git a/clang/Sema/SemaDecl.cpp b/clang/Sema/SemaDecl.cpp index dd8fe22cc94..381003f86af 100644 --- a/clang/Sema/SemaDecl.cpp +++ b/clang/Sema/SemaDecl.cpp @@ -1174,6 +1174,49 @@ void Sema::ActOnImpleIvarVsClassIvars(DeclTy *ClassDecl, } +void Sema::ActOnImplMethodsVsClassMethods(DeclTy* ImplClassDecl, + DeclTy* ClassDecl) { + ObjcImplementationDecl* IMPDecl = + cast<ObjcImplementationDecl>(static_cast<Decl*>(ImplClassDecl)); + assert(IMPDecl && "missing implmentation class decl"); + + ObjcInterfaceDecl* IDecl = + cast<ObjcInterfaceDecl>(static_cast<Decl*>(ClassDecl)); + assert(IDecl && "missing interface class decl"); + + llvm::DenseMap<const SelectorInfo*, char> Map; + // Check and see if instance methods in class interface have been + // implemented in the implementation class. + ObjcMethodDecl **methods = IMPDecl->getInsMethods(); + for (int i=0; i < IMPDecl->getNumInsMethods(); i++) { + Map[methods[i]->getSelector()] = 'a'; + } + + methods = IDecl->getInsMethods(); + for (int j = 0; j < IDecl->getNumInsMethods(); j++) + if (!Map.count(methods[j]->getSelector())) { + llvm::SmallString<128> buf; + Diag(methods[j]->getLocation(), diag::warn_undef_method_impl, + methods[j]->getSelector()->getName(buf)); + } + Map.clear(); + // Check and see if class methods in class interface have been + // implemented in the implementation class. + methods = IMPDecl->getClsMethods(); + for (int i=0; i < IMPDecl->getNumClsMethods(); i++) { + Map[methods[i]->getSelector()] = 'a'; + } + + methods = IDecl->getClsMethods(); + for (int j = 0; j < IDecl->getNumClsMethods(); j++) + if (!Map.count(methods[j]->getSelector())) { + llvm::SmallString<128> buf; + Diag(methods[j]->getLocation(), diag::warn_undef_method_impl, + methods[j]->getSelector()->getName(buf)); + } + return; +} + /// ObjcClassDeclaration - /// Scope will always be top level file scope. Action::DeclTy * @@ -1560,7 +1603,17 @@ void Sema::ObjcAddMethodsToClass(DeclTy *ClassDecl, static_cast<Decl*>(ClassDecl)); Category->ObjcAddCatMethods(&insMethods[0], insMethods.size(), &clsMethods[0], clsMethods.size()); - } + } + else if (isa<ObjcImplementationDecl>(static_cast<Decl *>(ClassDecl))) { + ObjcImplementationDecl* ImplClass = cast<ObjcImplementationDecl>( + static_cast<Decl*>(ClassDecl)); + ImplClass->ObjcAddImplMethods(&insMethods[0], insMethods.size(), + &clsMethods[0], clsMethods.size()); + ObjcInterfaceDecl* IDecl = + Context.getObjCInterfaceDecl(ImplClass->getIdentifier()); + if (IDecl) + ActOnImplMethodsVsClassMethods(ImplClass, IDecl); + } else assert(0 && "Sema::ObjcAddMethodsToClass(): Unknown DeclTy"); return; |

