summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorNikolai Kosjar <nikolai.kosjar@qt.io>2019-10-07 14:31:32 +0200
committerNikolai Kosjar <nikolai.kosjar@qt.io>2019-10-08 09:20:10 +0000
commit54fefd89b86f9b7c3496317bcfcf3882ff72e67c (patch)
tree284667f5855e901148f5e7f70aae87a4c28db275 /src
parentc2aaa9340881f8220c5683d253a147c2cd77ff6e (diff)
downloadqt-creator-54fefd89b86f9b7c3496317bcfcf3882ff72e67c.tar.gz
C++: Transfer noexcept specifier for refactoring actions
This applies for e.g. * "Add Definition..." (on function decl) * "Move Definition..." (on function decl) * "Insert Virtual Functions of Base Class" (on class specifier) Fixes: QTCREATORBUG-11849 Fixes: QTCREATORBUG-19699 Change-Id: I0d259bc1782470f3b3f19617230005a5594a5cca Reviewed-by: Cristian Adam <cristian.adam@qt.io> Reviewed-by: Orgad Shaneh <orgads@gmail.com>
Diffstat (limited to 'src')
-rw-r--r--src/libs/3rdparty/cplusplus/Bind.cpp6
-rw-r--r--src/libs/3rdparty/cplusplus/Bind.h2
-rw-r--r--src/libs/3rdparty/cplusplus/Symbols.cpp6
-rw-r--r--src/libs/3rdparty/cplusplus/Symbols.h6
-rw-r--r--src/libs/cplusplus/CppRewriter.cpp1
-rw-r--r--src/libs/cplusplus/TypePrettyPrinter.cpp6
-rw-r--r--src/plugins/cppeditor/cppeditorplugin.h1
-rw-r--r--src/plugins/cppeditor/cppquickfix_test.cpp23
8 files changed, 49 insertions, 2 deletions
diff --git a/src/libs/3rdparty/cplusplus/Bind.cpp b/src/libs/3rdparty/cplusplus/Bind.cpp
index 053d4f1388..486efffc3d 100644
--- a/src/libs/3rdparty/cplusplus/Bind.cpp
+++ b/src/libs/3rdparty/cplusplus/Bind.cpp
@@ -1232,7 +1232,7 @@ FullySpecifiedType Bind::trailingReturnType(TrailingReturnTypeAST *ast, const Fu
return type;
}
-const StringLiteral *Bind::asStringLiteral(const ExpressionAST *ast)
+const StringLiteral *Bind::asStringLiteral(const AST *ast)
{
CPP_ASSERT(ast, return nullptr);
const int firstToken = ast->firstToken();
@@ -3265,7 +3265,11 @@ bool Bind::visit(FunctionDeclaratorAST *ast)
Function::RvalueRefQualifier);
}
+ // propagate exception spec
this->exceptionSpecification(ast->exception_specification, type);
+ if (ExceptionSpecificationAST *spec = ast->exception_specification)
+ fun->setExceptionSpecification(asStringLiteral(spec));
+
if (ast->as_cpp_initializer != nullptr) {
fun->setAmbiguous(true);
/*ExpressionTy as_cpp_initializer =*/ this->expression(ast->as_cpp_initializer);
diff --git a/src/libs/3rdparty/cplusplus/Bind.h b/src/libs/3rdparty/cplusplus/Bind.h
index 0898722964..ddeb46532e 100644
--- a/src/libs/3rdparty/cplusplus/Bind.h
+++ b/src/libs/3rdparty/cplusplus/Bind.h
@@ -104,7 +104,7 @@ protected:
void capture(CaptureAST *ast);
Function *lambdaDeclarator(LambdaDeclaratorAST *ast);
FullySpecifiedType trailingReturnType(TrailingReturnTypeAST *ast, const FullySpecifiedType &init);
- const StringLiteral *asStringLiteral(const ExpressionAST *ast);
+ const StringLiteral *asStringLiteral(const AST *ast);
virtual bool preVisit(AST *);
virtual void postVisit(AST *);
diff --git a/src/libs/3rdparty/cplusplus/Symbols.cpp b/src/libs/3rdparty/cplusplus/Symbols.cpp
index a895f7ed6c..aba1be3494 100644
--- a/src/libs/3rdparty/cplusplus/Symbols.cpp
+++ b/src/libs/3rdparty/cplusplus/Symbols.cpp
@@ -303,6 +303,7 @@ Function::Function(TranslationUnit *translationUnit, int sourceLocation, const N
Function::Function(Clone *clone, Subst *subst, Function *original)
: Scope(clone, subst, original)
, _returnType(clone->type(original->_returnType, subst))
+ , _exceptionSpecification(original->_exceptionSpecification)
, _flags(original->_flags)
{ }
@@ -534,6 +535,11 @@ bool Function::maybeValidPrototype(int actualArgumentCount) const
return true;
}
+const StringLiteral *Function::exceptionSpecification()
+{ return _exceptionSpecification; }
+
+void Function::setExceptionSpecification(const StringLiteral *spec)
+{ _exceptionSpecification = spec; }
Block::Block(TranslationUnit *translationUnit, int sourceLocation)
: Scope(translationUnit, sourceLocation, /*name = */ nullptr)
diff --git a/src/libs/3rdparty/cplusplus/Symbols.h b/src/libs/3rdparty/cplusplus/Symbols.h
index fd9417984e..71a076ac80 100644
--- a/src/libs/3rdparty/cplusplus/Symbols.h
+++ b/src/libs/3rdparty/cplusplus/Symbols.h
@@ -29,6 +29,8 @@
namespace CPlusPlus {
+class StringLiteral;
+
class CPLUSPLUS_EXPORT UsingNamespaceDirective: public Symbol
{
public:
@@ -363,6 +365,9 @@ public:
bool maybeValidPrototype(int actualArgumentCount) const;
+ const StringLiteral *exceptionSpecification();
+ void setExceptionSpecification(const StringLiteral *spec);
+
// Symbol's interface
virtual FullySpecifiedType type() const;
@@ -386,6 +391,7 @@ protected:
private:
FullySpecifiedType _returnType;
+ const StringLiteral *_exceptionSpecification = nullptr;
struct Flags {
unsigned _isVirtual: 1;
unsigned _isOverride: 1;
diff --git a/src/libs/cplusplus/CppRewriter.cpp b/src/libs/cplusplus/CppRewriter.cpp
index fdb5de3851..c52963b023 100644
--- a/src/libs/cplusplus/CppRewriter.cpp
+++ b/src/libs/cplusplus/CppRewriter.cpp
@@ -136,6 +136,7 @@ public:
funTy->setConst(type->isConst());
funTy->setVolatile(type->isVolatile());
funTy->setRefQualifier(type->refQualifier());
+ funTy->setExceptionSpecification(type->exceptionSpecification());
funTy->setName(rewrite->rewriteName(type->name()));
diff --git a/src/libs/cplusplus/TypePrettyPrinter.cpp b/src/libs/cplusplus/TypePrettyPrinter.cpp
index c46117dde7..2ad59c55c8 100644
--- a/src/libs/cplusplus/TypePrettyPrinter.cpp
+++ b/src/libs/cplusplus/TypePrettyPrinter.cpp
@@ -487,6 +487,12 @@ void TypePrettyPrinter::visit(Function *type)
? QLatin1String("&")
: QLatin1String("&&");
}
+
+ // add exception specifier
+ if (const StringLiteral *spec = type->exceptionSpecification()) {
+ appendSpace();
+ _text += QLatin1String(spec->chars());
+ }
}
}
diff --git a/src/plugins/cppeditor/cppeditorplugin.h b/src/plugins/cppeditor/cppeditorplugin.h
index 40b251fbef..04b6aeb040 100644
--- a/src/plugins/cppeditor/cppeditorplugin.h
+++ b/src/plugins/cppeditor/cppeditorplugin.h
@@ -126,6 +126,7 @@ private slots:
void test_quickfix_InsertDefFromDecl_ignoreSurroundingGeneratedDeclarations();
void test_quickfix_InsertDefFromDecl_respectWsInOperatorNames1();
void test_quickfix_InsertDefFromDecl_respectWsInOperatorNames2();
+ void test_quickfix_InsertDefFromDecl_noexcept_specifier();
void test_quickfix_InsertDefFromDecl_macroUsesAtEndOfFile1();
void test_quickfix_InsertDefFromDecl_macroUsesAtEndOfFile2();
void test_quickfix_InsertDefFromDecl_erroneousStatementAtEndOfFile();
diff --git a/src/plugins/cppeditor/cppquickfix_test.cpp b/src/plugins/cppeditor/cppquickfix_test.cpp
index 4c7be6a228..63f1290b6a 100644
--- a/src/plugins/cppeditor/cppquickfix_test.cpp
+++ b/src/plugins/cppeditor/cppquickfix_test.cpp
@@ -2502,6 +2502,29 @@ void CppEditorPlugin::test_quickfix_InsertDefFromDecl_respectWsInOperatorNames2(
QuickFixOperationTest(singleDocument(original, expected), &factory);
}
+/// Check that the noexcept exception specifier is transferred
+void CppEditorPlugin::test_quickfix_InsertDefFromDecl_noexcept_specifier()
+{
+ QByteArray original =
+ "class Foo\n"
+ "{\n"
+ " void @foo() noexcept(false);\n"
+ "};\n";
+ QByteArray expected =
+ "class Foo\n"
+ "{\n"
+ " void foo() noexcept(false);\n"
+ "};\n"
+ "\n"
+ "void Foo::foo() noexcept(false)\n"
+ "{\n"
+ "\n"
+ "}\n";
+
+ InsertDefFromDecl factory;
+ QuickFixOperationTest(singleDocument(original, expected), &factory);
+}
+
/// Check if a function like macro use is not separated by the function to insert
/// Case: Macro preceded by preproceesor directives and declaration.
void CppEditorPlugin::test_quickfix_InsertDefFromDecl_macroUsesAtEndOfFile1()