Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions lib/symboldatabase.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -123,18 +123,18 @@ static bool isExecutableScope(const Token* tok)
return false;
}

static bool isEnumDefinition(const Token* tok)
const Token* SymbolDatabase::isEnumDefinition(const Token* tok)
{
if (!Token::Match(tok, "enum class| %name% {|:"))
return false;
if (!Token::Match(tok, "enum class| %name%| {|:"))
return nullptr;
while (!Token::Match(tok, "[{:]"))
tok = tok->next();
if (tok->str() == "{")
return true;
return tok;
tok = tok->next(); // skip ':'
while (Token::Match(tok, "%name%|::"))
tok = tok->next();
return Token::simpleMatch(tok, "{");
return Token::simpleMatch(tok, "{") ? tok : nullptr;
}

void SymbolDatabase::createSymbolDatabaseFindAllScopes()
Expand Down
3 changes: 3 additions & 0 deletions lib/symboldatabase.h
Original file line number Diff line number Diff line change
Expand Up @@ -1409,6 +1409,9 @@ class CPPCHECKLIB SymbolDatabase {
void clangSetVariables(const std::vector<const Variable *> &variableList);
void createSymbolDatabaseExprIds();

/* returns the opening { if tok points to enum */
static const Token* isEnumDefinition(const Token* tok);

private:
friend class Scope;
friend class Function;
Expand Down
12 changes: 10 additions & 2 deletions lib/tokenize.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -8608,8 +8608,16 @@ void Tokenizer::findGarbageCode() const
syntaxError(tok2, "Unexpected token '" + (tok2 ? tok2->str() : "") + "'");
}
}
if (Token::Match(tok, "enum : %num%| {"))
syntaxError(tok->tokAt(2), "Unexpected token '" + tok->strAt(2) + "'");
if (tok->str() == "enum") {
if (Token::Match(tok->next(), ": %num%| {"))
syntaxError(tok->tokAt(2), "Unexpected token '" + tok->strAt(2) + "'");
if (const Token* start = SymbolDatabase::isEnumDefinition(tok)) {
for (const Token* tok2 = start->next(); tok2 && tok2 != start->link(); tok2 = tok2->next()) {
if (tok2->str() == ";")
syntaxError(tok2);
}
}
}
}

