Moc: parse trailing return type

Pick-to: 5.15 6.1
Fixes: QTBUG-71123
Change-Id: I1c3749f0892fddcc433c9afcb1d6d7c30c97c9d9
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
This commit is contained in:
Mårten Nordheim 2020-04-23 15:32:32 +02:00
parent e3e070e87b
commit 12b8283f89
5 changed files with 201 additions and 9 deletions

View File

@ -198,6 +198,7 @@ Type Moc::parseType()
case DOUBLE:
case VOID:
case BOOL:
case AUTO:
type.name += lexem();
isVoid |= (lookup(0) == VOID);
break;
@ -467,15 +468,6 @@ bool Moc::parseFunction(FunctionDef *def, bool inMacro)
scopedFunctionName = tempType.isScoped;
}
// we don't support references as return types, it's too dangerous
if (def->type.referenceType == Type::Reference) {
QByteArray rawName = def->type.rawName;
def->type = Type("void");
def->type.rawName = rawName;
}
def->normalizedType = normalizeType(def->type.name);
if (!test(RPAREN)) {
parseFunctionArguments(def);
next(RPAREN);
@ -498,6 +490,10 @@ bool Moc::parseFunction(FunctionDef *def, bool inMacro)
next(LPAREN);
until(RPAREN);
}
if (def->type.name == "auto" && test(ARROW))
def->type = parseType(); // Parse trailing return-type
if (test(SEMIC))
;
else if ((def->inlineCode = test(LBRACE)))
@ -515,6 +511,22 @@ bool Moc::parseFunction(FunctionDef *def, bool inMacro)
warning(msg.constData());
return false;
}
QList<QByteArray> typeNameParts = normalizeType(def->type.name).split(' ');
if (typeNameParts.contains("auto")) {
// We expected a trailing return type but we haven't seen one
error("Function declared with auto as return type but missing trailing return type. "
"Return type deduction is not supported.");
}
// we don't support references as return types, it's too dangerous
if (def->type.referenceType == Type::Reference) {
QByteArray rawName = def->type.rawName;
def->type = Type("void");
def->type.rawName = rawName;
}
def->normalizedType = normalizeType(def->type.name);
return true;
}

View File

