diff --git a/src/network/access/qhttpheaders.cpp b/src/network/access/qhttpheaders.cpp index 5ad28b8920e..06f6368b7f5 100644 --- a/src/network/access/qhttpheaders.cpp +++ b/src/network/access/qhttpheaders.cpp @@ -94,6 +94,15 @@ public: }; QT_DEFINE_QESDP_SPECIALIZATION_DTOR(QHttpHeadersPrivate) +template <> void QExplicitlySharedDataPointer::detach() +{ + if (!d) { + d = new QHttpHeadersPrivate(); + d->ref.ref(); + } else if (d->ref.loadRelaxed() != 1) { + detach_helper(); + } +} // This list is from IANA HTTP Field Name Registry // https://www.iana.org/assignments/http-fields @@ -472,7 +481,7 @@ static constexpr auto headerNames = qOffsetStringArray( /*! Creates a new QHttpHeaders object. */ -QHttpHeaders::QHttpHeaders() : d(new QHttpHeadersPrivate) +QHttpHeaders::QHttpHeaders() noexcept : d() { } @@ -542,11 +551,8 @@ QHttpHeaders &QHttpHeaders::operator=(const QHttpHeaders &other) /*! \fn QHttpHeaders::QHttpHeaders(QHttpHeaders &&other) noexcept - Move-constructs the object from \a other. - - \note The moved-from object \a other is placed in a - partially-formed state, in which the only valid operations are - destruction and assignment of a new value. + Move-constructs the object from \a other, which will be left + \l{isEmpty()}{empty}. */ /*! @@ -554,9 +560,7 @@ QHttpHeaders &QHttpHeaders::operator=(const QHttpHeaders &other) Move-assigns \a other and returns a reference to this object. - \note The moved-from object \a other is placed in a - partially-formed state, in which the only valid operations are - destruction and assignment of a new value. + \a other will be left \l{isEmpty()}{empty}. */ /*! @@ -578,11 +582,14 @@ QDebug operator<<(QDebug debug, const QHttpHeaders &headers) const QDebugStateSaver saver(debug); debug.resetFormat().nospace(); - debug << "QHttpHeaders(headers = "; - const char *separator = ""; - for (const auto &h : headers.d->headers) { - debug << separator << h.name << ':' << h.value; - separator = " | "; + debug << "QHttpHeaders("; + if (headers.d) { + debug << "headers = "; + const char *separator = ""; + for (const auto &h : headers.d->headers) { + debug << separator << h.name << ':' << h.value; + separator = " | "; + } } debug << ")"; return debug; @@ -867,6 +874,8 @@ bool QHttpHeaders::replace(qsizetype i, WellKnownHeader name, QAnyStringView new */ bool QHttpHeaders::contains(QAnyStringView name) const { + if (!d) + return false; return std::any_of(d->headers.cbegin(), d->headers.cend(), [&name](const Header &header) { return headerNameIs(header, name); }); } @@ -924,6 +933,8 @@ void QHttpHeaders::removeAt(qsizetype i) */ QByteArrayView QHttpHeaders::value(QAnyStringView name, QByteArrayView defaultValue) const noexcept { + if (!d) + return defaultValue; for (const auto &h : std::as_const(d->headers)) { if (headerNameIs(h, name)) return h.value; @@ -948,6 +959,8 @@ QByteArrayView QHttpHeaders::value(WellKnownHeader name, QByteArrayView defaultV QList QHttpHeaders::values(QAnyStringView name) const { QList values; + if (!d) + return values; for (const auto &h : std::as_const(d->headers)) { if (headerNameIs(h, name)) values.append(h.value); @@ -1028,6 +1041,8 @@ QByteArray QHttpHeaders::combinedValue(WellKnownHeader name) const */ qsizetype QHttpHeaders::size() const noexcept { + if (!d) + return 0; return d->headers.size(); } @@ -1059,6 +1074,8 @@ QByteArrayView QHttpHeaders::wellKnownHeaderName(WellKnownHeader name) noexcept QList> QHttpHeaders::toListOfPairs() const { QList> list; + if (!d) + return list; list.reserve(size()); for (const auto & h : std::as_const(d->headers)) list.append({h.name, h.value}); @@ -1072,6 +1089,8 @@ QList> QHttpHeaders::toListOfPairs() const QMultiMap QHttpHeaders::toMultiMap() const { QMultiMap map; + if (!d) + return map; for (const auto &h : std::as_const(d->headers)) map.insert(h.name, h.value); return map; @@ -1084,6 +1103,8 @@ QMultiMap QHttpHeaders::toMultiMap() const QMultiHash QHttpHeaders::toMultiHash() const { QMultiHash hash; + if (!d) + return hash; hash.reserve(size()); for (const auto &h : std::as_const(d->headers)) hash.insert(h.name, h.value); diff --git a/src/network/access/qhttpheaders.h b/src/network/access/qhttpheaders.h index cd65ef5c33f..fb426eed809 100644 --- a/src/network/access/qhttpheaders.h +++ b/src/network/access/qhttpheaders.h @@ -201,7 +201,7 @@ public: }; Q_ENUM(WellKnownHeader) - Q_NETWORK_EXPORT QHttpHeaders(); + Q_NETWORK_EXPORT QHttpHeaders() noexcept; Q_NETWORK_EXPORT ~QHttpHeaders(); Q_NETWORK_EXPORT QHttpHeaders(const QHttpHeaders &other);