diff options
author | Friedemann Kleint <Friedemann.Kleint@qt.io> | 2021-09-06 11:49:35 +0200 |
---|---|---|
committer | Friedemann Kleint <Friedemann.Kleint@qt.io> | 2021-09-09 20:06:23 +0200 |
commit | 47885c3c9d1ca4eb13daf79a0f6c73c8fce350cc (patch) | |
tree | eed3cfe07669d40431178287f43d191e3bcec15e | |
parent | aec162c77194898eb04fff83036e8157db3eb051 (diff) |
shiboken6: Split out node classes from OverloadData
OverloadData represents a tree, the root node of which has
the list of all functions and a list of children, which represent
an argument/type combination.
This was all in one class, where it was unclear which member function
or member variable was applicable to the node type.
To fix this, split out a root node class and an argument node class.
Rename nextOverloadData() to children() and previousOverloadData()
to parent() to make the relationship clearer.
Task-number: PYSIDE-1653
Change-Id: Ife63e78604bc42c08cc8cd0056d1c810060ba886
Reviewed-by: Christian Tismer <tismer@stackless.com>
-rw-r--r-- | sources/shiboken6/generator/shiboken/cppgenerator.cpp | 80 | ||||
-rw-r--r-- | sources/shiboken6/generator/shiboken/cppgenerator.h | 10 | ||||
-rw-r--r-- | sources/shiboken6/generator/shiboken/overloaddata.cpp | 477 | ||||
-rw-r--r-- | sources/shiboken6/generator/shiboken/overloaddata.h | 155 |
4 files changed, 409 insertions, 313 deletions
diff --git a/sources/shiboken6/generator/shiboken/cppgenerator.cpp b/sources/shiboken6/generator/shiboken/cppgenerator.cpp index aac949459..bc173d8a6 100644 --- a/sources/shiboken6/generator/shiboken/cppgenerator.cpp +++ b/sources/shiboken6/generator/shiboken/cppgenerator.cpp @@ -2467,15 +2467,16 @@ static void checkTypeViability(const AbstractMetaFunctionCPtr &func) checkTypeViability(func, func->arguments().at(i).type(), i + 1); } -void CppGenerator::writeTypeCheck(TextStream &s, const OverloadData *overloadData, +void CppGenerator::writeTypeCheck(TextStream &s, + const QSharedPointer<OverloadDataNode> &overloadData, const QString &argumentName) const { QSet<const TypeEntry *> numericTypes; - const OverloadDataList &overloads = overloadData->previousOverloadData()->nextOverloadData(); - for (OverloadData *od : overloads) { - for (const auto &func : od->overloads()) { + const OverloadDataList &siblings = overloadData->parent()->children(); + for (const auto &sibling : siblings) { + for (const auto &func : sibling->overloads()) { checkTypeViability(func); - const AbstractMetaType &argType = od->argument(func)->type(); + const AbstractMetaType &argType = sibling->argument(func)->type(); if (!argType.isPrimitive()) continue; if (ShibokenGenerator::isNumber(argType.typeEntry())) @@ -2779,7 +2780,7 @@ void CppGenerator::writeOverloadedFunctionDecisor(TextStream &s, const OverloadD s << decl->name() << "::"; s << func->signatureComment() << '\n'; } - writeOverloadedFunctionDecisorEngine(s, &overloadData); + writeOverloadedFunctionDecisorEngine(s, overloadData, &overloadData); s << '\n'; // Ensure that the direct overload that called this reverse @@ -2800,10 +2801,11 @@ void CppGenerator::writeOverloadedFunctionDecisor(TextStream &s, const OverloadD } void CppGenerator::writeOverloadedFunctionDecisorEngine(TextStream &s, - const OverloadData *parentOverloadData) const + const OverloadData &overloadData, + const OverloadDataRootNode *node) const { - bool hasDefaultCall = parentOverloadData->nextArgumentHasDefaultValue(); - auto referenceFunction = parentOverloadData->referenceFunction(); + bool hasDefaultCall = node->nextArgumentHasDefaultValue(); + auto referenceFunction = node->referenceFunction(); // If the next argument has not an argument with a default value, it is still possible // that one of the overloads for the current overload data has its final occurrence here. @@ -2811,8 +2813,8 @@ void CppGenerator::writeOverloadedFunctionDecisorEngine(TextStream &s, // variable to be used further on this method on the conditional that identifies default // method calls. if (!hasDefaultCall) { - for (const auto &func : parentOverloadData->overloads()) { - if (parentOverloadData->isFinalOccurrence(func)) { + for (const auto &func : node->overloads()) { + if (node->isFinalOccurrence(func)) { referenceFunction = func; hasDefaultCall = true; break; @@ -2820,13 +2822,13 @@ void CppGenerator::writeOverloadedFunctionDecisorEngine(TextStream &s, } } - int maxArgs = parentOverloadData->maxArgs(); + const int maxArgs = overloadData.maxArgs(); // Python constructors always receive multiple arguments. - const bool usePyArgs = parentOverloadData->pythonFunctionWrapperUsesListOfArguments(); + const bool usePyArgs = overloadData.pythonFunctionWrapperUsesListOfArguments(); // Functions without arguments are identified right away. if (maxArgs == 0) { - s << "overloadId = " << parentOverloadData->headOverloadData()->overloads().indexOf(referenceFunction) + s << "overloadId = " << overloadData.functionNumber(referenceFunction) << "; // " << referenceFunction->minimalSignature() << '\n'; return; @@ -2834,15 +2836,15 @@ void CppGenerator::writeOverloadedFunctionDecisorEngine(TextStream &s, // To decide if a method call is possible at this point the current overload // data object cannot be the head, since it is just an entry point, or a root, // for the tree of arguments and it does not represent a valid method call. - if (!parentOverloadData->isHeadOverloadData()) { - bool isLastArgument = parentOverloadData->nextOverloadData().isEmpty(); - bool signatureFound = parentOverloadData->overloads().size() == 1; + if (!node->isRoot()) { + const bool isLastArgument = node->children().isEmpty(); + const bool signatureFound = node->overloads().size() == 1; // The current overload data describes the last argument of a signature, // so the method can be identified right now. if (isLastArgument || (signatureFound && !hasDefaultCall)) { - const auto func = parentOverloadData->referenceFunction(); - s << "overloadId = " << parentOverloadData->headOverloadData()->overloads().indexOf(func) + const auto func = node->referenceFunction(); + s << "overloadId = " << overloadData.functionNumber(func) << "; // " << func->minimalSignature() << '\n'; return; } @@ -2853,40 +2855,40 @@ void CppGenerator::writeOverloadedFunctionDecisorEngine(TextStream &s, // If the next argument has a default value the decisor can perform a method call; // it just need to check if the number of arguments received from Python are equal // to the number of parameters preceding the argument with the default value. - const OverloadDataList &overloads = parentOverloadData->nextOverloadData(); + const OverloadDataList &children = node->children(); if (hasDefaultCall) { isFirst = false; - int numArgs = parentOverloadData->argPos() + 1; + int numArgs = node->argPos() + 1; s << "if (numArgs == " << numArgs << ") {\n"; { Indentation indent(s); auto func = referenceFunction; - for (OverloadData *overloadData : overloads) { - const auto defValFunc = overloadData->getFunctionWithDefaultValue(); + for (const auto &child : children) { + const auto defValFunc = child->getFunctionWithDefaultValue(); if (!defValFunc.isNull()) { func = defValFunc; break; } } - s << "overloadId = " << parentOverloadData->headOverloadData()->overloads().indexOf(func) + s << "overloadId = " << overloadData.functionNumber(func) << "; // " << func->minimalSignature() << '\n'; } s << '}'; } - for (OverloadData *overloadData : overloads) { - bool signatureFound = overloadData->overloads().size() == 1 - && !overloadData->getFunctionWithDefaultValue() - && !overloadData->findNextArgWithDefault(); + for (auto child : children) { + bool signatureFound = child->overloads().size() == 1 + && !child->getFunctionWithDefaultValue() + && !child->findNextArgWithDefault(); - const auto refFunc = overloadData->referenceFunction(); + const auto refFunc = child->referenceFunction(); QStringList typeChecks; QString pyArgName = (usePyArgs && maxArgs > 1) - ? pythonArgsAt(overloadData->argPos()) + ? pythonArgsAt(child->argPos()) : QLatin1String(PYTHON_ARG); - OverloadData *od = overloadData; + auto od = child; int startArg = od->argPos(); int sequenceArgCount = 0; while (od && !od->argType().isVarargs()) { @@ -2913,14 +2915,14 @@ void CppGenerator::writeOverloadedFunctionDecisorEngine(TextStream &s, sequenceArgCount++; - if (od->nextOverloadData().isEmpty() + if (od->children().isEmpty() || od->nextArgumentHasDefaultValue() - || od->nextOverloadData().size() != 1 - || od->overloads().size() != od->nextOverloadData().constFirst()->overloads().size()) { - overloadData = od; + || od->children().size() != 1 + || od->overloads().size() != od->children().constFirst()->overloads().size()) { + child = od; od = nullptr; } else { - od = od->nextOverloadData().constFirst(); + od = od->children().constFirst(); } } @@ -2958,7 +2960,7 @@ void CppGenerator::writeOverloadedFunctionDecisorEngine(TextStream &s, s << ") {\n"; { Indentation indent(s); - writeOverloadedFunctionDecisorEngine(s, overloadData); + writeOverloadedFunctionDecisorEngine(s, overloadData, child.data()); } s << "}"; } @@ -4922,8 +4924,8 @@ void CppGenerator::writeRichCompareFunction(TextStream &s, bool first = true; OverloadData overloadData(overloads, api()); - const OverloadDataList &nextOverloads = overloadData.nextOverloadData(); - for (OverloadData *od : nextOverloads) { + const OverloadDataList &nextOverloads = overloadData.children(); + for (const auto &od : nextOverloads) { const auto func = od->referenceFunction(); if (func->isStatic()) continue; diff --git a/sources/shiboken6/generator/shiboken/cppgenerator.h b/sources/shiboken6/generator/shiboken/cppgenerator.h index b1628ff8b..a2e977545 100644 --- a/sources/shiboken6/generator/shiboken/cppgenerator.h +++ b/sources/shiboken6/generator/shiboken/cppgenerator.h @@ -32,6 +32,11 @@ #include "shibokengenerator.h" #include "abstractmetalang_enums.h" +#include <QtCore/QSharedPointer> + +class OverloadDataNode; +class OverloadDataRootNode; + /** * The CppGenerator generate the implementations of C++ bindings classes. */ @@ -121,7 +126,7 @@ private: void writeTypeCheck(TextStream &s, AbstractMetaType argType, const QString &argumentName, bool isNumber = false, const QString &customType = QString(), bool rejectNull = false) const; - void writeTypeCheck(TextStream& s, const OverloadData *overloadData, + void writeTypeCheck(TextStream& s, const QSharedPointer<OverloadDataNode> &overloadData, const QString &argumentName) const; static void writeTypeDiscoveryFunction(TextStream &s, const AbstractMetaClass *metaClass); @@ -204,7 +209,8 @@ private: void writeOverloadedFunctionDecisor(TextStream &s, const OverloadData &overloadData) const; /// Recursive auxiliar method to the other writeOverloadedFunctionDecisor. void writeOverloadedFunctionDecisorEngine(TextStream &s, - const OverloadData *parentOverloadData) const; + const OverloadData &overloadData, + const OverloadDataRootNode *node) const; /// Writes calls to all the possible method/function overloads. void writeFunctionCalls(TextStream &s, diff --git a/sources/shiboken6/generator/shiboken/overloaddata.cpp b/sources/shiboken6/generator/shiboken/overloaddata.cpp index 2a1acad9a..137a37aeb 100644 --- a/sources/shiboken6/generator/shiboken/overloaddata.cpp +++ b/sources/shiboken6/generator/shiboken/overloaddata.cpp @@ -70,7 +70,7 @@ static QString getTypeName(const AbstractMetaType &type) return typeName; } -static QString getTypeName(const OverloadData *ov) +static QString getTypeName(const OverloadDataNodePtr &ov) { return ov->hasArgumentTypeReplace() ? ov->argumentTypeReplaced() : getTypeName(ov->argType()); } @@ -145,19 +145,19 @@ static QString msgCyclicDependency(const QString &funcName, const QString &graph return result; } -static inline int overloadNumber(const OverloadData *o) +static inline int overloadNumber(const OverloadDataNodePtr &o) { return o->referenceFunction()->overloadNumber(); } -bool OverloadData::sortByOverloadNumberModification() +static bool sortByOverloadNumberModification(OverloadDataList &list) { - if (std::all_of(m_nextOverloadData.cbegin(), m_nextOverloadData.cend(), - [](const OverloadData *o) { return overloadNumber(o) == TypeSystem::OverloadNumberDefault; })) { + if (std::all_of(list.cbegin(), list.cend(), + [](const OverloadDataNodePtr &o) { return overloadNumber(o) == TypeSystem::OverloadNumberDefault; })) { return false; } - std::stable_sort(m_nextOverloadData.begin(), m_nextOverloadData.end(), - [] (const OverloadData *o1, const OverloadData *o2) { + std::stable_sort(list.begin(), list.end(), + [] (const OverloadDataNodePtr &o1, const OverloadDataNodePtr &o2) { return overloadNumber(o1) < overloadNumber(o2); }); return true; @@ -175,7 +175,7 @@ using OverloadGraph = Graph<QString>; * * Side effects: Modifies m_nextOverloadData */ -void OverloadData::sortNextOverloads() +void OverloadDataRootNode::sortNextOverloads(const ApiExtractorResult &api) { QHash<QString, OverloadDataList> typeToOverloads; @@ -193,10 +193,10 @@ void OverloadData::sortNextOverloads() static const QStringList signedIntegerPrimitives{intT(), shortT(), longT(), longLongT()}; // sort the children overloads - for (OverloadData *ov : qAsConst(m_nextOverloadData)) - ov->sortNextOverloads(); + for (const auto &ov : qAsConst(m_children)) + ov->sortNextOverloads(api); - if (m_nextOverloadData.size() <= 1 || sortByOverloadNumberModification()) + if (m_children.size() <= 1 || sortByOverloadNumberModification(m_children)) return; // Populates the OverloadSortData object containing map and reverseMap, to map type names to ids, @@ -204,7 +204,7 @@ void OverloadData::sortNextOverloads() // with graph sorting using integers. OverloadGraph graph; - for (OverloadData *ov : qAsConst(m_nextOverloadData)) { + for (const auto &ov : qAsConst(m_children)) { const QString typeName = getTypeName(ov); auto it = typeToOverloads.find(typeName); if (it == typeToOverloads.end()) { @@ -238,7 +238,7 @@ void OverloadData::sortNextOverloads() for (const QString &primitive : qAsConst(nonIntegerPrimitives)) graph.addNode(getImplicitConversionTypeName(ov->argType(), instantiation, nullptr, primitive)); } else { - const auto &funcs = m_api.implicitConversions(instantiation); + const auto &funcs = api.implicitConversions(instantiation); for (const auto &function : funcs) graph.addNode(getImplicitConversionTypeName(ov->argType(), instantiation, function)); } @@ -265,12 +265,12 @@ void OverloadData::sortNextOverloads() AbstractMetaFunctionCList involvedConversions; - for (OverloadData *ov : qAsConst(m_nextOverloadData)) { + for (const auto &ov : qAsConst(m_children)) { const AbstractMetaType &targetType = ov->argType(); const QString targetTypeEntryName = getTypeName(ov); // Process implicit conversions - const auto &functions = m_api.implicitConversions(targetType); + const auto &functions = api.implicitConversions(targetType); for (const auto &function : functions) { QString convertibleType; if (function->isConversionOperator()) @@ -293,7 +293,7 @@ void OverloadData::sortNextOverloads() // Process inheritance relationships if (targetType.isValue() || targetType.isObject()) { - auto metaClass = AbstractMetaClass::findClass(m_api.classes(), + auto metaClass = AbstractMetaClass::findClass(api.classes(), targetType.typeEntry()); const AbstractMetaClassList &ancestors = metaClass->allTypeSystemAncestors(); for (const AbstractMetaClass *ancestor : ancestors) { @@ -322,7 +322,7 @@ void OverloadData::sortNextOverloads() } } else { - const auto &funcs = m_api.implicitConversions(instantiation); + const auto &funcs = api.implicitConversions(instantiation); for (const auto &function : funcs) { QString convertibleTypeName = getImplicitConversionTypeName(ov->argType(), instantiation, function); @@ -373,7 +373,7 @@ void OverloadData::sortNextOverloads() if (graph.hasNode(qStringT()) && graph.hasNode(qByteArrayT())) graph.addEdge(qStringT(), qByteArrayT()); - for (OverloadData *ov : qAsConst(m_nextOverloadData)) { + for (const auto &ov : qAsConst(m_children)) { const AbstractMetaType &targetType = ov->argType(); if (!targetType.isEnum()) continue; @@ -399,8 +399,8 @@ void OverloadData::sortNextOverloads() const auto unmappedResult = graph.topologicalSort(); if (!unmappedResult.isValid()) { QString funcName = referenceFunction()->name(); - if (referenceFunction()->ownerClass()) - funcName.prepend(referenceFunction()->ownerClass()->name() + QLatin1Char('.')); + if (auto owner = referenceFunction()->ownerClass()) + funcName.prepend(owner->name() + QLatin1Char('.')); // Dump overload graph QString graphName = QDir::tempPath() + QLatin1Char('/') + funcName + QLatin1String(".dot"); @@ -414,12 +414,12 @@ void OverloadData::sortNextOverloads() qCWarning(lcShiboken, "%s", qPrintable(msgCyclicDependency(funcName, graphName, cyclic, involvedConversions))); } - m_nextOverloadData.clear(); + m_children.clear(); for (const auto &typeName : unmappedResult.result) { const auto oit = typeToOverloads.constFind(typeName); if (oit != typeToOverloads.cend()) { std::copy(oit.value().crbegin(), oit.value().crend(), - std::back_inserter(m_nextOverloadData)); + std::back_inserter(m_children)); } } } @@ -443,11 +443,16 @@ static std::pair<int, int> getMinMaxArgs(const AbstractMetaFunctionCPtr &func) return {minArgs, maxArgs}; } +const OverloadDataRootNode *OverloadDataNode::parent() const +{ + return m_parent; +} + /** * Root constructor for OverloadData * * This constructor receives the list of overloads for a given function and iterates generating - * the graph of OverloadData instances. Each OverloadData instance references an argument/type + * the graph of OverloadData instances. Each OverloadDataNode instance references an argument/type * combination. * * Example: @@ -461,8 +466,8 @@ static std::pair<int, int> getMinMaxArgs(const AbstractMetaFunctionCPtr &func) * */ OverloadData::OverloadData(const AbstractMetaFunctionCList &overloads, - const ApiExtractorResult &api) - : m_argType(), m_overloads(overloads), m_headOverloadData(this), m_api(api) + const ApiExtractorResult &api) : + OverloadDataRootNode(overloads) { for (const auto &func : overloads) { const auto minMaxArgs = getMinMaxArgs(func); @@ -470,49 +475,52 @@ OverloadData::OverloadData(const AbstractMetaFunctionCList &overloads, m_minArgs = minMaxArgs.first; if (minMaxArgs.second > m_maxArgs) m_maxArgs = minMaxArgs.second; - OverloadData *currentOverloadData = this; + OverloadDataRootNode *currentOverloadData = this; const AbstractMetaArgumentList &arguments = func->arguments(); for (const AbstractMetaArgument &arg : arguments) { if (func->argumentRemoved(arg.argumentIndex() + 1)) continue; - currentOverloadData = currentOverloadData->addOverloadData(func, arg); + currentOverloadData = currentOverloadData->addOverloadDataNode(func, arg); } } // Sort the overload possibilities so that the overload decisor code goes for the most // important cases first, based on the topological order of the implicit conversions - sortNextOverloads(); + sortNextOverloads(api); } -OverloadData::OverloadData(OverloadData *headOverloadData, const AbstractMetaFunctionCPtr &func, - const AbstractMetaType &argType, int argPos, - const ApiExtractorResult &api) : - m_argType(argType), m_headOverloadData(headOverloadData), m_api(api), +OverloadDataNode::OverloadDataNode(const AbstractMetaFunctionCPtr &func, + OverloadDataRootNode *parent, + const AbstractMetaType &argType, int argPos, + const QString argTypeReplaced) : + m_argType(argType), + m_argTypeReplaced(argTypeReplaced), + m_parent(parent), m_argPos(argPos) { if (func) this->addOverload(func); } -void OverloadData::addOverload(const AbstractMetaFunctionCPtr &func) +void OverloadDataNode::addOverload(const AbstractMetaFunctionCPtr &func) { m_overloads.append(func); } -OverloadData *OverloadData::addOverloadData(const AbstractMetaFunctionCPtr &func, - const AbstractMetaArgument &arg) +OverloadDataNode *OverloadDataRootNode::addOverloadDataNode(const AbstractMetaFunctionCPtr &func, + const AbstractMetaArgument &arg) { const AbstractMetaType &argType = arg.type(); - OverloadData *overloadData = nullptr; + OverloadDataNodePtr overloadData; if (!func->isOperatorOverload()) { - for (OverloadData *tmp : qAsConst(m_nextOverloadData)) { + for (const auto &tmp : qAsConst(m_children)) { // TODO: 'const char *', 'char *' and 'char' will have the same TypeEntry? // If an argument have a type replacement, then we should create a new overloaddata // for it, unless the next argument also have a identical type replacement. - QString replacedArg = func->typeReplaced(tmp->m_argPos + 1); - bool argsReplaced = !replacedArg.isEmpty() || !tmp->m_argTypeReplaced.isEmpty(); - if ((!argsReplaced && typesAreEqual(tmp->m_argType, argType)) + QString replacedArg = func->typeReplaced(tmp->argPos() + 1); + bool argsReplaced = !replacedArg.isEmpty() || tmp->hasArgumentTypeReplace(); + if ((!argsReplaced && typesAreEqual(tmp->argType(), argType)) || (argsReplaced && replacedArg == tmp->argumentTypeReplaced())) { tmp->addOverload(func); overloadData = tmp; @@ -520,17 +528,15 @@ OverloadData *OverloadData::addOverloadData(const AbstractMetaFunctionCPtr &func } } - if (!overloadData) { - overloadData = new OverloadData(m_headOverloadData, func, argType, m_argPos + 1, m_api); - overloadData->m_previousOverloadData = this; + if (overloadData.isNull()) { QString typeReplaced = func->typeReplaced(arg.argumentIndex() + 1); - - if (!typeReplaced.isEmpty()) - overloadData->m_argTypeReplaced = typeReplaced; - m_nextOverloadData.append(overloadData); + const int argpos = argPos() + 1; + overloadData.reset(new OverloadDataNode(func, this, argType, argpos, + typeReplaced)); + m_children.append(overloadData); } - return overloadData; + return overloadData.data(); } bool OverloadData::hasNonVoidReturnType() const @@ -622,14 +628,21 @@ bool OverloadData::hasStaticAndInstanceFunctions() const return OverloadData::hasStaticFunction() && OverloadData::hasInstanceFunction(); } -AbstractMetaFunctionCPtr OverloadData::referenceFunction() const +OverloadDataRootNode::OverloadDataRootNode(const AbstractMetaFunctionCList &o) : + m_overloads(o) +{ +} + +OverloadDataRootNode::~OverloadDataRootNode() = default; + +AbstractMetaFunctionCPtr OverloadDataRootNode::referenceFunction() const { return m_overloads.constFirst(); } -const AbstractMetaArgument *OverloadData::argument(const AbstractMetaFunctionCPtr &func) const +const AbstractMetaArgument *OverloadDataNode::argument(const AbstractMetaFunctionCPtr &func) const { - if (isHeadOverloadData() || !m_overloads.contains(func)) + if (isRoot() || !m_overloads.contains(func)) return nullptr; int argPos = 0; @@ -644,53 +657,54 @@ const AbstractMetaArgument *OverloadData::argument(const AbstractMetaFunctionCPt return &func->arguments().at(m_argPos + removed); } -bool OverloadData::nextArgumentHasDefaultValue() const +bool OverloadDataRootNode::nextArgumentHasDefaultValue() const { - for (OverloadData *overloadData : m_nextOverloadData) { + for (const auto &overloadData : m_children) { if (!overloadData->getFunctionWithDefaultValue().isNull()) return true; } return false; } -static OverloadData *_findNextArgWithDefault(OverloadData *overloadData) +static const OverloadDataRootNode *_findNextArgWithDefault(const OverloadDataRootNode *overloadData) { if (!overloadData->getFunctionWithDefaultValue().isNull()) return overloadData; - OverloadData *result = nullptr; - const OverloadDataList &data = overloadData->nextOverloadData(); - for (OverloadData *odata : data) { - OverloadData *tmp = _findNextArgWithDefault(odata); + const OverloadDataRootNode *result = nullptr; + const OverloadDataList &data = overloadData->children(); + for (const auto &odata : data) { + const auto *tmp = _findNextArgWithDefault(odata.data()); if (!result || (tmp && result->argPos() > tmp->argPos())) result = tmp; } return result; } -OverloadData *OverloadData::findNextArgWithDefault() +const OverloadDataRootNode *OverloadDataRootNode::findNextArgWithDefault() { return _findNextArgWithDefault(this); } -bool OverloadData::isFinalOccurrence(const AbstractMetaFunctionCPtr &func) const +bool OverloadDataRootNode::isFinalOccurrence(const AbstractMetaFunctionCPtr &func) const { - for (const OverloadData *pd : m_nextOverloadData) { + for (const auto &pd : m_children) { if (pd->overloads().contains(func)) return false; } return true; } -AbstractMetaFunctionCPtr OverloadData::getFunctionWithDefaultValue() const +AbstractMetaFunctionCPtr OverloadDataRootNode::getFunctionWithDefaultValue() const { + const int argpos = argPos(); for (const auto &func : m_overloads) { int removedArgs = 0; - for (int i = 0; i <= m_argPos + removedArgs; i++) { + for (int i = 0; i <= argpos + removedArgs; i++) { if (func->argumentRemoved(i + 1)) removedArgs++; } - if (func->arguments().at(m_argPos + removedArgs).hasDefaultValueExpression()) + if (func->arguments().at(argpos + removedArgs).hasDefaultValueExpression()) return func; } return {}; @@ -700,7 +714,7 @@ QList<int> OverloadData::invalidArgumentLengths() const { QSet<int> validArgLengths; - for (const auto &func : qAsConst(m_headOverloadData->m_overloads)) { + for (const auto &func : m_overloads) { const AbstractMetaArgumentList args = func->arguments(); int offset = 0; for (int i = 0; i < args.size(); ++i) { @@ -715,7 +729,7 @@ QList<int> OverloadData::invalidArgumentLengths() const } QList<int> invalidArgLengths; - for (int i = minArgs() + 1; i < maxArgs(); i++) { + for (int i = m_minArgs + 1; i < m_maxArgs; i++) { if (!validArgLengths.contains(i)) invalidArgLengths.append(i); } @@ -760,11 +774,19 @@ void OverloadData::dumpGraph(const QString &filename) const { QFile file(filename); if (file.open(QFile::WriteOnly)) { - TextStream s(&file); - s << m_headOverloadData->dumpGraph(); + QTextStream s(&file); + dumpRootGraph(s, m_minArgs, m_maxArgs); } } +QString OverloadData::dumpGraph() const +{ + QString result; + QTextStream s(&result); + dumpRootGraph(s, m_minArgs, m_maxArgs); + return result; +} + static inline QString toHtml(QString s) { s.replace(QLatin1Char('<'), QLatin1String("<")); @@ -773,140 +795,136 @@ static inline QString toHtml(QString s) return s; } -QString OverloadData::dumpGraph() const +void OverloadDataRootNode::dumpRootGraph(QTextStream &s, int minArgs, int maxArgs) const { - QString result; - QTextStream s(&result); - if (m_argPos == -1) { - const auto rfunc = referenceFunction(); - s << "digraph OverloadedFunction {\n"; - s << " graph [fontsize=12 fontname=freemono labelloc=t splines=true overlap=false rankdir=LR];\n"; - - // Shows all function signatures - s << "legend [fontsize=9 fontname=freemono shape=rect label=\""; - for (const auto &func : m_overloads) { - s << "f" << functionNumber(func) << " : " - << toHtml(func->type().cppSignature()) - << ' ' << toHtml(func->minimalSignature()) << "\\l"; - } - s << "\"];\n"; - - // Function box title - s << " \"" << rfunc->name() << "\" [shape=plaintext style=\"filled,bold\" margin=0 fontname=freemono fillcolor=white penwidth=1 "; - s << "label=<<table border=\"0\" cellborder=\"0\" cellpadding=\"3\" bgcolor=\"white\">"; - s << "<tr><td bgcolor=\"black\" align=\"center\" cellpadding=\"6\" colspan=\"2\"><font color=\"white\">"; - if (rfunc->ownerClass()) - s << rfunc->ownerClass()->name() << "::"; - s << toHtml(rfunc->name()) << "</font>"; - if (rfunc->isVirtual()) { - s << "<br/><font color=\"white\" point-size=\"10\"><<"; - if (rfunc->isAbstract()) - s << "pure "; - s << "virtual>></font>"; - } - s << "</td></tr>"; - - // Function return type - s << "<tr><td bgcolor=\"gray\" align=\"right\">original type</td><td bgcolor=\"gray\" align=\"left\">" - << toHtml(rfunc->type().cppSignature()) - << "</td></tr>"; + const auto rfunc = referenceFunction(); + s << "digraph OverloadedFunction {\n"; + s << " graph [fontsize=12 fontname=freemono labelloc=t splines=true overlap=false rankdir=LR];\n"; - // Shows type changes for all function signatures - for (const auto &func : m_overloads) { - if (func->typeReplaced(0).isEmpty()) - continue; - s << "<tr><td bgcolor=\"gray\" align=\"right\">f" << functionNumber(func); - s << "-type</td><td bgcolor=\"gray\" align=\"left\">"; - s << toHtml(func->typeReplaced(0)) << "</td></tr>"; - } + // Shows all function signatures + s << "legend [fontsize=9 fontname=freemono shape=rect label=\""; + for (const auto &func : m_overloads) { + s << "f" << functionNumber(func) << " : " + << toHtml(func->type().cppSignature()) + << ' ' << toHtml(func->minimalSignature()) << "\\l"; + } + s << "\"];\n"; + + // Function box title + s << " \"" << rfunc->name() << "\" [shape=plaintext style=\"filled,bold\" margin=0 fontname=freemono fillcolor=white penwidth=1 "; + s << "label=<<table border=\"0\" cellborder=\"0\" cellpadding=\"3\" bgcolor=\"white\">"; + s << "<tr><td bgcolor=\"black\" align=\"center\" cellpadding=\"6\" colspan=\"2\"><font color=\"white\">"; + if (rfunc->ownerClass()) + s << rfunc->ownerClass()->name() << "::"; + s << toHtml(rfunc->name()) << "</font>"; + if (rfunc->isVirtual()) { + s << "<br/><font color=\"white\" point-size=\"10\"><<"; + if (rfunc->isAbstract()) + s << "pure "; + s << "virtual>></font>"; + } + s << "</td></tr>"; - // Minimum and maximum number of arguments - s << "<tr><td bgcolor=\"gray\" align=\"right\">minArgs</td><td bgcolor=\"gray\" align=\"left\">"; - s << minArgs() << "</td></tr>"; - s << "<tr><td bgcolor=\"gray\" align=\"right\">maxArgs</td><td bgcolor=\"gray\" align=\"left\">"; - s << maxArgs() << "</td></tr>"; - - if (rfunc->ownerClass()) { - if (rfunc->implementingClass() != rfunc->ownerClass()) - s << "<tr><td align=\"right\">implementor</td><td align=\"left\">" << rfunc->implementingClass()->name() << "</td></tr>"; - if (rfunc->declaringClass() != rfunc->ownerClass() && rfunc->declaringClass() != rfunc->implementingClass()) - s << "<tr><td align=\"right\">declarator</td><td align=\"left\">" << rfunc->declaringClass()->name() << "</td></tr>"; - } + // Function return type + s << "<tr><td bgcolor=\"gray\" align=\"right\">original type</td><td bgcolor=\"gray\" align=\"left\">" + << toHtml(rfunc->type().cppSignature()) + << "</td></tr>"; - // Overloads for the signature to present point - s << "<tr><td bgcolor=\"gray\" align=\"right\">overloads</td><td bgcolor=\"gray\" align=\"left\">"; - for (const auto &func : m_overloads) - s << 'f' << functionNumber(func) << ' '; - s << "</td></tr>"; + // Shows type changes for all function signatures + for (const auto &func : m_overloads) { + if (func->typeReplaced(0).isEmpty()) + continue; + s << "<tr><td bgcolor=\"gray\" align=\"right\">f" << functionNumber(func); + s << "-type</td><td bgcolor=\"gray\" align=\"left\">"; + s << toHtml(func->typeReplaced(0)) << "</td></tr>"; + } - s << "</table>> ];\n"; + // Minimum and maximum number of arguments + s << "<tr><td bgcolor=\"gray\" align=\"right\">minArgs</td><td bgcolor=\"gray\" align=\"left\">"; + s << minArgs << "</td></tr>"; + s << "<tr><td bgcolor=\"gray\" align=\"right\">maxArgs</td><td bgcolor=\"gray\" align=\"left\">"; + s << maxArgs << "</td></tr>"; + + if (rfunc->ownerClass()) { + if (rfunc->implementingClass() != rfunc->ownerClass()) + s << "<tr><td align=\"right\">implementor</td><td align=\"left\">" << rfunc->implementingClass()->name() << "</td></tr>"; + if (rfunc->declaringClass() != rfunc->ownerClass() && rfunc->declaringClass() != rfunc->implementingClass()) + s << "<tr><td align=\"right\">declarator</td><td align=\"left\">" << rfunc->declaringClass()->name() << "</td></tr>"; + } - for (const OverloadData *pd : m_nextOverloadData) - s << " \"" << rfunc->name() << "\" -> " << pd->dumpGraph(); + // Overloads for the signature to present point + s << "<tr><td bgcolor=\"gray\" align=\"right\">overloads</td><td bgcolor=\"gray\" align=\"left\">"; + for (const auto &func : m_overloads) + s << 'f' << functionNumber(func) << ' '; + s << "</td></tr>"; - s << "}\n"; - } else { - QString argId = QLatin1String("arg_") + QString::number(quintptr(this)); - s << argId << ";\n"; + s << "</table>> ];\n"; - s << " \"" << argId << "\" [shape=\"plaintext\" style=\"filled,bold\" margin=\"0\" fontname=\"freemono\" fillcolor=\"white\" penwidth=1 "; - s << "label=<<table border=\"0\" cellborder=\"0\" cellpadding=\"3\" bgcolor=\"white\">"; + for (const auto &pd : m_children) { + s << " \"" << rfunc->name() << "\" -> "; + pd->dumpNodeGraph(s); + } - // Argument box title - s << "<tr><td bgcolor=\"black\" align=\"left\" cellpadding=\"2\" colspan=\"2\">"; - s << "<font color=\"white\" point-size=\"11\">arg #" << argPos() << "</font></td></tr>"; + s << "}\n"; +} - // Argument type information - QString type = hasArgumentTypeReplace() ? argumentTypeReplaced() : argType().cppSignature(); - s << "<tr><td bgcolor=\"gray\" align=\"right\">type</td><td bgcolor=\"gray\" align=\"left\">"; - s << toHtml(type) << "</td></tr>"; - if (hasArgumentTypeReplace()) { - s << "<tr><td bgcolor=\"gray\" align=\"right\">orig. type</td><td bgcolor=\"gray\" align=\"left\">"; - s << toHtml(argType().cppSignature()) << "</td></tr>"; - } +void OverloadDataNode::dumpNodeGraph(QTextStream &s) const +{ + QString argId = QLatin1String("arg_") + QString::number(quintptr(this)); + s << argId << ";\n"; + + s << " \"" << argId << "\" [shape=\"plaintext\" style=\"filled,bold\" margin=\"0\" fontname=\"freemono\" fillcolor=\"white\" penwidth=1 "; + s << "label=<<table border=\"0\" cellborder=\"0\" cellpadding=\"3\" bgcolor=\"white\">"; + + // Argument box title + s << "<tr><td bgcolor=\"black\" align=\"left\" cellpadding=\"2\" colspan=\"2\">"; + s << "<font color=\"white\" point-size=\"11\">arg #" << argPos() << "</font></td></tr>"; + + // Argument type information + QString type = hasArgumentTypeReplace() ? argumentTypeReplaced() : argType().cppSignature(); + s << "<tr><td bgcolor=\"gray\" align=\"right\">type</td><td bgcolor=\"gray\" align=\"left\">"; + s << toHtml(type) << "</td></tr>"; + if (hasArgumentTypeReplace()) { + s << "<tr><td bgcolor=\"gray\" align=\"right\">orig. type</td><td bgcolor=\"gray\" align=\"left\">"; + s << toHtml(argType().cppSignature()) << "</td></tr>"; + } - // Overloads for the signature to present point - s << "<tr><td bgcolor=\"gray\" align=\"right\">overloads</td><td bgcolor=\"gray\" align=\"left\">"; - for (const auto &func : m_overloads) - s << 'f' << functionNumber(func) << ' '; - s << "</td></tr>"; + // Overloads for the signature to present point + s << "<tr><td bgcolor=\"gray\" align=\"right\">overloads</td><td bgcolor=\"gray\" align=\"left\">"; + for (const auto &func : m_overloads) + s << 'f' << functionNumber(func) << ' '; + s << "</td></tr>"; - // Show default values (original and modified) for various functions - for (const auto &func : m_overloads) { - const AbstractMetaArgument *arg = argument(func); - if (!arg) - continue; - QString argDefault = arg->defaultValueExpression(); - if (!argDefault.isEmpty() || - argDefault != arg->originalDefaultValueExpression()) { - s << "<tr><td bgcolor=\"gray\" align=\"right\">f" << functionNumber(func); - s << "-default</td><td bgcolor=\"gray\" align=\"left\">"; - s << argDefault << "</td></tr>"; - } - if (argDefault != arg->originalDefaultValueExpression()) { - s << "<tr><td bgcolor=\"gray\" align=\"right\">f" << functionNumber(func); - s << "-orig-default</td><td bgcolor=\"gray\" align=\"left\">"; - s << arg->originalDefaultValueExpression() << "</td></tr>"; - } + // Show default values (original and modified) for various functions + for (const auto &func : m_overloads) { + const AbstractMetaArgument *arg = argument(func); + if (!arg) + continue; + QString argDefault = arg->defaultValueExpression(); + if (!argDefault.isEmpty() || + argDefault != arg->originalDefaultValueExpression()) { + s << "<tr><td bgcolor=\"gray\" align=\"right\">f" << functionNumber(func); + s << "-default</td><td bgcolor=\"gray\" align=\"left\">"; + s << argDefault << "</td></tr>"; + } + if (argDefault != arg->originalDefaultValueExpression()) { + s << "<tr><td bgcolor=\"gray\" align=\"right\">f" << functionNumber(func); + s << "-orig-default</td><td bgcolor=\"gray\" align=\"left\">"; + s << arg->originalDefaultValueExpression() << "</td></tr>"; } + } - s << "</table>>];\n"; + s << "</table>>];\n"; - for (const OverloadData *pd : m_nextOverloadData) - s << " " << argId << " -> " << pd->dumpGraph(); + for (const auto &pd : m_children) { + s << " " << argId << " -> "; + pd->dumpNodeGraph(s); } - return result; -} - -int OverloadData::functionNumber(const AbstractMetaFunctionCPtr &func) const -{ - return m_headOverloadData->m_overloads.indexOf(func); } -OverloadData::~OverloadData() +int OverloadDataRootNode::functionNumber(const AbstractMetaFunctionCPtr &func) const { - while (!m_nextOverloadData.isEmpty()) - delete m_nextOverloadData.takeLast(); + return m_overloads.indexOf(func); } bool OverloadData::pythonFunctionWrapperUsesListOfArguments() const @@ -924,16 +942,6 @@ bool OverloadData::pythonFunctionWrapperUsesListOfArguments() const || hasArgumentWithDefaultValue(); } -bool OverloadData::hasArgumentTypeReplace() const -{ - return !m_argTypeReplaced.isEmpty(); -} - -QString OverloadData::argumentTypeReplaced() const -{ - return m_argTypeReplaced; -} - bool OverloadData::hasArgumentWithDefaultValue() const { if (maxArgs() == 0) @@ -971,9 +979,9 @@ AbstractMetaArgumentList OverloadData::getArgumentsWithDefaultValues(const Abstr } #ifndef QT_NO_DEBUG_STREAM -void OverloadData::formatDebug(QDebug &d) const + +void OverloadDataRootNode::formatReferenceFunction(QDebug &d) const { - const qsizetype count = m_overloads.size(); auto refFunc = referenceFunction(); d << '"'; if (auto owner = refFunc->ownerClass()) @@ -981,36 +989,73 @@ void OverloadData::formatDebug(QDebug &d) const d << refFunc->minimalSignature() << '"'; if (m_overloads.constFirst()->isReverseOperator()) d << " [reverseop]"; - d << ", argType=" << m_argType << ", minArgs=" << m_minArgs << ", maxArgs=" << m_maxArgs - << ", argPos=" << m_argPos; - if (!m_argTypeReplaced.isEmpty()) - d << ", argTypeReplaced=\"" << m_argTypeReplaced << '"'; +} +void OverloadDataRootNode::formatOverloads(QDebug &d) const +{ + const qsizetype count = m_overloads.size(); + d << ", overloads[" << count << ']'; if (count < 2) return; - d << "\", overloads[" << count << "]=("; - const int oldVerbosity = d.verbosity(); - d.setVerbosity(3); - for (int i = 0; i < count; ++i) { - if (i) - d << '\n'; - d << m_overloads.at(i).data(); - } - d.setVerbosity(oldVerbosity); - d << ')'; + d << "=("; + for (int i = 0; i < count; ++i) { + if (i) + d << '\n'; + d << m_overloads.at(i)->signature(); + } + d << ')'; } -QDebug operator<<(QDebug d, const OverloadData *od) +void OverloadDataRootNode::formatNextOverloadData(QDebug &d) const +{ + const qsizetype count = m_children.size(); + d << ", next[" << count << ']'; + if (d.verbosity() >= 3) { + d << "=("; + for (int i = 0; i < count; ++i) { + if (i) + d << '\n'; + m_children.at(i)->formatDebug(d); + } + d << ')'; + } +} + +void OverloadDataRootNode::formatDebug(QDebug &d) const +{ + formatReferenceFunction(d); + formatOverloads(d); + formatNextOverloadData(d); +} + +void OverloadDataNode::formatDebug(QDebug &d) const +{ + d << "OverloadDataNode("; + formatReferenceFunction(d); + d << ", argType=" << m_argType << ", argPos=" << m_argPos; + if (!m_argTypeReplaced.isEmpty()) + d << ", argTypeReplaced=\"" << m_argTypeReplaced << '"'; + formatOverloads(d); + formatNextOverloadData(d); + d << ')'; +} + +void OverloadData::formatDebug(QDebug &d) const +{ + d << "OverloadData("; + formatReferenceFunction(d); + d << ", minArgs=" << m_minArgs << ", maxArgs=" << m_maxArgs; + formatOverloads(d); + formatNextOverloadData(d); + d << ')'; +} + +QDebug operator<<(QDebug d, const OverloadData &od) { QDebugStateSaver saver(d); d.noquote(); d.nospace(); - d << "OverloadData("; - if (od) - od->formatDebug(d); - else - d << '0'; - d << ')'; + od.formatDebug(d); return d; } #endif // !QT_NO_DEBUG_STREAM diff --git a/sources/shiboken6/generator/shiboken/overloaddata.h b/sources/shiboken6/generator/shiboken/overloaddata.h index d9c5bd24c..fb367b259 100644 --- a/sources/shiboken6/generator/shiboken/overloaddata.h +++ b/sources/shiboken6/generator/shiboken/overloaddata.h @@ -33,25 +33,113 @@ #include <QtCore/QBitArray> #include <QtCore/QList> +#include <QtCore/QSharedPointer> QT_FORWARD_DECLARE_CLASS(QDebug) +QT_FORWARD_DECLARE_CLASS(QTextStream) -class OverloadData; -using OverloadDataList = QList<OverloadData *>; +class OverloadDataNode; +using OverloadDataNodePtr = QSharedPointer<OverloadDataNode>; +using OverloadDataList = QList<OverloadDataNodePtr>; -class OverloadData +/// The root node of OverloadData. It contains all functions +class OverloadDataRootNode { public: - OverloadData(const AbstractMetaFunctionCList &overloads, - const ApiExtractorResult &api); - ~OverloadData(); + virtual ~OverloadDataRootNode(); - int minArgs() const { return m_headOverloadData->m_minArgs; } - int maxArgs() const { return m_headOverloadData->m_maxArgs; } - int argPos() const { return m_argPos; } + OverloadDataRootNode(const OverloadDataRootNode &) = delete; + OverloadDataRootNode &operator=(const OverloadDataRootNode &) = delete; + OverloadDataRootNode(OverloadDataRootNode &&) = delete; + OverloadDataRootNode &operator=(OverloadDataRootNode &&) = delete; + + virtual int argPos() const { return -1; } + virtual const OverloadDataRootNode *parent() const { return nullptr; } + + bool isRoot() const { return parent() == nullptr; } + + AbstractMetaFunctionCPtr referenceFunction() const; + + const AbstractMetaFunctionCList &overloads() const { return m_overloads; } + const OverloadDataList &children() const { return m_children; } + + bool nextArgumentHasDefaultValue() const; + + /// Returns the function that has a default value at the current OverloadData argument position, otherwise returns null. + AbstractMetaFunctionCPtr getFunctionWithDefaultValue() const; + + /// Returns the nearest occurrence, including this instance, of an argument with a default value. + const OverloadDataRootNode *findNextArgWithDefault(); + bool isFinalOccurrence(const AbstractMetaFunctionCPtr &func) const; + + int functionNumber(const AbstractMetaFunctionCPtr &func) const; + +#ifndef QT_NO_DEBUG_STREAM + virtual void formatDebug(QDebug &d) const; +#endif + + OverloadDataNode *addOverloadDataNode(const AbstractMetaFunctionCPtr &func, + const AbstractMetaArgument &arg); + +protected: + OverloadDataRootNode(const AbstractMetaFunctionCList &o= {}); + + void dumpRootGraph(QTextStream &s, int minArgs, int maxArgs) const; + void sortNextOverloads(const ApiExtractorResult &api); + + +#ifndef QT_NO_DEBUG_STREAM + void formatReferenceFunction(QDebug &d) const; + void formatOverloads(QDebug &d) const; + void formatNextOverloadData(QDebug &d) const; +#endif + + AbstractMetaFunctionCList m_overloads; + OverloadDataList m_children; +}; + +/// OverloadDataNode references an argument/type combination. +class OverloadDataNode : public OverloadDataRootNode +{ +public: + explicit OverloadDataNode(const AbstractMetaFunctionCPtr &func, + OverloadDataRootNode *parent, + const AbstractMetaType &argType, int argPos, + const QString argTypeReplaced = {}); + void addOverload(const AbstractMetaFunctionCPtr &func); + + int argPos() const override { return m_argPos; } + const OverloadDataRootNode *parent() const override; + void dumpNodeGraph(QTextStream &s) const; const AbstractMetaType &argType() const { return m_argType; } + bool hasArgumentTypeReplace() const { return !m_argTypeReplaced.isEmpty(); } + const QString &argumentTypeReplaced() const { return m_argTypeReplaced; } + + const AbstractMetaArgument *argument(const AbstractMetaFunctionCPtr &func) const; + +#ifndef QT_NO_DEBUG_STREAM + void formatDebug(QDebug &d) const override; +#endif + +private: + AbstractMetaType m_argType; + QString m_argTypeReplaced; + OverloadDataRootNode *m_parent = nullptr; + + int m_argPos = -1; +}; + +class OverloadData : public OverloadDataRootNode +{ +public: + explicit OverloadData(const AbstractMetaFunctionCList &overloads, + const ApiExtractorResult &api); + + int minArgs() const { return m_minArgs; } + int maxArgs() const { return m_maxArgs; } + /// Returns true if any of the overloads for the current OverloadData has a return type different from void. bool hasNonVoidReturnType() const; @@ -82,27 +170,6 @@ public: /// Returns true if among the overloads passed as argument there are static and non-static methods altogether. static bool hasStaticAndInstanceFunctions(const AbstractMetaFunctionCList &overloads); - AbstractMetaFunctionCPtr referenceFunction() const; - const AbstractMetaArgument *argument(const AbstractMetaFunctionCPtr &func) const; - OverloadDataList overloadDataOnPosition(int argPos) const; - - bool isHeadOverloadData() const { return this == m_headOverloadData; } - - /// Returns the root OverloadData object that represents all the overloads. - OverloadData *headOverloadData() const { return m_headOverloadData; } - - /// Returns the function that has a default value at the current OverloadData argument position, otherwise returns null. - AbstractMetaFunctionCPtr getFunctionWithDefaultValue() const; - - bool nextArgumentHasDefaultValue() const; - /// Returns the nearest occurrence, including this instance, of an argument with a default value. - OverloadData *findNextArgWithDefault(); - bool isFinalOccurrence(const AbstractMetaFunctionCPtr &func) const; - - const AbstractMetaFunctionCList &overloads() const { return m_overloads; } - OverloadDataList nextOverloadData() const { return m_nextOverloadData; } - OverloadData *previousOverloadData() const { return m_previousOverloadData; } - QList<int> invalidArgumentLengths() const; static int numberOfRemovedArguments(const AbstractMetaFunctionCPtr &func); @@ -116,9 +183,6 @@ public: /// Returns true if a list of arguments is used (METH_VARARGS) bool pythonFunctionWrapperUsesListOfArguments() const; - bool hasArgumentTypeReplace() const; - QString argumentTypeReplaced() const; - bool hasArgumentWithDefaultValue() const; static bool hasArgumentWithDefaultValue(const AbstractMetaFunctionCPtr &func); @@ -126,37 +190,16 @@ public: static AbstractMetaArgumentList getArgumentsWithDefaultValues(const AbstractMetaFunctionCPtr &func); #ifndef QT_NO_DEBUG_STREAM - void formatDebug(QDebug &) const; + void formatDebug(QDebug &) const override; #endif private: - OverloadData(OverloadData *headOverloadData, const AbstractMetaFunctionCPtr &func, - const AbstractMetaType &argType, int argPos, - const ApiExtractorResult &api); - - void addOverload(const AbstractMetaFunctionCPtr &func); - OverloadData *addOverloadData(const AbstractMetaFunctionCPtr &func, const AbstractMetaArgument &arg); - - void sortNextOverloads(); - bool sortByOverloadNumberModification(); - - int functionNumber(const AbstractMetaFunctionCPtr &func) const; - - AbstractMetaType m_argType; - QString m_argTypeReplaced; - AbstractMetaFunctionCList m_overloads; - - OverloadData *m_headOverloadData = nullptr; - OverloadDataList m_nextOverloadData; - OverloadData *m_previousOverloadData = nullptr; - const ApiExtractorResult m_api; int m_minArgs = 256; int m_maxArgs = 0; - int m_argPos = -1; }; #ifndef QT_NO_DEBUG_STREAM -QDebug operator<<(QDebug, const OverloadData *); +QDebug operator<<(QDebug, const OverloadData &); #endif #endif // OVERLOADDATA_H |