diff options
author | Fariborz Jahanian <fjahanian@apple.com> | 2007-09-12 18:23:47 +0000 |
---|---|---|
committer | Fariborz Jahanian <fjahanian@apple.com> | 2007-09-12 18:23:47 +0000 |
commit | cfb31fab5e33565c1455dd43c4fc642218edb68a (patch) | |
tree | d0cb975de5979c61e557f391d86cafaf715e88e0 | |
parent | 7b412cb823f09378d45a0d0baf1127f4466c640c (diff) | |
download | llvm-cfb31fab5e33565c1455dd43c4fc642218edb68a.tar.gz |
Patch for building method declaration nodes. Also fixed a segfault in cocoa.m due
to use of @property.
llvm-svn: 41880
-rw-r--r-- | clang/AST/Decl.cpp | 16 | ||||
-rw-r--r-- | clang/Parse/ParseObjc.cpp | 2 | ||||
-rw-r--r-- | clang/Sema/Sema.h | 7 | ||||
-rw-r--r-- | clang/Sema/SemaDecl.cpp | 44 | ||||
-rw-r--r-- | clang/include/clang/AST/Decl.h | 9 |
5 files changed, 71 insertions, 7 deletions
diff --git a/clang/AST/Decl.cpp b/clang/AST/Decl.cpp index 0e6c218f2d5f..e84532923be6 100644 --- a/clang/AST/Decl.cpp +++ b/clang/AST/Decl.cpp @@ -164,6 +164,22 @@ FieldDecl* RecordDecl::getMember(IdentifierInfo *name) { return 0; } +void ObjcMethodDecl::setMethodParams(ParmVarDecl **NewParamInfo, + unsigned NumParams) { + assert(ParamInfo == 0 && "Already has param info!"); + + // Zero params -> null pointer. + if (NumParams) { + ParamInfo = new ParmVarDecl*[NumParams]; + memcpy(ParamInfo, NewParamInfo, sizeof(ParmVarDecl*)*NumParams); + NumMethodParams = NumParams; + } +} + +ObjcMethodDecl::~ObjcMethodDecl() { + delete[] ParamInfo; +} + /// addObjcMethods - Insert instance and methods declarations into /// ObjcInterfaceDecl's InsMethods and ClsMethods fields. /// diff --git a/clang/Parse/ParseObjc.cpp b/clang/Parse/ParseObjc.cpp index 803fe2f6707c..7ddcaabb04b4 100644 --- a/clang/Parse/ParseObjc.cpp +++ b/clang/Parse/ParseObjc.cpp @@ -229,7 +229,7 @@ void Parser::ParseObjCInterfaceDeclList(DeclTy *interfaceDecl) { ConsumeToken(); continue; } else if (ocKind == tok::objc_property) { - ParseObjCPropertyDecl(0/*FIXME*/); + ParseObjCPropertyDecl(interfaceDecl); continue; } else { Diag(Tok, diag::err_objc_illegal_interface_qual); diff --git a/clang/Sema/Sema.h b/clang/Sema/Sema.h index b6fe89a3fa19..7a3466f97d32 100644 --- a/clang/Sema/Sema.h +++ b/clang/Sema/Sema.h @@ -360,6 +360,13 @@ public: virtual void ObjcAddMethodsToClass(DeclTy *ClassDecl, DeclTy **allMethods, unsigned allNum); + virtual DeclTy *ObjcBuildMethodDeclaration(SourceLocation MethodLoc, + tok::TokenKind MethodType, TypeTy *ReturnType, + ObjcKeywordInfo *Keywords, unsigned NumKeywords, + AttributeList *AttrList); + virtual DeclTy *ObjcBuildMethodDeclaration(SourceLocation MethodLoc, + tok::TokenKind MethodType, TypeTy *ReturnType, + IdentifierInfo *SelectorName, AttributeList *AttrList); virtual void ObjcAddInstanceVariable(DeclTy *ClassDec, DeclTy *Ivar, tok::ObjCKeywordKind visibility); diff --git a/clang/Sema/SemaDecl.cpp b/clang/Sema/SemaDecl.cpp index 6bfae197e3c1..d367038cddfa 100644 --- a/clang/Sema/SemaDecl.cpp +++ b/clang/Sema/SemaDecl.cpp @@ -1197,8 +1197,10 @@ void Sema::ParseRecordBody(SourceLocation RecLoc, DeclTy *RecDecl, void Sema::ObjcAddMethodsToClass(DeclTy *ClassDecl, DeclTy **allMethods, unsigned allNum) { - // FIXME: Add method insertion code here. -#if 0 + // FIXME: Fix this when we can handle methods declared in protocols. + // See Parser::ParseObjCAtProtocolDeclaration + if (!ClassDecl) + return; ObjcInterfaceDecl *Interface = cast<ObjcInterfaceDecl>( static_cast<Decl*>(ClassDecl)); llvm::SmallVector<ObjcMethodDecl*, 32> insMethods; @@ -1215,10 +1217,46 @@ void Sema::ObjcAddMethodsToClass(DeclTy *ClassDecl, } Interface->ObjcAddMethods(&insMethods[0], insMethods.size(), &clsMethods[0], clsMethods.size()); -#endif return; } +Sema::DeclTy *Sema::ObjcBuildMethodDeclaration(SourceLocation MethodLoc, + tok::TokenKind MethodType, TypeTy *ReturnType, + ObjcKeywordInfo *Keywords, unsigned NumKeywords, + AttributeList *AttrList) { + assert(NumKeywords && "Selector must be specified"); + // FIXME: SelectorName to be changed to comform to objc's abi for method names + IdentifierInfo *SelectorName = Keywords[0].SelectorName; + llvm::SmallVector<ParmVarDecl*, 16> Params; + + for (unsigned i = 0; i < NumKeywords; i++) { + ObjcKeywordInfo *arg = &Keywords[i]; + // FIXME: arg->AttrList must be stored too! + ParmVarDecl* Param = new ParmVarDecl(arg->ColonLoc, arg->ArgumentName, + QualType::getFromOpaquePtr(arg->TypeInfo), + VarDecl::None, 0); + // FIXME: 'InvalidType' does not get set by caller yet. + if (arg->InvalidType) + Param->setInvalidDecl(); + Params.push_back(Param); + } + QualType resultDeclType = QualType::getFromOpaquePtr(ReturnType); + ObjcMethodDecl* ObjcMethod = new ObjcMethodDecl(MethodLoc, + SelectorName, resultDeclType, + 0, -1, AttrList, MethodType == tok::minus); + ObjcMethod->setMethodParams(&Params[0], NumKeywords); + return ObjcMethod; +} + +Sema::DeclTy *Sema::ObjcBuildMethodDeclaration(SourceLocation MethodLoc, + tok::TokenKind MethodType, TypeTy *ReturnType, + IdentifierInfo *SelectorName, AttributeList *AttrList) { + // FIXME: SelectorName to be changed to comform to objc's abi for method names + QualType resultDeclType = QualType::getFromOpaquePtr(ReturnType); + return new ObjcMethodDecl(MethodLoc, SelectorName, resultDeclType, 0, -1, + AttrList, MethodType == tok::minus); +} + Sema::DeclTy *Sema::ParseEnumConstant(Scope *S, DeclTy *theEnumDecl, DeclTy *lastEnumConst, SourceLocation IdLoc, IdentifierInfo *Id, diff --git a/clang/include/clang/AST/Decl.h b/clang/include/clang/AST/Decl.h index d65ba6e4f458..aba9e17ded25 100644 --- a/clang/include/clang/AST/Decl.h +++ b/clang/include/clang/AST/Decl.h @@ -583,19 +583,21 @@ public: class ObjcMethodDecl : public Decl { public: ObjcMethodDecl(SourceLocation L, IdentifierInfo *Id, QualType T, + ParmVarDecl **paramInfo = 0, int numParams=-1, AttributeList *M = 0, bool isInstance = true, Decl *PrevDecl = 0) - : Decl(ObjcMethod, L, Id, PrevDecl), MethodDeclType(T), ParamInfo(0), + : Decl(ObjcMethod, L, Id, PrevDecl), MethodDeclType(T), + ParamInfo(paramInfo), NumMethodParams(numParams), MethodAttrs(M), IsInstance(isInstance) {} virtual ~ObjcMethodDecl(); QualType getMethodType() const { return MethodDeclType; } - unsigned getNumMethodParams() const; + unsigned getNumMethodParams() const { return NumMethodParams; } ParmVarDecl *getMethodParamDecl(unsigned i) { assert(i < getNumMethodParams() && "Illegal param #"); return ParamInfo[i]; } - void setParams(ParmVarDecl **NewParamInfo, unsigned NumParams); + void setMethodParams(ParmVarDecl **NewParamInfo, unsigned NumParams); AttributeList *getMethodAttrs() const {return MethodAttrs;} bool isInstance() const { return IsInstance; } @@ -610,6 +612,7 @@ private: /// ParamInfo - new[]'d array of pointers to VarDecls for the formal /// parameters of this Method. This is null if there are no formals. ParmVarDecl **ParamInfo; + int NumMethodParams; // -1 if no parameters /// List of attributes for this method declaration. AttributeList *MethodAttrs; |