aboutsummaryrefslogtreecommitdiffstats
path: root/sources/shiboken6/generator/shiboken/cppgenerator.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'sources/shiboken6/generator/shiboken/cppgenerator.cpp')
-rw-r--r--sources/shiboken6/generator/shiboken/cppgenerator.cpp372
1 files changed, 203 insertions, 169 deletions
diff --git a/sources/shiboken6/generator/shiboken/cppgenerator.cpp b/sources/shiboken6/generator/shiboken/cppgenerator.cpp
index d4aa6d242..e679efbbd 100644
--- a/sources/shiboken6/generator/shiboken/cppgenerator.cpp
+++ b/sources/shiboken6/generator/shiboken/cppgenerator.cpp
@@ -30,6 +30,7 @@
#include "cppgenerator.h"
#include "ctypenames.h"
+#include "pytypenames.h"
#include "fileout.h"
#include "overloaddata.h"
#include <abstractmetaenum.h>
@@ -57,9 +58,8 @@
static const char CPP_ARG0[] = "cppArg0";
-QHash<QString, QString> CppGenerator::m_nbFuncs = QHash<QString, QString>();
-QHash<QString, QString> CppGenerator::m_sqFuncs = QHash<QString, QString>();
-QHash<QString, QString> CppGenerator::m_mpFuncs = QHash<QString, QString>();
+static inline QString reprFunction() { return QStringLiteral("__repr__"); }
+
QString CppGenerator::m_currentErrorCode(QLatin1String("{}"));
static const char typeNameFunc[] = R"CPP(
@@ -121,83 +121,74 @@ TextStream &operator<<(TextStream &s, const returnStatement &r)
return s;
}
-CppGenerator::CppGenerator()
-{
- // Number protocol structure members names
- m_nbFuncs.insert(QLatin1String("__add__"), QLatin1String("nb_add"));
- m_nbFuncs.insert(QLatin1String("__sub__"), QLatin1String("nb_subtract"));
- m_nbFuncs.insert(QLatin1String("__mul__"), QLatin1String("nb_multiply"));
- m_nbFuncs.insert(QLatin1String("__div__"), QLatin1String("nb_divide"));
- m_nbFuncs.insert(QLatin1String("__mod__"), QLatin1String("nb_remainder"));
- m_nbFuncs.insert(QLatin1String("__neg__"), QLatin1String("nb_negative"));
- m_nbFuncs.insert(QLatin1String("__pos__"), QLatin1String("nb_positive"));
- m_nbFuncs.insert(QLatin1String("__invert__"), QLatin1String("nb_invert"));
- m_nbFuncs.insert(QLatin1String("__lshift__"), QLatin1String("nb_lshift"));
- m_nbFuncs.insert(QLatin1String("__rshift__"), QLatin1String("nb_rshift"));
- m_nbFuncs.insert(QLatin1String("__and__"), QLatin1String("nb_and"));
- m_nbFuncs.insert(QLatin1String("__xor__"), QLatin1String("nb_xor"));
- m_nbFuncs.insert(QLatin1String("__or__"), QLatin1String("nb_or"));
- m_nbFuncs.insert(QLatin1String("__iadd__"), QLatin1String("nb_inplace_add"));
- m_nbFuncs.insert(QLatin1String("__isub__"), QLatin1String("nb_inplace_subtract"));
- m_nbFuncs.insert(QLatin1String("__imul__"), QLatin1String("nb_inplace_multiply"));
- m_nbFuncs.insert(QLatin1String("__idiv__"), QLatin1String("nb_inplace_divide"));
- m_nbFuncs.insert(QLatin1String("__imod__"), QLatin1String("nb_inplace_remainder"));
- m_nbFuncs.insert(QLatin1String("__ilshift__"), QLatin1String("nb_inplace_lshift"));
- m_nbFuncs.insert(QLatin1String("__irshift__"), QLatin1String("nb_inplace_rshift"));
- m_nbFuncs.insert(QLatin1String("__iand__"), QLatin1String("nb_inplace_and"));
- m_nbFuncs.insert(QLatin1String("__ixor__"), QLatin1String("nb_inplace_xor"));
- m_nbFuncs.insert(QLatin1String("__ior__"), QLatin1String("nb_inplace_or"));
- m_nbFuncs.insert(QLatin1String("bool"), QLatin1String("nb_nonzero"));
-
- // sequence protocol functions
- m_sequenceProtocol.insert(QLatin1String("__len__"),
- {QLatin1String("PyObject *self"),
- QLatin1String("Py_ssize_t")});
- m_sequenceProtocol.insert(QLatin1String("__getitem__"),
- {QLatin1String("PyObject *self, Py_ssize_t _i"),
- QLatin1String("PyObject*")});
- m_sequenceProtocol.insert(QLatin1String("__setitem__"),
- {QLatin1String("PyObject *self, Py_ssize_t _i, PyObject *_value"),
- intT()});
- m_sequenceProtocol.insert(QLatin1String("__getslice__"),
- {QLatin1String("PyObject *self, Py_ssize_t _i1, Py_ssize_t _i2"),
- QLatin1String("PyObject*")});
- m_sequenceProtocol.insert(QLatin1String("__setslice__"),
- {QLatin1String("PyObject *self, Py_ssize_t _i1, Py_ssize_t _i2, PyObject *_value"),
- intT()});
- m_sequenceProtocol.insert(QLatin1String("__contains__"),
- {QLatin1String("PyObject *self, PyObject *_value"),
- intT()});
- m_sequenceProtocol.insert(QLatin1String("__concat__"),
- {QLatin1String("PyObject *self, PyObject *_other"),
- QLatin1String("PyObject*")});
+// Protocol function name / function parameters / return type
+struct ProtocolEntry
+{
+ QString name;
+ QString arguments;
+ QString returnType;
+};
- // Sequence protocol structure members names
- m_sqFuncs.insert(QLatin1String("__concat__"), QLatin1String("sq_concat"));
- m_sqFuncs.insert(QLatin1String("__contains__"), QLatin1String("sq_contains"));
- m_sqFuncs.insert(QLatin1String("__getitem__"), QLatin1String("sq_item"));
- m_sqFuncs.insert(QLatin1String("__getslice__"), QLatin1String("sq_slice"));
- m_sqFuncs.insert(QLatin1String("__len__"), QLatin1String("sq_length"));
- m_sqFuncs.insert(QLatin1String("__setitem__"), QLatin1String("sq_ass_item"));
- m_sqFuncs.insert(QLatin1String("__setslice__"), QLatin1String("sq_ass_slice"));
-
- // mapping protocol function
- m_mappingProtocol.insert(QLatin1String("__mlen__"),
- {QLatin1String("PyObject *self"),
- QLatin1String("Py_ssize_t")});
- m_mappingProtocol.insert(QLatin1String("__mgetitem__"),
- {QLatin1String("PyObject *self, PyObject *_key"),
- QLatin1String("PyObject*")});
- m_mappingProtocol.insert(QLatin1String("__msetitem__"),
- {QLatin1String("PyObject *self, PyObject *_key, PyObject *_value"),
- intT()});
+using ProtocolEntries = QList<ProtocolEntry>;
- // Sequence protocol structure members names
- m_mpFuncs.insert(QLatin1String("__mlen__"), QLatin1String("mp_length"));
- m_mpFuncs.insert(QLatin1String("__mgetitem__"), QLatin1String("mp_subscript"));
- m_mpFuncs.insert(QLatin1String("__msetitem__"), QLatin1String("mp_ass_subscript"));
+static bool contains(const ProtocolEntries &l, const QString &needle)
+{
+ for (const auto &m : l) {
+ if (m.name == needle)
+ return true;
+ }
+ return false;
+}
+
+// Maps special function names to function parameters and return types
+// used by CPython API in the mapping protocol.
+const ProtocolEntries &mappingProtocols()
+{
+ static const ProtocolEntries result = {
+ {QLatin1String("__mlen__"),
+ QLatin1String("PyObject *self"),
+ QLatin1String("Py_ssize_t")},
+ {QLatin1String("__mgetitem__"),
+ QLatin1String("PyObject *self, PyObject *_key"),
+ QLatin1String("PyObject*")},
+ {QLatin1String("__msetitem__"),
+ QLatin1String("PyObject *self, PyObject *_key, PyObject *_value"),
+ intT()}};
+ return result;
+}
+
+// Maps special function names to function parameters and return types
+// used by CPython API in the sequence protocol.
+const ProtocolEntries &sequenceProtocols()
+{
+ static const ProtocolEntries result = {
+ {QLatin1String("__len__"),
+ QLatin1String("PyObject *self"),
+ QLatin1String("Py_ssize_t")},
+ {QLatin1String("__getitem__"),
+ QLatin1String("PyObject *self, Py_ssize_t _i"),
+ QLatin1String("PyObject*")},
+ {QLatin1String("__setitem__"),
+ QLatin1String("PyObject *self, Py_ssize_t _i, PyObject *_value"),
+ intT()},
+ {QLatin1String("__getslice__"),
+ QLatin1String("PyObject *self, Py_ssize_t _i1, Py_ssize_t _i2"),
+ QLatin1String("PyObject*")},
+ {QLatin1String("__setslice__"),
+ QLatin1String("PyObject *self, Py_ssize_t _i1, Py_ssize_t _i2, PyObject *_value"),
+ intT()},
+ {QLatin1String("__contains__"),
+ QLatin1String("PyObject *self, PyObject *_value"),
+ intT()},
+ {QLatin1String("__concat__"),
+ QLatin1String("PyObject *self, PyObject *_other"),
+ QLatin1String("PyObject*")}
+ };
+ return result;
}
+CppGenerator::CppGenerator() = default;
+
QString CppGenerator::fileNameSuffix() const
{
return QLatin1String("_wrapper.cpp");
@@ -273,6 +264,15 @@ std::optional<AbstractMetaType>
return {};
}
+void CppGenerator::clearTpFuncs()
+{
+ m_tpFuncs = {
+ {QLatin1String("__str__"), {}}, {QLatin1String("__str__"), {}},
+ {reprFunction(), {}}, {QLatin1String("__iter__"), {}},
+ {QLatin1String("__next__"), {}}
+ };
+}
+
using FunctionGroupMap = QMap<QString, AbstractMetaFunctionList>;
// Prevent ELF symbol qt_version_tag from being generated into the source
@@ -541,8 +541,10 @@ void CppGenerator::generateClass(TextStream &s, const GeneratorContext &classCon
continue;
const AbstractMetaFunction *rfunc = overloads.constFirst();
- if (m_sequenceProtocol.contains(rfunc->name()) || m_mappingProtocol.contains(rfunc->name()))
+ if (contains(sequenceProtocols(), rfunc->name())
+ || contains(mappingProtocols(), rfunc->name())) {
continue;
+ }
if (rfunc->isConstructor()) {
// @TODO: Implement constructor support for smart pointers, so that they can be
@@ -1072,7 +1074,7 @@ void CppGenerator::writeVirtualMethodNative(TextStream &s,
if (!convert && argTypeEntry->isPrimitive()) {
if (argTypeEntry->basicReferencedTypeEntry())
argTypeEntry = argTypeEntry->basicReferencedTypeEntry();
- convert = !m_formatUnits.contains(argTypeEntry->name());
+ convert = !formatUnits().contains(argTypeEntry->name());
}
StringStream ac(TextStream::Language::Cpp);
@@ -2448,6 +2450,18 @@ void CppGenerator::writeArgumentConversion(TextStream &s,
writeUnusedVariableCast(s, argName);
}
+static const QStringList &knownPythonTypes()
+{
+ static const QStringList result = {
+ pyBoolT(), pyIntT(), pyFloatT(), pyLongT(),
+ QLatin1String("PyObject"), QLatin1String("PyString"),
+ QLatin1String("PyBuffer"), QLatin1String("PySequence"),
+ QLatin1String("PyTuple"), QLatin1String("PyList"),
+ QLatin1String("PyDict"), QLatin1String("PyObject*"),
+ QLatin1String("PyObject *"), QLatin1String("PyTupleObject*")};
+ return result;
+}
+
std::optional<AbstractMetaType>
CppGenerator::getArgumentType(const AbstractMetaFunction *func, int argPos) const
{
@@ -2466,7 +2480,7 @@ std::optional<AbstractMetaType>
}
auto argType = buildAbstractMetaTypeFromString(typeReplaced);
- if (!argType.has_value() && !m_knownPythonTypes.contains(typeReplaced)) {
+ if (!argType.has_value() && !knownPythonTypes().contains(typeReplaced)) {
qCWarning(lcShiboken, "%s",
qPrintable(msgUnknownTypeInArgumentTypeReplacement(typeReplaced, func)));
}
@@ -4078,8 +4092,8 @@ QString CppGenerator::multipleInheritanceInitializerFunctionName(const AbstractM
bool CppGenerator::supportsMappingProtocol(const AbstractMetaClass *metaClass) const
{
- for (auto it = m_mappingProtocol.cbegin(), end = m_mappingProtocol.cend(); it != end; ++it) {
- if (metaClass->hasFunction(it.key()))
+ for (const auto &m : mappingProtocols()) {
+ if (metaClass->hasFunction(m.name))
return true;
}
@@ -4096,8 +4110,8 @@ bool CppGenerator::supportsNumberProtocol(const AbstractMetaClass *metaClass) co
bool CppGenerator::supportsSequenceProtocol(const AbstractMetaClass *metaClass) const
{
- for (auto it = m_sequenceProtocol.cbegin(), end = m_sequenceProtocol.cend(); it != end; ++it) {
- if (metaClass->hasFunction(it.key()))
+ for (const auto &seq : sequenceProtocols()) {
+ if (metaClass->hasFunction(seq.name))
return true;
}
@@ -4230,15 +4244,15 @@ void CppGenerator::writeClassDefinition(TextStream &s,
tp_getset = cpythonGettersSettersDefinitionName(metaClass);
// search for special functions
- ShibokenGenerator::clearTpFuncs();
+ clearTpFuncs();
const AbstractMetaFunctionList &funcs = metaClass->functions();
for (AbstractMetaFunction *func : funcs) {
if (m_tpFuncs.contains(func->name()))
m_tpFuncs[func->name()] = cpythonFunctionName(func);
}
- if (m_tpFuncs.value(QLatin1String("__repr__")).isEmpty()
+ if (m_tpFuncs.value(reprFunction()).isEmpty()
&& metaClass->hasToStringCapability()) {
- m_tpFuncs[QLatin1String("__repr__")] = writeReprFunction(s,
+ m_tpFuncs[reprFunction()] = writeReprFunction(s,
classContext,
metaClass->toStringCapabilityIndirections());
}
@@ -4276,7 +4290,7 @@ void CppGenerator::writeClassDefinition(TextStream &s,
<< "}\n\nstatic PyType_Slot " << className << "_slots[] = {\n" << indent
<< "{Py_tp_base, nullptr}, // inserted by introduceWrapperType\n"
<< pyTypeSlotEntry("Py_tp_dealloc", tp_dealloc)
- << pyTypeSlotEntry("Py_tp_repr", m_tpFuncs.value(QLatin1String("__repr__")))
+ << pyTypeSlotEntry("Py_tp_repr", m_tpFuncs.value(reprFunction()))
<< pyTypeSlotEntry("Py_tp_hash", tp_hash)
<< pyTypeSlotEntry("Py_tp_call", tp_call)
<< pyTypeSlotEntry("Py_tp_str", m_tpFuncs.value(QLatin1String("__str__")))
@@ -4318,16 +4332,13 @@ void CppGenerator::writeMappingMethods(TextStream &s,
const AbstractMetaClass *metaClass,
const GeneratorContext &context) const
{
- for (auto it = m_mappingProtocol.cbegin(), end = m_mappingProtocol.cend(); it != end; ++it) {
- const AbstractMetaFunction *func = metaClass->findFunction(it.key());
+ for (const auto & m : mappingProtocols()) {
+ const AbstractMetaFunction *func = metaClass->findFunction(m.name);
if (!func)
continue;
QString funcName = cpythonFunctionName(func);
- QString funcArgs = it.value().first;
- QString funcRetVal = it.value().second;
-
CodeSnipList snips = func->injectedCodeSnips(TypeSystem::CodeSnipPositionAny, TypeSystem::TargetLangCode);
- s << funcRetVal << ' ' << funcName << '(' << funcArgs << ")\n{\n";
+ s << m.returnType << ' ' << funcName << '(' << m.arguments << ")\n{\n";
writeInvalidPyObjectCheck(s, QLatin1String("self"));
writeCppSelfDefinition(s, func, context);
@@ -4345,17 +4356,15 @@ void CppGenerator::writeSequenceMethods(TextStream &s,
{
bool injectedCode = false;
- for (auto it = m_sequenceProtocol.cbegin(), end = m_sequenceProtocol.cend(); it != end; ++it) {
- const AbstractMetaFunction *func = metaClass->findFunction(it.key());
+ for (const auto &seq : sequenceProtocols()) {
+ const AbstractMetaFunction *func = metaClass->findFunction(seq.name);
if (!func)
continue;
injectedCode = true;
QString funcName = cpythonFunctionName(func);
- QString funcArgs = it.value().first;
- QString funcRetVal = it.value().second;
CodeSnipList snips = func->injectedCodeSnips(TypeSystem::CodeSnipPositionAny, TypeSystem::TargetLangCode);
- s << funcRetVal << ' ' << funcName << '(' << funcArgs << ")\n{\n" << indent;
+ s << seq.returnType << ' ' << funcName << '(' << seq.arguments << ")\n{\n" << indent;
writeInvalidPyObjectCheck(s, QLatin1String("self"));
writeCppSelfDefinition(s, func, context);
@@ -4369,16 +4378,30 @@ void CppGenerator::writeSequenceMethods(TextStream &s,
writeDefaultSequenceMethods(s, context);
}
+// Sequence protocol structure member names
+static const QHash<QString, QString> &sqFuncs()
+{
+ static const QHash<QString, QString> result = {
+ {QLatin1String("__concat__"), QLatin1String("sq_concat")},
+ {QLatin1String("__contains__"), QLatin1String("sq_contains")},
+ {QLatin1String("__getitem__"), QLatin1String("sq_item")},
+ {QLatin1String("__getslice__"), QLatin1String("sq_slice")},
+ {QLatin1String("__len__"), QLatin1String("sq_length")},
+ {QLatin1String("__setitem__"), QLatin1String("sq_ass_item")},
+ {QLatin1String("__setslice__"), QLatin1String("sq_ass_slice")}
+ };
+ return result;
+}
+
void CppGenerator::writeTypeAsSequenceDefinition(TextStream &s, const AbstractMetaClass *metaClass) const
{
bool hasFunctions = false;
QMap<QString, QString> funcs;
- for (auto it = m_sequenceProtocol.cbegin(), end = m_sequenceProtocol.cend(); it != end; ++it) {
- const QString &funcName = it.key();
- const AbstractMetaFunction *func = metaClass->findFunction(funcName);
- funcs[funcName] = func ? cpythonFunctionName(func).prepend(QLatin1Char('&')) : QString();
- if (!hasFunctions && func)
+ for (const auto &seq : sequenceProtocols()) {
+ if (const AbstractMetaFunction *func = metaClass->findFunction(seq.name)) {
+ funcs.insert(seq.name, QLatin1Char('&') + cpythonFunctionName(func));
hasFunctions = true;
+ }
}
QString baseName = cpythonBaseName(metaClass);
@@ -4390,69 +4413,78 @@ void CppGenerator::writeTypeAsSequenceDefinition(TextStream &s, const AbstractMe
funcs[QLatin1String("__setitem__")] = baseName + QLatin1String("__setitem__");
}
- for (QHash<QString, QString>::const_iterator it = m_sqFuncs.cbegin(), end = m_sqFuncs.cend(); it != end; ++it) {
+ for (auto it = sqFuncs().cbegin(), end = sqFuncs().cend(); it != end; ++it) {
const QString &sqName = it.key();
- if (funcs[sqName].isEmpty())
- continue;
- s << "{Py_" << it.value() << ", (void *)" << funcs[sqName] << "},\n";
+ auto fit = funcs.constFind(sqName);
+ if (fit != funcs.constEnd()) {
+ s << "{Py_" << it.value() << ", reinterpret_cast<void *>("
+ << fit.value() << ")},\n";
+ }
}
}
void CppGenerator::writeTypeAsMappingDefinition(TextStream &s, const AbstractMetaClass *metaClass) const
{
- bool hasFunctions = false;
+ // Sequence protocol structure members names
+ static const QHash<QString, QString> mpFuncs{
+ {QLatin1String("__mlen__"), QLatin1String("mp_length")},
+ {QLatin1String("__mgetitem__"), QLatin1String("mp_subscript")},
+ {QLatin1String("__msetitem__"), QLatin1String("mp_ass_subscript")},
+ };
QMap<QString, QString> funcs;
- for (auto it = m_mappingProtocol.cbegin(), end = m_mappingProtocol.cend(); it != end; ++it) {
- const QString &funcName = it.key();
- const AbstractMetaFunction *func = metaClass->findFunction(funcName);
- funcs[funcName] = func ? cpythonFunctionName(func).prepend(QLatin1Char('&')) : QLatin1String("0");
- if (!hasFunctions && func)
- hasFunctions = true;
- }
-
- //use default implementation
- if (!hasFunctions) {
- funcs.insert(QLatin1String("__mlen__"), QString());
- funcs.insert(QLatin1String("__mgetitem__"), QString());
- funcs.insert(QLatin1String("__msetitem__"), QString());
- }
-
- for (auto it = m_mpFuncs.cbegin(), end = m_mpFuncs.cend(); it != end; ++it) {
- const QString &mpName = it.key();
- if (funcs[mpName].isEmpty())
- continue;
- s << "{Py_" << it.value() << ", (void *)" << funcs[mpName] << "},\n";
- }
+ for (const auto &m : mappingProtocols()) {
+ if (const AbstractMetaFunction *func = metaClass->findFunction(m.name)) {
+ const QString entry = QLatin1String("reinterpret_cast<void *>(&")
+ + cpythonFunctionName(func) + QLatin1Char(')');
+ funcs.insert(m.name, entry);
+ } else {
+ funcs.insert(m.name, QLatin1String(NULL_PTR));
+ }
+ }
+
+ for (auto it = mpFuncs.cbegin(), end = mpFuncs.cend(); it != end; ++it) {
+ const auto fit = funcs.constFind(it.key());
+ if (fit != funcs.constEnd())
+ s << "{Py_" << it.value() << ", " << fit.value() << "},\n";
+ }
+}
+
+// Number protocol structure members names
+static const QHash<QString, QString> &nbFuncs()
+{
+ static const QHash<QString, QString> result = {
+ {QLatin1String("__add__"), QLatin1String("nb_add")},
+ {QLatin1String("__sub__"), QLatin1String("nb_subtract")},
+ {QLatin1String("__mul__"), QLatin1String("nb_multiply")},
+ {QLatin1String("__div__"), QLatin1String("nb_divide")},
+ {QLatin1String("__mod__"), QLatin1String("nb_remainder")},
+ {QLatin1String("__neg__"), QLatin1String("nb_negative")},
+ {QLatin1String("__pos__"), QLatin1String("nb_positive")},
+ {QLatin1String("__invert__"), QLatin1String("nb_invert")},
+ {QLatin1String("__lshift__"), QLatin1String("nb_lshift")},
+ {QLatin1String("__rshift__"), QLatin1String("nb_rshift")},
+ {QLatin1String("__and__"), QLatin1String("nb_and")},
+ {QLatin1String("__xor__"), QLatin1String("nb_xor")},
+ {QLatin1String("__or__"), QLatin1String("nb_or")},
+ {QLatin1String("__iadd__"), QLatin1String("nb_inplace_add")},
+ {QLatin1String("__isub__"), QLatin1String("nb_inplace_subtract")},
+ {QLatin1String("__imul__"), QLatin1String("nb_inplace_multiply")},
+ {QLatin1String("__idiv__"), QLatin1String("nb_inplace_divide")},
+ {QLatin1String("__imod__"), QLatin1String("nb_inplace_remainder")},
+ {QLatin1String("__ilshift__"), QLatin1String("nb_inplace_lshift")},
+ {QLatin1String("__irshift__"), QLatin1String("nb_inplace_rshift")},
+ {QLatin1String("__iand__"), QLatin1String("nb_inplace_and")},
+ {QLatin1String("__ixor__"), QLatin1String("nb_inplace_xor")},
+ {QLatin1String("__ior__"), QLatin1String("nb_inplace_or")},
+ {boolT(), QLatin1String("nb_nonzero")}
+ };
+ return result;
}
void CppGenerator::writeTypeAsNumberDefinition(TextStream &s, const AbstractMetaClass *metaClass) const
{
QMap<QString, QString> nb;
- nb.insert(QLatin1String("__add__"), QString());
- nb.insert(QLatin1String("__sub__"), QString());
- nb.insert(QLatin1String("__mul__"), QString());
- nb.insert(QLatin1String("__div__"), QString());
- nb.insert(QLatin1String("__mod__"), QString());
- nb.insert(QLatin1String("__neg__"), QString());
- nb.insert(QLatin1String("__pos__"), QString());
- nb.insert(QLatin1String("__invert__"), QString());
- nb.insert(QLatin1String("__lshift__"), QString());
- nb.insert(QLatin1String("__rshift__"), QString());
- nb.insert(QLatin1String("__and__"), QString());
- nb.insert(QLatin1String("__xor__"), QString());
- nb.insert(QLatin1String("__or__"), QString());
- nb.insert(QLatin1String("__iadd__"), QString());
- nb.insert(QLatin1String("__isub__"), QString());
- nb.insert(QLatin1String("__imul__"), QString());
- nb.insert(QLatin1String("__idiv__"), QString());
- nb.insert(QLatin1String("__imod__"), QString());
- nb.insert(QLatin1String("__ilshift__"), QString());
- nb.insert(QLatin1String("__irshift__"), QString());
- nb.insert(QLatin1String("__iand__"), QString());
- nb.insert(QLatin1String("__ixor__"), QString());
- nb.insert(QLatin1String("__ior__"), QString());
-
const QList<AbstractMetaFunctionList> opOverloads =
filterGroupedOperatorFunctions(metaClass,
AbstractMetaClass::ArithmeticOp
@@ -4468,27 +4500,29 @@ void CppGenerator::writeTypeAsNumberDefinition(TextStream &s, const AbstractMeta
QString baseName = cpythonBaseName(metaClass);
if (hasBoolCast(metaClass))
- nb.insert(QLatin1String("bool"), baseName + QLatin1String("___nb_bool"));
+ nb.insert(boolT(), baseName + QLatin1String("___nb_bool"));
- for (QHash<QString, QString>::const_iterator it = m_nbFuncs.cbegin(), end = m_nbFuncs.cend(); it != end; ++it) {
+ for (auto it = nbFuncs().cbegin(), end = nbFuncs().cend(); it != end; ++it) {
const QString &nbName = it.key();
- if (nb[nbName].isEmpty())
- continue;
-
- if (nbName == QLatin1String("bool")) {
- s << "{Py_nb_bool, (void *)" << nb[nbName] << "},\n";
- } else {
- bool excludeFromPy3K = nbName == QLatin1String("__div__") || nbName == QLatin1String("__idiv__");
- if (!excludeFromPy3K)
- s << "{Py_" << it.value() << ", (void *)" << nb[nbName] << "},\n";
+ if (nbName == QLatin1String("__div__") || nbName == QLatin1String("__idiv__"))
+ continue; // excludeFromPy3K
+ const auto nbIt = nb.constFind(nbName);
+ if (nbIt != nb.constEnd()) {
+ const QString fixednbName = nbName == boolT()
+ ? QLatin1String("nb_bool") : it.value();
+ s << "{Py_" << fixednbName << ", reinterpret_cast<void *>("
+ << nbIt.value() << ")},\n";
}
}
- if (!nb[QLatin1String("__div__")].isEmpty())
- s << "{Py_nb_true_divide, (void *)" << nb[QLatin1String("__div__")] << "},\n";
- if (!nb[QLatin1String("__idiv__")].isEmpty()) {
+ auto nbIt = nb.constFind(QLatin1String("__div__"));
+ if (nbIt != nb.constEnd())
+ s << "{Py_nb_true_divide, reinterpret_cast<void *>(" << nbIt.value() << ")},\n";
+
+ nbIt = nb.constFind(QLatin1String("__idiv__"));
+ if (nbIt != nb.constEnd()) {
s << "// This function is unused in Python 3. We reference it here.\n"
- << "{0, (void *)" << nb[QLatin1String("__idiv__")] << "},\n"
+ << "{0, reinterpret_cast<void *>(" << nbIt.value() << ")},\n"
<< "// This list is ending at the first 0 entry.\n"
<< "// Therefore, we need to put the unused functions at the very end.\n";
}
@@ -6413,7 +6447,7 @@ QString CppGenerator::writeReprFunction(TextStream &s,
uint indirections) const
{
const AbstractMetaClass *metaClass = context.metaClass();
- QString funcName = cpythonBaseName(metaClass) + QLatin1String("__repr__");
+ QString funcName = cpythonBaseName(metaClass) + reprFunction();
s << "extern \"C\"\n{\n"
<< "static PyObject *" << funcName << "(PyObject *self)\n{\n" << indent;
writeCppSelfDefinition(s, context);