1
0
Fork 0

fix path normalization for Windows (#7566)

This commit is contained in:
Jan 2018-11-30 16:21:30 +01:00 committed by GitHub
parent 2d73f04008
commit 643b58a347
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 76 additions and 0 deletions

View File

@ -71,6 +71,29 @@ std::string removeTrailingSeparator(std::string const& name) {
void normalizePath(std::string& name) {
std::replace(name.begin(), name.end(), '/', TRI_DIR_SEPARATOR_CHAR);
#ifdef _WIN32
// for Windows the situation is a bit more complicated,
// as a mere replacement of all forward slashes to backslashes
// may leave us with a double backslash for sequences like "bla/\foo".
// in this case we collapse duplicate dir separators to a single one.
// we intentionally ignore the first 2 characters, because they may
// contain a network share filename such as "\\foo\bar"
size_t const n = name.size();
size_t out = 0;
for (size_t i = 0; i < n; ++i) {
if (name[i] == TRI_DIR_SEPARATOR_CHAR && out > 1 && name[out - 1] == TRI_DIR_SEPARATOR_CHAR) {
continue;
}
name[out++] = name[i];
}
if (out != n) {
name.resize(out);
}
#endif
}
////////////////////////////////////////////////////////////////////////////////

View File

@ -358,6 +358,59 @@ SECTION("tst_absolute_paths") {
TRI_Free(path);
#endif
}
SECTION("tst_normalize") {
std::string path;
path = "/foo/bar/baz";
FileUtils::normalizePath(path);
#ifdef _WIN32
CHECK(std::string("\\foo\\bar\\baz") == path);
#else
CHECK(std::string("/foo/bar/baz") == path);
#endif
path = "\\foo\\bar\\baz";
FileUtils::normalizePath(path);
#ifdef _WIN32
CHECK(std::string("\\foo\\bar\\baz") == path);
#else
CHECK(std::string("\\foo\\bar\\baz") == path);
#endif
path = "/foo/bar\\baz";
FileUtils::normalizePath(path);
#ifdef _WIN32
CHECK(std::string("\\foo\\bar\\baz") == path);
#else
CHECK(std::string("/foo/bar\\baz") == path);
#endif
path = "/foo/bar/\\baz";
FileUtils::normalizePath(path);
#ifdef _WIN32
CHECK(std::string("\\foo\\bar\\baz") == path);
#else
CHECK(std::string("/foo/bar/\\baz") == path);
#endif
path = "//foo\\/bar/\\baz";
FileUtils::normalizePath(path);
#ifdef _WIN32
CHECK(std::string("\\\\foo\\bar\\baz") == path);
#else
CHECK(std::string("//foo\\/bar/\\baz") == path);
#endif
path = "\\\\foo\\/bar/\\baz";
FileUtils::normalizePath(path);
#ifdef _WIN32
CHECK(std::string("\\\\foo\\bar\\baz") == path);
#else
CHECK(std::string("\\\\foo\\/bar/\\baz") == path);
#endif
}
}
////////////////////////////////////////////////////////////////////////////////