From 0bab9ba6e37ced872c6f0db212ef11387060858b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Marjam=C3=A4ki?= Date: Sat, 25 Jan 2020 14:47:51 +0100 Subject: [PATCH] Clang import; Handle clang-9 range for loop --- lib/clangimport.cpp | 22 ++++++++++++++++----- test/testclangimport.cpp | 42 ++++++++++++++++++++++++++++++++++++++-- 2 files changed, 57 insertions(+), 7 deletions(-) diff --git a/lib/clangimport.cpp b/lib/clangimport.cpp index b84ec4ae7..8c56c6428 100644 --- a/lib/clangimport.cpp +++ b/lib/clangimport.cpp @@ -625,11 +625,23 @@ Token *clangimport::AstNode::createTokens(TokenList *tokenList) if (nodeType == CXXForRangeStmt) { Token *forToken = addtoken(tokenList, "for"); Token *par1 = addtoken(tokenList, "("); - children[5]->children[0]->mExtTokens.pop_back(); - children[5]->children[0]->children.clear(); - Token *expr1 = children[5]->children[0]->createTokens(tokenList); + AstNodePtr varDecl; + if (children[6]->nodeType == DeclStmt) + varDecl = children[6]->children[0]; + else + varDecl = children[5]->children[0]; + varDecl->mExtTokens.pop_back(); + varDecl->children.clear(); + Token *expr1 = varDecl->createTokens(tokenList); Token *colon = addtoken(tokenList, ":"); - Token *expr2 = children[0]->children[0]->children[0]->createTokens(tokenList); + AstNodePtr range; + for (int i = 0; i < 2; i++) { + if (children[i] && children[i]->nodeType == DeclStmt && children[i]->children[0]->nodeType == VarDecl) { + range = children[i]->children[0]->children[0]; + break; + } + } + Token *expr2 = range->createTokens(tokenList); Token *par2 = addtoken(tokenList, ")"); par1->link(par2); @@ -640,7 +652,7 @@ Token *clangimport::AstNode::createTokens(TokenList *tokenList) par1->astOperand1(forToken); par1->astOperand2(colon); - createScope(tokenList, Scope::ScopeType::eFor, children[6], forToken); + createScope(tokenList, Scope::ScopeType::eFor, children.back(), forToken); return nullptr; } if (nodeType == CXXMethodDecl) { diff --git a/test/testclangimport.cpp b/test/testclangimport.cpp index 66e577163..dd4697509 100644 --- a/test/testclangimport.cpp +++ b/test/testclangimport.cpp @@ -47,7 +47,8 @@ private: TEST_CASE(cxxConstructExpr2); TEST_CASE(cxxConstructExpr3); TEST_CASE(cxxDeleteExpr); - TEST_CASE(cxxForRangeStmt); + TEST_CASE(cxxForRangeStmt1); + TEST_CASE(cxxForRangeStmt2); TEST_CASE(cxxMemberCall); TEST_CASE(cxxMethodDecl); TEST_CASE(cxxNewExpr); @@ -344,7 +345,7 @@ private: ASSERT_EQUALS("void f ( int * p@1 ) { delete p@1 ; }", parse(clang)); } - void cxxForRangeStmt() { + void cxxForRangeStmt1() { const char clang[] = "`-FunctionDecl 0x4280820 line:4:6 foo 'void ()'\n" " `-CompoundStmt 0x42810f0 \n" " `-CXXForRangeStmt 0x4281090 \n" @@ -380,6 +381,43 @@ private: parse(clang)); } + void cxxForRangeStmt2() { + // clang 9 + const char clang[] = "`-FunctionDecl 0xc15d98 col:6 foo 'void ()'\n" + " `-CompoundStmt 0xc16668 \n" + " `-CXXForRangeStmt 0xc165f8 \n" + " |-<<>>\n" + " |-DeclStmt 0xc161c0 \n" + " | `-VarDecl 0xc15f48 col:25 implicit referenced __range1 'int const (&)[4]' cinit\n" + " | `-DeclRefExpr 0xc15e38 'const int [4]' lvalue Var 0xc15ac0 'values' 'const int [4]'\n" + " |-DeclStmt 0xc16498 \n" + " | `-VarDecl 0xc16228 col:24 implicit used __begin1 'const int *':'const int *' cinit\n" + " | `-ImplicitCastExpr 0xc163b0 'const int *' \n" + " | `-DeclRefExpr 0xc161d8 'int const[4]' lvalue Var 0xc15f48 '__range1' 'int const (&)[4]' non_odr_use_constant\n" + " |-DeclStmt 0xc164b0 \n" + " | `-VarDecl 0xc162a0 col:24 implicit used __end1 'const int *':'const int *' cinit\n" + " | `-BinaryOperator 0xc16400 'const int *' '+'\n" + " | |-ImplicitCastExpr 0xc163e8 'const int *' \n" + " | | `-DeclRefExpr 0xc161f8 'int const[4]' lvalue Var 0xc15f48 '__range1' 'int const (&)[4]' non_odr_use_constant\n" + " | `-IntegerLiteral 0xc163c8 'long' 4\n" + " |-BinaryOperator 0xc16538 'bool' '!='\n" + " | |-ImplicitCastExpr 0xc16508 'const int *':'const int *' \n" + " | | `-DeclRefExpr 0xc164c8 'const int *':'const int *' lvalue Var 0xc16228 '__begin1' 'const int *':'const int *'\n" + " | `-ImplicitCastExpr 0xc16520 'const int *':'const int *' \n" + " | `-DeclRefExpr 0xc164e8 'const int *':'const int *' lvalue Var 0xc162a0 '__end1' 'const int *':'const int *'\n" + " |-UnaryOperator 0xc16578 'const int *':'const int *' lvalue prefix '++'\n" + " | `-DeclRefExpr 0xc16558 'const int *':'const int *' lvalue Var 0xc16228 '__begin1' 'const int *':'const int *'\n" + " |-DeclStmt 0xc15ed8 \n" + " | `-VarDecl 0xc15e70 col:23 v 'int' cinit\n" + " | `-ImplicitCastExpr 0xc165e0 'int' \n" + " | `-UnaryOperator 0xc165c8 'const int' lvalue prefix '*' cannot overflow\n" + " | `-ImplicitCastExpr 0xc165b0 'const int *':'const int *' \n" + " | `-DeclRefExpr 0xc16590 'const int *':'const int *' lvalue Var 0xc16228 '__begin1' 'const int *':'const int *'\n" + " `-CompoundStmt 0xc16658 "; + ASSERT_EQUALS("void foo ( ) { for ( int v@1 : values ) { } }", + parse(clang)); + } + void cxxMemberCall() { const char clang[] = "`-FunctionDecl 0x320dc80 col:6 bar 'void ()'\n" " `-CompoundStmt 0x323bb08 \n"