diff options
author | Christian Tismer <tismer@stackless.com> | 2020-12-26 13:01:20 +0100 |
---|---|---|
committer | Qt Cherry-pick Bot <cherrypick_bot@qt-project.org> | 2021-01-04 14:56:55 +0000 |
commit | 3f1abffcbc1149ad8876ad0ef842968963a8015b (patch) | |
tree | a00d570be86fdf360c104f058c2456bdfd05fefc /sources | |
parent | 8247c49a22f8d35bdac949948e25432800ff3d5b (diff) |
basewrapper: clear all traces of special Q*Application treatment
After simplifying qApp so much, it is no longer necessary to treat
Q*Application special. We now can allow garbage collection for
all objects which simplifies the code quite much.
Then it was easy to shrink the implementation to a single function
`MakeQAppWrapper`, which made the whole "qapp_macro" files no
longer necessary.
This cosmetic change will probably not be back-ported to 5.15 .
Task-number: PYSIDE-1447
Change-Id: I8ae3c5575e62bd7b5d6bac65c25775c712bb178f
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Friedemann Kleint <Friedemann.Kleint@qt.io>
(cherry picked from commit 8998f9c1a9116151b679c61ad36fedcc74cc75a1)
Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
Diffstat (limited to 'sources')
-rw-r--r-- | sources/pyside6/libpyside/pyside.cpp | 1 | ||||
-rw-r--r-- | sources/shiboken6/generator/shiboken/cppgenerator.cpp | 5 | ||||
-rw-r--r-- | sources/shiboken6/libshiboken/CMakeLists.txt | 2 | ||||
-rw-r--r-- | sources/shiboken6/libshiboken/basewrapper.cpp | 70 | ||||
-rw-r--r-- | sources/shiboken6/libshiboken/basewrapper.h | 8 | ||||
-rw-r--r-- | sources/shiboken6/libshiboken/qapp_macro.cpp | 98 | ||||
-rw-r--r-- | sources/shiboken6/libshiboken/qapp_macro.h | 52 | ||||
-rw-r--r-- | sources/shiboken6/libshiboken/sbkstaticstrings.cpp | 1 | ||||
-rw-r--r-- | sources/shiboken6/libshiboken/sbkstaticstrings_p.h | 1 |
9 files changed, 49 insertions, 189 deletions
diff --git a/sources/pyside6/libpyside/pyside.cpp b/sources/pyside6/libpyside/pyside.cpp index 7c8b613d3..7cc17f0c6 100644 --- a/sources/pyside6/libpyside/pyside.cpp +++ b/sources/pyside6/libpyside/pyside.cpp @@ -58,7 +58,6 @@ #include <sbkconverter.h> #include <sbkstring.h> #include <sbkstaticstrings.h> -#include <qapp_macro.h> #include <QtCore/QByteArray> #include <QtCore/QCoreApplication> diff --git a/sources/shiboken6/generator/shiboken/cppgenerator.cpp b/sources/shiboken6/generator/shiboken/cppgenerator.cpp index 45d0d072d..8858132b2 100644 --- a/sources/shiboken6/generator/shiboken/cppgenerator.cpp +++ b/sources/shiboken6/generator/shiboken/cppgenerator.cpp @@ -354,7 +354,6 @@ void CppGenerator::generateClass(TextStream &s, const GeneratorContext &classCon << "#include <pyside.h>\n" << "#include <pysideqenum.h>\n" << "#include <feature_select.h>\n" - << "#include <qapp_macro.h>\n\n" << "QT_WARNING_DISABLE_DEPRECATED\n\n"; } @@ -4224,15 +4223,14 @@ void CppGenerator::writeClassDefinition(TextStream &s, tp_new = QLatin1String("SbkDummyNew /* PYSIDE-595: Prevent replacement " "of \"0\" with base->tp_new. */"); } - tp_flags.append(QLatin1String("|Py_TPFLAGS_HAVE_GC")); } else if (isQApp) { tp_new = QLatin1String("SbkQAppTpNew"); // PYSIDE-571: need singleton app } else { tp_new = QLatin1String("SbkObjectTpNew"); - tp_flags.append(QLatin1String("|Py_TPFLAGS_HAVE_GC")); } + tp_flags.append(QLatin1String("|Py_TPFLAGS_HAVE_GC")); QString tp_richcompare; if (!metaClass->isNamespace() && metaClass->hasComparisonOperatorOverload()) @@ -5974,7 +5972,6 @@ bool CppGenerator::finishGeneration() s << R"(#include <pyside.h> #include <pysideqenum.h> #include <feature_select.h> -#include <qapp_macro.h> )"; } diff --git a/sources/shiboken6/libshiboken/CMakeLists.txt b/sources/shiboken6/libshiboken/CMakeLists.txt index 1fdc48ccc..444fd8ce2 100644 --- a/sources/shiboken6/libshiboken/CMakeLists.txt +++ b/sources/shiboken6/libshiboken/CMakeLists.txt @@ -57,7 +57,6 @@ sbkstaticstrings.cpp bindingmanager.cpp threadstatesaver.cpp shibokenbuffer.cpp -qapp_macro.cpp pep384impl.cpp voidptr.cpp bufferprocs_py37.cpp @@ -139,7 +138,6 @@ install(FILES shibokenbuffer.h sbkpython.h pep384impl.h - qapp_macro.h voidptr.h bufferprocs_py37.h "${CMAKE_CURRENT_BINARY_DIR}/sbkversion.h" diff --git a/sources/shiboken6/libshiboken/basewrapper.cpp b/sources/shiboken6/libshiboken/basewrapper.cpp index fd38ec3ac..ce6b0bacf 100644 --- a/sources/shiboken6/libshiboken/basewrapper.cpp +++ b/sources/shiboken6/libshiboken/basewrapper.cpp @@ -56,7 +56,6 @@ #include <algorithm> #include "threadstatesaver.h" #include "signature.h" -#include "qapp_macro.h" #include "voidptr.h" #include <iostream> @@ -314,9 +313,7 @@ static void SbkDeallocWrapperCommon(PyObject *pyObj, bool canDelete) // be invoked and it trying to delete this object while it is still in // progress from the first time around, resulting in a double delete and a // crash. - // PYSIDE-571: Some objects do not use GC, so check this! - if (PyObject_IS_GC(pyObj)) - PyObject_GC_UnTrack(pyObj); + PyObject_GC_UnTrack(pyObj); // Check that Python is still initialized as sometimes this is called by a static destructor // after Python interpeter is shutdown. @@ -428,6 +425,41 @@ void SbkObjectTypeDealloc(PyObject *pyObj) } } +//////////////////////////////////////////////////////////////////////////// +// +// Support for the qApp macro. +// +// qApp is a macro in Qt5. In Python, we simulate that a little by a +// variable that monitors Q*Application.instance(). +// This variable is also able to destroy the app by qApp.shutdown(). +// + +PyObject *MakeQAppWrapper(PyTypeObject *type) +{ + static PyObject *qApp_last = nullptr; + + // protecting from multiple application instances + if (!(type == nullptr || qApp_last == Py_None)) { + const char *res_name = PepType_GetNameStr(Py_TYPE(qApp_last)); + const char *type_name = PepType_GetNameStr(type); + PyErr_Format(PyExc_RuntimeError, "Please destroy the %s singleton before" + " creating a new %s instance.", res_name, type_name); + return nullptr; + } + + // monitoring the last application state + PyObject *qApp_curr = type != nullptr ? PyObject_GC_New(PyObject, type) : Py_None; + static PyObject *builtins = PyEval_GetBuiltins(); + if (PyDict_SetItem(builtins, Shiboken::PyName::qApp(), qApp_curr) < 0) + return nullptr; + qApp_last = qApp_curr; + // Note: This Py_INCREF would normally be wrong because the qApp + // object already has a reference from PyObject_GC_New. But this is + // exactly the needed reference that keeps qApp alive from alone! + Py_INCREF(qApp_curr); + return qApp_curr; +} + ////////////////////////////////////////////////////////////////////////////// // // PYSIDE-1019: Support switchable extensions @@ -466,7 +498,7 @@ static PyObject *Sbk_TypeGet___dict__(PyTypeObject *type, void *context) * This is the override for getting a dict. */ auto dict = type->tp_dict; - if (dict == NULL) + if (dict == nullptr) Py_RETURN_NONE; if (SelectFeatureSet != nullptr) dict = SelectFeatureSet(type); @@ -623,40 +655,18 @@ static PyObject *_setupNew(SbkObject *self, PyTypeObject *subtype) self->ob_dict = nullptr; self->weakreflist = nullptr; self->d = d; + PyObject_GC_Track(reinterpret_cast<PyObject *>(self)); return reinterpret_cast<PyObject *>(self); } PyObject *SbkObjectTpNew(PyTypeObject *subtype, PyObject *, PyObject *) { SbkObject *self = PyObject_GC_New(SbkObject, subtype); - PyObject *res = _setupNew(self, subtype); - PyObject_GC_Track(reinterpret_cast<PyObject *>(self)); - return res; + return _setupNew(self, subtype); } PyObject *SbkQAppTpNew(PyTypeObject *subtype, PyObject *, PyObject *) { - // PYSIDE-571: - // For qApp, we need to create a singleton Python object. - // We cannot track this with the GC, because it is a static variable! - - // Python 2 has a weird handling of flags in derived classes that Python 3 - // does not have. Observed with bug_307.py. - // But it could theoretically also happen with Python3. - // Therefore we enforce that there is no GC flag, ever! - - // PYSIDE-560: - // We avoid to use this in Python 3, because we have a hard time to get - // write access to these flags - - // PYSIDE-1447: - // Since Python 3.8, we have the same weird flags handling in Python 3.8 - // as well. The singleton Python is no longer needed and we could remove - // the whole special handling, maybe in another checkin. - if (PyType_HasFeature(subtype, Py_TPFLAGS_HAVE_GC)) { - subtype->tp_flags &= ~Py_TPFLAGS_HAVE_GC; - subtype->tp_free = PyObject_Del; - } auto self = reinterpret_cast<SbkObject *>(MakeQAppWrapper(subtype)); return self == nullptr ? nullptr : _setupNew(self, subtype); } @@ -736,7 +746,7 @@ PyObject *FallbackRichCompare(PyObject *self, PyObject *other, int op) opstrings[op], self->ob_type->tp_name, other->ob_type->tp_name); - return NULL; + return nullptr; } Py_INCREF(res); return res; diff --git a/sources/shiboken6/libshiboken/basewrapper.h b/sources/shiboken6/libshiboken/basewrapper.h index 204c4c1c3..fedd143c2 100644 --- a/sources/shiboken6/libshiboken/basewrapper.h +++ b/sources/shiboken6/libshiboken/basewrapper.h @@ -118,8 +118,12 @@ struct LIBSHIBOKEN_API SbkObjectType }; LIBSHIBOKEN_API PyObject *SbkObjectTpNew(PyTypeObject *subtype, PyObject *, PyObject *); -// the special case of a switchable singleton -LIBSHIBOKEN_API PyObject *SbkQAppTpNew(PyTypeObject *subtype, PyObject *args, PyObject *kwds); + +/// The special case of a switchable singleton Q*Application. +LIBSHIBOKEN_API PyObject *SbkQAppTpNew(PyTypeObject *subtype, PyObject *, PyObject *); + +/// Create a new Q*Application wrapper and monitor it. +LIBSHIBOKEN_API PyObject *MakeQAppWrapper(PyTypeObject *type); /** * PYSIDE-832: Use object_dealloc instead of nullptr. diff --git a/sources/shiboken6/libshiboken/qapp_macro.cpp b/sources/shiboken6/libshiboken/qapp_macro.cpp deleted file mode 100644 index 03a8d0496..000000000 --- a/sources/shiboken6/libshiboken/qapp_macro.cpp +++ /dev/null @@ -1,98 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2020 The Qt Company Ltd. -** Contact: https://www.qt.io/licensing/ -** -** This file is part of Qt for Python. -** -** $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$ -** -****************************************************************************/ - -#include "basewrapper.h" -#include "autodecref.h" - -extern "C" -{ - -#include "qapp_macro.h" - -//////////////////////////////////////////////////////////////////////////// -// -// Support for the qApp macro. -// -// qApp is a macro in Qt5. In Python, we simulate that a little by a -// variable that monitors Q*Application.instance(). -// This variable is also able to destroy the app by qApp.shutdown(). -// - -static PyObject *qApp_name = nullptr; -static PyObject *qApp_last = nullptr; - -static PyObject *monitor_qApp_var(PyObject *qApp_curr) -{ - static bool init_done; - static PyObject *builtins = PyEval_GetBuiltins(); - - if (!init_done) { - qApp_name = Py_BuildValue("s", "qApp"); - if (qApp_name == nullptr) - return nullptr; - // This is a borrowed reference - Py_INCREF(builtins); - init_done = true; - } - - if (PyDict_SetItem(builtins, qApp_name, qApp_curr) < 0) - return nullptr; - qApp_last = qApp_curr; - Py_INCREF(qApp_curr); - return qApp_curr; -} - -PyObject *MakeQAppWrapper(PyTypeObject *type) -{ - if (type == nullptr) - type = Py_TYPE(Py_None); - if (!(type == Py_TYPE(Py_None) || Py_TYPE(qApp_last) == Py_TYPE(Py_None))) { - const char *res_name = PepType_GetNameStr(Py_TYPE(qApp_last)); - const char *type_name = PepType_GetNameStr(type); - PyErr_Format(PyExc_RuntimeError, "Please destroy the %s singleton before" - " creating a new %s instance.", res_name, type_name); - return nullptr; - } - PyObject *self = type != Py_TYPE(Py_None) ? PyObject_New(PyObject, type) : Py_None; - return monitor_qApp_var(self); -} - -} //extern "C" - -// end of module diff --git a/sources/shiboken6/libshiboken/qapp_macro.h b/sources/shiboken6/libshiboken/qapp_macro.h deleted file mode 100644 index 9abd17c17..000000000 --- a/sources/shiboken6/libshiboken/qapp_macro.h +++ /dev/null @@ -1,52 +0,0 @@ -/**************************************************************************** -** -** Copyright (C) 2017 The Qt Company Ltd. -** Contact: https://www.qt.io/licensing/ -** -** This file is part of Qt for Python. -** -** $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$ -** -****************************************************************************/ - -#ifndef QAPP_MACRO_H -#define QAPP_MACRO_H - -#include "sbkpython.h" - -extern "C" -{ - -LIBSHIBOKEN_API PyObject *MakeQAppWrapper(PyTypeObject *type); - -} // extern "C" - -#endif // QAPP_MACRO_H diff --git a/sources/shiboken6/libshiboken/sbkstaticstrings.cpp b/sources/shiboken6/libshiboken/sbkstaticstrings.cpp index cd42643f8..35fc2a410 100644 --- a/sources/shiboken6/libshiboken/sbkstaticstrings.cpp +++ b/sources/shiboken6/libshiboken/sbkstaticstrings.cpp @@ -58,6 +58,7 @@ STATIC_STRING_IMPL(fset, "fset") STATIC_STRING_IMPL(loads, "loads") STATIC_STRING_IMPL(multi, "multi") STATIC_STRING_IMPL(name, "name") +STATIC_STRING_IMPL(qApp, "qApp") STATIC_STRING_IMPL(result, "result") STATIC_STRING_IMPL(select_id, "select_id") STATIC_STRING_IMPL(value, "value") diff --git a/sources/shiboken6/libshiboken/sbkstaticstrings_p.h b/sources/shiboken6/libshiboken/sbkstaticstrings_p.h index acfc71409..308966481 100644 --- a/sources/shiboken6/libshiboken/sbkstaticstrings_p.h +++ b/sources/shiboken6/libshiboken/sbkstaticstrings_p.h @@ -51,6 +51,7 @@ PyObject *marshal(); PyObject *method(); PyObject *mro(); PyObject *overload(); +PyObject *qApp(); PyObject *staticmethod(); } // namespace PyName namespace PyMagicName |