Fix #11453, #11490 internalAstError with templates (#4986)

* Fix #11490 internalAstError with unknown template in index expression

* Comment

* Fix #11490
This commit is contained in:
chrchr-github 2023-04-19 21:20:57 +02:00 committed by GitHub
parent 938ad990f5
commit bf3be95046
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 34 additions and 13 deletions

View File

@ -5178,22 +5178,10 @@ void Tokenizer::createLinks2()
if (!top2 || top2->str() != "<") {
if (token->str() == ">>")
continue;
if (!Token::Match(token->next(), "%name%|%cop%|%assign%|::|,|(|)|{|}|;|[|:|.|=|...") &&
if (!Token::Match(token->next(), "%name%|%cop%|%assign%|::|,|(|)|{|}|;|[|]|:|.|=|...") &&
!Token::Match(token->next(), "&& %name% ="))
continue;
}
// if > is followed by [ .. "new a<b>[" is expected
// unless this is from varidiac expansion
if (token->strAt(1) == "[" && !Token::simpleMatch(token->tokAt(-1), "... >") &&
!Token::Match(token->tokAt(1), "[ ]")) {
Token *prev = type.top()->previous();
while (prev && Token::Match(prev->previous(), ":: %name%"))
prev = prev->tokAt(-2);
if (prev && prev->str() != "new")
prev = prev->previous();
if (!prev || prev->str() != "new")
continue;
}
if (token->str() == ">>" && top1 && top2) {
type.pop();

View File

@ -3454,6 +3454,39 @@ private:
ASSERT_EQUALS(true, tok1->link() == tok2);
ASSERT_EQUALS(true, tok2->link() == tok1);
}
{
// #11453
const char code[] = "template<typename T>\n"
"std::array<T, 1> a{};\n"
"void f() {\n"
" if (a<int>[0]) {}\n"
"}\n";
errout.str("");
Tokenizer tokenizer(&settings0, this);
std::istringstream istr(code);
ASSERT(tokenizer.tokenize(istr, "test.cpp"));
const Token* tok1 = Token::findsimplematch(tokenizer.tokens(), "< int");
const Token* tok2 = Token::findsimplematch(tok1, "> [");
ASSERT_EQUALS(true, tok1->link() == tok2);
ASSERT_EQUALS(true, tok2->link() == tok1);
}
{
// #11490
const char code[] = "void g() {\n"
" int b[2] = {};\n"
" if (b[idx<1>]) {}\n"
"}\n";
errout.str("");
Tokenizer tokenizer(&settings0, this);
std::istringstream istr(code);
ASSERT(tokenizer.tokenize(istr, "test.cpp"));
const Token* tok1 = Token::findsimplematch(tokenizer.tokens(), "< 1");
const Token* tok2 = Token::findsimplematch(tok1, "> ]");
ASSERT_EQUALS(true, tok1->link() == tok2);
ASSERT_EQUALS(true, tok2->link() == tok1);
}
}
void simplifyString() {