From f2df5c64bde5a3837048347b18c246e674de5caa Mon Sep 17 00:00:00 2001 From: Friedemann Kleint Date: Mon, 12 Jun 2017 15:31:53 +0200 Subject: QFileSystemEntry: Export static helper function checking for the root path This provides a helper function which does the check on the string. QFileInfo::isRoot() in addition checks for the existence of the directory, which can cause hangs with network drives. Use the new function in appropriate places in QtWidgets. Task-number: QTBUG-6039 Change-Id: I54d0d860713e82b28fa4069a5345b042337f9c52 Reviewed-by: Joerg Bornemann --- src/corelib/io/qfilesystementry.cpp | 30 +++++++++++++++++++---------- src/corelib/io/qfilesystementry_p.h | 3 +++ src/widgets/itemviews/qdirmodel.cpp | 10 ++++++---- src/widgets/itemviews/qfileiconprovider.cpp | 8 +++++--- 4 files changed, 34 insertions(+), 17 deletions(-) (limited to 'src') diff --git a/src/corelib/io/qfilesystementry.cpp b/src/corelib/io/qfilesystementry.cpp index de4c852068..cbff17d0f1 100644 --- a/src/corelib/io/qfilesystementry.cpp +++ b/src/corelib/io/qfilesystementry.cpp @@ -297,23 +297,27 @@ bool QFileSystemEntry::isAbsolute() const bool QFileSystemEntry::isDriveRoot() const { resolveFilePath(); + return QFileSystemEntry::isDriveRootPath(m_filePath); +} + +bool QFileSystemEntry::isDriveRootPath(const QString &path) +{ #ifndef Q_OS_WINRT - return (m_filePath.length() == 3 - && m_filePath.at(0).isLetter() && m_filePath.at(1) == QLatin1Char(':') - && m_filePath.at(2) == QLatin1Char('/')); + return (path.length() == 3 + && path.at(0).isLetter() && path.at(1) == QLatin1Char(':') + && path.at(2) == QLatin1Char('/')); #else // !Q_OS_WINRT - return m_filePath == QDir::rootPath(); + return path == QDir::rootPath(); #endif // !Q_OS_WINRT } -#endif +#endif // Q_OS_WIN -bool QFileSystemEntry::isRoot() const +bool QFileSystemEntry::isRootPath(const QString &path) { - resolveFilePath(); - if (m_filePath == QLatin1String("/") + if (path == QLatin1String("/") #if defined(Q_OS_WIN) - || isDriveRoot() - || isUncRoot(m_filePath) + || isDriveRootPath(path) + || isUncRoot(path) #endif ) return true; @@ -321,6 +325,12 @@ bool QFileSystemEntry::isRoot() const return false; } +bool QFileSystemEntry::isRoot() const +{ + resolveFilePath(); + return isRootPath(m_filePath); +} + bool QFileSystemEntry::isEmpty() const { return m_filePath.isEmpty() && m_nativeFilePath.isEmpty(); diff --git a/src/corelib/io/qfilesystementry_p.h b/src/corelib/io/qfilesystementry_p.h index 300a375377..700696d09e 100644 --- a/src/corelib/io/qfilesystementry_p.h +++ b/src/corelib/io/qfilesystementry_p.h @@ -94,6 +94,7 @@ public: #if defined(Q_OS_WIN) bool isDriveRoot() const; + static bool isDriveRootPath(const QString &path); #endif bool isRoot() const; @@ -103,6 +104,8 @@ public: *this = QFileSystemEntry(); } + Q_CORE_EXPORT static bool isRootPath(const QString &path); + private: // creates the QString version out of the bytearray version void resolveFilePath() const; diff --git a/src/widgets/itemviews/qdirmodel.cpp b/src/widgets/itemviews/qdirmodel.cpp index 95e6a1840d..5526da8509 100644 --- a/src/widgets/itemviews/qdirmodel.cpp +++ b/src/widgets/itemviews/qdirmodel.cpp @@ -52,6 +52,7 @@ #include #include #include +#include #include #include @@ -1104,8 +1105,9 @@ QString QDirModel::fileName(const QModelIndex &index) const if (!d->indexValid(index)) return QString(); QFileInfo info = fileInfo(index); - if (info.isRoot()) - return info.absoluteFilePath(); + const QString &path = info.absoluteFilePath(); + if (QFileSystemEntry::isRootPath(path)) + return path; if (d->resolveSymlinks && info.isSymLink()) info = d->resolvedInfo(info); return info.fileName(); @@ -1280,8 +1282,8 @@ QString QDirModelPrivate::name(const QModelIndex &index) const { const QDirNode *n = node(index); const QFileInfo info = n->info; - if (info.isRoot()) { - QString name = info.absoluteFilePath(); + QString name = info.absoluteFilePath(); + if (QFileSystemEntry::isRootPath(name)) { #if defined(Q_OS_WIN) if (name.startsWith(QLatin1Char('/'))) // UNC host return info.fileName(); diff --git a/src/widgets/itemviews/qfileiconprovider.cpp b/src/widgets/itemviews/qfileiconprovider.cpp index 8c3cf3859e..65ae6b9505 100644 --- a/src/widgets/itemviews/qfileiconprovider.cpp +++ b/src/widgets/itemviews/qfileiconprovider.cpp @@ -46,6 +46,7 @@ #include #include #include +#include #include #include #include @@ -247,10 +248,11 @@ QIcon QFileIconProvider::icon(const QFileInfo &info) const if (!retIcon.isNull()) return retIcon; - if (info.isRoot()) + const QString &path = info.absoluteFilePath(); + if (path.isEmpty() || QFileSystemEntry::isRootPath(path)) #if defined (Q_OS_WIN) && !defined(Q_OS_WINRT) { - UINT type = GetDriveType((wchar_t *)info.absoluteFilePath().utf16()); + UINT type = GetDriveType(reinterpret_cast(path.utf16())); switch (type) { case DRIVE_REMOVABLE: @@ -298,7 +300,7 @@ QIcon QFileIconProvider::icon(const QFileInfo &info) const QString QFileIconProvider::type(const QFileInfo &info) const { - if (info.isRoot()) + if (QFileSystemEntry::isRootPath(info.absoluteFilePath())) return QApplication::translate("QFileDialog", "Drive"); if (info.isFile()) { if (!info.suffix().isEmpty()) { -- cgit v1.2.3