diff options
Diffstat (limited to 'src/qtwaylandscanner/qtwaylandscanner.cpp')
-rw-r--r-- | src/qtwaylandscanner/qtwaylandscanner.cpp | 155 |
1 files changed, 72 insertions, 83 deletions
diff --git a/src/qtwaylandscanner/qtwaylandscanner.cpp b/src/qtwaylandscanner/qtwaylandscanner.cpp index 1a1f8bf16..7f2769fa9 100644 --- a/src/qtwaylandscanner/qtwaylandscanner.cpp +++ b/src/qtwaylandscanner/qtwaylandscanner.cpp @@ -1,44 +1,9 @@ -/**************************************************************************** -** -** Copyright (C) 2016 The Qt Company Ltd. -** Contact: https://www.qt.io/licensing/ -** -** This file is part of the tools applications of the Qt Toolkit. -** -** $QT_BEGIN_LICENSE:LGPL$ -** 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 Lesser General Public License Usage -** Alternatively, this file may be used under the terms of the GNU Lesser -** General Public License version 3 as published by the Free Software -** Foundation and appearing in the file LICENSE.LGPL3 included in the -** packaging of this file. Please review the following information to -** ensure the GNU Lesser General Public License version 3 requirements -** will be met: https://www.gnu.org/licenses/lgpl-3.0.html. -** -** GNU General Public License Usage -** Alternatively, this file may be used under the terms of the GNU -** General Public License version 2.0 or (at your option) the GNU General -** Public license version 3 or any later version approved by the KDE Free -** Qt Foundation. The licenses are as published by the Free Software -** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3 -** 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-2.0.html and -** https://www.gnu.org/licenses/gpl-3.0.html. -** -** $QT_END_LICENSE$ -** -****************************************************************************/ +// Copyright (C) 2016 The Qt Company Ltd. +// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only WITH Qt-GPL-exception-1.0 #include <QCoreApplication> #include <QFile> +#include <QFileInfo> #include <QXmlStreamReader> #include <vector> @@ -123,6 +88,7 @@ private: QByteArray m_scannerName; QByteArray m_headerPath; QByteArray m_prefix; + QByteArray m_buildMacro; QList <QByteArray> m_includes; QXmlStreamReader *m_xml = nullptr; }; @@ -156,6 +122,8 @@ bool Scanner::parseArguments(int argc, char **argv) m_headerPath = option.mid(14); } else if (option.startsWith("--prefix=")) { m_prefix = option.mid(10); + } else if (option.startsWith("--build-macro=")) { + m_buildMacro = option.mid(14); } else if (option.startsWith("--add-include=")) { auto include = option.mid(14); if (!include.isEmpty()) @@ -229,7 +197,7 @@ Scanner::WaylandEvent Scanner::readEvent(QXmlStreamReader &xml, bool request) .type = byteArrayValue(xml, "type"), .interface = byteArrayValue(xml, "interface"), .summary = byteArrayValue(xml, "summary"), - .allowNull = boolValue(xml, "allowNull"), + .allowNull = boolValue(xml, "allow-null"), }; event.arguments.push_back(std::move(argument)); } @@ -455,6 +423,8 @@ bool Scanner::process() //QByteArray preProcessorProtocolName = QByteArray(m_protocolName).replace('-', '_').toUpper(); QByteArray preProcessorProtocolName = QByteArray(m_protocolName).toUpper(); + const QByteArray fileBaseName = QFileInfo(file).completeBaseName().toLocal8Bit(); + std::vector<WaylandInterface> interfaces; while (m_xml->readNextStartElement()) { @@ -468,11 +438,31 @@ bool Scanner::process() return false; printf("// This file was generated by qtwaylandscanner\n"); - printf("// source file is %s\n\n", qPrintable(m_protocolFilePath)); + printf("// source file is %s\n\n", qPrintable(QFileInfo(file).fileName())); - for (auto b : qAsConst(m_includes)) + for (auto b : std::as_const(m_includes)) printf("#include %s\n", b.constData()); + auto printExportMacro = [this](const char *prefix, const QByteArray &preProcessorProtocolName) { + QByteArray exportMacro = prefix + preProcessorProtocolName + "_EXPORT"; + printf("#if !defined(%s)\n", exportMacro.constData()); + printf("# if defined(QT_SHARED) && !defined(QT_STATIC)\n"); + if (m_buildMacro.isEmpty()) { + printf("# define %s Q_DECL_EXPORT\n", exportMacro.constData()); + } else { + printf("# if defined(%s)\n", m_buildMacro.constData()); + printf("# define %s Q_DECL_EXPORT\n", exportMacro.constData()); + printf("# else\n"); + printf("# define %s Q_DECL_IMPORT\n", exportMacro.constData()); + printf("# endif\n"); + } + printf("# else\n"); + printf("# define %s\n", exportMacro.constData()); + printf("# endif\n"); + printf("#endif\n"); + return exportMacro; + }; + if (m_option == ServerHeader) { QByteArray inclusionGuard = QByteArray("QT_WAYLAND_SERVER_") + preProcessorProtocolName.constData(); printf("#ifndef %s\n", inclusionGuard.constData()); @@ -480,9 +470,9 @@ bool Scanner::process() printf("\n"); printf("#include \"wayland-server-core.h\"\n"); if (m_headerPath.isEmpty()) - printf("#include \"wayland-%s-server-protocol.h\"\n", QByteArray(m_protocolName).replace('_', '-').constData()); + printf("#include \"wayland-%s-server-protocol.h\"\n", fileBaseName.constData()); else - printf("#include <%s/wayland-%s-server-protocol.h>\n", m_headerPath.constData(), QByteArray(m_protocolName).replace('_', '-').constData()); + printf("#include <%s/wayland-%s-server-protocol.h>\n", m_headerPath.constData(), fileBaseName.constData()); printf("#include <QByteArray>\n"); printf("#include <QMultiMap>\n"); printf("#include <QString>\n"); @@ -501,17 +491,8 @@ bool Scanner::process() printf("QT_WARNING_DISABLE_GCC(\"-Wmissing-field-initializers\")\n"); printf("QT_WARNING_DISABLE_CLANG(\"-Wmissing-field-initializers\")\n"); QByteArray serverExport; - if (m_headerPath.size()) { - serverExport = QByteArray("Q_WAYLAND_SERVER_") + preProcessorProtocolName + "_EXPORT"; - printf("\n"); - printf("#if !defined(%s)\n", serverExport.constData()); - printf("# if defined(QT_SHARED)\n"); - printf("# define %s Q_DECL_EXPORT\n", serverExport.constData()); - printf("# else\n"); - printf("# define %s\n", serverExport.constData()); - printf("# endif\n"); - printf("#endif\n"); - } + if (m_headerPath.size()) + serverExport = printExportMacro("Q_WAYLAND_SERVER_", preProcessorProtocolName); printf("\n"); printf("namespace QtWaylandServer {\n"); @@ -637,7 +618,6 @@ bool Scanner::process() printf(" QMultiMap<struct ::wl_client*, Resource*> m_resource_map;\n"); printf(" Resource *m_resource;\n"); printf(" struct ::wl_global *m_global;\n"); - printf(" uint32_t m_globalVersion;\n"); printf(" struct DisplayDestroyedListener : ::wl_listener {\n"); printf(" %s *parent;\n", interfaceName); printf(" };\n"); @@ -655,13 +635,14 @@ bool Scanner::process() if (m_option == ServerCode) { if (m_headerPath.isEmpty()) - printf("#include \"qwayland-server-%s.h\"\n", QByteArray(m_protocolName).replace('_', '-').constData()); + printf("#include \"qwayland-server-%s.h\"\n", fileBaseName.constData()); else - printf("#include <%s/qwayland-server-%s.h>\n", m_headerPath.constData(), QByteArray(m_protocolName).replace('_', '-').constData()); + printf("#include <%s/qwayland-server-%s.h>\n", m_headerPath.constData(), fileBaseName.constData()); printf("\n"); printf("QT_BEGIN_NAMESPACE\n"); printf("QT_WARNING_PUSH\n"); printf("QT_WARNING_DISABLE_GCC(\"-Wmissing-field-initializers\")\n"); + printf("QT_WARNING_DISABLE_CLANG(\"-Wmissing-field-initializers\")\n"); printf("\n"); printf("namespace QtWaylandServer {\n"); @@ -718,7 +699,7 @@ bool Scanner::process() printf(" %s::~%s()\n", interfaceName, interfaceName); printf(" {\n"); - printf(" for (auto resource : qAsConst(m_resource_map))\n"); + printf(" for (auto resource : std::as_const(m_resource_map))\n"); printf(" resource->%s_object = nullptr;\n", interfaceNameStripped); printf("\n"); printf(" if (m_resource)\n"); @@ -762,7 +743,6 @@ bool Scanner::process() printf(" void %s::init(struct ::wl_display *display, int version)\n", interfaceName); printf(" {\n"); printf(" m_global = wl_global_create(display, &::%s_interface, version, this, bind_func);\n", interfaceName); - printf(" m_globalVersion = version;\n"); printf(" m_displayDestroyedListener.notify = %s::display_destroy_func;\n", interfaceName); printf(" m_displayDestroyedListener.parent = this;\n"); printf(" wl_display_add_destroy_listener(display, &m_displayDestroyedListener);\n"); @@ -794,7 +774,7 @@ bool Scanner::process() printf(" void %s::bind_func(struct ::wl_client *client, void *data, uint32_t version, uint32_t id)\n", interfaceName); printf(" {\n"); printf(" %s *that = static_cast<%s *>(data);\n", interfaceName, interfaceName); - printf(" that->add(client, id, qMin(that->m_globalVersion, version));\n"); + printf(" that->add(client, id, version);\n"); printf(" }\n"); printf("\n"); @@ -814,7 +794,9 @@ bool Scanner::process() printf(" if (Q_LIKELY(that)) {\n"); printf(" that->m_resource_map.remove(resource->client(), resource);\n"); printf(" that->%s_destroy_resource(resource);\n", interfaceNameStripped); - printf(" if (that->m_resource == resource)\n"); + printf("\n"); + printf(" that = resource->%s_object;\n", interfaceNameStripped); + printf(" if (that && that->m_resource == resource)\n"); printf(" that->m_resource = nullptr;\n"); printf(" }\n"); printf(" delete resource;\n"); @@ -958,9 +940,12 @@ bool Scanner::process() printf(",\n"); QByteArray cType = waylandToCType(a.type, a.interface); QByteArray qtType = waylandToQtType(a.type, a.interface, e.request); - if (a.type == "string") - printf(" %s.toUtf8().constData()", a.name.constData()); - else if (a.type == "array") + if (a.type == "string") { + printf(" "); + if (a.allowNull) + printf("%s.isNull() ? nullptr : ", a.name.constData()); + printf("%s.toUtf8().constData()", a.name.constData()); + } else if (a.type == "array") printf(" &%s_data", a.name.constData()); else if (cType == qtType) printf(" %s", a.name.constData()); @@ -983,9 +968,9 @@ bool Scanner::process() printf("#define %s\n", inclusionGuard.constData()); printf("\n"); if (m_headerPath.isEmpty()) - printf("#include \"wayland-%s-client-protocol.h\"\n", QByteArray(m_protocolName).replace('_', '-').constData()); + printf("#include \"wayland-%s-client-protocol.h\"\n", fileBaseName.constData()); else - printf("#include <%s/wayland-%s-client-protocol.h>\n", m_headerPath.constData(), QByteArray(m_protocolName).replace('_', '-').constData()); + printf("#include <%s/wayland-%s-client-protocol.h>\n", m_headerPath.constData(), fileBaseName.constData()); printf("#include <QByteArray>\n"); printf("#include <QString>\n"); printf("\n"); @@ -994,20 +979,12 @@ bool Scanner::process() printf("QT_BEGIN_NAMESPACE\n"); printf("QT_WARNING_PUSH\n"); printf("QT_WARNING_DISABLE_GCC(\"-Wmissing-field-initializers\")\n"); + printf("QT_WARNING_DISABLE_CLANG(\"-Wmissing-field-initializers\")\n"); QByteArray clientExport; + if (m_headerPath.size()) + clientExport = printExportMacro("Q_WAYLAND_CLIENT_", preProcessorProtocolName); - if (m_headerPath.size()) { - clientExport = QByteArray("Q_WAYLAND_CLIENT_") + preProcessorProtocolName + "_EXPORT"; - printf("\n"); - printf("#if !defined(%s)\n", clientExport.constData()); - printf("# if defined(QT_SHARED)\n"); - printf("# define %s Q_DECL_EXPORT\n", clientExport.constData()); - printf("# else\n"); - printf("# define %s\n", clientExport.constData()); - printf("# endif\n"); - printf("#endif\n"); - } printf("\n"); printf("namespace QtWayland {\n"); @@ -1043,6 +1020,8 @@ bool Scanner::process() printf("\n"); printf(" bool isInitialized() const;\n"); printf("\n"); + printf(" uint32_t version() const;"); + printf("\n"); printf(" static const struct ::wl_interface *interface();\n"); printEnums(interface.enums); @@ -1101,13 +1080,14 @@ bool Scanner::process() if (m_option == ClientCode) { if (m_headerPath.isEmpty()) - printf("#include \"qwayland-%s.h\"\n", QByteArray(m_protocolName).replace('_', '-').constData()); + printf("#include \"qwayland-%s.h\"\n", fileBaseName.constData()); else - printf("#include <%s/qwayland-%s.h>\n", m_headerPath.constData(), QByteArray(m_protocolName).replace('_', '-').constData()); + printf("#include <%s/qwayland-%s.h>\n", m_headerPath.constData(), fileBaseName.constData()); printf("\n"); printf("QT_BEGIN_NAMESPACE\n"); printf("QT_WARNING_PUSH\n"); printf("QT_WARNING_DISABLE_GCC(\"-Wmissing-field-initializers\")\n"); + printf("QT_WARNING_DISABLE_CLANG(\"-Wmissing-field-initializers\")\n"); printf("\n"); printf("namespace QtWayland {\n"); printf("\n"); @@ -1196,6 +1176,12 @@ bool Scanner::process() printf(" }\n"); printf("\n"); + printf(" uint32_t %s::version() const\n", interfaceName); + printf(" {\n"); + printf(" return wl_proxy_get_version(reinterpret_cast<wl_proxy*>(m_%s));\n", interfaceName); + printf(" }\n"); + printf("\n"); + printf(" const struct wl_interface *%s::interface()\n", interfaceName); printf(" {\n"); printf(" return &::%s_interface;\n", interfaceName); @@ -1228,7 +1214,7 @@ bool Scanner::process() printf("\n"); } int actualArgumentCount = new_id ? int(e.arguments.size()) - 1 : int(e.arguments.size()); - printf(" %s%s_%s(\n", new_id ? "return " : "", interfaceName, e.name.constData()); + printf(" %s::%s_%s(\n", new_id ? "return " : "", interfaceName, e.name.constData()); printf(" m_%s%s", interfaceName, actualArgumentCount > 0 ? "," : ""); bool needsComma = false; for (const WaylandArgument &a : e.arguments) { @@ -1245,9 +1231,12 @@ bool Scanner::process() } else { QByteArray cType = waylandToCType(a.type, a.interface); QByteArray qtType = waylandToQtType(a.type, a.interface, e.request); - if (a.type == "string") - printf(" %s.toUtf8().constData()", a.name.constData()); - else if (a.type == "array") + if (a.type == "string") { + printf(" "); + if (a.allowNull) + printf("%s.isNull() ? nullptr : ", a.name.constData()); + printf("%s.toUtf8().constData()", a.name.constData()); + } else if (a.type == "array") printf(" &%s_data", a.name.constData()); else if (cType == qtType) printf(" %s", a.name.constData()); |