diff --git a/lib/tokenize.cpp b/lib/tokenize.cpp index 21c3dfe2a..b50b9c466 100644 --- a/lib/tokenize.cpp +++ b/lib/tokenize.cpp @@ -449,7 +449,8 @@ void Tokenizer::simplifyTypedef() Token *typeEnd = 0; Token *argStart = 0; Token *argEnd = 0; - Token *num = 0; + Token *arrayStart = 0; + Token *arrayEnd = 0; Token *typeDef = tok; int offset = 1; bool functionPtr = false; @@ -550,10 +551,27 @@ void Tokenizer::simplifyTypedef() { typeName = tok->strAt(offset++); - if (tok->tokAt(offset) && Token::Match(tok->tokAt(offset), "[ %num% ]")) + if (tok->tokAt(offset) && tok->tokAt(offset)->str() == "[") { - num = tok->tokAt(offset + 1); - offset += 3; + arrayStart = tok->tokAt(offset); + + bool atEnd = false; + while (!atEnd) + { + while (tok->tokAt(offset + 1) && !Token::Match(tok->tokAt(offset + 1), ";|,")) + offset++; + + if (!tok->tokAt(offset + 1)) + return; // invalid input + else if (tok->tokAt(offset + 1)->str() == ";") + atEnd = true; + else if (tok->tokAt(offset)->str() == "]") + atEnd = true; + else + offset++; + } + + arrayEnd = tok->tokAt(offset++); } if (tok->tokAt(offset) && Token::Match(tok->tokAt(offset), ";|,")) @@ -751,17 +769,30 @@ void Tokenizer::simplifyTypedef() Token::createMutualLinks(tok2, tok3); } - if (num) + if (arrayStart && arrayEnd) { tok2 = tok2->next(); - tok2->insertToken("["); + Token * nextToken; + std::stack links; + for (nextToken = arrayStart; nextToken != arrayEnd->next(); nextToken = nextToken->next()) + { + tok2->insertToken(nextToken->strAt(0)); + tok2 = tok2->next(); + + // Check for links and fix them up + if (tok2->str() == "(" || tok2->str() == "[") + links.push(tok2); + if (tok2->str() == ")" || tok2->str() == "]") + { + Token * link = links.top(); + + tok2->link(link); + link->link(tok2); + + links.pop(); + } + } tok2 = tok2->next(); - Token *tok3 = tok2; - tok2->insertToken(num->strAt(0)); - tok2 = tok2->next(); - tok2->insertToken("]"); - tok2 = tok2->next(); - Token::createMutualLinks(tok2, tok3); } simplifyType = false; @@ -772,7 +803,8 @@ void Tokenizer::simplifyTypedef() done = true; else if (tok->str() == ",") { - num = 0; + arrayStart = 0; + arrayEnd = 0; offset = 1; while (tok->tokAt(offset) && Token::Match(tok->tokAt(offset), "*|&")) @@ -782,10 +814,23 @@ void Tokenizer::simplifyTypedef() { typeName = tok->strAt(offset++); - if (tok->tokAt(offset) && Token::Match(tok->tokAt(offset), "[ %num% ]")) + if (tok->tokAt(offset) && tok->tokAt(offset)->str() == "[") { - num = tok->tokAt(offset + 1); - offset += 3; + bool atEnd = false; + while (!atEnd) + { + while (tok->tokAt(offset + 1) && !Token::Match(tok->tokAt(offset + 1), ";|,")) + offset++; + + if (!tok->tokAt(offset + 1)) + return; // invalid input + else if (tok->tokAt(offset + 1)->str() == ";") + atEnd = true; + else if (tok->tokAt(offset)->str() == "]") + atEnd = true; + else + offset++; + } } if (tok->tokAt(offset) && Token::Match(tok->tokAt(offset), ";|,")) diff --git a/test/testsimplifytokens.cpp b/test/testsimplifytokens.cpp index a34d3d794..5a4029a31 100644 --- a/test/testsimplifytokens.cpp +++ b/test/testsimplifytokens.cpp @@ -165,6 +165,7 @@ private: TEST_CASE(simplifyTypedef26); TEST_CASE(simplifyTypedef27); TEST_CASE(simplifyTypedef28); + TEST_CASE(simplifyTypedef29); TEST_CASE(reverseArraySyntax) TEST_CASE(simplify_numeric_condition) @@ -2970,6 +2971,26 @@ private: ASSERT_EQUALS(expected, tok(code, false)); } + void simplifyTypedef29() + { + const char code[] = "typedef int array [ice_or::value, is_int::value>::value ? 1 : -1];\n" + "typedef int array1 [N];\n" + "typedef int array2 [N][M];\n" + "array a;\n" + "array1 a1;\n" + "array2 a2;"; + + const char expected[] = + "; " + "; " + "; " + "int a [ ice_or < is_int < int > :: value , is_int < UDT > :: value > :: value ? 1 : - 1 ] ; " + "int a1 [ N ] ; " + "int a2 [ N ] [ M ] ;"; + + ASSERT_EQUALS(expected, tok(code, false)); + } + void reverseArraySyntax() { ASSERT_EQUALS("a [ 13 ]", tok("13[a]"));