From c0c8b1be35973fbbc3328603bd3164d73cdd2858 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Mon, 25 Mar 2024 20:26:43 -0700 Subject: [PATCH] CBOR: de-inline some comparesEqual() and compareThreeWay() functions This is the first step in optimizing the comparisons by avoiding the conversions in user code. Thus, we don't de-inline the homogeneous compareThreeWay() functions. This is done with an extra level of indirection by adding static *_helper() functions, which have the advantage of being members and thus benefit from the class' friendships. And it allows us to pass QCborValueConstRef by value. Change-Id: I5f663c2f9f4149af84fefffd17c032b32eff7a4e Reviewed-by: Ivan Solovev --- src/corelib/serialization/qcborarray.h | 31 +++++++--- src/corelib/serialization/qcbormap.h | 29 +++++---- src/corelib/serialization/qcborvalue.cpp | 78 +++++++++++++++++++++++- src/corelib/serialization/qcborvalue.h | 34 ++++++++--- 4 files changed, 140 insertions(+), 32 deletions(-) diff --git a/src/corelib/serialization/qcborarray.h b/src/corelib/serialization/qcborarray.h index 777321a747..f70dd44425 100644 --- a/src/corelib/serialization/qcborarray.h +++ b/src/corelib/serialization/qcborarray.h @@ -229,10 +229,8 @@ public: QJsonArray toJsonArray() const; private: - friend bool comparesEqual(const QCborArray &lhs, const QCborArray &rhs) noexcept - { - return lhs.compare(rhs) == 0; - } + friend Q_CORE_EXPORT Q_DECL_PURE_FUNCTION bool + comparesEqual(const QCborArray &lhs, const QCborArray &rhs) noexcept; friend Qt::strong_ordering compareThreeWay(const QCborArray &lhs, const QCborArray &rhs) noexcept { @@ -241,16 +239,35 @@ private: } Q_DECLARE_STRONGLY_ORDERED(QCborArray) + static Q_DECL_PURE_FUNCTION bool + comparesEqual_helper(const QCborArray &lhs, const QCborValue &rhs) noexcept; + static Q_DECL_PURE_FUNCTION Qt::strong_ordering + compareThreeWay_helper(const QCborArray &lhs, const QCborValue &rhs) noexcept; + friend bool comparesEqual(const QCborArray &lhs, + const QCborValue &rhs) noexcept + { + return comparesEqual_helper(lhs, rhs); + } + friend Qt::strong_ordering compareThreeWay(const QCborArray &lhs, + const QCborValue &rhs) noexcept + { + return compareThreeWay_helper(lhs, rhs); + } + Q_DECLARE_STRONGLY_ORDERED(QCborArray, QCborValue) + + static Q_DECL_PURE_FUNCTION bool + comparesEqual_helper(const QCborArray &lhs, QCborValueConstRef rhs) noexcept; + static Q_DECL_PURE_FUNCTION Qt::strong_ordering + compareThreeWay_helper(const QCborArray &lhs, QCborValueConstRef rhs) noexcept; friend bool comparesEqual(const QCborArray &lhs, const QCborValueConstRef &rhs) noexcept { - return lhs.compare(rhs.toArray()) == 0; + return comparesEqual_helper(lhs, rhs); } friend Qt::strong_ordering compareThreeWay(const QCborArray &lhs, const QCborValueConstRef &rhs) noexcept { - const int c = lhs.compare(rhs.toArray()); - return Qt::compareThreeWay(c, 0); + return compareThreeWay_helper(lhs, rhs); } Q_DECLARE_STRONGLY_ORDERED(QCborArray, QCborValueConstRef) diff --git a/src/corelib/serialization/qcbormap.h b/src/corelib/serialization/qcbormap.h index 087334fdff..d83d27ff1d 100644 --- a/src/corelib/serialization/qcbormap.h +++ b/src/corelib/serialization/qcbormap.h @@ -300,10 +300,8 @@ private: friend class QJsonPrivate::Variant; void detach(qsizetype reserve = 0); - friend bool comparesEqual(const QCborMap &lhs, const QCborMap &rhs) noexcept - { - return lhs.compare(rhs) == 0; - } + friend Q_CORE_EXPORT Q_DECL_PURE_FUNCTION bool + comparesEqual(const QCborMap &lhs, const QCborMap &rhs) noexcept; friend Qt::strong_ordering compareThreeWay(const QCborMap &lhs, const QCborMap &rhs) noexcept { @@ -312,30 +310,35 @@ private: } Q_DECLARE_STRONGLY_ORDERED(QCborMap) + static Q_DECL_PURE_FUNCTION bool + comparesEqual_helper(const QCborMap &lhs, const QCborValue &rhs) noexcept; + static Q_DECL_PURE_FUNCTION Qt::strong_ordering + compareThreeWay_helper(const QCborMap &lhs, const QCborValue &rhs) noexcept; friend bool comparesEqual(const QCborMap &lhs, const QCborValue &rhs) noexcept { - return lhs.compare(rhs.toMap()) == 0; + return comparesEqual_helper(lhs, rhs); } - friend Qt::strong_ordering compareThreeWay(const QCborMap &lhs, const QCborValue &rhs) noexcept { - int c = lhs.compare(rhs.toMap()); - return Qt::compareThreeWay(c, 0); + return compareThreeWay_helper(lhs, rhs); } Q_DECLARE_STRONGLY_ORDERED(QCborMap, QCborValue) - friend bool comparesEqual(const QCborMap &lhs, const QCborValueConstRef &rhs) noexcept + static Q_DECL_PURE_FUNCTION bool + comparesEqual_helper(const QCborMap &lhs, QCborValueConstRef rhs) noexcept; + static Q_DECL_PURE_FUNCTION Qt::strong_ordering + compareThreeWay_helper(const QCborMap &lhs, QCborValueConstRef rhs) noexcept; + friend bool comparesEqual(const QCborMap &lhs, + const QCborValueConstRef &rhs) noexcept { - return lhs.compare(rhs.toMap()) == 0; + return comparesEqual_helper(lhs, rhs); } - friend Qt::strong_ordering compareThreeWay(const QCborMap &lhs, const QCborValueConstRef &rhs) noexcept { - int c = lhs.compare(rhs.toMap()); - return Qt::compareThreeWay(c, 0); + return compareThreeWay_helper(lhs, rhs); } Q_DECLARE_STRONGLY_ORDERED(QCborMap, QCborValueConstRef) diff --git a/src/corelib/serialization/qcborvalue.cpp b/src/corelib/serialization/qcborvalue.cpp index 07150e5d8c..d6e352cb35 100644 --- a/src/corelib/serialization/qcborvalue.cpp +++ b/src/corelib/serialization/qcborvalue.cpp @@ -1395,16 +1395,50 @@ int QCborValue::compare(const QCborValue &other) const return compareElementRecursive(container, e1, other.container, e2); } +bool comparesEqual(const QCborArray &lhs, const QCborArray &rhs) noexcept +{ + return lhs.compare(rhs) == 0; +} + int QCborArray::compare(const QCborArray &other) const noexcept { return compareContainer(d.data(), other.d.data()); } +bool QCborArray::comparesEqual_helper(const QCborArray &lhs, const QCborValue &rhs) noexcept +{ + return lhs.compare(rhs.toArray()) == 0; +} + +Qt::strong_ordering +QCborArray::compareThreeWay_helper(const QCborArray &lhs, const QCborValue &rhs) noexcept +{ + int c = lhs.compare(rhs.toArray()); + return Qt::compareThreeWay(c, 0); +} + +bool comparesEqual(const QCborMap &lhs, const QCborMap &rhs) noexcept +{ + return lhs.compare(rhs) == 0; +} + int QCborMap::compare(const QCborMap &other) const noexcept { return compareContainer(d.data(), other.d.data()); } +bool QCborMap::comparesEqual_helper(const QCborMap &lhs, const QCborValue &rhs) noexcept +{ + return lhs.compare(rhs.toMap()) == 0; +} + +Qt::strong_ordering +QCborMap::compareThreeWay_helper(const QCborMap &lhs, const QCborValue &rhs) noexcept +{ + int c = lhs.compare(rhs.toMap()); + return Qt::compareThreeWay(c, 0); +} + #if QT_CONFIG(cborstreamwriter) static void encodeToCbor(QCborStreamWriter &writer, const QCborContainerPrivate *d, qsizetype idx, QCborValue::EncodingOptions opt) @@ -2744,16 +2778,56 @@ QString QCborValueConstRef::concreteString(QCborValueConstRef self, const QStrin return self.d->stringAt(self.i); } -bool comparesEqual(const QCborValueConstRef &lhs, const QCborValueConstRef &rhs) noexcept +bool +QCborValueConstRef::comparesEqual_helper(QCborValueConstRef lhs, QCborValueConstRef rhs) noexcept { return lhs.compare(rhs.concrete()) == 0; } -bool comparesEqual(const QCborValueConstRef &lhs, const QCborValue &rhs) noexcept +Qt::strong_ordering +QCborValueConstRef::compareThreeWay_helper(QCborValueConstRef lhs, QCborValueConstRef rhs) noexcept +{ + int c = lhs.concrete().compare(rhs.concrete()); + return Qt::compareThreeWay(c, 0); +} + +bool +QCborValueConstRef::comparesEqual_helper(QCborValueConstRef lhs, const QCborValue &rhs) noexcept { return lhs.compare(rhs) == 0; } +Qt::strong_ordering +QCborValueConstRef::compareThreeWay_helper(QCborValueConstRef lhs, const QCborValue &rhs) noexcept +{ + int c = lhs.concrete().compare(rhs); + return Qt::compareThreeWay(c, 0); +} + +bool QCborArray::comparesEqual_helper(const QCborArray &lhs, QCborValueConstRef rhs) noexcept +{ + return lhs.compare(rhs.toArray()) == 0; +} + +Qt::strong_ordering +QCborArray::compareThreeWay_helper(const QCborArray &lhs, QCborValueConstRef rhs) noexcept +{ + int c = lhs.compare(rhs.toArray()); + return Qt::compareThreeWay(c, 0); +} + +bool QCborMap::comparesEqual_helper(const QCborMap &lhs, QCborValueConstRef rhs) noexcept +{ + return lhs.compare(rhs.toMap()) == 0; +} + +Qt::strong_ordering +QCborMap::compareThreeWay_helper(const QCborMap &lhs, QCborValueConstRef rhs) noexcept +{ + int c = lhs.compare(rhs.toMap()); + return Qt::compareThreeWay(c, 0); +} + QCborValue QCborValueConstRef::concrete(QCborValueConstRef self) noexcept { return self.d->valueAt(self.i); diff --git a/src/corelib/serialization/qcborvalue.h b/src/corelib/serialization/qcborvalue.h index 58013130b8..bb2c3ac0c5 100644 --- a/src/corelib/serialization/qcborvalue.h +++ b/src/corelib/serialization/qcborvalue.h @@ -249,8 +249,8 @@ public: QString toDiagnosticNotation(DiagnosticNotationOptions opts = Compact) const; private: - friend Q_CORE_EXPORT bool comparesEqual(const QCborValue &lhs, - const QCborValue &rhs) noexcept; + friend Q_CORE_EXPORT Q_DECL_PURE_FUNCTION + bool comparesEqual(const QCborValue &lhs, const QCborValue &rhs) noexcept; friend Qt::strong_ordering compareThreeWay(const QCborValue &lhs, const QCborValue &rhs) noexcept { @@ -389,24 +389,38 @@ protected: friend class QCborContainerPrivate; QCborValue concrete() const noexcept { return concrete(*this); } - friend Q_CORE_EXPORT bool comparesEqual(const QCborValueConstRef &lhs, - const QCborValueConstRef &rhs) noexcept; + static Q_CORE_EXPORT Q_DECL_PURE_FUNCTION bool + comparesEqual_helper(QCborValueConstRef lhs, QCborValueConstRef rhs) noexcept; + static Q_CORE_EXPORT Q_DECL_PURE_FUNCTION Qt::strong_ordering + compareThreeWay_helper(QCborValueConstRef lhs, QCborValueConstRef rhs) noexcept; + friend bool comparesEqual(const QCborValueConstRef &lhs, + const QCborValueConstRef &rhs) noexcept + { + return comparesEqual_helper(lhs, rhs); + } friend Qt::strong_ordering compareThreeWay(const QCborValueConstRef &lhs, const QCborValueConstRef &rhs) noexcept { - int c = lhs.compare(rhs.concrete()); - return Qt::compareThreeWay(c, 0); + return compareThreeWay_helper(lhs, rhs); } Q_DECLARE_STRONGLY_ORDERED(QCborValueConstRef) - friend Q_CORE_EXPORT bool comparesEqual(const QCborValueConstRef &lhs, - const QCborValue &rhs) noexcept; + + static Q_CORE_EXPORT Q_DECL_PURE_FUNCTION bool + comparesEqual_helper(QCborValueConstRef lhs, const QCborValue &rhs) noexcept; + static Q_CORE_EXPORT Q_DECL_PURE_FUNCTION Qt::strong_ordering + compareThreeWay_helper(QCborValueConstRef lhs, const QCborValue &rhs) noexcept; + friend bool comparesEqual(const QCborValueConstRef &lhs, + const QCborValue &rhs) noexcept + { + return comparesEqual_helper(lhs, rhs); + } friend Qt::strong_ordering compareThreeWay(const QCborValueConstRef &lhs, const QCborValue &rhs) noexcept { - int c = lhs.compare(rhs); - return Qt::compareThreeWay(c, 0); + return compareThreeWay_helper(lhs, rhs); } Q_DECLARE_STRONGLY_ORDERED(QCborValueConstRef, QCborValue) + static Q_CORE_EXPORT QCborValue concrete(QCborValueConstRef that) noexcept; static Q_CORE_EXPORT QCborValue::Type concreteType(QCborValueConstRef that) noexcept Q_DECL_PURE_FUNCTION; static Q_CORE_EXPORT bool