diff --git a/src/libs/utils/fileutils.cpp b/src/libs/utils/fileutils.cpp index fc539b044172b18eb40d9bd259aa0b1317cccbe8..15ab2755d6b24517e9c5a2e5523375873037ac08 100644 --- a/src/libs/utils/fileutils.cpp +++ b/src/libs/utils/fileutils.cpp @@ -526,10 +526,16 @@ bool FileName::operator>=(const FileName &other) const /// \returns whether FileName is a child of \a s bool FileName::isChildOf(const FileName &s) const { + if (s.isEmpty()) + return false; if (!QString::startsWith(s, cs)) return false; if (size() <= s.size()) return false; + // s is root, '/' was already tested in startsWith + if (s.QString::endsWith(QLatin1Char('/'))) + return true; + // s is a directory, next character should be '/' (/tmpdir is NOT a child of /tmp) return at(s.size()) == QLatin1Char('/'); } diff --git a/tests/auto/utils/fileutils/tst_fileutils.cpp b/tests/auto/utils/fileutils/tst_fileutils.cpp index db8cc6274f4bbbb13240bcfce2c913eef31fa0c2..211ad166eac225cefea2992f364ca224bc470061 100644 --- a/tests/auto/utils/fileutils/tst_fileutils.cpp +++ b/tests/auto/utils/fileutils/tst_fileutils.cpp @@ -45,6 +45,8 @@ public: private slots: void parentDir_data(); void parentDir(); + void isChildOf_data(); + void isChildOf(); }; void tst_fileutils::parentDir_data() @@ -92,5 +94,43 @@ void tst_fileutils::parentDir() QCOMPARE(result.toString(), parentPath); } +void tst_fileutils::isChildOf_data() +{ + QTest::addColumn("path"); + QTest::addColumn("childPath"); + QTest::addColumn("result"); + + QTest::newRow("empty path") << QString() << QString::fromLatin1("/tmp") << false; + QTest::newRow("root only") << QString::fromLatin1("/") << QString::fromLatin1("/tmp") << true; + QTest::newRow("/tmp/dir") << QString::fromLatin1("/tmp") << QString::fromLatin1("/tmp/dir") << true; + QTest::newRow("relative/path") << QString::fromLatin1("relative") << QString::fromLatin1("relative/path") << true; + QTest::newRow("/tmpdir") << QString::fromLatin1("/tmp") << QString::fromLatin1("/tmpdir") << false; + QTest::newRow("same") << QString::fromLatin1("/tmp/dir") << QString::fromLatin1("/tmp/dir") << false; + + // Windows stuff: +#ifdef Q_OS_WIN + QTest::newRow("C:/data") << QString::fromLatin1("C:/") << QString::fromLatin1("C:/data") << true; + QTest::newRow("C:/") << QString() << QString::fromLatin1("C:/") << false; + QTest::newRow("//./com1") << QString::fromLatin1("/") << QString::fromLatin1("//./com1") << true; + QTest::newRow("//?/path") << QString::fromLatin1("/") << QString::fromLatin1("//?/path") << true; + QTest::newRow("/Global??/UNC/host") << QString::fromLatin1("/Global??/UNC/host") + << QString::fromLatin1("/Global??/UNC/host/file") << true; + QTest::newRow("//server/directory/file") + << QString::fromLatin1("//server/directory") << QString::fromLatin1("//server/directory/file") << true; + QTest::newRow("//server/directory") + << QString::fromLatin1("//server") << QString::fromLatin1("//server/directory") << true; +#endif +} + +void tst_fileutils::isChildOf() +{ + QFETCH(QString, path); + QFETCH(QString, childPath); + QFETCH(bool, result); + + bool res = FileName::fromString(childPath).isChildOf(FileName::fromString(path)); + QCOMPARE(res, result); +} + QTEST_APPLESS_MAIN(tst_fileutils) #include "tst_fileutils.moc"