// Keywords in global scope
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
enum{C={;}=e};
4 changes: 2 additions & 2 deletions test/testsimplifytemplate.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3585,7 +3585,7 @@ class TestSimplifyTemplate : public TestFixture {
"using A2 = struct B2 { void f(T){} };\n"
"A2<bool> a2;\n"
"template<class T>\n"
"using A3 = enum B3 {b = 0;};\n"
"using A3 = enum B3 {b = 0};\n"
"A3<int> a3;";
const char exp[] = "template < int N > "
"using A1 = struct B1 { static auto constexpr value = N ; } ; "
Expand All @@ -3594,7 +3594,7 @@ class TestSimplifyTemplate : public TestFixture {
"using A2 = struct B2 { void f ( T ) { } } ; "
"A2 < bool > a2 ; "
"template < class T > "
"using A3 = enum B3 { b = 0 ; } ; "
"using A3 = enum B3 { b = 0 } ; "
"A3 < int > a3 ;";
ASSERT_EQUALS(exp, tok(code));
}
Expand Down
4 changes: 2 additions & 2 deletions test/testsimplifytypedef.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3353,8 +3353,8 @@ class TestSimplifyTypedef : public TestFixture {
" struct S { enum E { E0 }; };\n"
"}\n"
"typedef N::S T;\n"
"enum class E { a = T::E0; };\n";
ASSERT_EQUALS("namespace N { struct S { enum E { E0 } ; } ; } enum class E { a = N :: S :: E0 ; } ;", tok(code));
"enum class E { a = T::E0 };\n";
ASSERT_EQUALS("namespace N { struct S { enum E { E0 } ; } ; } enum class E { a = N :: S :: E0 } ;", tok(code));
}
{ // #11494
const char code[] = "typedef struct S {} KEY;\n"
Expand Down
1 change: 1 addition & 0 deletions test/testtokenize.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7132,6 +7132,7 @@ class TestTokenizer : public TestFixture {

ASSERT_THROW_INTERNAL_EQUALS(tokenizeAndStringify("enum : { };"), SYNTAX, "syntax error: Unexpected token '{'");
ASSERT_THROW_INTERNAL_EQUALS(tokenizeAndStringify("enum : 3 { };"), SYNTAX, "syntax error: Unexpected token '3'");
ASSERT_NO_THROW(tokenizeAndStringify("enum { E = int{} };"));

ASSERT_THROW_INTERNAL_EQUALS(tokenizeAndStringify("int a() { b((c)return 0) }"), SYNTAX, "syntax error");
ASSERT_THROW_EQUALS(tokenizeAndStringify("int f() { MACRO(x) return 0; }"),
Expand Down
22 changes: 11 additions & 11 deletions test/testvarid.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3838,63 +3838,63 @@ class TestVarID : public TestFixture {
void varidenum1() {
const char code[] = "const int eStart = 6;\n"
"enum myEnum {\n"
" A = eStart;\n"
" A = eStart\n"
"};\n";
const char expected[] = "1: const int eStart@1 = 6 ;\n"
"2: enum myEnum {\n"
"3: A = eStart@1 ;\n"
"3: A = eStart@1\n"
"4: } ;\n";
ASSERT_EQUALS(expected, tokenize(code));
}

void varidenum2() {
const char code[] = "const int eStart = 6;\n"
"enum myEnum {\n"
" A = f(eStart);\n"
" A = f(eStart)\n"
"};\n";
const char expected[] = "1: const int eStart@1 = 6 ;\n"
"2: enum myEnum {\n"
"3: A = f ( eStart@1 ) ;\n"
"3: A = f ( eStart@1 )\n"
"4: } ;\n";
ASSERT_EQUALS(expected, tokenize(code));
}

void varidenum3() {
const char code[] = "const int eStart = 6;\n"
"enum myEnum {\n"
" A = f(eStart, x);\n"
" A = f(eStart, x)\n"
"};\n";
const char expected[] = "1: const int eStart@1 = 6 ;\n"
"2: enum myEnum {\n"
"3: A = f ( eStart@1 , x ) ;\n"
"3: A = f ( eStart@1 , x )\n"
"4: } ;\n";
ASSERT_EQUALS(expected, tokenize(code));
}

void varidenum4() {
const char code[] = "const int eStart = 6;\n"
"enum myEnum {\n"
" A = f(x, eStart);\n"
" A = f(x, eStart)\n"
"};\n";
const char expected[] = "1: const int eStart@1 = 6 ;\n"
"2: enum myEnum {\n"
"3: A = f ( x , eStart@1 ) ;\n"
"3: A = f ( x , eStart@1 )\n"
"4: } ;\n";
ASSERT_EQUALS(expected, tokenize(code));
}

void varidenum5() {
const char code[] = "const int eStart = 6;\n"
"enum myEnum {\n"
" A = f(x, eStart, y);\n"
" A = f(x, eStart, y)\n"
"};\n";
const char expected[] = "1: const int eStart@1 = 6 ;\n"
"2: enum myEnum {\n"
"3: A = f ( x , eStart@1 , y ) ;\n"
"3: A = f ( x , eStart@1 , y )\n"
"4: } ;\n";
const char current[] = "1: const int eStart@1 = 6 ;\n"
"2: enum myEnum {\n"
"3: A = f ( x , eStart , y ) ;\n"
"3: A = f ( x , eStart , y )\n"
"4: } ;\n";
TODO_ASSERT_EQUALS(expected, current, tokenize(code));
}
Expand Down