Qt 5.6 issue with GCC 13 and -std=c++20 (Sailfish OS 5.1)

When I tried to build OSMScout in OBS yesterday, it failed with SFOS 5.1 target with strange error:

[  176s] In file included from /usr/include/qt5/QtCore/qfuture.h:41,
[  176s]                  from /usr/include/qt5/QtCore/QtCore:100,
[  176s]                  from /usr/include/qt5/QtQml/QtQmlDepends:3,
[  176s]                  from /usr/include/qt5/QtQml/QtQml:3,
[  176s]                  from /home/abuild/rpmbuild/BUILD/harbour-osmscout-2.43/dependencies/libosmscout/libosmscout-client-qt/src/osmscoutclientqt/SearchLocationModel.cpp:26:
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h:282:33: error: expected ')' before 'initialState'
[  176s]   282 |     QFutureInterface<void>(State initialState = NoState)
[  176s]       |                           ~     ^~~~~~~~~~~~~
[  176s]       |                                 )
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h:285:28: error: expected unqualified-id before 'const'
[  176s]   285 |     QFutureInterface<void>(const QFutureInterface<void> &other)
[  176s]       |                            ^~~~~
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h:285:28: error: expected ')' before 'const'
[  176s]   285 |     QFutureInterface<void>(const QFutureInterface<void> &other)
[  176s]       |                           ~^~~~~
[  176s]       |                            )
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h: In static member function 'static QFutureInterface<void> QFutureInterface<void>::canceledResult()':
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h:290:67: error: no matching function for call to 'QFutureInterface<void>::QFutureInterface(QFutureInterfaceBase::State)'
[  176s]   290 |     { return QFutureInterface(State(Started | Finished | Canceled)); }
[  176s]       |                                                                   ^
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h:279:7: note: candidate: 'QFutureInterface<void>::QFutureInterface()'
[  176s]   279 | class QFutureInterface<void> : public QFutureInterfaceBase
[  176s]       |       ^~~~~~~~~~~~~~~~~~~~~~
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h:279:7: note:   candidate expects 0 arguments, 1 provided
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h:279:7: note: candidate: 'QFutureInterface<void>::QFutureInterface(const QFutureInterface<void>&)'
[  176s] /usr/include/qt5/QtCore/qfutureinterface.h:279:7: note:   no known conversion for argument 1 from 'QFutureInterfaceBase::State' to 'const QFutureInterface<void>&'

After some investigation I found out that it is caused by “Functional-style cast in C++” that behaves slightly different in C++20 than C++17 and QFutureInterface<void> is evaluated as a type, not the a class constructor. Can you patch Qt to drop <void> please? It would help with usage of modern C++ standard.

6 Likes

I don’t know what is the standard procedure here, but would it be beneficial to tag Jolla employees, if this was directed towards them?

See also:

5 Likes

I was able to workaround the issues: workaround for Qt 5.6 incompatibility with C++20 · Karry/libosmscout@b565298 · GitHub

but it is not suitable in long term :frowning:

1 Like

Another way to work around this (or Jolla to fix this) is to remove the redundant <void> specifiers in the specialisation of QFutureInterface like so:

template <>
class QFutureInterface<void> : public QFutureInterfaceBase
{
public:
    QFutureInterface(State initialState = NoState)
        : QFutureInterfaceBase(initialState)
    { }
    QFutureInterface(const QFutureInterface<void> &other)
        : QFutureInterfaceBase(other)
    { }

    static QFutureInterface<void> canceledResult()
    { return QFutureInterface(State(Started | Finished | Canceled)); }

    QFutureInterface &operator=(const QFutureInterface &other)
    {
        QFutureInterfaceBase::operator=(other);
        return *this;
    }

    inline QFuture<void> future(); // implemented in qfuture.h

    void reportResult(const void *, int) { }
    void reportResults(const QVector<void> &, int) { }
    void reportFinished(const void * = Q_NULLPTR) { QFutureInterfaceBase::reportFinished(); }
};

(In ~/SailfishOS/mersdk/targets/SailfishOS-5.1.0.11-aarch64.default/usr/include/qt5/QtCore/qfutureinterface.h)

2 Likes