@ -13,6 +13,7 @@ set(JSON_HEADERS
cxx11-enums.h
cxx11-explicit-override-control.h
cxx11-final-classes.h
cxx11-trailing-return.h
cxx17-namespaces.h
dir-in-include-path.h
escapes-in-string-literals.h

View File

@ -645,6 +645,79 @@
"inputFile": "cxx11-final-classes.h",
"outputRevision": 68
},
{
"classes": [
{
"className": "CXX11TrailingReturn",
"object": true,
"qualifiedClassName": "CXX11TrailingReturn",
"signals": [
{
"access": "public",
"arguments": [
{
"name": "i",
"type": "int"
}
],
"name": "trailingSignalReturn",
"returnType": "void"
}
],
"slots": [
{
"access": "public",
"name": "fun",
"returnType": "void"
},
{
"access": "public",
"arguments": [
{
"name": "i",
"type": "int"
},
{
"name": "b",
"type": "char"
}
],
"name": "arguments",
"returnType": "int"
},
{
"access": "public",
"arguments": [
{
"name": "i",
"type": "int"
}
],
"name": "inlineFunc",
"returnType": "int"
},
{
"access": "public",
"name": "constRefReturn",
"returnType": "void"
},
{
"access": "public",
"name": "constConstRefReturn",
"returnType": "void"
}
],
"superClasses": [
{
"access": "public",
"name": "QObject"
}
]
}
],
"inputFile": "cxx11-trailing-return.h",
"outputRevision": 68
},
{
"classes": [
{

View File

@ -0,0 +1,68 @@
/****************************************************************************
**
** Copyright (C) 2020 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
** This file is part of the test suite of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:GPL-EXCEPT$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and The Qt Company. For licensing terms
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
** General Public License version 3 as published by the Free Software
** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
** included in the packaging of this file. Please review the following
** information to ensure the GNU General Public License requirements will
** be met: https://www.gnu.org/licenses/gpl-3.0.html.
**
** $QT_END_LICENSE$
**
****************************************************************************/
#ifndef CXX11_TRAILING_RETURN_H
#define CXX11_TRAILING_RETURN_H
#include <QtCore/QObject>
class CXX11TrailingReturn : public QObject
{
Q_OBJECT
public slots:
inline auto fun() -> void;
inline auto arguments(int i, char b) -> int;
inline auto inlineFunc(int i) -> int
{
return i + 1;
}
inline auto constRefReturn() -> const CXX11TrailingReturn &
{
return {};
}
inline auto constConstRefReturn() const -> const CXX11TrailingReturn &
{
return {};
}
signals:
auto trailingSignalReturn(int i) -> void;
};
auto CXX11TrailingReturn::fun() -> void
{
return;
}
auto CXX11TrailingReturn::arguments(int i, char b) -> int
{
return i + int(b);
}
#endif // CXX11_TRAILING_RETURN_H

View File

@ -63,6 +63,7 @@
#include "cxx11-enums.h"
#include "cxx11-final-classes.h"
#include "cxx11-explicit-override-control.h"
#include "cxx11-trailing-return.h"
#include "parse-defines.h"
#include "related-metaobjects-in-namespaces.h"
@ -700,6 +701,7 @@ private slots:
void privateClass();
void cxx11Enums_data();
void cxx11Enums();
void cxx11TrailingReturn();
void returnRefs();
void memberProperties_data();
void memberProperties();
@ -2231,6 +2233,30 @@ void tst_Moc::warnings_data()
<< QString()
<< QString("standard input:2:1: error: Plugin Metadata file \"does.not.exists\" does not exist. Declaration will be ignored");
QTest::newRow("Auto-declared, missing trailing return")
<< QByteArray("class X { \n public slots: \n auto fun() { return 1; } };")
<< QStringList()
<< 1
<< QString()
<< QString("standard input:3:1: error: Function declared with auto as return type but missing trailing return type. Return type deduction is not supported.");
QTest::newRow("Auto-declared, volatile auto as trailing return type")
<< QByteArray("class X { \n public slots: \n auto fun() -> volatile auto { return 1; } };")
<< QStringList()
<< 1
<< QString()
<< QString("standard input:3:1: error: Function declared with auto as return type but missing trailing return type. Return type deduction is not supported.");
// We don't currently support the decltype keyword, so it's not the same error as above.
// The test is just here to make sure this keeps generating an error until return type deduction
// is supported.
QTest::newRow("Auto-declared, decltype in trailing return type")
<< QByteArray("class X { \n public slots: \n auto fun() -> decltype(0+1) { return 1; } };")
<< QStringList()
<< 1
<< QString()
<< QString("standard input:3:1: error: Parse error at \"decltype\"");
#ifdef Q_OS_UNIX // Limit to Unix because the error message is platform-dependent
QTest::newRow("Q_PLUGIN_METADATA: unreadable file")
<< QByteArray("class X { \n Q_PLUGIN_METADATA(FILE \".\") \n };")
@ -2359,6 +2385,18 @@ void tst_Moc::cxx11Enums()
QCOMPARE(meta->enumerator(idx).isScoped(), isScoped);
}
void tst_Moc::cxx11TrailingReturn()
{
CXX11TrailingReturn retClass;
const QMetaObject *mobj = retClass.metaObject();
QVERIFY(mobj->indexOfSlot("fun()") != -1);
QVERIFY(mobj->indexOfSlot("arguments(int,char)") != -1);
QVERIFY(mobj->indexOfSlot("inlineFunc(int)") != -1);
QVERIFY(mobj->indexOfSlot("constRefReturn()") != -1);
QVERIFY(mobj->indexOfSlot("constConstRefReturn()") != -1);
QVERIFY(mobj->indexOfSignal("trailingSignalReturn(int)") != -1);
}
void tst_Moc::returnRefs()
{
TestClass tst;