aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorChristian Tismer <tismer@stackless.com>2021-10-04 17:51:18 +0200
committerChristian Tismer <tismer@stackless.com>2021-10-12 11:03:16 +0200
commit4788127dca1f90c0a83cbf3016da708404eaad69 (patch)
tree00026b5a74799160dfa4b9344ec7419fceea083d
parenta3f40e25ebe81804bf1e19d5ee64108d4304c9ab (diff)
shiboken: fix missing cleanup in overridden virtual methods of wrappers
In an error condition, all arguments must be invalidated in order to get a clean state. This is currently not done when an error condition exists. Rewrite the code to generate in a way that all destructions are done, regardless of function outcome. That needed some reordering of the code, in order to move the necessary cleanup right after the Python function call and before PyErr_Print/return. [ChangeLog][shiboken6] Overridden virtual methods are now always correctly finalized, regardless of errors. Change-Id: If87cc4631f9b5731c1b1b8c7bf204e72d8744cc7 Fixes: PYSIDE-656 Reviewed-by: Cristian Maureira-Fredes <cristian.maureira-fredes@qt.io> (cherry picked from commit 3e5bfbff99334b8c15ee705079d5a7f0cfa371d5)
-rw-r--r--sources/shiboken6/generator/shiboken/cppgenerator.cpp47
1 files changed, 25 insertions, 22 deletions
diff --git a/sources/shiboken6/generator/shiboken/cppgenerator.cpp b/sources/shiboken6/generator/shiboken/cppgenerator.cpp
index 44304375a..0a237ed8d 100644
--- a/sources/shiboken6/generator/shiboken/cppgenerator.cpp
+++ b/sources/shiboken6/generator/shiboken/cppgenerator.cpp
@@ -1166,24 +1166,38 @@ void CppGenerator::writeVirtualMethodNative(TextStream &s,
if (!func->injectedCodeCallsPythonOverride()) {
s << "Shiboken::AutoDecRef " << pyRetVar << "(PyObject_Call("
- << PYTHON_OVERRIDE_VAR << ", " << PYTHON_ARGS << ", nullptr));\n"
- << "if (" << pyRetVar << ".isNull()) {\n" << indent
- << "// An error happened in python code!\n"
- << "PyErr_Print();\n" << returnStatement << '\n' << outdent
- << "}\n";
+ << PYTHON_OVERRIDE_VAR << ", " << PYTHON_ARGS << ", nullptr));\n";
+
+ for (int argIndex : qAsConst(invalidateArgs)) {
+ s << "if (invalidateArg" << argIndex << ")\n" << indent
+ << "Shiboken::Object::invalidate(PyTuple_GET_ITEM(" << PYTHON_ARGS
+ << ", " << (argIndex - 1) << "));\n" << outdent;
+ }
+
+ s << "if (" << pyRetVar << ".isNull()) {\n" << indent
+ << "// An error happened in python code!\n"
+ << "PyErr_Print();\n"
+ << returnStatement << "\n" << outdent
+ << "}\n";
+
+ if (invalidateReturn) {
+ s << "bool invalidateArg0 = " << pyRetVar << "->ob_refcnt == 1;\n"
+ << "if (invalidateArg0)\n" << indent
+ << "Shiboken::Object::releaseOwnership(" << pyRetVar << ".object());\n" << outdent;
+ }
if (!func->isVoid()) {
- if (invalidateReturn)
- s << "bool invalidateArg0 = " << pyRetVar << "->ob_refcnt == 1;\n";
if (func->typeReplaced(0) != cPyObjectT()) {
s << "// Check return type\n";
+
if (func->typeReplaced(0).isEmpty()) {
- s << PYTHON_TO_CPPCONVERSION_STRUCT
- << ' ' << PYTHON_TO_CPP_VAR << " = "
- << cpythonIsConvertibleFunction(func->type())
- << pyRetVar << ");\n"
+
+ s << PYTHON_TO_CPPCONVERSION_STRUCT << ' '
+ << PYTHON_TO_CPP_VAR << " =\n" << indent
+ << cpythonIsConvertibleFunction(func->type())
+ << pyRetVar << ");\n" << outdent
<< "if (!" << PYTHON_TO_CPP_VAR << ") {\n" << indent
<< "Shiboken::warning(PyExc_RuntimeWarning, 2,\n" << indent
<< "\"Invalid return value in function %s, expected %s, got %s.\",\n"
@@ -1227,17 +1241,6 @@ void CppGenerator::writeVirtualMethodNative(TextStream &s,
}
}
- if (invalidateReturn) {
- s << "if (invalidateArg0)\n" << indent
- << "Shiboken::Object::releaseOwnership(" << pyRetVar
- << ".object());\n" << outdent;
- }
- for (int argIndex : qAsConst(invalidateArgs)) {
- s << "if (invalidateArg" << argIndex << ")\n" << indent
- << "Shiboken::Object::invalidate(PyTuple_GET_ITEM(" << PYTHON_ARGS
- << ", " << (argIndex - 1) << "));\n" << outdent;
- }
-
for (const FunctionModification &funcMod : func->modifications()) {
for (const ArgumentModification &argMod : funcMod.argument_mods()) {
if (argMod.index() == 0