From 8948042bd049d08e7653f78b60951408603edb8c Mon Sep 17 00:00:00 2001 From: Julien Blanc Date: Thu, 13 Aug 2015 09:03:39 +0200 Subject: QString perf improvement : removal of useless test Removed a test in QStringAlgorithms trimmed_helper. That test is not needed because both null / empty QStrings are already handled by the previous test, other cases are handled just fine by the general case. Change-Id: I26db1142a656a7d06dfdd6b3b8f8a3ee6ca22302 Reviewed-by: Thiago Macieira --- src/corelib/tools/qstringalgorithms_p.h | 2 -- 1 file changed, 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qstringalgorithms_p.h b/src/corelib/tools/qstringalgorithms_p.h index 65901b0286..a12874f567 100644 --- a/src/corelib/tools/qstringalgorithms_p.h +++ b/src/corelib/tools/qstringalgorithms_p.h @@ -101,8 +101,6 @@ template struct QStringAlgorithms if (begin == str.cbegin() && end == str.cend()) return str; - if (begin == end) - return StringType(); if (!isConst && str.isDetached()) return trimmed_helper_inplace(str, begin, end); return StringType(begin, end - begin); -- cgit v1.2.3 From a8f4fa217daa1b6f7b13cc48c1e5ee8d2d76b008 Mon Sep 17 00:00:00 2001 From: Dmitry Shachnev Date: Sat, 22 Aug 2015 12:07:42 +0300 Subject: Add QLockFilePrivate::processNameByPid implementation for GNU/kFreeBSD GLIBC does not provide kinfo_getproc, so we need to call sysctl manually. Change-Id: I3bf22959ff74b3b6c34b5360738e52086a3ff1b4 Reviewed-by: Joerg Bornemann Reviewed-by: Oswald Buddenhagen --- src/corelib/io/qlockfile_unix.cpp | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/io/qlockfile_unix.cpp b/src/corelib/io/qlockfile_unix.cpp index 815c0f025b..5ff4b1cbe1 100644 --- a/src/corelib/io/qlockfile_unix.cpp +++ b/src/corelib/io/qlockfile_unix.cpp @@ -56,7 +56,13 @@ # include #elif defined(Q_OS_BSD4) && !defined(Q_OS_IOS) # include +# if defined(__GLIBC__) && defined(__FreeBSD_kernel__) +# include +# include +# include +# else # include +# endif #endif QT_BEGIN_NAMESPACE @@ -234,9 +240,27 @@ QString QLockFilePrivate::processNameByPid(qint64 pid) buf[len] = 0; return QFileInfo(QFile::decodeName(buf)).fileName(); #elif defined(Q_OS_BSD4) && !defined(Q_OS_IOS) +# if defined(__GLIBC__) && defined(__FreeBSD_kernel__) + int mib[4] = { CTL_KERN, KERN_PROC, KERN_PROC_PID, pid }; + size_t len = 0; + if (sysctl(mib, 4, NULL, &len, NULL, 0) < 0) + return QString(); + kinfo_proc *proc = static_cast(malloc(len)); +# else kinfo_proc *proc = kinfo_getproc(pid); +# endif if (!proc) return QString(); +# if defined(__GLIBC__) && defined(__FreeBSD_kernel__) + if (sysctl(mib, 4, proc, &len, NULL, 0) < 0) { + free(proc); + return QString(); + } + if (proc->ki_pid != pid) { + free(proc); + return QString(); + } +# endif QString name = QFile::decodeName(proc->ki_comm); free(proc); return name; -- cgit v1.2.3 From 97de58db672fe0489faba856fcfd59a125609796 Mon Sep 17 00:00:00 2001 From: Nico Vertriest Date: Fri, 21 Aug 2015 12:43:36 +0200 Subject: Doc: Added link to Declarative State Machine Framework Added link in C++ documentation Task-number: QTBUG-46285 Change-Id: I0f330829f7df713d4f5292b2a300c5c9d3732bda Reviewed-by: Venugopal Shivashankar --- src/corelib/doc/qtcore.qdocconf | 3 +-- src/corelib/doc/src/statemachine.qdoc | 2 ++ 2 files changed, 3 insertions(+), 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/doc/qtcore.qdocconf b/src/corelib/doc/qtcore.qdocconf index 502689e4c2..3d64708def 100644 --- a/src/corelib/doc/qtcore.qdocconf +++ b/src/corelib/doc/qtcore.qdocconf @@ -25,8 +25,7 @@ qhp.QtCore.subprojects.classes.sortPages = true tagfile = ../../../doc/qtcore/qtcore.tags -depends += activeqt qtdbus qtgui qtwidgets qtnetwork qtdoc qtmacextras qtquick qtlinguist qtdesigner qtconcurrent qtxml qmake qtwinextras -# depends += qtqml # Qt namespace collides with QtQml::Qt, see QTBUG-38630 +depends += activeqt qtdbus qtgui qtwidgets qtnetwork qtdoc qtmacextras qtquick qtlinguist qtdesigner qtconcurrent qtxml qmake qtwinextras qtqml headerdirs += .. diff --git a/src/corelib/doc/src/statemachine.qdoc b/src/corelib/doc/src/statemachine.qdoc index e44a603959..d50851d816 100644 --- a/src/corelib/doc/src/statemachine.qdoc +++ b/src/corelib/doc/src/statemachine.qdoc @@ -71,6 +71,8 @@ which are currently active. All the states in a valid configuration of the state machine will have a common ancestor. + \sa {The Declarative State Machine Framework} + \section1 Classes in the State Machine Framework These classes are provided by qt for creating event-driven state machines. -- cgit v1.2.3 From dfb55da5d67c21179ccef107351a90be2815e1e2 Mon Sep 17 00:00:00 2001 From: Nico Vertriest Date: Thu, 3 Sep 2015 14:40:21 +0200 Subject: Doc: Added enums in qnamespace.qdoc MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Task-number: QTBUG-43810 Change-Id: Ib756382833fabecaae2526a413d046646f3e443e Reviewed-by: Topi Reiniö Reviewed-by: Martin Smith --- src/corelib/global/qnamespace.qdoc | 11 +++++++++++ 1 file changed, 11 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/global/qnamespace.qdoc b/src/corelib/global/qnamespace.qdoc index c6098007d1..2323ee2cb0 100644 --- a/src/corelib/global/qnamespace.qdoc +++ b/src/corelib/global/qnamespace.qdoc @@ -1695,6 +1695,17 @@ \value Key_Sleep \value Key_Zoom \value Key_Cancel + \value Key_MicVolumeUp + \value Key_Find + \value Key_Open + \value Key_MicVolumeDown + \value Key_New + \value Key_Settings + \value Key_Redo + \value Key_Exit + \value Key_Info + \value Key_Undo + \value Key_Guide \sa QKeyEvent::key() */ -- cgit v1.2.3 From 9588e1bba348acf9aa0d023ebb5195aa1bf69909 Mon Sep 17 00:00:00 2001 From: Nico Vertriest Date: Tue, 7 Jul 2015 15:29:05 +0200 Subject: Doc: Corrected link issues in qtbase Task-number: QTBUG-43810 Change-Id: I0a019becc53b222cb6a7df1fafdccd57aca5b598 Reviewed-by: Martin Smith --- src/corelib/io/qtextstream.cpp | 2 +- src/corelib/kernel/qmetaobject.cpp | 5 +++-- 2 files changed, 4 insertions(+), 3 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qtextstream.cpp b/src/corelib/io/qtextstream.cpp index 8ad1c2852c..aa14f545ec 100644 --- a/src/corelib/io/qtextstream.cpp +++ b/src/corelib/io/qtextstream.cpp @@ -2858,7 +2858,7 @@ QTextStream &endl(QTextStream &stream) /*! \relates QTextStream - Calls \l{QTextStream::flush()}{flush()} on \a stream and returns \a stream. + Calls QTextStream::flush() on \a stream and returns \a stream. \sa endl(), reset(), {QTextStream manipulators} */ diff --git a/src/corelib/kernel/qmetaobject.cpp b/src/corelib/kernel/qmetaobject.cpp index 6858209b12..1ef5ee0547 100644 --- a/src/corelib/kernel/qmetaobject.cpp +++ b/src/corelib/kernel/qmetaobject.cpp @@ -1548,12 +1548,13 @@ bool QMetaObject::invokeMethod(QObject *obj, /*! \fn QMetaObject::Connection &QMetaObject::Connection::operator=(Connection &&other) - Move-assigns \a other to this object. + Move-assigns \a other to this object, and returns a reference. */ /*! \fn QMetaObject::Connection::Connection(Connection &&o) - Move-constructs a Connection instance, making it point to the same object that \a o was pointing to. + Move-constructs a Connection instance, making it point to the same object + that \a o was pointing to. */ /*! -- cgit v1.2.3 From 880a8aa7e99bb91e7a815cadde72bb5230c815ea Mon Sep 17 00:00:00 2001 From: David Faure Date: Wed, 26 Aug 2015 13:27:49 +0200 Subject: QMimeType: add KDAB copyright to the code I contributed a lot to. Change-Id: I794259f28c7adbaad3cfb40f92a0ad2dc512e5b4 Reviewed-by: Thiago Macieira --- src/corelib/mimetypes/qmimedatabase.cpp | 1 + src/corelib/mimetypes/qmimedatabase.h | 1 + src/corelib/mimetypes/qmimedatabase_p.h | 1 + src/corelib/mimetypes/qmimeprovider.cpp | 1 + src/corelib/mimetypes/qmimeprovider_p.h | 1 + src/corelib/mimetypes/qmimetype.cpp | 1 + src/corelib/mimetypes/qmimetype.h | 1 + 7 files changed, 7 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/mimetypes/qmimedatabase.cpp b/src/corelib/mimetypes/qmimedatabase.cpp index bec7a79e8f..1ef890c46a 100644 --- a/src/corelib/mimetypes/qmimedatabase.cpp +++ b/src/corelib/mimetypes/qmimedatabase.cpp @@ -1,6 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2015 The Qt Company Ltd. +** Copyright (C) 2015 Klaralvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author David Faure ** Contact: http://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. diff --git a/src/corelib/mimetypes/qmimedatabase.h b/src/corelib/mimetypes/qmimedatabase.h index 912d9b8443..fd19636e27 100644 --- a/src/corelib/mimetypes/qmimedatabase.h +++ b/src/corelib/mimetypes/qmimedatabase.h @@ -1,6 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2015 The Qt Company Ltd. +** Copyright (C) 2015 Klaralvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author David Faure ** Contact: http://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. diff --git a/src/corelib/mimetypes/qmimedatabase_p.h b/src/corelib/mimetypes/qmimedatabase_p.h index e3cfe3443f..aa86f607c6 100644 --- a/src/corelib/mimetypes/qmimedatabase_p.h +++ b/src/corelib/mimetypes/qmimedatabase_p.h @@ -1,6 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2015 The Qt Company Ltd. +** Copyright (C) 2015 Klaralvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author David Faure ** Contact: http://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. diff --git a/src/corelib/mimetypes/qmimeprovider.cpp b/src/corelib/mimetypes/qmimeprovider.cpp index 887db51e5c..d26bfd0848 100644 --- a/src/corelib/mimetypes/qmimeprovider.cpp +++ b/src/corelib/mimetypes/qmimeprovider.cpp @@ -1,6 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2015 The Qt Company Ltd. +** Copyright (C) 2015 Klaralvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author David Faure ** Contact: http://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. diff --git a/src/corelib/mimetypes/qmimeprovider_p.h b/src/corelib/mimetypes/qmimeprovider_p.h index eaf95942f7..c0517d69a4 100644 --- a/src/corelib/mimetypes/qmimeprovider_p.h +++ b/src/corelib/mimetypes/qmimeprovider_p.h @@ -1,6 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2015 The Qt Company Ltd. +** Copyright (C) 2015 Klaralvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author David Faure ** Contact: http://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. diff --git a/src/corelib/mimetypes/qmimetype.cpp b/src/corelib/mimetypes/qmimetype.cpp index a5f9cb70d5..5398f9358e 100644 --- a/src/corelib/mimetypes/qmimetype.cpp +++ b/src/corelib/mimetypes/qmimetype.cpp @@ -1,6 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2015 The Qt Company Ltd. +** Copyright (C) 2015 Klaralvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author David Faure ** Contact: http://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. diff --git a/src/corelib/mimetypes/qmimetype.h b/src/corelib/mimetypes/qmimetype.h index 4ba3c53470..13184905b8 100644 --- a/src/corelib/mimetypes/qmimetype.h +++ b/src/corelib/mimetypes/qmimetype.h @@ -1,6 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2015 The Qt Company Ltd. +** Copyright (C) 2015 Klaralvdalens Datakonsult AB, a KDAB Group company, info@kdab.com, author David Faure ** Contact: http://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. -- cgit v1.2.3 From 5e41f4137dd42a9a639be8743ae95c8e159bd4e0 Mon Sep 17 00:00:00 2001 From: David Faure Date: Tue, 25 Aug 2015 14:30:07 +0200 Subject: QMimeDatabase: warn instead of asserting on bad magic. An invalid mime magic definition could lead to an assert. Replaced with a qWarning. Move all checking to the QMimeMagicRule constructor, and do keep invalid rules since they are need to parse child rules. Unit test added, with QTest::ignoreMessage when using the XML backend (there's no warning from update-mime-database when using the cache). Also make it easier to add more shared mime info files for tests. Task-number: QTBUG-44319 Done-with: Eike Ziller Change-Id: Ie39a160a106b650cdcee88778fa7eff9e932a988 Reviewed-by: Thiago Macieira --- src/corelib/mimetypes/qmimemagicrule.cpp | 68 +++++++++++++++++++++++++------ src/corelib/mimetypes/qmimemagicrule_p.h | 3 +- src/corelib/mimetypes/qmimetypeparser.cpp | 40 ++++-------------- src/corelib/mimetypes/qmimetypeparser_p.h | 2 + 4 files changed, 68 insertions(+), 45 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/mimetypes/qmimemagicrule.cpp b/src/corelib/mimetypes/qmimemagicrule.cpp index c8508ac0d2..6a3a429179 100644 --- a/src/corelib/mimetypes/qmimemagicrule.cpp +++ b/src/corelib/mimetypes/qmimemagicrule.cpp @@ -38,6 +38,7 @@ #ifndef QT_NO_MIMETYPE +#include "qmimetypeparser_p.h" #include #include #include @@ -231,26 +232,53 @@ static inline QByteArray makePattern(const QByteArray &value) return pattern; } -QMimeMagicRule::QMimeMagicRule(QMimeMagicRule::Type theType, +// Evaluate a magic match rule like +// +// + +QMimeMagicRule::QMimeMagicRule(const QString &typeStr, const QByteArray &theValue, - int theStartPos, - int theEndPos, - const QByteArray &theMask) : + const QString &offsets, + const QByteArray &theMask, + QString *errorString) : d(new QMimeMagicRulePrivate) { - Q_ASSERT(!theValue.isEmpty()); - - d->type = theType; d->value = theValue; - d->startPos = theStartPos; - d->endPos = theEndPos; d->mask = theMask; d->matchFunction = 0; + d->type = QMimeMagicRule::type(typeStr.toLatin1()); + if (d->type == Invalid) { + *errorString = QStringLiteral("Type %s is not supported").arg(typeStr); + } + + // Parse for offset as "1" or "1:10" + const int colonIndex = offsets.indexOf(QLatin1Char(':')); + const QString startPosStr = colonIndex == -1 ? offsets : offsets.mid(0, colonIndex); + const QString endPosStr = colonIndex == -1 ? offsets : offsets.mid(colonIndex + 1); + if (!QMimeTypeParserBase::parseNumber(startPosStr, &d->startPos, errorString) || + !QMimeTypeParserBase::parseNumber(endPosStr, &d->endPos, errorString)) { + d->type = Invalid; + return; + } + + if (d->value.isEmpty()) { + d->type = Invalid; + if (errorString) + *errorString = QLatin1String("Invalid empty magic rule value"); + return; + } + if (d->type >= Host16 && d->type <= Byte) { bool ok; d->number = d->value.toUInt(&ok, 0); // autodetect - Q_ASSERT(ok); + if (!ok) { + d->type = Invalid; + if (errorString) + *errorString = QString::fromLatin1("Invalid magic rule value \"%1\"").arg( + QString::fromLatin1(d->value)); + return; + } d->numberMask = !d->mask.isEmpty() ? d->mask.toUInt(&ok, 0) : 0; // autodetect } @@ -259,9 +287,23 @@ QMimeMagicRule::QMimeMagicRule(QMimeMagicRule::Type theType, d->pattern = makePattern(d->value); d->pattern.squeeze(); if (!d->mask.isEmpty()) { - Q_ASSERT(d->mask.size() >= 4 && d->mask.startsWith("0x")); - d->mask = QByteArray::fromHex(QByteArray::fromRawData(d->mask.constData() + 2, d->mask.size() - 2)); - Q_ASSERT(d->mask.size() == d->pattern.size()); + if (d->mask.size() < 4 || !d->mask.startsWith("0x")) { + d->type = Invalid; + if (errorString) + *errorString = QString::fromLatin1("Invalid magic rule mask \"%1\"").arg( + QString::fromLatin1(d->mask)); + return; + } + const QByteArray &tempMask = QByteArray::fromHex(QByteArray::fromRawData( + d->mask.constData() + 2, d->mask.size() - 2)); + if (tempMask.size() != d->pattern.size()) { + d->type = Invalid; + if (errorString) + *errorString = QString::fromLatin1("Invalid magic rule mask size \"%1\"").arg( + QString::fromLatin1(d->mask)); + return; + } + d->mask = tempMask; } else { d->mask.fill(char(-1), d->pattern.size()); } diff --git a/src/corelib/mimetypes/qmimemagicrule_p.h b/src/corelib/mimetypes/qmimemagicrule_p.h index 03ac1d1de9..6b64bfcc10 100644 --- a/src/corelib/mimetypes/qmimemagicrule_p.h +++ b/src/corelib/mimetypes/qmimemagicrule_p.h @@ -61,7 +61,8 @@ class QMimeMagicRule public: enum Type { Invalid = 0, String, Host16, Host32, Big16, Big32, Little16, Little32, Byte }; - QMimeMagicRule(Type type, const QByteArray &value, int startPos, int endPos, const QByteArray &mask = QByteArray()); + QMimeMagicRule(const QString &typeStr, const QByteArray &value, const QString &offsets, + const QByteArray &mask, QString *errorString); QMimeMagicRule(const QMimeMagicRule &other); ~QMimeMagicRule(); diff --git a/src/corelib/mimetypes/qmimetypeparser.cpp b/src/corelib/mimetypes/qmimetypeparser.cpp index 9610162c4f..8a8b97655a 100644 --- a/src/corelib/mimetypes/qmimetypeparser.cpp +++ b/src/corelib/mimetypes/qmimetypeparser.cpp @@ -153,8 +153,8 @@ QMimeTypeParserBase::ParseState QMimeTypeParserBase::nextState(ParseState curren return ParseError; } -// Parse int number from an (attribute) string) -static bool parseNumber(const QString &n, int *target, QString *errorMessage) +// Parse int number from an (attribute) string +bool QMimeTypeParserBase::parseNumber(const QString &n, int *target, QString *errorMessage) { bool ok; *target = n.toInt(&ok); @@ -165,37 +165,14 @@ static bool parseNumber(const QString &n, int *target, QString *errorMessage) return true; } -// Evaluate a magic match rule like -// -// #ifndef QT_NO_XMLSTREAMREADER -static bool createMagicMatchRule(const QXmlStreamAttributes &atts, - QString *errorMessage, QMimeMagicRule *&rule) +static QMimeMagicRule *createMagicMatchRule(const QXmlStreamAttributes &atts, QString *errorMessage) { const QString type = atts.value(QLatin1String(matchTypeAttributeC)).toString(); - QMimeMagicRule::Type magicType = QMimeMagicRule::type(type.toLatin1()); - if (magicType == QMimeMagicRule::Invalid) { - qWarning("%s: match type %s is not supported.", Q_FUNC_INFO, type.toUtf8().constData()); - return true; - } const QString value = atts.value(QLatin1String(matchValueAttributeC)).toString(); - if (value.isEmpty()) { - *errorMessage = QString::fromLatin1("Empty match value detected."); - return false; - } - // Parse for offset as "1" or "1:10" - int startPos, endPos; - const QString offsetS = atts.value(QLatin1String(matchOffsetAttributeC)).toString(); - const int colonIndex = offsetS.indexOf(QLatin1Char(':')); - const QString startPosS = colonIndex == -1 ? offsetS : offsetS.mid(0, colonIndex); - const QString endPosS = colonIndex == -1 ? offsetS : offsetS.mid(colonIndex + 1); - if (!parseNumber(startPosS, &startPos, errorMessage) || !parseNumber(endPosS, &endPos, errorMessage)) - return false; + const QString offsets = atts.value(QLatin1String(matchOffsetAttributeC)).toString(); const QString mask = atts.value(QLatin1String(matchMaskAttributeC)).toString(); - - rule = new QMimeMagicRule(magicType, value.toUtf8(), startPos, endPos, mask.toLatin1()); - - return true; + return new QMimeMagicRule(type, value.toUtf8(), offsets, mask.toLatin1(), errorMessage); } #endif @@ -283,9 +260,10 @@ bool QMimeTypeParserBase::parse(QIODevice *dev, const QString &fileName, QString } break; case ParseMagicMatchRule: { - QMimeMagicRule *rule = 0; - if (!createMagicMatchRule(atts, errorMessage, rule)) - return false; + QString magicErrorMessage; + QMimeMagicRule *rule = createMagicMatchRule(atts, &magicErrorMessage); + if (!rule->isValid()) + qWarning("QMimeDatabase: Error parsing %s\n%s", qPrintable(fileName), qPrintable(magicErrorMessage)); QList *ruleList; if (currentRules.isEmpty()) ruleList = &rules; diff --git a/src/corelib/mimetypes/qmimetypeparser_p.h b/src/corelib/mimetypes/qmimetypeparser_p.h index 2be4380cee..3a2e6b8a14 100644 --- a/src/corelib/mimetypes/qmimetypeparser_p.h +++ b/src/corelib/mimetypes/qmimetypeparser_p.h @@ -66,6 +66,8 @@ public: bool parse(QIODevice *dev, const QString &fileName, QString *errorMessage); + static bool parseNumber(const QString &n, int *target, QString *errorMessage); + protected: virtual bool process(const QMimeType &t, QString *errorMessage) = 0; virtual bool process(const QMimeGlobPattern &t, QString *errorMessage) = 0; -- cgit v1.2.3 From a6ec869211d67fed94e3513dc453a96717155121 Mon Sep 17 00:00:00 2001 From: Alex Trotsenko Date: Tue, 11 Aug 2015 13:23:32 +0300 Subject: Fix the spurious socket notifications under Windows To handle network events, QEventDispatcherWin32 uses I/O model based on notifications through the window message queue. Having successfully posted notification of a particular event to an application window, no further messages for that network event will be posted to the application window until the application makes the function call that implicitly re-enables notification of that network event. With these semantics, an application need not read all available data in response to an FD_READ message: a single recv in response to each FD_READ message is appropriate. If an application issues multiple recv calls in response to a single FD_READ, it can receive multiple FD_READ messages (including spurious). To solve this issue, this patch always disables the notifier after getting a notification, and re-enables it only when the message queue is empty. Task-number: QTBUG-46552 Change-Id: I05df67032911cd1f5927fa7912f7864bfbf8711e Reviewed-by: Joerg Bornemann --- src/corelib/kernel/qeventdispatcher_win.cpp | 112 +++++++++++++++++----------- src/corelib/kernel/qeventdispatcher_win_p.h | 11 ++- src/corelib/kernel/qsocketnotifier.cpp | 36 --------- 3 files changed, 80 insertions(+), 79 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/kernel/qeventdispatcher_win.cpp b/src/corelib/kernel/qeventdispatcher_win.cpp index 6da70cf0bd..695eb3d5d0 100644 --- a/src/corelib/kernel/qeventdispatcher_win.cpp +++ b/src/corelib/kernel/qeventdispatcher_win.cpp @@ -391,6 +391,8 @@ LRESULT QT_WIN_CALLBACK qt_internal_proc(HWND hwnd, UINT message, WPARAM wp, LPA QSockNot *sn = dict ? dict->value(wp) : 0; if (sn) { + d->doWsaAsyncSelect(sn->fd, 0); + d->active_fd[sn->fd].selected = false; if (type < 3) { QEvent event(QEvent::SockAct); QCoreApplication::sendEvent(sn->obj, &event); @@ -633,19 +635,12 @@ void QEventDispatcherWin32Private::sendTimerEvent(int timerId) } } -void QEventDispatcherWin32Private::doWsaAsyncSelect(int socket) +void QEventDispatcherWin32Private::doWsaAsyncSelect(int socket, long event) { Q_ASSERT(internalHwnd); - int sn_event = 0; - if (sn_read.contains(socket)) - sn_event |= FD_READ | FD_CLOSE | FD_ACCEPT; - if (sn_write.contains(socket)) - sn_event |= FD_WRITE | FD_CONNECT; - if (sn_except.contains(socket)) - sn_event |= FD_OOB; - // BoundsChecker may emit a warning for WSAAsyncSelect when sn_event == 0 + // BoundsChecker may emit a warning for WSAAsyncSelect when event == 0 // This is a BoundsChecker bug and not a Qt bug - WSAAsyncSelect(socket, internalHwnd, sn_event ? int(WM_QT_SOCKETNOTIFIER) : 0, sn_event); + WSAAsyncSelect(socket, internalHwnd, event ? int(WM_QT_SOCKETNOTIFIER) : 0, event); } void QEventDispatcherWin32::createInternalHwnd() @@ -658,13 +653,6 @@ void QEventDispatcherWin32::createInternalHwnd() installMessageHook(); - // register all socket notifiers - QList sockets = (d->sn_read.keys().toSet() - + d->sn_write.keys().toSet() - + d->sn_except.keys().toSet()).toList(); - for (int i = 0; i < sockets.count(); ++i) - d->doWsaAsyncSelect(sockets.at(i)); - // start all normal timers for (int i = 0; i < d->timerVec.count(); ++i) d->registerTimer(d->timerVec.at(i)); @@ -749,28 +737,40 @@ bool QEventDispatcherWin32::processEvents(QEventLoop::ProcessEventsFlags flags) msg = d->queuedSocketEvents.takeFirst(); } else { haveMessage = PeekMessage(&msg, 0, 0, 0, PM_REMOVE); - if (haveMessage && (flags & QEventLoop::ExcludeUserInputEvents) - && ((msg.message >= WM_KEYFIRST - && msg.message <= WM_KEYLAST) - || (msg.message >= WM_MOUSEFIRST - && msg.message <= WM_MOUSELAST) - || msg.message == WM_MOUSEWHEEL - || msg.message == WM_MOUSEHWHEEL - || msg.message == WM_TOUCH + if (haveMessage) { + if ((flags & QEventLoop::ExcludeUserInputEvents) + && ((msg.message >= WM_KEYFIRST + && msg.message <= WM_KEYLAST) + || (msg.message >= WM_MOUSEFIRST + && msg.message <= WM_MOUSELAST) + || msg.message == WM_MOUSEWHEEL + || msg.message == WM_MOUSEHWHEEL + || msg.message == WM_TOUCH #ifndef QT_NO_GESTURES - || msg.message == WM_GESTURE - || msg.message == WM_GESTURENOTIFY + || msg.message == WM_GESTURE + || msg.message == WM_GESTURENOTIFY #endif - || msg.message == WM_CLOSE)) { - // queue user input events for later processing - haveMessage = false; - d->queuedUserInputEvents.append(msg); - } - if (haveMessage && (flags & QEventLoop::ExcludeSocketNotifiers) - && (msg.message == WM_QT_SOCKETNOTIFIER && msg.hwnd == d->internalHwnd)) { - // queue socket events for later processing - haveMessage = false; - d->queuedSocketEvents.append(msg); + || msg.message == WM_CLOSE)) { + // queue user input events for later processing + d->queuedUserInputEvents.append(msg); + continue; + } + if ((flags & QEventLoop::ExcludeSocketNotifiers) + && (msg.message == WM_QT_SOCKETNOTIFIER && msg.hwnd == d->internalHwnd)) { + // queue socket events for later processing + d->queuedSocketEvents.append(msg); + continue; + } + } else if (!(flags & QEventLoop::ExcludeSocketNotifiers)) { + // register all socket notifiers + for (QSFDict::iterator it = d->active_fd.begin(), end = d->active_fd.end(); + it != end; ++it) { + QSockFd &sd = it.value(); + if (!sd.selected) { + d->doWsaAsyncSelect(it.key(), sd.event); + sd.selected = true; + } + } } } if (!haveMessage) { @@ -896,8 +896,25 @@ void QEventDispatcherWin32::registerSocketNotifier(QSocketNotifier *notifier) sn->fd = sockfd; dict->insert(sn->fd, sn); - if (d->internalHwnd) - d->doWsaAsyncSelect(sockfd); + long event = 0; + if (d->sn_read.contains(sockfd)) + event |= FD_READ | FD_CLOSE | FD_ACCEPT; + if (d->sn_write.contains(sockfd)) + event |= FD_WRITE | FD_CONNECT; + if (d->sn_except.contains(sockfd)) + event |= FD_OOB; + + QSFDict::iterator it = d->active_fd.find(sockfd); + if (it != d->active_fd.end()) { + QSockFd &sd = it.value(); + if (sd.selected) { + d->doWsaAsyncSelect(sockfd, 0); + sd.selected = false; + } + sd.event |= event; + } else { + d->active_fd.insert(sockfd, QSockFd(event)); + } } void QEventDispatcherWin32::unregisterSocketNotifier(QSocketNotifier *notifier) @@ -916,6 +933,19 @@ void QEventDispatcherWin32::unregisterSocketNotifier(QSocketNotifier *notifier) #endif Q_D(QEventDispatcherWin32); + QSFDict::iterator it = d->active_fd.find(sockfd); + if (it != d->active_fd.end()) { + QSockFd &sd = it.value(); + if (sd.selected) + d->doWsaAsyncSelect(sockfd, 0); + const long event[3] = { FD_READ | FD_CLOSE | FD_ACCEPT, FD_WRITE | FD_CONNECT, FD_OOB }; + sd.event ^= event[type]; + if (sd.event == 0) + d->active_fd.erase(it); + else + sd.selected = false; + } + QSNDict *sn_vec[3] = { &d->sn_read, &d->sn_write, &d->sn_except }; QSNDict *dict = sn_vec[type]; QSockNot *sn = dict->value(sockfd); @@ -924,9 +954,6 @@ void QEventDispatcherWin32::unregisterSocketNotifier(QSocketNotifier *notifier) dict->remove(sockfd); delete sn; - - if (d->internalHwnd) - d->doWsaAsyncSelect(sockfd); } void QEventDispatcherWin32::registerTimer(int timerId, int interval, Qt::TimerType timerType, QObject *object) @@ -1165,6 +1192,7 @@ void QEventDispatcherWin32::closingDown() unregisterSocketNotifier((*(d->sn_write.begin()))->obj); while (!d->sn_except.isEmpty()) unregisterSocketNotifier((*(d->sn_except.begin()))->obj); + Q_ASSERT(d->active_fd.isEmpty()); // clean up any timers for (int i = 0; i < d->timerVec.count(); ++i) diff --git a/src/corelib/kernel/qeventdispatcher_win_p.h b/src/corelib/kernel/qeventdispatcher_win_p.h index e59e29f1ff..8578110ee4 100644 --- a/src/corelib/kernel/qeventdispatcher_win_p.h +++ b/src/corelib/kernel/qeventdispatcher_win_p.h @@ -115,6 +115,14 @@ struct QSockNot { }; typedef QHash QSNDict; +struct QSockFd { + long event; + bool selected; + + explicit inline QSockFd(long ev = 0) : event(ev), selected(false) { } +}; +typedef QHash QSFDict; + struct WinTimerInfo { // internal timer info QObject *dispatcher; int timerId; @@ -169,7 +177,8 @@ public: QSNDict sn_read; QSNDict sn_write; QSNDict sn_except; - void doWsaAsyncSelect(int socket); + QSFDict active_fd; + void doWsaAsyncSelect(int socket, long event); QList winEventNotifierList; void activateEventNotifier(QWinEventNotifier * wen); diff --git a/src/corelib/kernel/qsocketnotifier.cpp b/src/corelib/kernel/qsocketnotifier.cpp index d789af2fd9..3a5eff0c19 100644 --- a/src/corelib/kernel/qsocketnotifier.cpp +++ b/src/corelib/kernel/qsocketnotifier.cpp @@ -98,42 +98,6 @@ public: QTcpSocket and QUdpSocket provide notification through signals, so there is normally no need to use a QSocketNotifier on them. - \section1 Notes for Windows Users - - The socket passed to QSocketNotifier will become non-blocking, even if - it was created as a blocking socket. - The activated() signal is sometimes triggered by high general activity - on the host, even if there is nothing to read. A subsequent read from - the socket can then fail, the error indicating that there is no data - available (e.g., \c{WSAEWOULDBLOCK}). This is an operating system - limitation, and not a bug in QSocketNotifier. - - To ensure that the socket notifier handles read notifications correctly, - follow these steps when you receive a notification: - - \list 1 - \li Disable the notifier. - \li Read data from the socket. - \li Re-enable the notifier if you are interested in more data (such as after - having written a new command to a remote server). - \endlist - - To ensure that the socket notifier handles write notifications correctly, - follow these steps when you receive a notification: - - \list 1 - \li Disable the notifier. - \li Write as much data as you can (before \c EWOULDBLOCK is returned). - \li Re-enable notifier if you have more data to write. - \endlist - - \b{Further information:} - On Windows, Qt always disables the notifier after getting a notification, - and only re-enables it if more data is expected. For example, if data is - read from the socket and it can be used to read more, or if reading or - writing is not possible because the socket would block, in which case - it is necessary to wait before attempting to read or write again. - \sa QFile, QProcess, QTcpSocket, QUdpSocket */ -- cgit v1.2.3 From deb6b5032c8eed35021b3c697a770645d90b11ed Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C3=89meric=20MASCHINO?= Date: Wed, 9 Sep 2015 22:56:32 +0200 Subject: Fixed compilation errors in qatomic_ia64.h QBasicAtomicOps::testAndSetRelaxed(T &, T, T) and QBasicAtomicOps::testAndSetOrdered(T &, T, T) bodies don't match any prototypes in qatomic_ia64.h: the optional parameter T *currentValue is missing. Task-number: QTBUG-48197 Change-Id: I0112c429b161b4a0ddb6e8a0400a436282ffb1c7 Reviewed-by: Thiago Macieira --- src/corelib/arch/qatomic_ia64.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/arch/qatomic_ia64.h b/src/corelib/arch/qatomic_ia64.h index c880e85209..2ba6d127d9 100644 --- a/src/corelib/arch/qatomic_ia64.h +++ b/src/corelib/arch/qatomic_ia64.h @@ -1035,16 +1035,16 @@ bool QBasicAtomicOps::deref(T &_q_value) Q_DECL_NOTHROW } template template inline -bool QBasicAtomicOps::testAndSetRelaxed(T &_q_value, T expectedValue, T newValue) Q_DECL_NOTHROW +bool QBasicAtomicOps::testAndSetRelaxed(T &_q_value, T expectedValue, T newValue, T *currentValue) Q_DECL_NOTHROW { - return testAndSetAcquire(_q_value, expectedValue, newValue); + return testAndSetAcquire(_q_value, expectedValue, newValue, currentValue); } template template inline -bool QBasicAtomicOps::testAndSetOrdered(T &_q_value, T expectedValue, T newValue) Q_DECL_NOTHROW +bool QBasicAtomicOps::testAndSetOrdered(T &_q_value, T expectedValue, T newValue, T *currentValue) Q_DECL_NOTHROW { orderedMemoryFence(_q_value); - return testAndSetAcquire(_q_value, expectedValue, newValue); + return testAndSetAcquire(_q_value, expectedValue, newValue, currentValue); } template template inline -- cgit v1.2.3 From e3fa2cb660b70d3b45a047bdb055959e36e8445f Mon Sep 17 00:00:00 2001 From: Joni Poikelin Date: Fri, 22 May 2015 13:09:57 +0300 Subject: Fix regression with QStandardPaths::standardLocations on Windows Commit f3bc9f5c5cee9dac8a7815c2861a9945b5341390 broke standardLocations by replacing them with same paths as writeable locations would return. Task-number: QTBUG-46279 Change-Id: I43150e3af13320a707c7882dd0f0cdcb2c6e8a70 Reviewed-by: Friedemann Kleint Reviewed-by: David Faure --- src/corelib/io/qstandardpaths_win.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qstandardpaths_win.cpp b/src/corelib/io/qstandardpaths_win.cpp index b1d5821a97..615f85a279 100644 --- a/src/corelib/io/qstandardpaths_win.cpp +++ b/src/corelib/io/qstandardpaths_win.cpp @@ -200,7 +200,7 @@ QStringList QStandardPaths::standardLocations(StandardLocation type) case AppDataLocation: case AppLocalDataLocation: case GenericDataLocation: - if (SHGetSpecialFolderPath(0, path, clsidForAppDataLocation(type), FALSE)) { + if (SHGetSpecialFolderPath(0, path, CSIDL_COMMON_APPDATA, FALSE)) { QString result = convertCharArray(path); if (type != GenericDataLocation && type != GenericConfigLocation) { #ifndef QT_BOOTSTRAPPED -- cgit v1.2.3 From 9b9f86985ff711838d9d1b486ed10823ba02a681 Mon Sep 17 00:00:00 2001 From: Kai Koehne Date: Fri, 18 Sep 2015 15:05:37 +0200 Subject: Fix compilation with QT_NO_[DEBUG|WARNING]_OUTPUT Change-Id: I4b92ac6b917c9979449b4834764497003d6de087 Reviewed-by: Friedemann Kleint --- src/corelib/io/qiodevice.cpp | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/io/qiodevice.cpp b/src/corelib/io/qiodevice.cpp index b908ae3145..cd448ad9cf 100644 --- a/src/corelib/io/qiodevice.cpp +++ b/src/corelib/io/qiodevice.cpp @@ -82,6 +82,7 @@ void debugBinaryString(const char *data, qint64 maxlen) static void checkWarnMessage(const QIODevice *device, const char *function, const char *what) { +#ifndef QT_NO_WARNING_OUTPUT QDebug d = qWarning(); d.noquote(); d.nospace(); @@ -97,6 +98,11 @@ static void checkWarnMessage(const QIODevice *device, const char *function, cons Q_UNUSED(device) #endif // !QT_NO_QOBJECT d << ": " << what; +#else + Q_UNUSED(device); + Q_UNUSED(function); + Q_UNUSED(what); +#endif // QT_NO_WARNING_OUTPUT } #define CHECK_MAXLEN(function, returnType) \ -- cgit v1.2.3 From 363e6e3d52ff7a048f0db9166f6e43137c92669c Mon Sep 17 00:00:00 2001 From: Joerg Bornemann Date: Mon, 21 Sep 2015 11:25:54 +0200 Subject: fix error message The error message mentioned a wrong function name. Change-Id: Ia2258744fd9268af6b00f54e74d40476ded3b0d2 Reviewed-by: Oswald Buddenhagen --- src/corelib/io/qwindowspipereader.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qwindowspipereader.cpp b/src/corelib/io/qwindowspipereader.cpp index 14aad0e193..c1f5d2aace 100644 --- a/src/corelib/io/qwindowspipereader.cpp +++ b/src/corelib/io/qwindowspipereader.cpp @@ -187,7 +187,7 @@ void QWindowsPipeReader::notified(quint32 numberOfBytesRead, quint32 errorCode, pipeBroken = true; break; default: - emit winError(errorCode, QLatin1String("QWindowsPipeReader::completeAsyncRead")); + emit winError(errorCode, QLatin1String("QWindowsPipeReader::notified")); pipeBroken = true; break; } -- cgit v1.2.3 From ec6556a2b99df373eb43ca009340a7f0f19bacbd Mon Sep 17 00:00:00 2001 From: David Faure Date: Sat, 1 Aug 2015 15:50:00 +0200 Subject: Fix two data races in QThread/QThreadData * theMainThread is written by the main thread and read by QThreadData::~QThreadData() (any managed thread) * QThreadData::thread is written by QThread::~QThread (in the parent thread) and read+written by QThreadData::~QThreadData (in the managed thread). This can happen because QThreadData is refcounted so the managed thread (which derefs it) races with the parent thread (which sets it to 0). Change-Id: I72de793716391a0937254cda6b4328fcad5060c7 Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/kernel/qcoreapplication.cpp | 12 ++++++------ src/corelib/kernel/qcoreapplication_p.h | 2 +- src/corelib/kernel/qobject.cpp | 2 +- src/corelib/thread/qthread_p.h | 2 +- src/corelib/thread/qthread_unix.cpp | 2 +- src/corelib/thread/qthread_win.cpp | 2 +- src/corelib/thread/qthreadstorage.cpp | 6 +++--- 7 files changed, 14 insertions(+), 14 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/kernel/qcoreapplication.cpp b/src/corelib/kernel/qcoreapplication.cpp index 37a26cf556..24427bd1af 100644 --- a/src/corelib/kernel/qcoreapplication.cpp +++ b/src/corelib/kernel/qcoreapplication.cpp @@ -460,8 +460,8 @@ QCoreApplicationPrivate::QCoreApplicationPrivate(int &aargc, char **aargv, uint qt_application_thread_id = QThread::currentThreadId(); # endif - // note: this call to QThread::currentThread() may end up setting theMainThread! - if (QThread::currentThread() != theMainThread) + QThread *cur = QThread::currentThread(); // note: this may end up setting theMainThread! + if (cur != theMainThread) qWarning("WARNING: QApplication was not created in the main() thread."); #endif } @@ -531,11 +531,11 @@ void QCoreApplicationPrivate::eventDispatcherReady() { } -QThread *QCoreApplicationPrivate::theMainThread = 0; +QBasicAtomicPointer QCoreApplicationPrivate::theMainThread = Q_BASIC_ATOMIC_INITIALIZER(0); QThread *QCoreApplicationPrivate::mainThread() { - Q_ASSERT(theMainThread != 0); - return theMainThread; + Q_ASSERT(theMainThread.load() != 0); + return theMainThread.load(); } void QCoreApplicationPrivate::checkReceiverThread(QObject *receiver) @@ -2671,7 +2671,7 @@ bool QCoreApplication::hasPendingEvents() QAbstractEventDispatcher *QCoreApplication::eventDispatcher() { if (QCoreApplicationPrivate::theMainThread) - return QCoreApplicationPrivate::theMainThread->eventDispatcher(); + return QCoreApplicationPrivate::theMainThread.load()->eventDispatcher(); return 0; } diff --git a/src/corelib/kernel/qcoreapplication_p.h b/src/corelib/kernel/qcoreapplication_p.h index 2646a28d71..e985f8d052 100644 --- a/src/corelib/kernel/qcoreapplication_p.h +++ b/src/corelib/kernel/qcoreapplication_p.h @@ -105,7 +105,7 @@ public: } void maybeQuit(); - static QThread *theMainThread; + static QBasicAtomicPointer theMainThread; static QThread *mainThread(); static void sendPostedEvents(QObject *receiver, int event_type, QThreadData *data); diff --git a/src/corelib/kernel/qobject.cpp b/src/corelib/kernel/qobject.cpp index bcc4e7f8e6..f2c67fb3a0 100644 --- a/src/corelib/kernel/qobject.cpp +++ b/src/corelib/kernel/qobject.cpp @@ -1468,7 +1468,7 @@ void QObject::moveToThread(QThread *targetThread) } else if (d->threadData != currentData) { qWarning("QObject::moveToThread: Current thread (%p) is not the object's thread (%p).\n" "Cannot move to target thread (%p)\n", - currentData->thread, d->threadData->thread, targetData ? targetData->thread : Q_NULLPTR); + currentData->thread.load(), d->threadData->thread.load(), targetData ? targetData->thread.load() : Q_NULLPTR); #ifdef Q_OS_MAC qWarning("You might be loading two sets of Qt binaries into the same process. " diff --git a/src/corelib/thread/qthread_p.h b/src/corelib/thread/qthread_p.h index 1ecd682ad1..8331816729 100644 --- a/src/corelib/thread/qthread_p.h +++ b/src/corelib/thread/qthread_p.h @@ -269,7 +269,7 @@ public: QStack eventLoops; QPostEventList postEventList; - QThread *thread; + QAtomicPointer thread; Qt::HANDLE threadId; QAtomicPointer eventDispatcher; QVector tls; diff --git a/src/corelib/thread/qthread_unix.cpp b/src/corelib/thread/qthread_unix.cpp index 77093c9cf1..5698a61326 100644 --- a/src/corelib/thread/qthread_unix.cpp +++ b/src/corelib/thread/qthread_unix.cpp @@ -225,7 +225,7 @@ QThreadData *QThreadData::current(bool createIfNecessary) data->isAdopted = true; data->threadId = (Qt::HANDLE)pthread_self(); if (!QCoreApplicationPrivate::theMainThread) - QCoreApplicationPrivate::theMainThread = data->thread; + QCoreApplicationPrivate::theMainThread = data->thread.load(); } return data; } diff --git a/src/corelib/thread/qthread_win.cpp b/src/corelib/thread/qthread_win.cpp index c16a2e958c..a4b853d62e 100644 --- a/src/corelib/thread/qthread_win.cpp +++ b/src/corelib/thread/qthread_win.cpp @@ -121,7 +121,7 @@ QThreadData *QThreadData::current(bool createIfNecessary) threadData->threadId = reinterpret_cast(GetCurrentThreadId()); if (!QCoreApplicationPrivate::theMainThread) { - QCoreApplicationPrivate::theMainThread = threadData->thread; + QCoreApplicationPrivate::theMainThread = threadData->thread.load(); // TODO: is there a way to reflect the branch's behavior using // WinRT API? } else { diff --git a/src/corelib/thread/qthreadstorage.cpp b/src/corelib/thread/qthreadstorage.cpp index 05ab01cc54..37892233f3 100644 --- a/src/corelib/thread/qthreadstorage.cpp +++ b/src/corelib/thread/qthreadstorage.cpp @@ -121,7 +121,7 @@ void **QThreadStorageData::get() const DEBUG_MSG("QThreadStorageData: Returning storage %d, data %p, for thread %p", id, *v, - data->thread); + data->thread.load()); return *v ? v : 0; } @@ -143,7 +143,7 @@ void **QThreadStorageData::set(void *p) DEBUG_MSG("QThreadStorageData: Deleting previous storage %d, data %p, for thread %p", id, value, - data->thread); + data->thread.load()); QMutexLocker locker(&destructorsMutex); DestructorMap *destr = destructors(); @@ -159,7 +159,7 @@ void **QThreadStorageData::set(void *p) // store new data value = p; - DEBUG_MSG("QThreadStorageData: Set storage %d for thread %p to %p", id, data->thread, p); + DEBUG_MSG("QThreadStorageData: Set storage %d for thread %p to %p", id, data->thread.load(), p); return &value; } -- cgit v1.2.3 From be2e0f75ae2e55f235b34b402b70628a839b7782 Mon Sep 17 00:00:00 2001 From: jian liang Date: Sun, 20 Sep 2015 23:08:59 +0800 Subject: Free the QFreeList object allocated memory on exit This memory allocation was introduced in 314c83c0c2f91532654f869b7dc6af1b7e8538da. With a compiler without thread safe statics support mutex.cpp use a function named freelist() to create the global QFreeList object. it will be created when the first time it was accessed, but will never be released. This patch use Q_DESTRUCTOR_FUNCTION to delete this object. Task-number: QTBUG-48359 Change-Id: I4e4716930930aa98630101a1f96de6a7672af9cb Reviewed-by: Thiago Macieira --- src/corelib/thread/qmutex.cpp | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/thread/qmutex.cpp b/src/corelib/thread/qmutex.cpp index 3269ee3ae8..742a572bef 100644 --- a/src/corelib/thread/qmutex.cpp +++ b/src/corelib/thread/qmutex.cpp @@ -571,19 +571,26 @@ FreeList *freelist() return &list; } #else +static QBasicAtomicPointer freeListPtr; + FreeList *freelist() { - static QAtomicPointer list; - FreeList *local = list.loadAcquire(); + FreeList *local = freeListPtr.loadAcquire(); if (!local) { local = new FreeList; - if (!list.testAndSetRelease(0, local)) { + if (!freeListPtr.testAndSetRelease(0, local)) { delete local; - local = list.loadAcquire(); + local = freeListPtr.loadAcquire(); } } return local; } + +static void qFreeListDeleter() +{ + delete freeListPtr.load(); +} +Q_DESTRUCTOR_FUNCTION(qFreeListDeleter) #endif } -- cgit v1.2.3 From c619d2daac9b1f61e8ad2320b59c648b6af6af90 Mon Sep 17 00:00:00 2001 From: Christian Kandeler Date: Tue, 22 Sep 2015 13:17:50 +0200 Subject: QDateTime: Ensure a valid timezone when using the "offset constructor". The timeZone() function used to assert when called on such an object (or, for a release build, return an invalid time zone). Change-Id: I6ae8316b2ad76f1f868e2498f7ce8aa3fcabf4a6 Reviewed-by: Thiago Macieira --- src/corelib/tools/qdatetime.cpp | 1 + 1 file changed, 1 insertion(+) (limited to 'src/corelib') diff --git a/src/corelib/tools/qdatetime.cpp b/src/corelib/tools/qdatetime.cpp index eb4eff32b4..d6428920e5 100644 --- a/src/corelib/tools/qdatetime.cpp +++ b/src/corelib/tools/qdatetime.cpp @@ -3123,6 +3123,7 @@ QTimeZone QDateTime::timeZone() const case Qt::UTC: return QTimeZone::utc(); case Qt::OffsetFromUTC: + return QTimeZone(d->m_offsetFromUtc); case Qt::TimeZone: Q_ASSERT(d->m_timeZone.isValid()); return d->m_timeZone; -- cgit v1.2.3 From dc716f2dc2df06c40b3709ded81a5b7588f53e7a Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Fri, 18 Sep 2015 18:01:50 -0700 Subject: ICC on Windows: Disable ref-qualified member functions in MSVC <= 2013 Like MSVC, ICC on Windows in debug mode always makes calls to dllexported functions instead of inlining them. Since MSVC 2013 doesn't know about ref-qualification of member functions, this creates an incompatibility between DLL creation and DLL use. Task-number: QTBUG-48349 Change-Id: I42e7ef1a481840699a8dffff14053b594810fb42 Reviewed-by: Olivier Goffart (Woboq GmbH) Reviewed-by: Lars Knoll --- src/corelib/global/qcompilerdetection.h | 3 +++ 1 file changed, 3 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/global/qcompilerdetection.h b/src/corelib/global/qcompilerdetection.h index 4828d8596a..9f79b3e70c 100644 --- a/src/corelib/global/qcompilerdetection.h +++ b/src/corelib/global/qcompilerdetection.h @@ -572,6 +572,9 @@ # if _MSC_VER < 1900 // ICC disables unicode string support when compatibility mode with MSVC 2013 or lower is active # undef Q_COMPILER_UNICODE_STRINGS +// Even though ICC knows about ref-qualified members, MSVC 2013 or lower doesn't, so +// certain member functions (like QString::toUpper) may be missing from the DLLs. +# undef Q_COMPILER_REF_QUALIFIERS // Disable constexpr unless the MS headers have constexpr in all the right places too // (like std::numeric_limits::max()) # undef Q_COMPILER_CONSTEXPR -- cgit v1.2.3 From 5445eb35414437672715108a60d07dc413c504d6 Mon Sep 17 00:00:00 2001 From: Erik Verbruggen Date: Mon, 21 Sep 2015 11:18:23 +0200 Subject: QStateMachine: make enterStates/exitStates virtual. This allows handling of state specific code when entering/exiting states during a micro-step. Change-Id: If2fa8dde9a1e209345950a93dee59414063d863e Reviewed-by: Simon Hausmann --- src/corelib/statemachine/qstatemachine_p.h | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/statemachine/qstatemachine_p.h b/src/corelib/statemachine/qstatemachine_p.h index fe7a06d16b..45c6dfcb33 100644 --- a/src/corelib/statemachine/qstatemachine_p.h +++ b/src/corelib/statemachine/qstatemachine_p.h @@ -134,16 +134,16 @@ public: virtual void beginMacrostep(); virtual void endMacrostep(bool didChange); virtual void exitInterpreter(); - void exitStates(QEvent *event, const QList &statesToExit_sorted, - const QHash > &assignmentsForEnteredStates); + virtual void exitStates(QEvent *event, const QList &statesToExit_sorted, + const QHash > &assignmentsForEnteredStates); QList computeExitSet(const QList &enabledTransitions, CalculationCache *cache); QSet computeExitSet_Unordered(const QList &enabledTransitions, CalculationCache *cache); QSet computeExitSet_Unordered(QAbstractTransition *t, CalculationCache *cache); void executeTransitionContent(QEvent *event, const QList &transitionList); - void enterStates(QEvent *event, const QList &exitedStates_sorted, - const QList &statesToEnter_sorted, - const QSet &statesForDefaultEntry, - QHash > &propertyAssignmentsForState + virtual void enterStates(QEvent *event, const QList &exitedStates_sorted, + const QList &statesToEnter_sorted, + const QSet &statesForDefaultEntry, + QHash > &propertyAssignmentsForState #ifndef QT_NO_ANIMATION , const QList &selectedAnimations #endif -- cgit v1.2.3 From 0f2da655ac05ff4d94e1f8171965aa13f22b1c21 Mon Sep 17 00:00:00 2001 From: Olivier Goffart Date: Fri, 11 Sep 2015 16:59:27 +0200 Subject: Remove wrong forward declaration It confuses auto complete Change-Id: Ida86f6c8dcca351339d2b41ad40cf5701f5bb2c4 Reviewed-by: Richard J. Moore --- src/corelib/mimetypes/qmimetype.h | 1 - 1 file changed, 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/mimetypes/qmimetype.h b/src/corelib/mimetypes/qmimetype.h index 3c153da21d..054a5841c4 100644 --- a/src/corelib/mimetypes/qmimetype.h +++ b/src/corelib/mimetypes/qmimetype.h @@ -44,7 +44,6 @@ QT_BEGIN_NAMESPACE class QMimeTypePrivate; -class QFileinfo; class QStringList; class QMimeType; -- cgit v1.2.3 From ddee17e7705fd3f64c564dcd926531d181387fd1 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Wed, 23 Sep 2015 10:41:21 -0700 Subject: Remove QT_WARNING_DISABLE_GCC for Clang There's QT_WARNING_DISABLE_CLANG for when a warning applies to a Clang build. Change-Id: I42e7ef1a481840699a8dffff1406ac36b6a6eac3 Reviewed-by: Allan Sandfeld Jensen --- src/corelib/global/qcompilerdetection.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/global/qcompilerdetection.h b/src/corelib/global/qcompilerdetection.h index 4828d8596a..1a999d24be 100644 --- a/src/corelib/global/qcompilerdetection.h +++ b/src/corelib/global/qcompilerdetection.h @@ -1140,7 +1140,7 @@ # define QT_WARNING_PUSH QT_DO_PRAGMA(clang diagnostic push) # define QT_WARNING_POP QT_DO_PRAGMA(clang diagnostic pop) # define QT_WARNING_DISABLE_CLANG(text) QT_DO_PRAGMA(clang diagnostic ignored text) -# define QT_WARNING_DISABLE_GCC(text) QT_DO_PRAGMA(GCC diagnostic ignored text) // GCC directives work in Clang too +# define QT_WARNING_DISABLE_GCC(text) # define QT_WARNING_DISABLE_INTEL(number) # define QT_WARNING_DISABLE_MSVC(number) #elif defined(Q_CC_GNU) && (__GNUC__ * 100 + __GNUC_MINOR__ >= 406) -- cgit v1.2.3 From 393c8d0b74ded30c40a5321df5cbbc76dac66eda Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Fri, 21 Aug 2015 14:02:38 -0700 Subject: Fix ICC warning about use of "defined" in a macro qhash.cpp(89): warning #3199: "defined" is always false in a macro expansion in Microsoft mode Change-Id: I7de033f80b0e4431b7f1ffff13fc960bcbb17352 Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/tools/qsimd_p.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qsimd_p.h b/src/corelib/tools/qsimd_p.h index be003f6c6d..bb9c26f762 100644 --- a/src/corelib/tools/qsimd_p.h +++ b/src/corelib/tools/qsimd_p.h @@ -150,7 +150,7 @@ # define QT_FUNCTION_TARGET(x) # endif #else -# define QT_COMPILER_SUPPORTS_HERE(x) defined(__ ## x ## __) +# define QT_COMPILER_SUPPORTS_HERE(x) (__ ## x ## __) # define QT_FUNCTION_TARGET(x) #endif -- cgit v1.2.3 From 1a6ac8319313b6e024305397512513387afcafb8 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Sun, 27 Sep 2015 11:43:47 -0700 Subject: Ensure there's no sign-extension here. Both e_shentsize and e_shtrndx are ELF half-words, which means C integers of rank less than int (they're quint16). That means this multiplcation was done actually as int, due to integer promotion from unsigned short. So preempt the integer promotion and force them to full- word integers (unsigned int). While the bit-pattern result of the multiplication is the same, the addition with e_shoff (a qelfoff_t = quintptr) wouldn't: the promotion from 32-bit int to 64-bit would first execute a sign-extension. Now, this shouldn't happen on regular ELF files, but it cause QLibrary to crash if a specially-crafted (or simply corrupt) plugin is found. Found by Coverity, CID 22642 Change-Id: I42e7ef1a481840699a8dffff1407e9f1282eeecf Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/plugin/qelfparser_p.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/plugin/qelfparser_p.cpp b/src/corelib/plugin/qelfparser_p.cpp index d93be439e0..3798231383 100644 --- a/src/corelib/plugin/qelfparser_p.cpp +++ b/src/corelib/plugin/qelfparser_p.cpp @@ -148,7 +148,7 @@ int QElfParser::parse(const char *dataStart, ulong fdlen, const QString &library #endif ElfSectionHeader strtab; - qulonglong soff = e_shoff + e_shentsize * (e_shtrndx); + qulonglong soff = e_shoff + qelfword_t(e_shentsize) * qelfword_t(e_shtrndx); if ((soff + e_shentsize) > fdlen || soff % 4 || soff == 0) { if (lib) -- cgit v1.2.3 From d24366a63281543e6c1a8e6b615ce882ea6259ab Mon Sep 17 00:00:00 2001 From: Christian Kandeler Date: Fri, 25 Sep 2015 10:45:20 +0200 Subject: Fix comparisons between QByteArray and QString. QByteArray::operator< and friends had their logic reversed. Task-number: QTBUG-48350 Change-Id: I625209cc922b47e78dfb8de9fe100411f285a628 Reviewed-by: Thiago Macieira --- src/corelib/tools/qstring.h | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qstring.h b/src/corelib/tools/qstring.h index 63107ff688..d44a5baf2a 100644 --- a/src/corelib/tools/qstring.h +++ b/src/corelib/tools/qstring.h @@ -1228,13 +1228,13 @@ inline bool QByteArray::operator==(const QString &s) const inline bool QByteArray::operator!=(const QString &s) const { return QString::compare_helper(s.constData(), s.size(), constData(), qstrnlen(constData(), size())) != 0; } inline bool QByteArray::operator<(const QString &s) const -{ return QString::compare_helper(s.constData(), s.size(), constData(), qstrnlen(constData(), size())) < 0; } -inline bool QByteArray::operator>(const QString &s) const { return QString::compare_helper(s.constData(), s.size(), constData(), qstrnlen(constData(), size())) > 0; } +inline bool QByteArray::operator>(const QString &s) const +{ return QString::compare_helper(s.constData(), s.size(), constData(), qstrnlen(constData(), size())) < 0; } inline bool QByteArray::operator<=(const QString &s) const -{ return QString::compare_helper(s.constData(), s.size(), constData(), qstrnlen(constData(), size())) <= 0; } -inline bool QByteArray::operator>=(const QString &s) const { return QString::compare_helper(s.constData(), s.size(), constData(), qstrnlen(constData(), size())) >= 0; } +inline bool QByteArray::operator>=(const QString &s) const +{ return QString::compare_helper(s.constData(), s.size(), constData(), qstrnlen(constData(), size())) <= 0; } #endif // !defined(QT_NO_CAST_FROM_ASCII) && !defined(QT_RESTRICTED_CAST_FROM_ASCII) #ifndef QT_NO_CAST_TO_ASCII -- cgit v1.2.3 From 4accd865c24b7ed918cb705913478bab5aeb5e6e Mon Sep 17 00:00:00 2001 From: David Faure Date: Mon, 14 Sep 2015 11:11:54 +0200 Subject: QLockFile: sync to disk to avoid leaving an empty lock file on crash The two lines of code are the same as in QFSFileEnginePrivate::nativeSyncToDisk, but we don't want to create a fileengine instance just for this. qlockfile_win.cpp already calls FlushFileBuffers, only the Unix implementation was missing the equivalent call. Task-number: QTBUG-44771 Change-Id: I2253972857e4de9d27ef442c92983a1088d6f03e Reviewed-by: Thiago Macieira --- src/corelib/io/qlockfile_unix.cpp | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/io/qlockfile_unix.cpp b/src/corelib/io/qlockfile_unix.cpp index 27f8a97fd4..b298b08939 100644 --- a/src/corelib/io/qlockfile_unix.cpp +++ b/src/corelib/io/qlockfile_unix.cpp @@ -178,6 +178,13 @@ QLockFile::LockError QLockFilePrivate::tryLock_sys() // We hold the lock, continue. fileHandle = fd; + // Sync to disk if possible. Ignore errors (e.g. not supported). +#if defined(_POSIX_SYNCHRONIZED_IO) && _POSIX_SYNCHRONIZED_IO > 0 + fdatasync(fileHandle); +#else + fsync(fileHandle); +#endif + return QLockFile::NoError; } -- cgit v1.2.3 From ab6f941b50db3a99304dc4fff450de7dbca570bf Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Sun, 27 Sep 2015 12:38:35 -0700 Subject: QUrl::setPort: use the original port number in the error message Otherwise the error message will always say -1. Change-Id: I42e7ef1a481840699a8dffff1407eceec1906254 Reviewed-by: David Faure --- src/corelib/io/qurl.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qurl.cpp b/src/corelib/io/qurl.cpp index 89f5aad97f..9bf359222a 100644 --- a/src/corelib/io/qurl.cpp +++ b/src/corelib/io/qurl.cpp @@ -2411,8 +2411,8 @@ void QUrl::setPort(int port) d->clearError(); if (port < -1 || port > 65535) { - port = -1; d->setError(QUrlPrivate::InvalidPortError, QString::number(port), 0); + port = -1; } d->port = port; -- cgit v1.2.3 From 84a806589f93240ef39696729c6ce4c10bc4ab02 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Sun, 27 Sep 2015 11:52:35 -0700 Subject: Fix sign-extension If data[0] were > 128 (that is, if the full size, encoded in big endian were > 2 GB), the result of the OR chain would be a negative int (due to C integer promotion rules). We're shifting into the sign bit, which is either implementation-defined behavior or, worse, undefined behavior. This negative number is then sign-extended to ulong (64-bit on 64-bit platforms), which then becomes a big number. This code was probably written with only 32-bit in mind, where there would be no size extension (sign or otherwise). This isn't too bad because there's a size check for the max size of QByteArray a few lines below, but we can fix it, so let's do it. Found by Coverity, CID 22530. Change-Id: I42e7ef1a481840699a8dffff1407ea6c22e1a0ec Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/tools/qbytearray.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qbytearray.cpp b/src/corelib/tools/qbytearray.cpp index 5ed72fc341..a9f361c205 100644 --- a/src/corelib/tools/qbytearray.cpp +++ b/src/corelib/tools/qbytearray.cpp @@ -578,8 +578,8 @@ QByteArray qUncompress(const uchar* data, int nbytes) qWarning("qUncompress: Input data is corrupted"); return QByteArray(); } - ulong expectedSize = (data[0] << 24) | (data[1] << 16) | - (data[2] << 8) | (data[3] ); + ulong expectedSize = uint((data[0] << 24) | (data[1] << 16) | + (data[2] << 8) | (data[3] )); ulong len = qMax(expectedSize, 1ul); QScopedPointer d; -- cgit v1.2.3 From 9830857629e58dccefe6cf6be84925a01fff20ba Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Sun, 27 Sep 2015 12:19:58 -0700 Subject: QFSFileEngine: Remove unused member Change-Id: I42e7ef1a481840699a8dffff1407ebea9c7cb423 Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/io/qfsfileengine_p.h | 1 - 1 file changed, 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qfsfileengine_p.h b/src/corelib/io/qfsfileengine_p.h index 8ba05fa8b9..0a7f551672 100644 --- a/src/corelib/io/qfsfileengine_p.h +++ b/src/corelib/io/qfsfileengine_p.h @@ -199,7 +199,6 @@ public: bool closeFileHandle; mutable uint is_sequential : 2; - mutable uint could_stat : 1; mutable uint tried_stat : 1; #if !defined(Q_OS_WINCE) mutable uint need_lstat : 1; -- cgit v1.2.3 From 9ef87603553c59f8666e868a69b75bf240b9cc12 Mon Sep 17 00:00:00 2001 From: Joerg Bornemann Date: Mon, 28 Sep 2015 16:25:02 +0200 Subject: QWindowsPipeWriter: clean up OVERLAPPED resource handling Use RAII to ensure that every code path cleans up the event handle, and re-initialize the whole OVERLAPPED object, not just the two offset members. Change-Id: If7e68ec6e61b7bb04df0d06734c04589f6822c4a Reviewed-by: Oswald Buddenhagen --- src/corelib/io/qwindowspipewriter.cpp | 39 ++++++++++++++++++++++++++++------- 1 file changed, 31 insertions(+), 8 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qwindowspipewriter.cpp b/src/corelib/io/qwindowspipewriter.cpp index 57053f129a..e75712ba80 100644 --- a/src/corelib/io/qwindowspipewriter.cpp +++ b/src/corelib/io/qwindowspipewriter.cpp @@ -90,11 +90,38 @@ qint64 QWindowsPipeWriter::write(const char *ptr, qint64 maxlen) return maxlen; } +class QPipeWriterOverlapped +{ +public: + QPipeWriterOverlapped() + { + overlapped.hEvent = CreateEvent(NULL, TRUE, FALSE, NULL); + } + + ~QPipeWriterOverlapped() + { + CloseHandle(overlapped.hEvent); + } + + void prepare() + { + const HANDLE hEvent = overlapped.hEvent; + ZeroMemory(&overlapped, sizeof overlapped); + overlapped.hEvent = hEvent; + } + + OVERLAPPED *operator&() + { + return &overlapped; + } + +private: + OVERLAPPED overlapped; +}; + void QWindowsPipeWriter::run() { - OVERLAPPED overl; - memset(&overl, 0, sizeof overl); - overl.hEvent = CreateEvent(NULL, TRUE, FALSE, NULL); + QPipeWriterOverlapped overl; forever { lock.lock(); while(data.isEmpty() && (!quitNow)) { @@ -115,8 +142,7 @@ void QWindowsPipeWriter::run() const char *ptrData = copy.data(); qint64 maxlen = copy.size(); qint64 totalWritten = 0; - overl.Offset = 0; - overl.OffsetHigh = 0; + overl.prepare(); while ((!quitNow) && totalWritten < maxlen) { DWORD written = 0; if (!WriteFile(writePipe, ptrData + totalWritten, @@ -130,11 +156,9 @@ void QWindowsPipeWriter::run() #ifndef Q_OS_WINCE if (GetLastError() == ERROR_IO_PENDING) { if (!GetOverlappedResult(writePipe, &overl, &written, TRUE)) { - CloseHandle(overl.hEvent); return; } } else { - CloseHandle(overl.hEvent); return; } #else @@ -154,7 +178,6 @@ void QWindowsPipeWriter::run() emit bytesWritten(totalWritten); emit canWrite(); } - CloseHandle(overl.hEvent); } #endif //QT_NO_THREAD -- cgit v1.2.3 From 7fe5f82e48c023edff7c1c60a14f3958ffda8ad2 Mon Sep 17 00:00:00 2001 From: Joerg Bornemann Date: Mon, 28 Sep 2015 16:27:51 +0200 Subject: clean up QWindowsPipeWriter I/O error handling Exit early, and add warning messages for (unlikely) error cases. Change-Id: I7130b2e298f3a644a9d0e96a3a1860350e11adff Reviewed-by: Oswald Buddenhagen --- src/corelib/io/qwindowspipewriter.cpp | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qwindowspipewriter.cpp b/src/corelib/io/qwindowspipewriter.cpp index e75712ba80..fd14523d45 100644 --- a/src/corelib/io/qwindowspipewriter.cpp +++ b/src/corelib/io/qwindowspipewriter.cpp @@ -147,18 +147,19 @@ void QWindowsPipeWriter::run() DWORD written = 0; if (!WriteFile(writePipe, ptrData + totalWritten, maxlen - totalWritten, &written, &overl)) { - - if (GetLastError() == 0xE8/*NT_STATUS_INVALID_USER_BUFFER*/) { + const DWORD writeError = GetLastError(); + if (writeError == 0xE8/*NT_STATUS_INVALID_USER_BUFFER*/) { // give the os a rest msleep(100); continue; } #ifndef Q_OS_WINCE - if (GetLastError() == ERROR_IO_PENDING) { - if (!GetOverlappedResult(writePipe, &overl, &written, TRUE)) { - return; - } - } else { + if (writeError != ERROR_IO_PENDING) { + qErrnoWarning(writeError, "QWindowsPipeWriter: async WriteFile failed."); + return; + } + if (!GetOverlappedResult(writePipe, &overl, &written, TRUE)) { + qErrnoWarning(GetLastError(), "QWindowsPipeWriter: GetOverlappedResult failed."); return; } #else -- cgit v1.2.3 From ac0184d6085d9e4f7f59352e563055311f4d8792 Mon Sep 17 00:00:00 2001 From: Louai Al-Khanji Date: Mon, 21 Sep 2015 15:39:16 +0300 Subject: Add qt_safe_ftok wrapper for ftok The ftok function unfortunately can return duplicate keys even for different files if the same project id is used. This is discussed e.g. in Stevens' "Advanced Programming in the UNIX Environment". We want the key to be predictable so we cannot just pass a random number as the project id. To reduce the propability of key collisions we hash the file name with the project number as seed for a predictable value. This is the same approach taken e.g. by Apache, but the real fix is to move away from System V IPC completely once this is feasible on our supported platforms. Task-number: QTBUG-48375 Change-Id: If1a57f215f7ddd147aa38919907cfb83db07aea0 Reviewed-by: Thiago Macieira --- src/corelib/kernel/qcore_unix_p.h | 14 ++++++++++++++ src/corelib/kernel/qsharedmemory_systemv.cpp | 2 +- src/corelib/kernel/qsystemsemaphore_systemv.cpp | 2 +- 3 files changed, 16 insertions(+), 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/kernel/qcore_unix_p.h b/src/corelib/kernel/qcore_unix_p.h index c744873fce..f80dcb5a50 100644 --- a/src/corelib/kernel/qcore_unix_p.h +++ b/src/corelib/kernel/qcore_unix_p.h @@ -47,6 +47,7 @@ #include "qplatformdefs.h" #include "qatomic.h" +#include "qhash.h" #ifndef Q_OS_UNIX # error "qcore_unix_p.h included on a non-Unix system" @@ -322,6 +323,19 @@ union qt_semun { unsigned short *array; /* array for GETALL, SETALL */ }; +#ifndef QT_POSIX_IPC +#ifndef QT_NO_SHAREDMEMORY +#ifndef Q_OS_ANDROID +static inline key_t qt_safe_ftok(const QByteArray &filename, int proj_id) +{ + // Unfortunately ftok can return colliding keys even for different files. + // Try to add some more entropy via qHash. + return ::ftok(filename.constData(), qHash(filename, proj_id)); +} +#endif // !Q_OS_ANDROID +#endif // !QT_NO_SHAREDMEMORY +#endif // !QT_POSIX_IPC + QT_END_NAMESPACE #endif diff --git a/src/corelib/kernel/qsharedmemory_systemv.cpp b/src/corelib/kernel/qsharedmemory_systemv.cpp index 29fee12c0b..0d2eea49e9 100644 --- a/src/corelib/kernel/qsharedmemory_systemv.cpp +++ b/src/corelib/kernel/qsharedmemory_systemv.cpp @@ -82,7 +82,7 @@ key_t QSharedMemoryPrivate::handle() return 0; } - unix_key = ftok(QFile::encodeName(nativeKey).constData(), 'Q'); + unix_key = qt_safe_ftok(QFile::encodeName(nativeKey), 'Q'); if (-1 == unix_key) { errorString = QSharedMemory::tr("%1: ftok failed").arg(QLatin1String("QSharedMemory::handle:")); error = QSharedMemory::KeyError; diff --git a/src/corelib/kernel/qsystemsemaphore_systemv.cpp b/src/corelib/kernel/qsystemsemaphore_systemv.cpp index 32a4bdef51..490de5f9ee 100644 --- a/src/corelib/kernel/qsystemsemaphore_systemv.cpp +++ b/src/corelib/kernel/qsystemsemaphore_systemv.cpp @@ -85,7 +85,7 @@ key_t QSystemSemaphorePrivate::handle(QSystemSemaphore::AccessMode mode) createdFile = (1 == built); // Get the unix key for the created file - unix_key = ftok(QFile::encodeName(fileName).constData(), 'Q'); + unix_key = qt_safe_ftok(QFile::encodeName(fileName), 'Q'); if (-1 == unix_key) { errorString = QCoreApplication::tr("%1: ftok failed", "QSystemSemaphore").arg(QLatin1String("QSystemSemaphore::handle:")); error = QSystemSemaphore::KeyError; -- cgit v1.2.3 From b86efb1ab9daa76965cda5bdebb225c9e3762e8e Mon Sep 17 00:00:00 2001 From: Edward Welbourne Date: Thu, 24 Sep 2015 11:03:38 +0200 Subject: Initialize QFutureWatcherBasePrivate::finished and test MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit It's accessed by QFutureWatcherBase::isFinished(), potentially before anything has set it. It gets to be initially true until setFuture() has given it us unfinished future and set it false. Add a regression test for matching state in future and watcher. Task-number: QTBUG-12358 Change-Id: Iae7bdaa434ab80f518afe4d7d55df99c391991a4 Reviewed-by: Frederik Gladhorn Reviewed-by: Thiago Macieira Reviewed-by: Jędrzej Nowacki --- src/corelib/thread/qfuturewatcher.cpp | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/thread/qfuturewatcher.cpp b/src/corelib/thread/qfuturewatcher.cpp index 3056216f6e..3863a47673 100644 --- a/src/corelib/thread/qfuturewatcher.cpp +++ b/src/corelib/thread/qfuturewatcher.cpp @@ -248,7 +248,7 @@ bool QFutureWatcherBase::isStarted() const /*! \fn bool QFutureWatcher::isFinished() const Returns \c true if the asynchronous computation represented by the future() - has finished; otherwise returns \c false. + has finished, or if no future has been set; otherwise returns \c false. */ bool QFutureWatcherBase::isFinished() const { @@ -379,7 +379,8 @@ void QFutureWatcherBase::disconnectNotify(const QMetaMethod &signal) */ QFutureWatcherBasePrivate::QFutureWatcherBasePrivate() : maximumPendingResultsReady(QThread::idealThreadCount() * 2), - resultAtConnected(0) + resultAtConnected(0), + finished(true) /* the initial m_future is a canceledResult(), with Finished set */ { } /*! @@ -400,7 +401,7 @@ void QFutureWatcherBase::disconnectOutputInterface(bool pendingAssignment) d->pendingResultsReady.store(0); qDeleteAll(d->pendingCallOutEvents); d->pendingCallOutEvents.clear(); - d->finished = false; + d->finished = false; /* May soon be amended, during connectOutputInterface() */ } futureInterface().d->disconnectOutputInterface(d_func()); -- cgit v1.2.3 From 1d6643895dbcf8b720cbf85103032839fae4aa09 Mon Sep 17 00:00:00 2001 From: Edward Welbourne Date: Thu, 24 Sep 2015 12:37:57 +0200 Subject: Moved a comment to where it belongs. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit There was another function between the comment and the one it documented. Change-Id: I4e96979261738b1ef264984da0d6a8245f2fb643 Reviewed-by: Jędrzej Nowacki Reviewed-by: Oswald Buddenhagen --- src/corelib/thread/qfuturewatcher.cpp | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/thread/qfuturewatcher.cpp b/src/corelib/thread/qfuturewatcher.cpp index 3863a47673..43eff83116 100644 --- a/src/corelib/thread/qfuturewatcher.cpp +++ b/src/corelib/thread/qfuturewatcher.cpp @@ -304,15 +304,6 @@ void QFutureWatcherBase::waitForFinished() futureInterface().waitForFinished(); } -/*! \fn void QFutureWatcher::setPendingResultsLimit(int limit) - - The setPendingResultsLimit() provides throttling control. When the number - of pending resultReadyAt() or resultsReadyAt() signals exceeds the - \a limit, the computation represented by the future will be throttled - automatically. The computation will resume once the number of pending - signals drops below the \a limit. -*/ - bool QFutureWatcherBase::event(QEvent *event) { Q_D(QFutureWatcherBase); @@ -342,6 +333,14 @@ bool QFutureWatcherBase::event(QEvent *event) return QObject::event(event); } +/*! \fn void QFutureWatcher::setPendingResultsLimit(int limit) + + The setPendingResultsLimit() provides throttling control. When the number + of pending resultReadyAt() or resultsReadyAt() signals exceeds the + \a limit, the computation represented by the future will be throttled + automatically. The computation will resume once the number of pending + signals drops below the \a limit. +*/ void QFutureWatcherBase::setPendingResultsLimit(int limit) { Q_D(QFutureWatcherBase); -- cgit v1.2.3 From 2c5126b9dec0c4997fd5b21f065f4152910633fe Mon Sep 17 00:00:00 2001 From: Edward Welbourne Date: Mon, 28 Sep 2015 15:37:45 +0200 Subject: Purge extraneous execute permissions. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Source files should not be executable. Change-Id: If9b9eaa6c8c7348ca6f48fa9253f3540e95aca37 Reviewed-by: Oswald Buddenhagen Reviewed-by: Frederik Gladhorn Reviewed-by: Jędrzej Nowacki --- src/corelib/tools/qalgorithms.qdoc | 0 1 file changed, 0 insertions(+), 0 deletions(-) mode change 100755 => 100644 src/corelib/tools/qalgorithms.qdoc (limited to 'src/corelib') diff --git a/src/corelib/tools/qalgorithms.qdoc b/src/corelib/tools/qalgorithms.qdoc old mode 100755 new mode 100644 -- cgit v1.2.3 From 8233e401b1892b27e669546c8df02c2320e8e775 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Sun, 27 Sep 2015 12:56:59 -0700 Subject: QLocale: remove (harmless) dead code On line 92 and on line 146, len == 2 or len == 3, so uc1 and uc2 cannot be 0, ever. Found by Coverity, CID 11013 and CID 11012. Change-Id: I42e7ef1a481840699a8dffff1407edefd3e7aa4f Reviewed-by: Oswald Buddenhagen --- src/corelib/tools/qlocale.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qlocale.cpp b/src/corelib/tools/qlocale.cpp index 181daa04e4..57ef53eea4 100644 --- a/src/corelib/tools/qlocale.cpp +++ b/src/corelib/tools/qlocale.cpp @@ -89,9 +89,9 @@ QLocale::Language QLocalePrivate::codeToLanguage(const QString &code) int len = code.length(); if (len != 2 && len != 3) return QLocale::C; - ushort uc1 = len-- > 0 ? code[0].toLower().unicode() : 0; - ushort uc2 = len-- > 0 ? code[1].toLower().unicode() : 0; - ushort uc3 = len-- > 0 ? code[2].toLower().unicode() : 0; + ushort uc1 = code[0].toLower().unicode(); + ushort uc2 = code[1].toLower().unicode(); + ushort uc3 = len > 2 ? code[2].toLower().unicode() : 0; const unsigned char *c = language_code_list; for (; *c != 0; c += 3) { @@ -145,9 +145,9 @@ QLocale::Country QLocalePrivate::codeToCountry(const QString &code) int len = code.length(); if (len != 2 && len != 3) return QLocale::AnyCountry; - ushort uc1 = len-- > 0 ? code[0].toUpper().unicode() : 0; - ushort uc2 = len-- > 0 ? code[1].toUpper().unicode() : 0; - ushort uc3 = len-- > 0 ? code[2].toUpper().unicode() : 0; + ushort uc1 = code[0].toUpper().unicode(); + ushort uc2 = code[1].toUpper().unicode(); + ushort uc3 = len > 2 ? code[2].toUpper().unicode() : 0; const unsigned char *c = country_code_list; for (; *c != 0; c += 3) { -- cgit v1.2.3 From e9365c2c2fecbc779c44456fb1c946905a670684 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Mon, 28 Sep 2015 15:26:57 -0700 Subject: Revert "Add support for same-file intrinsics with Clang 3.7" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This reverts commit 39c2b8c5c12dfb8560fa04ce346a129adb223e29. The feature is not working: $ clang -c -o /dev/null -msse2 -include tmmintrin.h -xc /dev/null In file included from :316: In file included from :1: /home/thiago/clang3.7/bin/../lib/clang/3.7.0/include/tmmintrin.h:28:2: error: "SSSE3 instruction set not enabled" For reference: $ icpc -c -o /dev/null -msse2 -include tmmintrin.h -xc /dev/null; echo $? 0 $ gcc -c -o /dev/null -msse2 -include tmmintrin.h -xc /dev/null; echo $? 0 Change-Id: I42e7ef1a481840699a8dffff140844cb8872ed6e Reviewed-by: Sérgio Martins --- src/corelib/tools/qsimd_p.h | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qsimd_p.h b/src/corelib/tools/qsimd_p.h index bb9c26f762..1e8b3420cf 100644 --- a/src/corelib/tools/qsimd_p.h +++ b/src/corelib/tools/qsimd_p.h @@ -54,9 +54,9 @@ * for the x86 and ARM intrinsics: * - GCC: the -mXXX or march=YYY flag is necessary before #include * up to 4.8; GCC >= 4.9 can include unconditionally - * - Clang: same as GCC, with unconditional inclusion with version 3.7 * - Intel CC: #include can happen unconditionally * - MSVC: #include can happen unconditionally + * - RVCT: ??? * * We will try to include all headers possible under this configuration. * @@ -138,8 +138,7 @@ #define QT_COMPILER_SUPPORTS(x) (QT_COMPILER_SUPPORTS_ ## x - 0) #if (defined(Q_CC_INTEL) || defined(Q_CC_MSVC) \ - || (defined(Q_CC_GNU) && !defined(Q_CC_CLANG) && (__GNUC__-0) * 100 + (__GNUC_MINOR__-0) >= 409) \ - || (defined(Q_CC_CLANG) && Q_CC_CLANG >= 307)) \ + || (defined(Q_CC_GNU) && !defined(Q_CC_CLANG) && (__GNUC__-0) * 100 + (__GNUC_MINOR__-0) >= 409)) \ && !defined(QT_BOOTSTRAPPED) # define QT_COMPILER_SUPPORTS_SIMD_ALWAYS # define QT_COMPILER_SUPPORTS_HERE(x) QT_COMPILER_SUPPORTS(x) -- cgit v1.2.3 From 7c0b9e1e8d069afab997efd3df9632d342b23150 Mon Sep 17 00:00:00 2001 From: Simon Hausmann Date: Fri, 2 Oct 2015 11:00:53 +0200 Subject: Fix build without PCH after commit 3ae2387f375798a983b6d052723f10fc88b63da0 Include errno.h for errno and EEXIST. Change-Id: Id28d5a08097319eb84b1fe9ef20c9be6ebe575fa Reviewed-by: Frederik Gladhorn --- src/corelib/io/qtemporarydir.cpp | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/io/qtemporarydir.cpp b/src/corelib/io/qtemporarydir.cpp index c7150d7b33..71436c6497 100644 --- a/src/corelib/io/qtemporarydir.cpp +++ b/src/corelib/io/qtemporarydir.cpp @@ -49,6 +49,10 @@ #include #endif +#if !defined(Q_OS_WIN) +#include +#endif + QT_BEGIN_NAMESPACE //************* QTemporaryDirPrivate -- cgit v1.2.3 From 549eada0ab1b277b380251beb16379b77cd9d8a1 Mon Sep 17 00:00:00 2001 From: Topi Reinio Date: Fri, 25 Sep 2015 14:26:23 +0200 Subject: Doc: Use correct image in Qt::BusyCursor documentation Change-Id: I54e832808a37d46f5520c57ceb2a270685ed3f94 Task-number: QTBUG-48445 Reviewed-by: Martin Smith --- src/corelib/global/qnamespace.qdoc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/global/qnamespace.qdoc b/src/corelib/global/qnamespace.qdoc index 7947f7d1a0..adfa28d384 100644 --- a/src/corelib/global/qnamespace.qdoc +++ b/src/corelib/global/qnamespace.qdoc @@ -2405,7 +2405,7 @@ \value WhatsThisCursor \inlineimage cursor-whatsthis.png An arrow with a question mark, typically used to indicate the presence of What's This? help for a widget. - \value BusyCursor \inlineimage cursor-wait.png + \value BusyCursor \inlineimage cursor-busy.png An hourglass or watch cursor, usually shown during operations that allow the user to interact with the application while they are performed in the -- cgit v1.2.3 From fbf3daef384706cd5ddc15c48bcf0b3980eaf6a4 Mon Sep 17 00:00:00 2001 From: Topi Reinio Date: Thu, 24 Sep 2015 10:10:19 +0200 Subject: Doc: Update obsolete URLs to external documentation Change-Id: I199de83971701c14e903e712fcdcd29aaff95c6d Task-number: QTBUG-48420 Reviewed-by: Venugopal Shivashankar Reviewed-by: Liang Qi --- src/corelib/doc/src/eventsandfilters.qdoc | 2 +- src/corelib/global/qnamespace.qdoc | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/doc/src/eventsandfilters.qdoc b/src/corelib/doc/src/eventsandfilters.qdoc index a4710eb288..99a40bb1b8 100644 --- a/src/corelib/doc/src/eventsandfilters.qdoc +++ b/src/corelib/doc/src/eventsandfilters.qdoc @@ -100,7 +100,7 @@ event delivery mechanisms are flexible. The documentation for QCoreApplication::notify() concisely tells the whole story; the \e{Qt Quarterly} article - \l{http://doc.qt.digia.com/qq/qq11-events.html}{Another Look at Events} + \l{http://doc.qt.io/archives/qq/qq11-events.html}{Another Look at Events} rehashes it less concisely. Here we will explain enough for 95% of applications. diff --git a/src/corelib/global/qnamespace.qdoc b/src/corelib/global/qnamespace.qdoc index adfa28d384..b8ce8792cb 100644 --- a/src/corelib/global/qnamespace.qdoc +++ b/src/corelib/global/qnamespace.qdoc @@ -2715,7 +2715,7 @@ "\l{http://bugreports.qt.io/browse/QTWEBSITE-13}{http://bugreports.qt.../QTWEBSITE-13/}"), whereas Qt::ElideRight is appropriate for other strings (e.g., - "\l{http://doc.qt.digia.com/qq/qq09-mac-deployment.html}{Deploying Applications on Ma...}"). + "\l{http://doc.qt.io/archives/qq/qq09-mac-deployment.html}{Deploying Applications on Ma...}"). \sa QAbstractItemView::textElideMode, QFontMetrics::elidedText(), AlignmentFlag, QTabBar::elideMode */ -- cgit v1.2.3 From d49169ae890bcf4f341b7c2f36b875668f063de6 Mon Sep 17 00:00:00 2001 From: Nico Vertriest Date: Tue, 29 Sep 2015 13:36:16 +0200 Subject: Doc: replace \target with \keyword if at start of page MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit A \target whose purpose is to link to the top of a page (and not to a section within a page) works better as a \keyword, because \target generates a new html anchor which, in this case, is not tied to any title element on the page. A \keyword links to the page itself, as expected. Task-number: QTBUG-48482 Change-Id: I957551edd0eb7e665358d04b37dab41e2686b851 Reviewed-by: Topi Reiniö --- src/corelib/doc/src/objectmodel/metaobjects.qdoc | 2 +- src/corelib/doc/src/objectmodel/properties.qdoc | 2 +- src/corelib/global/qnamespace.qdoc | 2 +- src/corelib/plugin/qplugin.qdoc | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/doc/src/objectmodel/metaobjects.qdoc b/src/corelib/doc/src/objectmodel/metaobjects.qdoc index a482c5cc8b..52c134c517 100644 --- a/src/corelib/doc/src/objectmodel/metaobjects.qdoc +++ b/src/corelib/doc/src/objectmodel/metaobjects.qdoc @@ -32,7 +32,7 @@ \ingroup qt-basic-concepts \keyword meta-object - \target Meta-Object System + \keyword Meta-Object System Qt's meta-object system provides the signals and slots mechanism for inter-object communication, run-time type information, and the dynamic diff --git a/src/corelib/doc/src/objectmodel/properties.qdoc b/src/corelib/doc/src/objectmodel/properties.qdoc index 55622dd56b..28be328e3a 100644 --- a/src/corelib/doc/src/objectmodel/properties.qdoc +++ b/src/corelib/doc/src/objectmodel/properties.qdoc @@ -31,7 +31,7 @@ \brief An overview of Qt's property system. \ingroup qt-basic-concepts - \target Qt's Property System + \keyword Qt's Property System Qt provides a sophisticated property system similar to the ones supplied by some compiler vendors. However, as a compiler- and diff --git a/src/corelib/global/qnamespace.qdoc b/src/corelib/global/qnamespace.qdoc index b8ce8792cb..3dc791397c 100644 --- a/src/corelib/global/qnamespace.qdoc +++ b/src/corelib/global/qnamespace.qdoc @@ -28,7 +28,7 @@ /*! \namespace Qt \inmodule QtCore - \target Qt Namespace + \keyword Qt Namespace \brief The Qt namespace contains miscellaneous identifiers used throughout the Qt library. diff --git a/src/corelib/plugin/qplugin.qdoc b/src/corelib/plugin/qplugin.qdoc index 94f5bc8a30..00ecb30430 100644 --- a/src/corelib/plugin/qplugin.qdoc +++ b/src/corelib/plugin/qplugin.qdoc @@ -28,7 +28,7 @@ /*! \headerfile \title Defining Plugins - \target qtplugin-defining-plugins + \keyword qtplugin-defining-plugins \ingroup plugins \brief The header file defines macros for defining plugins. -- cgit v1.2.3 From 76cd806e6de3f9ed8e89b73dc5babfb227ea8760 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tor=20Arne=20Vestb=C3=B8?= Date: Fri, 2 Oct 2015 13:53:31 +0200 Subject: Remove extra semicolon in declaration of QMacAutoReleasePool Change-Id: Ie7f92fae5f80fc2a8b4dae58f6688ea47dbcb95b Reviewed-by: Simon Hausmann --- src/corelib/global/qglobal.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/global/qglobal.h b/src/corelib/global/qglobal.h index 6ee3e37ce6..4813c2b100 100644 --- a/src/corelib/global/qglobal.h +++ b/src/corelib/global/qglobal.h @@ -602,7 +602,7 @@ public: QMacAutoReleasePool(); ~QMacAutoReleasePool(); private: - Q_DISABLE_COPY(QMacAutoReleasePool); + Q_DISABLE_COPY(QMacAutoReleasePool) NSAutoreleasePool *pool; }; -- cgit v1.2.3 From da5b8bfe4647f4a0494e7dd2e08d6652f72803f0 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Mon, 5 Oct 2015 10:53:00 +0200 Subject: Add missing "We mean it" comments to private headers. Change-Id: If81a5e1db0fe93377e7cc54a78b01c50b44abe57 Reviewed-by: Liang Qi --- src/corelib/global/qhooks_p.h | 11 +++++++++++ 1 file changed, 11 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/global/qhooks_p.h b/src/corelib/global/qhooks_p.h index 12a59a1399..3ff4980abe 100644 --- a/src/corelib/global/qhooks_p.h +++ b/src/corelib/global/qhooks_p.h @@ -35,6 +35,17 @@ #ifndef QHOOKS_H #define QHOOKS_H +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists purely as an +// implementation detail. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + #include QT_BEGIN_NAMESPACE -- cgit v1.2.3 From 9684e16f002f4f813c49141de2933a7fb0c71461 Mon Sep 17 00:00:00 2001 From: Thiago Macieira Date: Sun, 27 Sep 2015 13:26:56 -0700 Subject: QUtf8Codec: Remove dead code The maximum value for charsNeeded is 4, so if bytesAvailable is less than charsNeeded - 1, the it's at most 2. It can't be larger than 2. Found by Coverity, CID 11000. Change-Id: I42e7ef1a481840699a8dffff1407ef9221a4fd80 Reviewed-by: Lars Knoll --- src/corelib/codecs/qutfcodec_p.h | 2 -- 1 file changed, 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/codecs/qutfcodec_p.h b/src/corelib/codecs/qutfcodec_p.h index 99887352c9..d97145c6fc 100644 --- a/src/corelib/codecs/qutfcodec_p.h +++ b/src/corelib/codecs/qutfcodec_p.h @@ -217,8 +217,6 @@ namespace QUtf8Functions return Traits::Error; if (bytesAvailable > 1 && !isContinuationByte(Traits::peekByte(src, 1))) return Traits::Error; - if (bytesAvailable > 2 && !isContinuationByte(Traits::peekByte(src, 2))) - return Traits::Error; return Traits::EndOfString; } -- cgit v1.2.3 From 590c73bee2083c8dc8635123726e138a26dd3a97 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Fri, 2 Oct 2015 09:08:45 +0200 Subject: Add static assert checking QT_POINTER_SIZE. QT_POINTER_SIZE is determined by the configure test ptrsize, which has been observed to fail due to unrelated build issues. Add a check to verify the correct size. Task-number: QTBUG-48525 Change-Id: I4fcb9761b54370b39c0d3e1e0a6d0aa3c0223f40 Reviewed-by: Joerg Bornemann --- src/corelib/global/qglobal.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/global/qglobal.cpp b/src/corelib/global/qglobal.cpp index 7da9713e80..02220d0db2 100644 --- a/src/corelib/global/qglobal.cpp +++ b/src/corelib/global/qglobal.cpp @@ -120,7 +120,9 @@ Q_CORE_EXPORT void *qMemSet(void *dest, int c, size_t n); // (if this list becomes too long, consider factoring into a separate file) Q_STATIC_ASSERT_X(sizeof(int) == 4, "Qt assumes that int is 32 bits"); Q_STATIC_ASSERT_X(UCHAR_MAX == 255, "Qt assumes that char is 8 bits"); - +#ifndef QT_BOOTSTRAPPED +Q_STATIC_ASSERT_X(QT_POINTER_SIZE == sizeof(void *), "configure test ptrsize failed to correctly determine QT_POINTER_SIZE"); +#endif /*! \class QFlag -- cgit v1.2.3 From c87bb03e5eb53b7a33a8501b8f5b4227ec7ddd57 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Wed, 24 Jun 2015 15:25:11 +0200 Subject: QDebug: add missing docs for op<<(Container) Change-Id: I9f89d8e792bf0d432a0b2522f26026c6ad81e2f4 Reviewed-by: Thiago Macieira --- src/corelib/io/qdebug.cpp | 56 +++++++++++++++++++++++++++++++++++++++++++++++ src/corelib/io/qdebug.h | 16 +++++++------- 2 files changed, 64 insertions(+), 8 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qdebug.cpp b/src/corelib/io/qdebug.cpp index 30086b2dac..6b8f832eed 100644 --- a/src/corelib/io/qdebug.cpp +++ b/src/corelib/io/qdebug.cpp @@ -668,6 +668,62 @@ QDebug &QDebug::resetFormat() \internal */ +/*! + \fn QDebug operator<<(QDebug stream, const QList &list) + \relates QDebug + + Writes the contents of \a list to \a stream. \c T needs to + support streaming into QDebug. +*/ + +/*! + \fn QDebug operator<<(QDebug stream, const QVector &vector) + \relates QDebug + + Writes the contents of \a vector to \a stream. \c T needs to + support streaming into QDebug. +*/ + +/*! + \fn QDebug operator<<(QDebug stream, const QSet &set) + \relates QDebug + + Writes the contents of \a set to \a stream. \c T needs to + support streaming into QDebug. +*/ + +/*! + \fn QDebug operator<<(QDebug stream, const QMap &map) + \relates QDebug + + Writes the contents of \a map to \a stream. Both \c Key and + \c T need to support streaming into QDebug. +*/ + +/*! + \fn QDebug operator<<(QDebug stream, const QHash &hash) + \relates QDebug + + Writes the contents of \a hash to \a stream. Both \c Key and + \c T need to support streaming into QDebug. +*/ + +/*! + \fn QDebug operator<<(QDebug stream, const QPair &pair) + \relates QDebug + + Writes the contents of \a pair to \a stream. Both \c T1 and + \c T2 need to support streaming into QDebug. +*/ + +/*! + \fn QDebug operator<<(QDebug stream, const QFlags &flag) + \relates QDebug + \since 4.7 + + Writes \a flag to \a stream. +*/ + /*! \class QDebugStateSaver diff --git a/src/corelib/io/qdebug.h b/src/corelib/io/qdebug.h index 3c3ceba249..7c75608e2a 100644 --- a/src/corelib/io/qdebug.h +++ b/src/corelib/io/qdebug.h @@ -201,12 +201,12 @@ inline QDebug operator<<(QDebug debug, const QVector &vec) return operator<<(debug, vec.toList()); } -template -inline QDebug operator<<(QDebug debug, const QMap &map) +template +inline QDebug operator<<(QDebug debug, const QMap &map) { const bool oldSetting = debug.autoInsertSpaces(); debug.nospace() << "QMap("; - for (typename QMap::const_iterator it = map.constBegin(); + for (typename QMap::const_iterator it = map.constBegin(); it != map.constEnd(); ++it) { debug << '(' << it.key() << ", " << it.value() << ')'; } @@ -215,12 +215,12 @@ inline QDebug operator<<(QDebug debug, const QMap &map) return debug.maybeSpace(); } -template -inline QDebug operator<<(QDebug debug, const QHash &hash) +template +inline QDebug operator<<(QDebug debug, const QHash &hash) { const bool oldSetting = debug.autoInsertSpaces(); debug.nospace() << "QHash("; - for (typename QHash::const_iterator it = hash.constBegin(); + for (typename QHash::const_iterator it = hash.constBegin(); it != hash.constEnd(); ++it) debug << '(' << it.key() << ", " << it.value() << ')'; debug << ')'; @@ -261,7 +261,7 @@ inline QDebug operator<<(QDebug debug, const QContiguousCache &cache) return debug.maybeSpace(); } -#ifndef QT_NO_QOBJECT +#if !defined(QT_NO_QOBJECT) && !defined(Q_QDOC) Q_CORE_EXPORT QDebug qt_QMetaEnum_debugOperator(QDebug&, int value, const QMetaObject *meta, const char *name); Q_CORE_EXPORT QDebug qt_QMetaEnum_flagDebugOperator(QDebug &dbg, quint64 value, const QMetaObject *meta, const char *name); @@ -290,7 +290,7 @@ inline typename QtPrivate::QEnableIf< !QtPrivate::IsQEnumHelper::Value && !QtPrivate::IsQEnumHelper >::Value, QDebug>::Type qt_QMetaEnum_flagDebugOperator_helper(QDebug debug, const QFlags &flags) -#else // !QT_NO_QOBJECT +#else // !QT_NO_QOBJECT && !Q_QDOC template inline QDebug qt_QMetaEnum_flagDebugOperator_helper(QDebug debug, const QFlags &flags) #endif -- cgit v1.2.3 From 48e9f69dfbec7650fb8aa4c99c8978082a87186e Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Sun, 19 Jul 2015 21:43:23 +0200 Subject: doc: fix a typo in QVersionNumber docs Change-Id: I6ba901efe0822ed1d5ae8359f8b7aefe730f2d06 Reviewed-by: Keith Gardner Reviewed-by: Thiago Macieira --- src/corelib/tools/qversionnumber.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qversionnumber.cpp b/src/corelib/tools/qversionnumber.cpp index 4197fc47b1..f432820252 100644 --- a/src/corelib/tools/qversionnumber.cpp +++ b/src/corelib/tools/qversionnumber.cpp @@ -202,7 +202,7 @@ QVector QVersionNumber::segments() const Returns an equivalent version number but with all trailing zeros removed. To check if two numbers are equivalent, use normalized() on both version - numbers before perforing the compare. + numbers before performing the compare. \snippet qversionnumber/main.cpp 4 */ -- cgit v1.2.3 From 52812e9a2b578d3c25f85612a6fdcffbdefd84e1 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Mon, 6 Jul 2015 16:57:31 +0200 Subject: QMulti(Map|Hash): add move ctor from Q(Map|Hash) There was a copy ctor, a move ctor was missing. Change-Id: If09a4d4c74682169759eff43b298f6c77702c169 Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/tools/qhash.h | 3 +++ src/corelib/tools/qmap.h | 3 +++ 2 files changed, 6 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/tools/qhash.h b/src/corelib/tools/qhash.h index 8d65a018ae..8e71925fd9 100644 --- a/src/corelib/tools/qhash.h +++ b/src/corelib/tools/qhash.h @@ -948,6 +948,9 @@ public: // compiler-generated destructor is fine! QMultiHash(const QHash &other) : QHash(other) {} +#ifdef Q_COMPILER_RVALUE_REFS + QMultiHash(QHash &&other) Q_DECL_NOTHROW : QHash(std::move(other)) {} +#endif void swap(QMultiHash &other) { QHash::swap(other); } // prevent QMultiHash<->QHash swaps inline typename QHash::iterator replace(const Key &key, const T &value) diff --git a/src/corelib/tools/qmap.h b/src/corelib/tools/qmap.h index b7bd268bda..df2e5f1caf 100644 --- a/src/corelib/tools/qmap.h +++ b/src/corelib/tools/qmap.h @@ -1177,6 +1177,9 @@ public: } #endif QMultiMap(const QMap &other) : QMap(other) {} +#ifdef Q_COMPILER_RVALUE_REFS + QMultiMap(QMap &&other) Q_DECL_NOTHROW : QMap(std::move(other)) {} +#endif inline void swap(QMultiMap &other) { QMap::swap(other); } inline typename QMap::iterator replace(const Key &key, const T &value) -- cgit v1.2.3 From f89803e459ca02ad4be0c2e1620b80b0cb248642 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Fri, 3 Jul 2015 13:24:31 +0200 Subject: Make container move semantics consistent Make all containers (excepting QVarLengthArray) - nothrow default-constructible - nothrow move-constructible - nothrow move-assignable - nothrow swappable [ChangeLog][QtCore] All containers (with the exception of QVarLengthArray, but including QSharedPointer) are now nothrow_default_constructible, nothrow_move_constructible, nothrow_move_assignable, and nothrow-swappable. Change-Id: I12138d262f9f7f600f0e1218137da208c12e7c0a Reviewed-by: Thiago Macieira --- src/corelib/tools/qbitarray.h | 2 +- src/corelib/tools/qhash.h | 4 ++-- src/corelib/tools/qlinkedlist.h | 9 +++++---- src/corelib/tools/qlist.h | 7 ++++--- src/corelib/tools/qmap.h | 12 ++++++------ src/corelib/tools/qqueue.h | 2 +- src/corelib/tools/qset.h | 4 ++-- src/corelib/tools/qstack.h | 2 +- 8 files changed, 22 insertions(+), 20 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qbitarray.h b/src/corelib/tools/qbitarray.h index 4e5c26b86a..e686d53db4 100644 --- a/src/corelib/tools/qbitarray.h +++ b/src/corelib/tools/qbitarray.h @@ -48,7 +48,7 @@ class Q_CORE_EXPORT QBitArray QByteArray d; public: - inline QBitArray() {} + inline QBitArray() Q_DECL_NOTHROW {} explicit QBitArray(int size, bool val = false); QBitArray(const QBitArray &other) : d(other.d) {} inline QBitArray &operator=(const QBitArray &other) { d = other.d; return *this; } diff --git a/src/corelib/tools/qhash.h b/src/corelib/tools/qhash.h index 8e71925fd9..a18dd74706 100644 --- a/src/corelib/tools/qhash.h +++ b/src/corelib/tools/qhash.h @@ -935,7 +935,7 @@ template class QMultiHash : public QHash { public: - QMultiHash() {} + QMultiHash() Q_DECL_NOTHROW {} #ifdef Q_COMPILER_INITIALIZER_LISTS inline QMultiHash(std::initializer_list > list) { @@ -951,7 +951,7 @@ public: #ifdef Q_COMPILER_RVALUE_REFS QMultiHash(QHash &&other) Q_DECL_NOTHROW : QHash(std::move(other)) {} #endif - void swap(QMultiHash &other) { QHash::swap(other); } // prevent QMultiHash<->QHash swaps + void swap(QMultiHash &other) Q_DECL_NOTHROW { QHash::swap(other); } // prevent QMultiHash<->QHash swaps inline typename QHash::iterator replace(const Key &key, const T &value) { return QHash::insert(key, value); } diff --git a/src/corelib/tools/qlinkedlist.h b/src/corelib/tools/qlinkedlist.h index f216aa121c..2854885d60 100644 --- a/src/corelib/tools/qlinkedlist.h +++ b/src/corelib/tools/qlinkedlist.h @@ -74,7 +74,7 @@ class QLinkedList union { QLinkedListData *d; QLinkedListNode *e; }; public: - inline QLinkedList() : d(const_cast(&QLinkedListData::shared_null)) { } + inline QLinkedList() Q_DECL_NOTHROW : d(const_cast(&QLinkedListData::shared_null)) { } inline QLinkedList(const QLinkedList &l) : d(l.d) { d->ref.ref(); if (!d->sharable) detach(); } #if defined(Q_COMPILER_INITIALIZER_LISTS) inline QLinkedList(std::initializer_list list) @@ -86,11 +86,12 @@ public: ~QLinkedList(); QLinkedList &operator=(const QLinkedList &); #ifdef Q_COMPILER_RVALUE_REFS - inline QLinkedList(QLinkedList &&other) : d(other.d) { other.d = const_cast(&QLinkedListData::shared_null); } - inline QLinkedList &operator=(QLinkedList &&other) + QLinkedList(QLinkedList &&other) Q_DECL_NOTHROW + : d(other.d) { other.d = const_cast(&QLinkedListData::shared_null); } + QLinkedList &operator=(QLinkedList &&other) Q_DECL_NOTHROW { QLinkedList moved(std::move(other)); swap(moved); return *this; } #endif - inline void swap(QLinkedList &other) { qSwap(d, other.d); } + inline void swap(QLinkedList &other) Q_DECL_NOTHROW { qSwap(d, other.d); } bool operator==(const QLinkedList &l) const; inline bool operator!=(const QLinkedList &l) const { return !(*this == l); } diff --git a/src/corelib/tools/qlist.h b/src/corelib/tools/qlist.h index 32e0141d55..9a57a2c6a5 100644 --- a/src/corelib/tools/qlist.h +++ b/src/corelib/tools/qlist.h @@ -143,11 +143,12 @@ public: ~QList(); QList &operator=(const QList &l); #ifdef Q_COMPILER_RVALUE_REFS - inline QList(QList &&other) : d(other.d) { other.d = const_cast(&QListData::shared_null); } - inline QList &operator=(QList &&other) + inline QList(QList &&other) Q_DECL_NOTHROW + : d(other.d) { other.d = const_cast(&QListData::shared_null); } + inline QList &operator=(QList &&other) Q_DECL_NOTHROW { QList moved(std::move(other)); swap(moved); return *this; } #endif - inline void swap(QList &other) { qSwap(d, other.d); } + inline void swap(QList &other) Q_DECL_NOTHROW { qSwap(d, other.d); } #ifdef Q_COMPILER_INITIALIZER_LISTS inline QList(std::initializer_list args) : d(const_cast(&QListData::shared_null)) diff --git a/src/corelib/tools/qmap.h b/src/corelib/tools/qmap.h index df2e5f1caf..fe9ddaaa32 100644 --- a/src/corelib/tools/qmap.h +++ b/src/corelib/tools/qmap.h @@ -321,7 +321,7 @@ class QMap QMapData *d; public: - inline QMap() : d(static_cast *>(const_cast(&QMapDataBase::shared_null))) { } + inline QMap() Q_DECL_NOTHROW : d(static_cast *>(const_cast(&QMapDataBase::shared_null))) { } #ifdef Q_COMPILER_INITIALIZER_LISTS inline QMap(std::initializer_list > list) : d(static_cast *>(const_cast(&QMapDataBase::shared_null))) @@ -336,17 +336,17 @@ public: QMap &operator=(const QMap &other); #ifdef Q_COMPILER_RVALUE_REFS - inline QMap(QMap &&other) + inline QMap(QMap &&other) Q_DECL_NOTHROW : d(other.d) { other.d = static_cast *>( const_cast(&QMapDataBase::shared_null)); } - inline QMap &operator=(QMap &&other) + inline QMap &operator=(QMap &&other) Q_DECL_NOTHROW { QMap moved(std::move(other)); swap(moved); return *this; } #endif - inline void swap(QMap &other) { qSwap(d, other.d); } + inline void swap(QMap &other) Q_DECL_NOTHROW { qSwap(d, other.d); } explicit QMap(const typename std::map &other); std::map toStdMap() const; @@ -1168,7 +1168,7 @@ template class QMultiMap : public QMap { public: - QMultiMap() {} + QMultiMap() Q_DECL_NOTHROW {} #ifdef Q_COMPILER_INITIALIZER_LISTS inline QMultiMap(std::initializer_list > list) { @@ -1180,7 +1180,7 @@ public: #ifdef Q_COMPILER_RVALUE_REFS QMultiMap(QMap &&other) Q_DECL_NOTHROW : QMap(std::move(other)) {} #endif - inline void swap(QMultiMap &other) { QMap::swap(other); } + void swap(QMultiMap &other) Q_DECL_NOTHROW { QMap::swap(other); } inline typename QMap::iterator replace(const Key &key, const T &value) { return QMap::insert(key, value); } diff --git a/src/corelib/tools/qqueue.h b/src/corelib/tools/qqueue.h index 7a7abab070..0cb8353d0f 100644 --- a/src/corelib/tools/qqueue.h +++ b/src/corelib/tools/qqueue.h @@ -44,7 +44,7 @@ class QQueue : public QList { public: // compiler-generated special member functions are fine! - inline void swap(QQueue &other) { QList::swap(other); } // prevent QList<->QQueue swaps + inline void swap(QQueue &other) Q_DECL_NOTHROW { QList::swap(other); } // prevent QList<->QQueue swaps #ifndef Q_QDOC // bring in QList::swap(int, int). We cannot say using QList::swap, // because we don't want to make swap(QList&) available. diff --git a/src/corelib/tools/qset.h b/src/corelib/tools/qset.h index aeba6cf68d..ed89617cd6 100644 --- a/src/corelib/tools/qset.h +++ b/src/corelib/tools/qset.h @@ -48,7 +48,7 @@ class QSet typedef QHash Hash; public: - inline QSet() {} + inline QSet() Q_DECL_NOTHROW {} #ifdef Q_COMPILER_INITIALIZER_LISTS inline QSet(std::initializer_list list) { @@ -60,7 +60,7 @@ public: // compiler-generated copy/move ctor/assignment operators are fine! // compiler-generated destructor is fine! - inline void swap(QSet &other) { q_hash.swap(other.q_hash); } + inline void swap(QSet &other) Q_DECL_NOTHROW { q_hash.swap(other.q_hash); } inline bool operator==(const QSet &other) const { return q_hash == other.q_hash; } diff --git a/src/corelib/tools/qstack.h b/src/corelib/tools/qstack.h index 278e89ca2f..cb72316c32 100644 --- a/src/corelib/tools/qstack.h +++ b/src/corelib/tools/qstack.h @@ -44,7 +44,7 @@ class QStack : public QVector { public: // compiler-generated special member functions are fine! - inline void swap(QStack &other) { QVector::swap(other); } // prevent QVector<->QStack swaps + inline void swap(QStack &other) Q_DECL_NOTHROW { QVector::swap(other); } // prevent QVector<->QStack swaps inline void push(const T &t) { QVector::append(t); } T pop(); T &top(); -- cgit v1.2.3 From b1a8f75db8740a630e97994df0465251208a3470 Mon Sep 17 00:00:00 2001 From: Lars Knoll Date: Mon, 21 Sep 2015 14:11:16 +0200 Subject: Add \since 5.6 to method docs and document the changed signal Change-Id: I9a727a2a01927693e8182eb5518ee4d8f6e5be23 Reviewed-by: Thiago Macieira Reviewed-by: Erik Verbruggen --- src/corelib/statemachine/qhistorystate.cpp | 13 +++++++++++++ 1 file changed, 13 insertions(+) (limited to 'src/corelib') diff --git a/src/corelib/statemachine/qhistorystate.cpp b/src/corelib/statemachine/qhistorystate.cpp index a0ebb9d239..8887ce27e5 100644 --- a/src/corelib/statemachine/qhistorystate.cpp +++ b/src/corelib/statemachine/qhistorystate.cpp @@ -166,6 +166,8 @@ QHistoryState::~QHistoryState() Returns this history state's default transition. The default transition is taken when the history state has never been entered before. The target states of the default transition therefore make up the default state. + + \since 5.6 */ QAbstractTransition *QHistoryState::defaultTransition() const { @@ -178,6 +180,8 @@ QAbstractTransition *QHistoryState::defaultTransition() const This will set the source state of the \a transition to the history state. Note that the eventTest method of the \a transition will never be called. + + \since 5.6 */ void QHistoryState::setDefaultTransition(QAbstractTransition *transition) { @@ -290,6 +294,15 @@ bool QHistoryState::event(QEvent *e) \sa QHistoryState::historyType */ +/*! + \fn QHistoryState::defaultTransitionChanged() + \since 5.6 + + This signal is emitted when the defaultTransition property is changed. + + \sa QHistoryState::defaultTransition +*/ + QT_END_NAMESPACE #endif //QT_NO_STATEMACHINE -- cgit v1.2.3 From 275f5347efffd3919aae884eb5943fbe36010fc5 Mon Sep 17 00:00:00 2001 From: Lars Knoll Date: Mon, 21 Sep 2015 14:20:25 +0200 Subject: Fix \since This API only appeared in 5.6. Change-Id: I3ddda44f7c55c94c7f22f76f83a45094209d8c39 Reviewed-by: Thiago Macieira --- src/corelib/tools/qcommandlineparser.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qcommandlineparser.cpp b/src/corelib/tools/qcommandlineparser.cpp index 20e0688f45..15c7a0646f 100644 --- a/src/corelib/tools/qcommandlineparser.cpp +++ b/src/corelib/tools/qcommandlineparser.cpp @@ -325,13 +325,13 @@ void QCommandLineParser::setSingleDashWordOptionMode(QCommandLineParser::SingleD \sa setOptionsAfterPositionalArgumentsMode() - \since 5.5 + \since 5.6 */ /*! Sets the parsing mode to \a parsingMode. This must be called before process() or parse(). - \since 5.5 + \since 5.6 */ void QCommandLineParser::setOptionsAfterPositionalArgumentsMode(QCommandLineParser::OptionsAfterPositionalArgumentsMode parsingMode) { -- cgit v1.2.3 From a3a7d485fa2d572225c7050badf28784316aec37 Mon Sep 17 00:00:00 2001 From: Olivier Goffart Date: Wed, 30 Sep 2015 23:27:20 +0200 Subject: Fix crash in QMetaProperty::write for custom types and conversion MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit if t >= QMetaType::User, we would not return false nor call convert. We would then pass a pointer to whatever is in the QVariant to the qt_metacall that is expecting a pointer to an object of a different type. Since we have custom converters, we can call QVarent::convert even for custom types anyway. [ChangeLog][QtCore] Fixed crash when setting a QVariant of a different type to a property of a custom type. Attempt to do a conversion instead. Task-number: QTBUG-40644 Change-Id: Ib6fbd7e7ddcf25c5ee247ea04177e079f6d7de35 Reviewed-by: Jędrzej Nowacki --- src/corelib/kernel/qmetaobject.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/kernel/qmetaobject.cpp b/src/corelib/kernel/qmetaobject.cpp index f1ad74efb4..6abec27684 100644 --- a/src/corelib/kernel/qmetaobject.cpp +++ b/src/corelib/kernel/qmetaobject.cpp @@ -1,7 +1,7 @@ /**************************************************************************** ** ** Copyright (C) 2015 The Qt Company Ltd. -** Copyright (C) 2014 Olivier Goffart +** Copyright (C) 2015 Olivier Goffart ** Contact: http://www.qt.io/licensing/ ** ** This file is part of the QtCore module of the Qt Toolkit. @@ -3068,7 +3068,7 @@ bool QMetaProperty::write(QObject *object, const QVariant &value) const if (t == QMetaType::UnknownType) return false; } - if (t != QMetaType::QVariant && t != (uint)value.userType() && (t < QMetaType::User && !v.convert((QVariant::Type)t))) + if (t != QMetaType::QVariant && int(t) != value.userType() && !v.convert(t)) return false; } -- cgit v1.2.3 From de70798859e0363c8ca3133a4ed1a1092cfe47f5 Mon Sep 17 00:00:00 2001 From: Olivier Goffart Date: Tue, 6 Oct 2015 10:14:26 +0200 Subject: QMetaProperty::write should reset the property if an empty QVariant is given MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit [ChangeLog][QtCore][QMetaProperty] write() now resets the property if an empty QVariant is given, or set a default constructed object if the property is not resettable Change-Id: I9f9b57114e740f03ec4db6f223c1e8280a3d5209 Reviewed-by: Jędrzej Nowacki Reviewed-by: Oswald Buddenhagen --- src/corelib/kernel/qmetaobject.cpp | 16 ++++++++++++++-- src/corelib/kernel/qobject.cpp | 2 +- 2 files changed, 15 insertions(+), 3 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/kernel/qmetaobject.cpp b/src/corelib/kernel/qmetaobject.cpp index 6abec27684..820af298c0 100644 --- a/src/corelib/kernel/qmetaobject.cpp +++ b/src/corelib/kernel/qmetaobject.cpp @@ -3028,6 +3028,11 @@ QVariant QMetaProperty::read(const QObject *object) const Writes \a value as the property's value to the given \a object. Returns true if the write succeeded; otherwise returns \c false. + If \a value is not of the same type type as the property, a conversion + is attempted. An empty QVariant() is equivalent to a call to reset() + if this property is resetable, or setting a default-constructed object + otherwise. + \sa read(), reset(), isWritable() */ bool QMetaProperty::write(QObject *object, const QVariant &value) const @@ -3068,8 +3073,15 @@ bool QMetaProperty::write(QObject *object, const QVariant &value) const if (t == QMetaType::UnknownType) return false; } - if (t != QMetaType::QVariant && int(t) != value.userType() && !v.convert(t)) - return false; + if (t != QMetaType::QVariant && int(t) != value.userType()) { + if (!value.isValid()) { + if (isResettable()) + return reset(object); + v = QVariant(t, 0); + } else if (!v.convert(t)) { + return false; + } + } } // the status variable is changed by qt_metacall to indicate what it did diff --git a/src/corelib/kernel/qobject.cpp b/src/corelib/kernel/qobject.cpp index 4bd8b4b662..c9884cd76c 100644 --- a/src/corelib/kernel/qobject.cpp +++ b/src/corelib/kernel/qobject.cpp @@ -3831,7 +3831,7 @@ int QObjectPrivate::signalIndex(const char *signalName, \b{Note:} Dynamic properties starting with "_q_" are reserved for internal purposes. - \sa property(), metaObject(), dynamicPropertyNames() + \sa property(), metaObject(), dynamicPropertyNames(), QMetaProperty::write() */ bool QObject::setProperty(const char *name, const QVariant &value) { -- cgit v1.2.3 From 48663eafd3521eadcd6094178afa75909dc3c09e Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Sat, 10 Oct 2015 10:00:32 +0200 Subject: QtCore/qmake: drop some unneeded QChar -> QString conversions Change-Id: Id2fb5089b0ec51073efb846b59ecc63942cfb60d Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/kernel/qvariant.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib') diff --git a/src/corelib/kernel/qvariant.cpp b/src/corelib/kernel/qvariant.cpp index 35f178e6a9..fdcbdb1c45 100644 --- a/src/corelib/kernel/qvariant.cpp +++ b/src/corelib/kernel/qvariant.cpp @@ -413,7 +413,7 @@ static bool convert(const QVariant::Private *d, int t, void *result, bool *ok) QString *str = static_cast(result); switch (d->type) { case QVariant::Char: - *str = QString(*v_cast(d)); + *str = *v_cast(d); break; case QMetaType::Char: case QMetaType::SChar: -- cgit v1.2.3 From a6ddae873bbe4c3cc68949f5a2758b5458422e7c Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Sat, 10 Oct 2015 10:34:46 +0200 Subject: QtCore: Don't compare QChars to literal 0s This is prone to ambiguities, even though we currently don't run into them. Use QChar::isNull() instead. Change-Id: I71843878b3f4f8a5deae2ef57a6f6628461be216 Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/io/qdir.cpp | 2 +- src/corelib/tools/qstring.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qdir.cpp b/src/corelib/io/qdir.cpp index e1d9858a66..4d2b36632f 100644 --- a/src/corelib/io/qdir.cpp +++ b/src/corelib/io/qdir.cpp @@ -138,7 +138,7 @@ inline QChar QDirPrivate::getFilterSepChar(const QString &nameFilter) // static inline QStringList QDirPrivate::splitFilters(const QString &nameFilter, QChar sep) { - if (sep == 0) + if (sep.isNull()) sep = getFilterSepChar(nameFilter); QStringList ret = nameFilter.split(sep); for (int i = 0; i < ret.count(); ++i) diff --git a/src/corelib/tools/qstring.cpp b/src/corelib/tools/qstring.cpp index e3a3cc79c6..ea220ed557 100644 --- a/src/corelib/tools/qstring.cpp +++ b/src/corelib/tools/qstring.cpp @@ -1509,7 +1509,7 @@ QString::QString(const QChar *unicode, int size) } else { if (size < 0) { size = 0; - while (unicode[size] != 0) + while (!unicode[size].isNull()) ++size; } if (!size) { -- cgit v1.2.3 From 2463b4452da6267d23bf1008a6472b30690690bc Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Sat, 10 Oct 2015 10:38:29 +0200 Subject: QtCore: don't convert single characters to QString for QTextCodec::fromUnicode() Use the fromUnicode(QChar *, int size) overload instead. Saves 0.5KiB text size on Linux GCC 4.9 AMD64 release builds. Change-Id: I1a1081e09bff4c2116288b8c2616e1bb7ee2bb42 Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/io/qsettings.cpp | 5 +++-- src/corelib/xml/qxmlstream.cpp | 3 ++- 2 files changed, 5 insertions(+), 3 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qsettings.cpp b/src/corelib/io/qsettings.cpp index b9993c454e..458109888f 100644 --- a/src/corelib/io/qsettings.cpp +++ b/src/corelib/io/qsettings.cpp @@ -632,8 +632,9 @@ void QSettingsPrivate::iniEscapedString(const QString &str, QByteArray &result, int startPos = result.size(); result.reserve(startPos + str.size() * 3 / 2); + const QChar *unicode = str.unicode(); for (i = 0; i < str.size(); ++i) { - uint ch = str.at(i).unicode(); + uint ch = unicode[i].unicode(); if (ch == ';' || ch == ',' || ch == '=') needsQuotes = true; @@ -687,7 +688,7 @@ void QSettingsPrivate::iniEscapedString(const QString &str, QByteArray &result, #ifndef QT_NO_TEXTCODEC } else if (useCodec) { // slow - result += codec->fromUnicode(str.at(i)); + result += codec->fromUnicode(&unicode[i], 1); #endif } else { result += (char)ch; diff --git a/src/corelib/xml/qxmlstream.cpp b/src/corelib/xml/qxmlstream.cpp index 13c84db9ae..69e2e5d5c1 100644 --- a/src/corelib/xml/qxmlstream.cpp +++ b/src/corelib/xml/qxmlstream.cpp @@ -3013,7 +3013,8 @@ void QXmlStreamWriterPrivate::checkIfASCIICompatibleCodec() #ifndef QT_NO_TEXTCODEC Q_ASSERT(encoder); // assumes ASCII-compatibility for all 8-bit encodings - const QByteArray bytes = encoder->fromUnicode(QStringLiteral(" ")); + QChar space = QLatin1Char(' '); + const QByteArray bytes = encoder->fromUnicode(&space, 1); isCodecASCIICompatible = (bytes.count() == 1); #else isCodecASCIICompatible = true; -- cgit v1.2.3 From 690f9a7e74701e64db1035ccb11673942988d927 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Sat, 10 Oct 2015 23:40:58 +0200 Subject: QtCore: use QStringRef in more places Apart from removing some unwanted allocations, also reduces text size by ~800B on Linux AMD64 GCC 4.9 release builds. Change-Id: Ibcd1d8264f54f2b165b69bee8aa50ff7f4ad3a10 Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/io/qfilesystemengine.cpp | 2 +- src/corelib/io/qfilesystementry.cpp | 3 +-- src/corelib/io/qfilesystemwatcher.cpp | 6 ++++-- src/corelib/io/qresource.cpp | 6 +++--- src/corelib/io/qsettings.cpp | 4 ++-- src/corelib/io/qsettings_mac.cpp | 4 ++-- src/corelib/plugin/qpluginloader.cpp | 6 +++--- 7 files changed, 16 insertions(+), 15 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qfilesystemengine.cpp b/src/corelib/io/qfilesystemengine.cpp index e4dec2b7fb..a49d69d447 100644 --- a/src/corelib/io/qfilesystemengine.cpp +++ b/src/corelib/io/qfilesystemengine.cpp @@ -152,7 +152,7 @@ static bool _q_resolveEntryAndCreateLegacyEngine_recursive(QFileSystemEntry &ent const QStringList &paths = QDir::searchPaths(filePath.left(prefixSeparator)); for (int i = 0; i < paths.count(); i++) { - entry = QFileSystemEntry(QDir::cleanPath(paths.at(i) % QLatin1Char('/') % filePath.mid(prefixSeparator + 1))); + entry = QFileSystemEntry(QDir::cleanPath(paths.at(i) % QLatin1Char('/') % filePath.midRef(prefixSeparator + 1))); // Recurse! if (_q_resolveEntryAndCreateLegacyEngine_recursive(entry, data, engine, true)) return true; diff --git a/src/corelib/io/qfilesystementry.cpp b/src/corelib/io/qfilesystementry.cpp index 79f16a0839..709970e3ac 100644 --- a/src/corelib/io/qfilesystementry.cpp +++ b/src/corelib/io/qfilesystementry.cpp @@ -53,8 +53,7 @@ static bool isUncRoot(const QString &server) if (idx == -1 || idx + 1 == localPath.length()) return true; - localPath = localPath.right(localPath.length() - idx - 1).trimmed(); - return localPath.isEmpty(); + return localPath.rightRef(localPath.length() - idx - 1).trimmed().isEmpty(); } static inline QString fixIfRelativeUncPath(const QString &path) diff --git a/src/corelib/io/qfilesystemwatcher.cpp b/src/corelib/io/qfilesystemwatcher.cpp index 7fc3049f46..23a2fbecdb 100644 --- a/src/corelib/io/qfilesystemwatcher.cpp +++ b/src/corelib/io/qfilesystemwatcher.cpp @@ -296,7 +296,9 @@ QStringList QFileSystemWatcher::addPaths(const QStringList &paths) QFileSystemWatcherEngine *engine = 0; - if(!objectName().startsWith(QLatin1String("_qt_autotest_force_engine_"))) { + const QString on = objectName(); + + if (!on.startsWith(QLatin1String("_qt_autotest_force_engine_"))) { // Normal runtime case - search intelligently for best engine if(d->native) { engine = d->native; @@ -307,7 +309,7 @@ QStringList QFileSystemWatcher::addPaths(const QStringList &paths) } else { // Autotest override case - use the explicitly selected engine only - QString forceName = objectName().mid(26); + const QStringRef forceName = on.midRef(26); if(forceName == QLatin1String("poller")) { qDebug() << "QFileSystemWatcher: skipping native engine, using only polling engine"; d_func()->initPollerEngine(); diff --git a/src/corelib/io/qresource.cpp b/src/corelib/io/qresource.cpp index 4e6079306b..0674ef34e0 100644 --- a/src/corelib/io/qresource.cpp +++ b/src/corelib/io/qresource.cpp @@ -800,8 +800,8 @@ bool QResourceRoot::mappingRootSubdir(const QString &path, QString *match) const { const QString root = mappingRoot(); if(!root.isEmpty()) { - const QStringList root_segments = root.split(QLatin1Char('/'), QString::SkipEmptyParts), - path_segments = path.split(QLatin1Char('/'), QString::SkipEmptyParts); + const QVector root_segments = root.splitRef(QLatin1Char('/'), QString::SkipEmptyParts), + path_segments = path.splitRef(QLatin1Char('/'), QString::SkipEmptyParts); if(path_segments.size() <= root_segments.size()) { int matched = 0; for(int i = 0; i < path_segments.size(); ++i) { @@ -811,7 +811,7 @@ bool QResourceRoot::mappingRootSubdir(const QString &path, QString *match) const } if(matched == path_segments.size()) { if(match && root_segments.size() > matched) - *match = root_segments.at(matched); + *match = root_segments.at(matched).toString(); return true; } } diff --git a/src/corelib/io/qsettings.cpp b/src/corelib/io/qsettings.cpp index 458109888f..0c44582af8 100644 --- a/src/corelib/io/qsettings.cpp +++ b/src/corelib/io/qsettings.cpp @@ -488,7 +488,7 @@ QVariant QSettingsPrivate::stringToVariant(const QString &s) if (s.startsWith(QLatin1Char('@'))) { if (s.endsWith(QLatin1Char(')'))) { if (s.startsWith(QLatin1String("@ByteArray("))) { - return QVariant(s.toLatin1().mid(11, s.size() - 12)); + return QVariant(s.midRef(11, s.size() - 12).toLatin1()); } else if (s.startsWith(QLatin1String("@Variant(")) || s.startsWith(QLatin1String("@DateTime("))) { #ifndef QT_NO_DATASTREAM @@ -501,7 +501,7 @@ QVariant QSettingsPrivate::stringToVariant(const QString &s) version = QDataStream::Qt_4_0; offset = 9; } - QByteArray a(s.toLatin1().mid(offset)); + QByteArray a = s.midRef(offset).toLatin1(); QDataStream stream(&a, QIODevice::ReadOnly); stream.setVersion(version); QVariant result; diff --git a/src/corelib/io/qsettings_mac.cpp b/src/corelib/io/qsettings_mac.cpp index 1ad198b990..f1d2e81bdc 100644 --- a/src/corelib/io/qsettings_mac.cpp +++ b/src/corelib/io/qsettings_mac.cpp @@ -403,11 +403,11 @@ QMacSettingsPrivate::QMacSettingsPrivate(QSettings::Scope scope, const QString & } while ((nextDot = domainName.indexOf(QLatin1Char('.'), curPos)) != -1) { - javaPackageName.prepend(domainName.mid(curPos, nextDot - curPos)); + javaPackageName.prepend(domainName.midRef(curPos, nextDot - curPos)); javaPackageName.prepend(QLatin1Char('.')); curPos = nextDot + 1; } - javaPackageName.prepend(domainName.mid(curPos)); + javaPackageName.prepend(domainName.midRef(curPos)); javaPackageName = javaPackageName.toLower(); if (curPos == 0) javaPackageName.prepend(QLatin1String("com.")); diff --git a/src/corelib/plugin/qpluginloader.cpp b/src/corelib/plugin/qpluginloader.cpp index 292ad30525..24101be87b 100644 --- a/src/corelib/plugin/qpluginloader.cpp +++ b/src/corelib/plugin/qpluginloader.cpp @@ -286,9 +286,9 @@ static QString locatePlugin(const QString& fileName) suffixes.prepend(QString()); // Split up "subdir/filename" - const int slash = fileName.lastIndexOf('/'); - const QString baseName = fileName.mid(slash + 1); - const QString basePath = isAbsolute ? QString() : fileName.left(slash + 1); // keep the '/' + const int slash = fileName.lastIndexOf(QLatin1Char('/')); + const QStringRef baseName = fileName.midRef(slash + 1); + const QStringRef basePath = isAbsolute ? QStringRef() : fileName.leftRef(slash + 1); // keep the '/' const bool debug = qt_debug_component(); -- cgit v1.2.3 From 5962c6e37e747044ab005ca53c7a90b4db210767 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Sat, 10 Oct 2015 23:41:14 +0200 Subject: QtCore: use QStringBuilder in more places Change-Id: I1a2016039c6cfa35505b987b6d4627bf806500ba Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/io/qprocess.cpp | 12 ++---------- src/corelib/io/qtldurl.cpp | 15 +++++---------- 2 files changed, 7 insertions(+), 20 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qprocess.cpp b/src/corelib/io/qprocess.cpp index 8ee8d0b703..8fbe96adb9 100644 --- a/src/corelib/io/qprocess.cpp +++ b/src/corelib/io/qprocess.cpp @@ -156,16 +156,8 @@ QStringList QProcessEnvironmentPrivate::toList() const { QStringList result; result.reserve(hash.size()); - Hash::ConstIterator it = hash.constBegin(), - end = hash.constEnd(); - for ( ; it != end; ++it) { - QString data = nameToString(it.key()); - QString value = valueToString(it.value()); - data.reserve(data.length() + value.length() + 1); - data.append(QLatin1Char('=')); - data.append(value); - result << data; - } + for (Hash::const_iterator it = hash.cbegin(), end = hash.cend(); it != end; ++it) + result << nameToString(it.key()) + QLatin1Char('=') + valueToString(it.value()); return result; } diff --git a/src/corelib/io/qtldurl.cpp b/src/corelib/io/qtldurl.cpp index d68d0ddf46..265055083e 100644 --- a/src/corelib/io/qtldurl.cpp +++ b/src/corelib/io/qtldurl.cpp @@ -99,19 +99,14 @@ Q_CORE_EXPORT bool qIsEffectiveTLD(const QString &domain) if (containsTLDEntry(domain)) return true; - if (domain.contains(QLatin1Char('.'))) { - int count = domain.size() - domain.indexOf(QLatin1Char('.')); - QString wildCardDomain; - wildCardDomain.reserve(count + 1); - wildCardDomain.append(QLatin1Char('*')); - wildCardDomain.append(domain.right(count)); + const int dot = domain.indexOf(QLatin1Char('.')); + if (dot >= 0) { + int count = domain.size() - dot; + QString wildCardDomain = QLatin1Char('*') + domain.rightRef(count); // 2. if table contains '*.bar.com', // test if table contains '!foo.bar.com' if (containsTLDEntry(wildCardDomain)) { - QString exceptionDomain; - exceptionDomain.reserve(domain.size() + 1); - exceptionDomain.append(QLatin1Char('!')); - exceptionDomain.append(domain); + QString exceptionDomain = QLatin1Char('!') + domain; return (! containsTLDEntry(exceptionDomain)); } } -- cgit v1.2.3 From a2f6ece27f95eb7cb9940af6ba734d4ba52bf4cb Mon Sep 17 00:00:00 2001 From: Giuseppe D'Angelo Date: Fri, 9 Oct 2015 11:13:27 +0200 Subject: QLockFile: fix errno handling In case of a lock failure, we potentially pollute the errno value before printing it. Also, switch to qt_error_string, as strerror is not reentrant. Change-Id: I952aac14204637155726bcefc0ed8a21d7fcd501 Reviewed-by: David Faure --- src/corelib/io/qlockfile_unix.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qlockfile_unix.cpp b/src/corelib/io/qlockfile_unix.cpp index 5ff4b1cbe1..bd9f8a5988 100644 --- a/src/corelib/io/qlockfile_unix.cpp +++ b/src/corelib/io/qlockfile_unix.cpp @@ -171,8 +171,10 @@ QLockFile::LockError QLockFilePrivate::tryLock_sys() } } // Ensure nobody else can delete the file while we have it - if (!setNativeLocks(fd)) - qWarning() << "setNativeLocks failed:" << strerror(errno); + if (!setNativeLocks(fd)) { + const int errnoSaved = errno; + qWarning() << "setNativeLocks failed:" << qt_error_string(errnoSaved); + } if (qt_write_loop(fd, fileData.constData(), fileData.size()) < fileData.size()) { close(fd); -- cgit v1.2.3 From a623fe8d2a60ff333d5779f877e3b20f0e141ff1 Mon Sep 17 00:00:00 2001 From: Juha Turunen Date: Sun, 11 Oct 2015 20:29:51 -0700 Subject: Fixed a QTimer::singleShot() crash when a functor callback is used If QTimer::singleShot() is used with a functor callback and a context object with different thread affinity than the caller, a crash can occur. If the context object's thread is scheduled before connecting to QCoreApplication::aboutToQuit(), the timer has a change to fire and QSingleShotTimer::timerEvent() will delete the QSingleShotTimer object making the this pointer used in the connection invalid. This can occur relatively often if an interval of 0 is used. Making the moveToThread() call the last thing in the constructor ensures that the constructor gets to run to completion before the timer has a chance to fire. Task-number: QTBUG-48700 Change-Id: Iab73d02933635821b8d1ca1ff3d53e92eca85834 Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/kernel/qtimer.cpp | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/kernel/qtimer.cpp b/src/corelib/kernel/qtimer.cpp index b9109a96aa..af9a1be6ab 100644 --- a/src/corelib/kernel/qtimer.cpp +++ b/src/corelib/kernel/qtimer.cpp @@ -278,15 +278,10 @@ QSingleShotTimer::QSingleShotTimer(int msec, Qt::TimerType timerType, const QObj { timerId = startTimer(msec, timerType); if (r && thread() != r->thread()) { - // We need the invocation to happen in the receiver object's thread. - // So, move QSingleShotTimer to the correct thread. Before that occurs, we - // shall remove the parent from the object. + // Avoid leaking the QSingleShotTimer instance in case the application exits before the timer fires + connect(QCoreApplication::instance(), &QCoreApplication::aboutToQuit, this, &QObject::deleteLater); setParent(0); moveToThread(r->thread()); - - // Given we're also parentless now, we should take defence against leaks - // in case the application quits before we expire. - connect(QCoreApplication::instance(), &QCoreApplication::aboutToQuit, this, &QObject::deleteLater); } } -- cgit v1.2.3 From f9bf737d74c2493f7a535048cb4992d3e4cd3c99 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Tue, 13 Oct 2015 09:06:58 +0200 Subject: Examples/Doc snippets: Fix single-character string literals. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Use character literals where applicable. Change-Id: I79fa5018f05735201ae35ee94ba0d356fcad1056 Reviewed-by: Topi Reiniö --- src/corelib/doc/snippets/code/doc_src_containers.cpp | 6 +++--- src/corelib/doc/snippets/code/src_corelib_tools_qhash.cpp | 6 +++--- src/corelib/doc/snippets/code/src_corelib_tools_qlinkedlist.cpp | 6 +++--- src/corelib/doc/snippets/code/src_corelib_tools_qmap.cpp | 6 +++--- src/corelib/doc/snippets/qstring/main.cpp | 4 ++-- src/corelib/doc/snippets/qstringlist/main.cpp | 2 +- 6 files changed, 15 insertions(+), 15 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/doc/snippets/code/doc_src_containers.cpp b/src/corelib/doc/snippets/code/doc_src_containers.cpp index 00971d69b9..395e48bc89 100644 --- a/src/corelib/doc/snippets/code/doc_src_containers.cpp +++ b/src/corelib/doc/snippets/code/doc_src_containers.cpp @@ -176,7 +176,7 @@ QMap map; ... QMap::const_iterator i; for (i = map.constBegin(); i != map.constEnd(); ++i) - qDebug() << i.key() << ":" << i.value(); + qDebug() << i.key() << ':' << i.value(); //! [13] @@ -236,7 +236,7 @@ foreach (const QString &str, list) { QMap map; ... foreach (const QString &str, map.keys()) - qDebug() << str << ":" << map.value(str); + qDebug() << str << ':' << map.value(str); //! [19] @@ -245,7 +245,7 @@ QMultiMap map; ... foreach (const QString &str, map.uniqueKeys()) { foreach (int i, map.values(str)) - qDebug() << str << ":" << i; + qDebug() << str << ':' << i; } //! [20] diff --git a/src/corelib/doc/snippets/code/src_corelib_tools_qhash.cpp b/src/corelib/doc/snippets/code/src_corelib_tools_qhash.cpp index 0ac7cb5769..0976488a48 100644 --- a/src/corelib/doc/snippets/code/src_corelib_tools_qhash.cpp +++ b/src/corelib/doc/snippets/code/src_corelib_tools_qhash.cpp @@ -220,7 +220,7 @@ for (i = hash.begin(); i != hash.end(); ++i) //! [19] QHash::iterator i = hash.begin(); while (i != hash.end()) { - if (i.key().startsWith("_")) + if (i.key().startsWith('_')) i = hash.erase(i); else ++i; @@ -233,7 +233,7 @@ QHash::iterator i = hash.begin(); while (i != hash.end()) { QHash::iterator prev = i; ++i; - if (prev.key().startsWith("_")) + if (prev.key().startsWith('_')) hash.erase(prev); } //! [20] @@ -242,7 +242,7 @@ while (i != hash.end()) { //! [21] // WRONG while (i != hash.end()) { - if (i.key().startsWith("_")) + if (i.key().startsWith('_')) hash.erase(i); ++i; } diff --git a/src/corelib/doc/snippets/code/src_corelib_tools_qlinkedlist.cpp b/src/corelib/doc/snippets/code/src_corelib_tools_qlinkedlist.cpp index 014af8b0ee..f1cf644df6 100644 --- a/src/corelib/doc/snippets/code/src_corelib_tools_qlinkedlist.cpp +++ b/src/corelib/doc/snippets/code/src_corelib_tools_qlinkedlist.cpp @@ -128,7 +128,7 @@ QLinkedList list; ... QLinkedList::iterator i = list.begin(); while (i != list.end()) { - if ((*i).startsWith("_")) + if ((*i).startsWith('_')) i = list.erase(i); else ++i; @@ -141,7 +141,7 @@ QLinkedList::iterator i = list.begin(); while (i != list.end()) { QLinkedList::iterator previous = i; ++i; - if ((*previous).startsWith("_")) + if ((*previous).startsWith('_')) list.erase(previous); } //! [11] @@ -150,7 +150,7 @@ while (i != list.end()) { //! [12] // WRONG while (i != list.end()) { - if ((*i).startsWith("_")) + if ((*i).startsWith('_')) list.erase(i); ++i; } diff --git a/src/corelib/doc/snippets/code/src_corelib_tools_qmap.cpp b/src/corelib/doc/snippets/code/src_corelib_tools_qmap.cpp index 29e53fc700..3241991129 100644 --- a/src/corelib/doc/snippets/code/src_corelib_tools_qmap.cpp +++ b/src/corelib/doc/snippets/code/src_corelib_tools_qmap.cpp @@ -234,7 +234,7 @@ for (i = map.begin(); i != map.end(); ++i) //! [20] QMap::iterator i = map.begin(); while (i != map.end()) { - if (i.key().startsWith("_")) + if (i.key().startsWith('_')) i = map.erase(i); else ++i; @@ -247,7 +247,7 @@ QMap::iterator i = map.begin(); while (i != map.end()) { QMap::iterator prev = i; ++i; - if (prev.key().startsWith("_")) + if (prev.key().startsWith('_')) map.erase(prev); } //! [21] @@ -256,7 +256,7 @@ while (i != map.end()) { //! [22] // WRONG while (i != map.end()) { - if (i.key().startsWith("_")) + if (i.key().startsWith('_')) map.erase(i); ++i; } diff --git a/src/corelib/doc/snippets/qstring/main.cpp b/src/corelib/doc/snippets/qstring/main.cpp index e03e705a0b..d0b5fb00f3 100644 --- a/src/corelib/doc/snippets/qstring/main.cpp +++ b/src/corelib/doc/snippets/qstring/main.cpp @@ -777,10 +777,10 @@ void Widget::splitCaseSensitiveFunction() //! [62] QString str = "a,,b,c"; - QStringList list1 = str.split(","); + QStringList list1 = str.split(','); // list1: [ "a", "", "b", "c" ] - QStringList list2 = str.split(",", QString::SkipEmptyParts); + QStringList list2 = str.split(',', QString::SkipEmptyParts); // list2: [ "a", "b", "c" ] //! [62] } diff --git a/src/corelib/doc/snippets/qstringlist/main.cpp b/src/corelib/doc/snippets/qstringlist/main.cpp index 64f2061786..04d4dc8a89 100644 --- a/src/corelib/doc/snippets/qstringlist/main.cpp +++ b/src/corelib/doc/snippets/qstringlist/main.cpp @@ -82,7 +82,7 @@ Widget::Widget(QWidget *parent) //! [5] //! [6] QStringList list; //! [5] - list = str.split(","); + list = str.split(','); // list: ["Arial", "Helvetica", "Times", "Courier"] //! [6] -- cgit v1.2.3 From bba86a01c9828d03b1564984a08561d62686d329 Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Tue, 13 Oct 2015 09:26:59 +0200 Subject: Libraries: Fix single-character string literals. Use character literals where applicable. Change-Id: I8e198774c2247c1cc1d852a41b59b301199b7878 Reviewed-by: Marc Mutz --- src/corelib/io/qfilesystemwatcher_win.cpp | 2 +- src/corelib/io/qsettings_mac.cpp | 2 +- src/corelib/json/qjsondocument.cpp | 2 +- src/corelib/json/qjsonvalue.cpp | 10 +++++----- src/corelib/json/qjsonwriter.cpp | 4 ++-- src/corelib/statemachine/qstatemachine.cpp | 6 +++--- src/corelib/tools/qregularexpression.cpp | 10 +++++----- 7 files changed, 18 insertions(+), 18 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/io/qfilesystemwatcher_win.cpp b/src/corelib/io/qfilesystemwatcher_win.cpp index 4907a20a5f..410753868e 100644 --- a/src/corelib/io/qfilesystemwatcher_win.cpp +++ b/src/corelib/io/qfilesystemwatcher_win.cpp @@ -186,7 +186,7 @@ QStringList QWindowsFileSystemWatcherEngine::addPaths(const QStringList &paths, } if (!found) { QWindowsFileSystemWatcherEngineThread *thread = new QWindowsFileSystemWatcherEngineThread(); - DEBUG() << " ###Creating new thread" << thread << "(" << (threads.count()+1) << "threads)"; + DEBUG() << " ###Creating new thread" << thread << '(' << (threads.count()+1) << "threads)"; thread->handles.append(handle.handle); thread->handleForDir.insert(QFileSystemWatcherPathKey(absolutePath), handle); diff --git a/src/corelib/io/qsettings_mac.cpp b/src/corelib/io/qsettings_mac.cpp index f1d2e81bdc..e0b317b4c2 100644 --- a/src/corelib/io/qsettings_mac.cpp +++ b/src/corelib/io/qsettings_mac.cpp @@ -386,7 +386,7 @@ QMacSettingsPrivate::QMacSettingsPrivate(QSettings::Scope scope, const QString & if (main_bundle_identifier != NULL) { QString bundle_identifier(qtKey(main_bundle_identifier)); // CFBundleGetIdentifier returns identifier separated by slashes rather than periods. - QStringList bundle_identifier_components = bundle_identifier.split(QLatin1String("/")); + QStringList bundle_identifier_components = bundle_identifier.split(QLatin1Char('/')); // pre-reverse them so that when they get reversed again below, they are in the com.company.product format. QStringList bundle_identifier_components_reversed; for (int i=0; i(o.d->header->root()), json, 0, true); dbg.nospace() << "QJsonDocument(" << json.constData() // print as utf-8 string without extra quotation marks - << ")"; + << ')'; return dbg; } #endif diff --git a/src/corelib/json/qjsonvalue.cpp b/src/corelib/json/qjsonvalue.cpp index ae6a3678bd..4c7a44b4a0 100644 --- a/src/corelib/json/qjsonvalue.cpp +++ b/src/corelib/json/qjsonvalue.cpp @@ -738,23 +738,23 @@ QDebug operator<<(QDebug dbg, const QJsonValue &o) dbg << "QJsonValue(null)"; break; case QJsonValue::Bool: - dbg.nospace() << "QJsonValue(bool, " << o.toBool() << ")"; + dbg.nospace() << "QJsonValue(bool, " << o.toBool() << ')'; break; case QJsonValue::Double: - dbg.nospace() << "QJsonValue(double, " << o.toDouble() << ")"; + dbg.nospace() << "QJsonValue(double, " << o.toDouble() << ')'; break; case QJsonValue::String: - dbg.nospace() << "QJsonValue(string, " << o.toString() << ")"; + dbg.nospace() << "QJsonValue(string, " << o.toString() << ')'; break; case QJsonValue::Array: dbg.nospace() << "QJsonValue(array, "; dbg << o.toArray(); - dbg << ")"; + dbg << ')'; break; case QJsonValue::Object: dbg.nospace() << "QJsonValue(object, "; dbg << o.toObject(); - dbg << ")"; + dbg << ')'; break; } return dbg; diff --git a/src/corelib/json/qjsonwriter.cpp b/src/corelib/json/qjsonwriter.cpp index 99f83554c2..45a05e93a3 100644 --- a/src/corelib/json/qjsonwriter.cpp +++ b/src/corelib/json/qjsonwriter.cpp @@ -137,13 +137,13 @@ static void valueToJson(const QJsonPrivate::Base *b, const QJsonPrivate::Value & json += compact ? "[" : "[\n"; arrayContentToJson(static_cast(v.base(b)), json, indent + (compact ? 0 : 1), compact); json += QByteArray(4*indent, ' '); - json += "]"; + json += ']'; break; case QJsonValue::Object: json += compact ? "{" : "{\n"; objectContentToJson(static_cast(v.base(b)), json, indent + (compact ? 0 : 1), compact); json += QByteArray(4*indent, ' '); - json += "}"; + json += '}'; break; case QJsonValue::Null: default: diff --git a/src/corelib/statemachine/qstatemachine.cpp b/src/corelib/statemachine/qstatemachine.cpp index c5e251b37b..3ffe191093 100644 --- a/src/corelib/statemachine/qstatemachine.cpp +++ b/src/corelib/statemachine/qstatemachine.cpp @@ -1288,7 +1288,7 @@ QVariant QStateMachinePrivate::savedValueForRestorable(const QList= 0; --i) { QAbstractState *s = exitedStates_sorted.at(i); @@ -1311,7 +1311,7 @@ void QStateMachinePrivate::registerRestorable(QAbstractState *state, QObject *ob const QVariant &value) { #ifdef QSTATEMACHINE_RESTORE_PROPERTIES_DEBUG - qDebug() << q_func() << ": registerRestorable(" << state << object << propertyName << value << ")"; + qDebug() << q_func() << ": registerRestorable(" << state << object << propertyName << value << ')'; #endif RestorableId id(object, propertyName); QHash &restorables = registeredRestorablesForState[state]; @@ -1327,7 +1327,7 @@ void QStateMachinePrivate::unregisterRestorables(const QList & const QByteArray &propertyName) { #ifdef QSTATEMACHINE_RESTORE_PROPERTIES_DEBUG - qDebug() << q_func() << ": unregisterRestorables(" << states << object << propertyName << ")"; + qDebug() << q_func() << ": unregisterRestorables(" << states << object << propertyName << ')'; #endif RestorableId id(object, propertyName); for (int i = 0; i < states.size(); ++i) { diff --git a/src/corelib/tools/qregularexpression.cpp b/src/corelib/tools/qregularexpression.cpp index d8b0bf6e9f..81b108059b 100644 --- a/src/corelib/tools/qregularexpression.cpp +++ b/src/corelib/tools/qregularexpression.cpp @@ -2479,7 +2479,7 @@ QDataStream &operator>>(QDataStream &in, QRegularExpression &re) QDebug operator<<(QDebug debug, const QRegularExpression &re) { QDebugStateSaver saver(debug); - debug.nospace() << "QRegularExpression(" << re.pattern() << ", " << re.patternOptions() << ")"; + debug.nospace() << "QRegularExpression(" << re.pattern() << ", " << re.patternOptions() << ')'; return debug; } @@ -2521,7 +2521,7 @@ QDebug operator<<(QDebug debug, QRegularExpression::PatternOptions patternOption flags.chop(1); } - debug.nospace() << "QRegularExpression::PatternOptions(" << flags << ")"; + debug.nospace() << "QRegularExpression::PatternOptions(" << flags << ')'; return debug; } @@ -2550,7 +2550,7 @@ QDebug operator<<(QDebug debug, const QRegularExpressionMatch &match) for (int i = 0; i <= match.lastCapturedIndex(); ++i) { debug << i << ":(" << match.capturedStart(i) << ", " << match.capturedEnd(i) - << ", " << match.captured(i) << ")"; + << ", " << match.captured(i) << ')'; if (i < match.lastCapturedIndex()) debug << ", "; } @@ -2558,12 +2558,12 @@ QDebug operator<<(QDebug debug, const QRegularExpressionMatch &match) debug << ", has partial match: (" << match.capturedStart(0) << ", " << match.capturedEnd(0) << ", " - << match.captured(0) << ")"; + << match.captured(0) << ')'; } else { debug << ", no match"; } - debug << ")"; + debug << ')'; return debug; } -- cgit v1.2.3 From 967e4f258cd39991fd2d0ac3753544900d51fbc2 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Tue, 31 Mar 2015 00:14:24 +0200 Subject: QLinkedList/QSet: add {const_,}reverse_iterator, {c,}r{begin,end}() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Now all Qt sequential containers consistently provide reverse iterators. The associative ones, by way of not returning std::pair from op*, can't just use std::reverse_iterator. They would miss .key() and .value() methods. So that has to wait for 5.7. The reverse versions of the new key_iterators can also just use std::reverse_iterator, but I'm afraid that after bikeshedding over keyRBegin() vs. rKeyBegin() vs. reverseKeyBegin() vs. rkbegin() vs. krbegin() (<-- of course, what else?), it would anyway be too late for 5.6, so defer, too. [ChangeLog][QtCore][QLinkedList/QSet] Added rbegin(), crbegin(), rend(), crend(), and reverse_iterator and const_reverse_iterator typedefs. Task-number: QTBUG-25919 Change-Id: I58316fffade469e9a42c61d7aa1455ae3443fd94 Reviewed-by: Sérgio Martins Reviewed-by: Olivier Goffart (Woboq GmbH) --- src/corelib/tools/qlinkedlist.cpp | 78 +++++++++++++++++++++++++++++++++++++++ src/corelib/tools/qlinkedlist.h | 23 +++++++++--- src/corelib/tools/qset.h | 25 ++++++++++--- src/corelib/tools/qset.qdoc | 78 +++++++++++++++++++++++++++++++++++++++ 4 files changed, 192 insertions(+), 12 deletions(-) (limited to 'src/corelib') diff --git a/src/corelib/tools/qlinkedlist.cpp b/src/corelib/tools/qlinkedlist.cpp index fbd263e88b..5d91bfe924 100644 --- a/src/corelib/tools/qlinkedlist.cpp +++ b/src/corelib/tools/qlinkedlist.cpp @@ -388,6 +388,52 @@ const QLinkedListData QLinkedListData::shared_null = { \sa constBegin(), end() */ +/*! \fn QLinkedList::reverse_iterator QLinkedList::rbegin() + \since 5.6 + + Returns a \l{STL-style iterators}{STL-style} reverse iterator pointing to the first + item in the list, in reverse order. + + \sa begin(), crbegin(), rend() +*/ + +/*! \fn QLinkedList::const_reverse_iterator QLinkedList::rbegin() const + \since 5.6 + \overload +*/ + +/*! \fn QLinkedList::const_reverse_iterator QLinkedList::crbegin() const + \since 5.6 + + Returns a const \l{STL-style iterators}{STL-style} reverse iterator pointing to the first + item in the list, in reverse order. + + \sa begin(), rbegin(), rend() +*/ + +/*! \fn QLinkedList::reverse_iterator QLinkedList::rend() + \since 5.6 + + Returns a \l{STL-style iterators}{STL-style} reverse iterator pointing to one past + the last item in the list, in reverse order. + + \sa end(), crend(), rbegin() +*/ + +/*! \fn QLinkedList::const_reverse_iterator QLinkedList::rend() const + \since 5.6 + \overload +*/ + +/*! \fn QLinkedList::const_reverse_iterator QLinkedList::crend() const + \since 5.6 + + Returns a const \l{STL-style iterators}{STL-style} reverse iterator pointing to one + past the last item in the list, in reverse order. + + \sa end(), rend(), rbegin() +*/ + /*! \fn QLinkedList::iterator QLinkedList::insert(iterator before, const T &value) Inserts \a value in front of the item pointed to by the iterator @@ -423,6 +469,38 @@ const QLinkedListData QLinkedListData::shared_null = { Qt-style synonym for QLinkedList::const_iterator. */ +/*! \typedef QLinkedList::reverse_iterator + \since 5.6 + + The QLinkedList::reverse_iterator typedef provides an STL-style non-const + reverse iterator for QLinkedList. + + It is simply a typedef for \c{std::reverse_iterator}. + + \warning Iterators on implicitly shared containers do not work + exactly like STL-iterators. You should avoid copying a container + while iterators are active on that container. For more information, + read \l{Implicit sharing iterator problem}. + + \sa QLinkedList::rbegin(), QLinkedList::rend(), QLinkedList::const_reverse_iterator, QLinkedList::iterator +*/ + +/*! \typedef QLinkedList::const_reverse_iterator + \since 5.6 + + The QLinkedList::const_reverse_iterator typedef provides an STL-style const + reverse iterator for QLinkedList. + + It is simply a typedef for \c{std::reverse_iterator}. + + \warning Iterators on implicitly shared containers do not work + exactly like STL-iterators. You should avoid copying a container + while iterators are active on that container. For more information, + read \l{Implicit sharing iterator problem}. + + \sa QLinkedList::rbegin(), QLinkedList::rend(), QLinkedList::reverse_iterator, QLinkedList::const_iterator +*/ + /*! \typedef QLinkedList::size_type diff --git a/src/corelib/tools/qlinkedlist.h b/src/corelib/tools/qlinkedlist.h index 2854885d60..110529d843 100644 --- a/src/corelib/tools/qlinkedlist.h +++ b/src/corelib/tools/qlinkedlist.h @@ -183,14 +183,25 @@ public: friend class const_iterator; // stl style + typedef std::reverse_iterator reverse_iterator; + typedef std::reverse_iterator const_reverse_iterator; + inline iterator begin() { detach(); return e->n; } - inline const_iterator begin() const { return e->n; } - inline const_iterator cbegin() const { return e->n; } - inline const_iterator constBegin() const { return e->n; } + inline const_iterator begin() const Q_DECL_NOTHROW { return e->n; } + inline const_iterator cbegin() const Q_DECL_NOTHROW { return e->n; } + inline const_iterator constBegin() const Q_DECL_NOTHROW { return e->n; } inline iterator end() { detach(); return e; } - inline const_iterator end() const { return e; } - inline const_iterator cend() const { return e; } - inline const_iterator constEnd() const { return e; } + inline const_iterator end() const Q_DECL_NOTHROW { return e; } + inline const_iterator cend() const Q_DECL_NOTHROW { return e; } + inline const_iterator constEnd() const Q_DECL_NOTHROW { return e; } + + reverse_iterator rbegin() { return reverse_iterator(end()); } + reverse_iterator rend() { return reverse_iterator(begin()); } + const_reverse_iterator rbegin() const Q_DECL_NOTHROW { return const_reverse_iterator(end()); } + const_reverse_iterator rend() const Q_DECL_NOTHROW { return const_reverse_iterator(begin()); } + const_reverse_iterator crbegin() const Q_DECL_NOTHROW { return const_reverse_iterator(end()); } + const_reverse_iterator crend() const Q_DECL_NOTHROW { return const_reverse_iterator(begin()); } + iterator insert(iterator before, const T &t); iterator erase(iterator pos); iterator erase(iterator first, iterator last); diff --git a/src/corelib/tools/qset.h b/src/corelib/tools/qset.h index ed89617cd6..3f4208e8b3 100644 --- a/src/corelib/tools/qset.h +++ b/src/corelib/tools/qset.h @@ -39,6 +39,8 @@ #include #endif +#include + QT_BEGIN_NAMESPACE @@ -161,14 +163,25 @@ public: }; // STL style + typedef std::reverse_iterator reverse_iterator; + typedef std::reverse_iterator const_reverse_iterator; + inline iterator begin() { return q_hash.begin(); } - inline const_iterator begin() const { return q_hash.begin(); } - inline const_iterator cbegin() const { return q_hash.begin(); } - inline const_iterator constBegin() const { return q_hash.constBegin(); } + inline const_iterator begin() const Q_DECL_NOTHROW { return q_hash.begin(); } + inline const_iterator cbegin() const Q_DECL_NOTHROW { return q_hash.begin(); } + inline const_iterator constBegin() const Q_DECL_NOTHROW { return q_hash.constBegin(); } inline iterator end() { return q_hash.end(); } - inline const_iterator end() const { return q_hash.end(); } - inline const_iterator cend() const { return q_hash.end(); } - inline const_iterator constEnd() const { return q_hash.constEnd(); } + inline const_iterator end() const Q_DECL_NOTHROW { return q_hash.end(); } + inline const_iterator cend() const Q_DECL_NOTHROW { return q_hash.end(); } + inline const_iterator constEnd() const Q_DECL_NOTHROW { return q_hash.constEnd(); } + + reverse_iterator rbegin() { return reverse_iterator(end()); } + reverse_iterator rend() { return reverse_iterator(begin()); } + const_reverse_iterator rbegin() const Q_DECL_NOTHROW { return const_reverse_iterator(end()); } + const_reverse_iterator rend() const Q_DECL_NOTHROW { return const_reverse_iterator(begin()); } + const_reverse_iterator crbegin() const Q_DECL_NOTHROW { return const_reverse_iterator(end()); } + const_reverse_iterator crend() const Q_DECL_NOTHROW { return const_reverse_iterator(begin()); } + iterator erase(iterator i) { Q_ASSERT_X(isValidIterator(i), "QSet::erase", "The specified const_iterator argument 'i' is invalid"); diff --git a/src/corelib/tools/qset.qdoc b/src/corelib/tools/qset.qdoc index d91a589aa1..542def4651 100644 --- a/src/corelib/tools/qset.qdoc +++ b/src/corelib/tools/qset.qdoc @@ -384,6 +384,52 @@ \sa constBegin(), end() */ +/*! \fn QSet::reverse_iterator QSet::rbegin() + \since 5.6 + + Returns a \l{STL-style iterators}{STL-style} reverse iterator pointing to the first + item in the set, in reverse order. + + \sa begin(), crbegin(), rend() +*/ + +/*! \fn QSet::const_reverse_iterator QSet::rbegin() const + \since 5.6 + \overload +*/ + +/*! \fn QSet::const_reverse_iterator QSet::crbegin() const + \since 5.6 + + Returns a const \l{STL-style iterators}{STL-style} reverse iterator pointing to the first + item in the set, in reverse order. + + \sa begin(), rbegin(), rend() +*/ + +/*! \fn QSet::reverse_iterator QSet::rend() + \since 5.6 + + Returns a \l{STL-style iterators}{STL-style} reverse iterator pointing to one past + the last item in the set, in reverse order. + + \sa end(), crend(), rbegin() +*/ + +/*! \fn QSet::const_reverse_iterator QSet::rend() const + \since 5.6 + \overload +*/ + +/*! \fn QSet::const_reverse_iterator QSet::crend() const + \since 5.6 + + Returns a const \l{STL-style iterators}{STL-style} reverse iterator pointing to one + past the last item in the set, in reverse order. + + \sa end(), rend(), rbegin() +*/ + /*! \typedef QSet::Iterator \since 4.2 @@ -445,6 +491,38 @@ Typedef for T. Provided for STL compatibility. */ +/*! \typedef QSet::reverse_iterator + \since 5.6 + + The QSet::reverse_iterator typedef provides an STL-style non-const + reverse iterator for QSet. + + It is simply a typedef for \c{std::reverse_iterator}. + + \warning Iterators on implicitly shared containers do not work + exactly like STL-iterators. You should avoid copying a container + while iterators are active on that container. For more information, + read \l{Implicit sharing iterator problem}. + + \sa QSet::rbegin(), QSet::rend(), QSet::const_reverse_iterator, QSet::iterator +*/ + +/*! \typedef QSet::const_reverse_iterator + \since 5.6 + + The QSet::const_reverse_iterator typedef provides an STL-style const + reverse iterator for QSet. + + It is simply a typedef for \c{std::reverse_iterator}. + + \warning Iterators on implicitly shared containers do not work + exactly like STL-iterators. You should avoid copying a container + while iterators are active on that container. For more information, + read \l{Implicit sharing iterator problem}. + + \sa QSet::rbegin(), QSet::rend(), QSet::reverse_iterator, QSet::const_iterator +*/ + /*! \fn QSet::const_iterator QSet::insert(const T &value) -- cgit v1.2.3