Commit 61132f26 authored by Erik Verbruggen's avatar Erik Verbruggen
Browse files

Fixed Q_ENUMS/Q_FLAGS parsing of enum names.

parent fd81a276
...@@ -805,15 +805,13 @@ bool CheckDeclaration::visit(ObjCPropertyDeclarationAST *ast) ...@@ -805,15 +805,13 @@ bool CheckDeclaration::visit(ObjCPropertyDeclarationAST *ast)
bool CheckDeclaration::visit(QtEnumDeclarationAST *ast) bool CheckDeclaration::visit(QtEnumDeclarationAST *ast)
{ {
for (NameListAST *iter = ast->enumerator_list; iter; iter = iter->next) checkQEnumsQFlagsNames(ast->enumerator_list, "Q_ENUMS");
semantic()->check(iter->value, _scope);
return false; return false;
} }
bool CheckDeclaration::visit(QtFlagsDeclarationAST *ast) bool CheckDeclaration::visit(QtFlagsDeclarationAST *ast)
{ {
for (NameListAST *iter = ast->flag_enums_list; iter; iter = iter->next) checkQEnumsQFlagsNames(ast->flag_enums_list, "Q_FLAGS");
semantic()->check(iter->value, _scope);
return false; return false;
} }
...@@ -830,3 +828,38 @@ bool CheckDeclaration::visit(QtPropertyDeclarationAST *ast) ...@@ -830,3 +828,38 @@ bool CheckDeclaration::visit(QtPropertyDeclarationAST *ast)
} }
return false; return false;
} }
void CheckDeclaration::checkQEnumsQFlagsNames(NameListAST *nameListAst,
const char *declName)
{
for (NameListAST *iter = nameListAst; iter; iter = iter->next) {
if (!iter)
continue;
const Name *name = semantic()->check(iter->value, _scope);
if (!name)
continue;
if (name->isNameId())
continue;
const QualifiedNameId *qName = name->asQualifiedNameId();
if (!qName)
translationUnit()->error(iter->firstToken(), "invalid name in %s",
declName);
else if (qName->isGlobal())
translationUnit()->error(iter->firstToken(),
"invalid name '%s' in %s",
qName->identifier()->chars(), declName);
else {
for (unsigned i = 0; i < qName->nameCount(); ++i) {
const Name *namePart = qName->nameAt(i);
if (!namePart || !namePart->isNameId()) {
translationUnit()->error(iter->firstToken(),
"invalid name '%s' in %s",
qName->identifier()->chars(), declName);
}
}
}
}
}
...@@ -107,6 +107,9 @@ private: ...@@ -107,6 +107,9 @@ private:
bool checkPropertyAttribute(ObjCPropertyAttributeAST *attrAst, bool checkPropertyAttribute(ObjCPropertyAttributeAST *attrAst,
int &flags, int &flags,
int attr); int attr);
void checkQEnumsQFlagsNames(NameListAST *nameListAst,
const char *declName);
private: private:
DeclarationAST *_declaration; DeclarationAST *_declaration;
Scope *_scope; Scope *_scope;
......
...@@ -1899,7 +1899,7 @@ bool Parser::parseQtEnumDeclaration(DeclarationAST *&node) ...@@ -1899,7 +1899,7 @@ bool Parser::parseQtEnumDeclaration(DeclarationAST *&node)
match(T_LPAREN, &ast->lparen_token); match(T_LPAREN, &ast->lparen_token);
for (NameListAST **iter = &ast->enumerator_list; LA() && LA() != T_RPAREN; iter = &(*iter)->next) { for (NameListAST **iter = &ast->enumerator_list; LA() && LA() != T_RPAREN; iter = &(*iter)->next) {
NameAST *name_ast = 0; NameAST *name_ast = 0;
if (!parseEnumName(name_ast)) if (!parseName(name_ast))
break; break;
*iter = new (_pool) NameListAST; *iter = new (_pool) NameListAST;
(*iter)->value = name_ast; (*iter)->value = name_ast;
...@@ -1909,37 +1909,6 @@ bool Parser::parseQtEnumDeclaration(DeclarationAST *&node) ...@@ -1909,37 +1909,6 @@ bool Parser::parseQtEnumDeclaration(DeclarationAST *&node)
return true; return true;
} }
bool Parser::parseEnumName(NameAST *&node)
{
DEBUG_THIS_RULE();
unsigned global_scope_token = 0;
if (LA() == T_COLON_COLON)
global_scope_token = consumeToken();
NestedNameSpecifierListAST *nested_name_specifier = 0;
parseNestedNameSpecifierOpt(nested_name_specifier,
/*acceptTemplateId=*/ true);
unsigned identifier_token = 0;
match(T_IDENTIFIER, &identifier_token);
if (global_scope_token == 0 && nested_name_specifier == 0
&& identifier_token == 0)
return false;
SimpleNameAST *name_ast = new (_pool) SimpleNameAST;
name_ast->identifier_token = identifier_token;
if (nested_name_specifier || global_scope_token) {
QualifiedNameAST *q_name_ast = new (_pool) QualifiedNameAST;
q_name_ast->nested_name_specifier_list = nested_name_specifier;
q_name_ast->unqualified_name = name_ast;
q_name_ast->global_scope_token = global_scope_token;
} else {
node = name_ast;
}
return true;
}
// q-flags-decl ::= 'Q_FLAGS' '(' q-flags-list? ')' // q-flags-decl ::= 'Q_FLAGS' '(' q-flags-list? ')'
// q-flags-list ::= identifier // q-flags-list ::= identifier
// q-flags-list ::= q-flags-list identifier // q-flags-list ::= q-flags-list identifier
...@@ -1963,7 +1932,7 @@ bool Parser::parseQtFlags(DeclarationAST *&node) ...@@ -1963,7 +1932,7 @@ bool Parser::parseQtFlags(DeclarationAST *&node)
match(T_LPAREN, &ast->lparen_token); match(T_LPAREN, &ast->lparen_token);
for (NameListAST **iter = &ast->flag_enums_list; LA() && LA() != T_RPAREN; iter = &(*iter)->next) { for (NameListAST **iter = &ast->flag_enums_list; LA() && LA() != T_RPAREN; iter = &(*iter)->next) {
NameAST *name_ast = 0; NameAST *name_ast = 0;
if (!parseEnumName(name_ast)) if (!parseName(name_ast))
break; break;
*iter = new (_pool) NameListAST; *iter = new (_pool) NameListAST;
(*iter)->value = name_ast; (*iter)->value = name_ast;
......
...@@ -80,7 +80,6 @@ public: ...@@ -80,7 +80,6 @@ public:
bool parseAccessDeclaration(DeclarationAST *&node); bool parseAccessDeclaration(DeclarationAST *&node);
bool parseQtPropertyDeclaration(DeclarationAST *&node); bool parseQtPropertyDeclaration(DeclarationAST *&node);
bool parseQtEnumDeclaration(DeclarationAST *&node); bool parseQtEnumDeclaration(DeclarationAST *&node);
bool parseEnumName(NameAST *&node);
bool parseQtFlags(DeclarationAST *&node); bool parseQtFlags(DeclarationAST *&node);
bool parseAdditiveExpression(ExpressionAST *&node); bool parseAdditiveExpression(ExpressionAST *&node);
bool parseAndExpression(ExpressionAST *&node); bool parseAndExpression(ExpressionAST *&node);
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment