diff options
author | Leandro Melo <leandro.melo@nokia.com> | 2012-06-08 11:52:45 +0200 |
---|---|---|
committer | Leandro Melo <leandro.melo@nokia.com> | 2012-06-11 09:14:59 +0200 |
commit | a66e344b424643fce71c127fdfb0a21103ca0171 (patch) | |
tree | 389c8a40f822a552d5fdc99aaf1d44a07acbf858 | |
parent | ec5c280e21ea159287621ab564a14c74582588a5 (diff) | |
download | qt-creator-a66e344b424643fce71c127fdfb0a21103ca0171.tar.gz |
C++: Fix crash on invalid class name
Task-number: QTCREATORBUG-7462
Change-Id: Ic1df4b535c5a617efa707110138c76e6e7ef1e4b
Reviewed-by: Robert Löhning <robert.loehning@nokia.com>
Reviewed-by: Leandro Melo <leandro.melo@nokia.com>
-rw-r--r-- | src/libs/3rdparty/cplusplus/Bind.cpp | 35 | ||||
-rw-r--r-- | src/libs/3rdparty/cplusplus/Bind.h | 2 |
2 files changed, 23 insertions, 14 deletions
diff --git a/src/libs/3rdparty/cplusplus/Bind.cpp b/src/libs/3rdparty/cplusplus/Bind.cpp index 0d006911e4..6df1951b66 100644 --- a/src/libs/3rdparty/cplusplus/Bind.cpp +++ b/src/libs/3rdparty/cplusplus/Bind.cpp @@ -1851,6 +1851,8 @@ bool Bind::visit(SimpleDeclarationAST *ast) name = elabTypeSpec->name->name; } + ensureValidClassName(&name, sourceLocation); + ForwardClassDeclaration *decl = control()->newForwardClassDeclaration(sourceLocation, name); setDeclSpecifiers(decl, type); _scope->addMember(decl); @@ -2882,20 +2884,7 @@ bool Bind::visit(ClassSpecifierAST *ast) } } - // get the unqualified class name - const QualifiedNameId *q = className->asQualifiedNameId(); - const Name *unqualifiedClassName = q ? q->name() : className; - - if (! unqualifiedClassName) // paranoia check - className = 0; - else if (! (unqualifiedClassName->isNameId() || unqualifiedClassName->isTemplateNameId())) { - translationUnit()->error(sourceLocation, "expected a class-name"); - - className = unqualifiedClassName->identifier(); - - if (q && className) - className = control()->qualifiedNameId(q->base(), className); - } + ensureValidClassName(&className, sourceLocation); } Class *klass = control()->newClass(sourceLocation, className); @@ -3124,6 +3113,24 @@ bool Bind::visit(ArrayDeclaratorAST *ast) return false; } +void Bind::ensureValidClassName(const Name **name, unsigned sourceLocation) +{ + if (!*name) + return; + + const QualifiedNameId *qName = (*name)->asQualifiedNameId(); + if (qName) + *name = qName->name(); + + if (!(*name)->isNameId() && !(*name)->isTemplateNameId()) { + translationUnit()->error(sourceLocation, "expected a class-name"); + + *name = (*name)->identifier(); + if (qName) + *name = control()->qualifiedNameId(qName->base(), *name); + } +} + int Bind::visibilityForAccessSpecifier(int tokenKind) { switch (tokenKind) { diff --git a/src/libs/3rdparty/cplusplus/Bind.h b/src/libs/3rdparty/cplusplus/Bind.h index d1fff79ea5..de0cf12557 100644 --- a/src/libs/3rdparty/cplusplus/Bind.h +++ b/src/libs/3rdparty/cplusplus/Bind.h @@ -274,6 +274,8 @@ protected: private: static const int kMaxDepth; + void ensureValidClassName(const Name **name, unsigned sourceLocation); + Scope *_scope; ExpressionTy _expression; const Name *_name; |