Mercurial > hg > CbC > CbC_llvm
changeset 28:273f76252412
create __CbC_env automatically when input file contains code segment
author | Kaito Tokumori <e105711@ie.u-ryukyu.ac.jp> |
---|---|
date | Sun, 08 Dec 2013 00:16:12 +0900 |
parents | ecf2394747e1 |
children | 00b59dd660f7 |
files | tools/clang/include/clang/Parse/Parser.h tools/clang/lib/Parse/ParseDecl.cpp |
diffstat | 2 files changed, 155 insertions(+), 2 deletions(-) [+] |
line wrap: on
line diff
--- a/tools/clang/include/clang/Parse/Parser.h Tue Nov 12 20:27:46 2013 +0900 +++ b/tools/clang/include/clang/Parse/Parser.h Sun Dec 08 00:16:12 2013 +0900 @@ -1660,6 +1660,10 @@ void ParseStructDeclaration(ParsingDeclSpec &DS, FieldCallback &Callback); +#ifndef noCbC + bool Create__CbC_envStruct(SourceLocation Loc, AccessSpecifier AS); +#endif + bool isDeclarationSpecifier(bool DisambiguatingWithExpression = false); bool isTypeSpecifierQualifier(); bool isTypeQualifier() const;
--- a/tools/clang/lib/Parse/ParseDecl.cpp Tue Nov 12 20:27:46 2013 +0900 +++ b/tools/clang/lib/Parse/ParseDecl.cpp Sun Dec 08 00:16:12 2013 +0900 @@ -2876,11 +2876,17 @@ break; #ifndef noCbC case tok::kw___code: { + //start of creating __CbC_env + bool isInvalid__CbC_env = Create__CbC_envStruct(Loc,AS); + //end of creating __CbC_env + if (DS.getSourceRange().isInvalid()) { + DS.SetRangeStart(Tok.getLocation()); + DS.SetRangeEnd(Tok.getLocation()); + } LangOptions* LOP; LOP = const_cast<LangOptions*>(&getLangOpts()); LOP->HasCodeSegment = 1; - isInvalid = DS.SetTypeSpecType(DeclSpec::TST___code, Loc, PrevSpec, - DiagID); + isInvalid = (DS.SetTypeSpecType(DeclSpec::TST___code, Loc, PrevSpec, DiagID) || isInvalid__CbC_env); break; } #endif @@ -5655,3 +5661,146 @@ } return false; } + +#ifndef noCbC +bool Parser::Create__CbC_envStruct(SourceLocation Loc, AccessSpecifier AS) { + ParsingDeclSpec SDS(*this); + if (SDS.getSourceRange().isInvalid()) { + SDS.SetRangeStart(Loc); + SDS.SetRangeEnd(Loc); + } + Token identifierToken; + identifierToken.startToken(); + const char *CbC_envId = "__CbC_env"; + identifierToken.setLength(9); //length of __CbC_env + identifierToken.setKind(tok::raw_identifier); + identifierToken.setRawIdentifierData(CbC_envId); + IdentifierInfo *Name; + Name = PP.getIdentifierInfo(StringRef(identifierToken.getRawIdentifierData(),identifierToken.getLength())); + identifierToken.setIdentifierInfo(Name); + identifierToken.setKind(Name->getTokenID()); + + // Check previous definition. If the __CbC_env has been already defined, we have not to create again. + LookupResult Previous(Actions, Name, Loc, Actions.LookupTagName, Actions.ForRedeclaration); + if(Actions.LookupName(Previous, getCurScope())) + return false; + + // start ParseClassSpecifier + DeclSpec::TST TagType = DeclSpec::TST_struct; + DeclResult TagOrTempResult = true; // invalid + bool Owned = false; + bool IsDependent = false; + ParsedAttributesWithRange attrs(AttrFactory); + MultiTemplateParamsArg TParams; + + TagOrTempResult = Actions.ActOnTag(getCurScope(), TagType, Sema::TUK_Definition, Loc, + SDS.getTypeSpecScope(), Name, Loc, attrs.getList(), AS, + SDS.getModulePrivateSpecLoc(), + TParams, Owned, IsDependent, + SourceLocation(), false, + clang::TypeResult()); + // start ParseStructUnionBody + Decl *TagDecl = TagOrTempResult.get(); + PrettyDeclStackTraceEntry CrashInfo(Actions, TagDecl, Loc, "parsing struct/union body"); + ParseScope StructScope(this, Scope::ClassScope|Scope::DeclScope); + Actions.ActOnTagStartDefinition(getCurScope(), TagDecl); + SmallVector<Decl *, 32> FieldDecls; + ParsingDeclSpec ret_pPDS(*this); + + if (ret_pPDS.getSourceRange().isInvalid()) { + ret_pPDS.SetRangeStart(Loc); + ret_pPDS.SetRangeEnd(Loc); + } + bool isInvalid = false; + const char *PrevSpec = 0; + unsigned DiagID = 0; + isInvalid = ret_pPDS.SetTypeSpecType(DeclSpec::TST_void, Loc, PrevSpec, + DiagID); + ret_pPDS.SetRangeEnd(Loc); + + // ここまでで void読み込んだ。 PreSpeとDiagIDは未使用。 + // TokenKindがstar(*)になる。 + ret_pPDS.Finish(Diags, PP); //これは consumeTokenでTokenがstarになったあとのもの。 + + ret_pPDS.getParsedSpecifiers(); + SourceLocation CommaLoc; + ParsingFieldDeclarator ret_pDeclaratorInfo(*this, ret_pPDS); + ret_pDeclaratorInfo.D.setCommaLoc(CommaLoc); + ColonProtectionRAIIObject ret_pX(*this); + Token ret_pToken; + ret_pToken.startToken(); + const char *ret_pId = "ret_p"; + ret_pToken.setLength(5); //length of ret_p + ret_pToken.setKind(tok::raw_identifier); + ret_pToken.setRawIdentifierData(ret_pId); + IdentifierInfo *II; + II = PP.getIdentifierInfo(StringRef(ret_pToken.getRawIdentifierData(),ret_pToken.getLength())); + ret_pToken.setIdentifierInfo(II); + ret_pToken.setKind(II->getTokenID()); + ret_pDeclaratorInfo.D.SetRangeEnd(Loc); + DeclSpec ret_pDS(AttrFactory); + ret_pDS.Finish(Diags,PP); + ret_pDeclaratorInfo.D.SetIdentifier(II,Loc); + // ここでConsumeToken()が入る。Kindはsemi(;)に。 + ret_pDeclaratorInfo.D.AddTypeInfo(DeclaratorChunk::getPointer(ret_pDS.getTypeQualifiers(), Loc,ret_pDS.getConstSpecLoc(), + ret_pDS.getVolatileSpecLoc(),ret_pDS.getRestrictSpecLoc()), + ret_pDS.getAttributes(),SourceLocation()); + Decl *Field = Actions.ActOnField(getCurScope(), TagDecl, + ret_pDeclaratorInfo.D.getDeclSpec().getSourceRange().getBegin(), + ret_pDeclaratorInfo.D, ret_pDeclaratorInfo.BitfieldSize); + FieldDecls.push_back(Field); + ret_pDeclaratorInfo.complete(Field); + // こっからjmp_buf(intのポインタ)の作成。 + ParsingDeclSpec jmp_bufPDS(*this); + + if (jmp_bufPDS.getSourceRange().isInvalid()) { + jmp_bufPDS.SetRangeStart(Loc); + jmp_bufPDS.SetRangeEnd(Loc); + } + DiagID = 0; + isInvalid = (jmp_bufPDS.SetTypeSpecType(DeclSpec::TST_int, Loc, PrevSpec, DiagID) || isInvalid); + jmp_bufPDS.SetRangeEnd(Loc); + jmp_bufPDS.Finish(Diags, PP); + jmp_bufPDS.getParsedSpecifiers(); + CommaLoc = SourceLocation(); + ParsingFieldDeclarator jmp_bufDeclaratorInfo(*this, jmp_bufPDS); + jmp_bufDeclaratorInfo.D.setCommaLoc(CommaLoc); + ColonProtectionRAIIObject env_pX(*this); + jmp_bufDeclaratorInfo.D.SetRangeEnd(Loc); + Token envToken; + envToken.startToken(); + const char *env_pId = "env"; + envToken.setLength(3); //length of env + envToken.setKind(tok::raw_identifier); + envToken.setRawIdentifierData(env_pId); + II = PP.getIdentifierInfo(StringRef(envToken.getRawIdentifierData(),envToken.getLength())); + envToken.setIdentifierInfo(II); + envToken.setKind(II->getTokenID()); + jmp_bufDeclaratorInfo.D.SetRangeEnd(Loc); + DeclSpec jmp_bufDS(AttrFactory); + jmp_bufDS.Finish(Diags,PP); + jmp_bufDeclaratorInfo.D.SetIdentifier(II,Loc); + // ここでConsumeToken()が入る。Kindはsemi(;)に。 + jmp_bufDeclaratorInfo.D.AddTypeInfo(DeclaratorChunk::getPointer(jmp_bufDS.getTypeQualifiers(), Loc,jmp_bufDS.getConstSpecLoc(), + jmp_bufDS.getVolatileSpecLoc(),jmp_bufDS.getRestrictSpecLoc()), + jmp_bufDS.getAttributes(),SourceLocation()); + Field = Actions.ActOnField(getCurScope(), TagDecl, + jmp_bufDeclaratorInfo.D.getDeclSpec().getSourceRange().getBegin(), + jmp_bufDeclaratorInfo.D, jmp_bufDeclaratorInfo.BitfieldSize); + FieldDecls.push_back(Field); + jmp_bufDeclaratorInfo.complete(Field); + Actions.ActOnFields(getCurScope(),Loc, TagDecl, FieldDecls,Loc, Loc,attrs.getList()); + StructScope.Exit(); + Actions.ActOnTagFinishDefinition(getCurScope(), TagDecl,Loc); + bool Result; + Result = SDS.SetTypeSpecType(TagType, Loc,Loc.isValid() ? Loc : Loc,PrevSpec, DiagID, TagOrTempResult.get(), Owned); + if (Result){ + Diag(Loc, DiagID) << PrevSpec; + } + SDS.Finish(Diags,PP); + Decl *TheDecl = Actions.ParsedFreeStandingDeclSpec(getCurScope(), AS, SDS); + SDS.complete(TheDecl); + Actions.ConvertDeclToDeclGroup(TheDecl); + return isInvalid; +} +#endif