1 //===- llvm/unittest/Support/Path.cpp - Path tests ------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "llvm/Support/Path.h"
10 #include "llvm/ADT/STLExtras.h"
11 #include "llvm/ADT/ScopeExit.h"
12 #include "llvm/ADT/SmallVector.h"
13 #include "llvm/ADT/Triple.h"
14 #include "llvm/BinaryFormat/Magic.h"
15 #include "llvm/Config/llvm-config.h"
16 #include "llvm/Support/Compiler.h"
17 #include "llvm/Support/ConvertUTF.h"
18 #include "llvm/Support/Errc.h"
19 #include "llvm/Support/ErrorHandling.h"
20 #include "llvm/Support/FileSystem.h"
21 #include "llvm/Support/FileUtilities.h"
22 #include "llvm/Support/Host.h"
23 #include "llvm/Support/MemoryBuffer.h"
24 #include "llvm/Support/raw_ostream.h"
25 #include "llvm/Testing/Support/Error.h"
26 #include "llvm/Testing/Support/SupportHelpers.h"
27 #include "gmock/gmock.h"
28 #include "gtest/gtest.h"
29 
30 #ifdef _WIN32
31 #include "llvm/ADT/ArrayRef.h"
32 #include "llvm/Support/Chrono.h"
33 #include "llvm/Support/Windows/WindowsSupport.h"
34 #include <windows.h>
35 #include <winerror.h>
36 #endif
37 
38 #ifdef LLVM_ON_UNIX
39 #include <pwd.h>
40 #include <sys/stat.h>
41 #endif
42 
43 using namespace llvm;
44 using namespace llvm::sys;
45 
46 #define ASSERT_NO_ERROR(x)                                                     \
47   if (std::error_code ASSERT_NO_ERROR_ec = x) {                                \
48     SmallString<128> MessageStorage;                                           \
49     raw_svector_ostream Message(MessageStorage);                               \
50     Message << #x ": did not return errc::success.\n"                          \
51             << "error number: " << ASSERT_NO_ERROR_ec.value() << "\n"          \
52             << "error message: " << ASSERT_NO_ERROR_ec.message() << "\n";      \
53     GTEST_FATAL_FAILURE_(MessageStorage.c_str());                              \
54   } else {                                                                     \
55   }
56 
57 #define ASSERT_ERROR(x)                                                        \
58   if (!x) {                                                                    \
59     SmallString<128> MessageStorage;                                           \
60     raw_svector_ostream Message(MessageStorage);                               \
61     Message << #x ": did not return a failure error code.\n";                  \
62     GTEST_FATAL_FAILURE_(MessageStorage.c_str());                              \
63   }
64 
65 namespace {
66 
67 struct FileDescriptorCloser {
68   explicit FileDescriptorCloser(int FD) : FD(FD) {}
69   ~FileDescriptorCloser() { ::close(FD); }
70   int FD;
71 };
72 
73 TEST(is_style_Style, Works) {
74   using namespace llvm::sys::path;
75   // Check platform-independent results.
76   EXPECT_TRUE(is_style_posix(Style::posix));
77   EXPECT_TRUE(is_style_windows(Style::windows));
78   EXPECT_FALSE(is_style_posix(Style::windows));
79   EXPECT_FALSE(is_style_windows(Style::posix));
80 
81   // Check platform-dependent results.
82 #if defined(_WIN32)
83   EXPECT_FALSE(is_style_posix(Style::native));
84   EXPECT_TRUE(is_style_windows(Style::native));
85 #else
86   EXPECT_TRUE(is_style_posix(Style::native));
87   EXPECT_FALSE(is_style_windows(Style::native));
88 #endif
89 }
90 
91 TEST(is_separator, Works) {
92   EXPECT_TRUE(path::is_separator('/'));
93   EXPECT_FALSE(path::is_separator('\0'));
94   EXPECT_FALSE(path::is_separator('-'));
95   EXPECT_FALSE(path::is_separator(' '));
96 
97   EXPECT_TRUE(path::is_separator('\\', path::Style::windows));
98   EXPECT_FALSE(path::is_separator('\\', path::Style::posix));
99 
100   EXPECT_EQ(path::is_style_windows(path::Style::native),
101             path::is_separator('\\'));
102 }
103 
104 TEST(is_absolute_gnu, Works) {
105   // Test tuple <Path, ExpectedPosixValue, ExpectedWindowsValue>.
106   const std::tuple<StringRef, bool, bool> Paths[] = {
107       std::make_tuple("", false, false),
108       std::make_tuple("/", true, true),
109       std::make_tuple("/foo", true, true),
110       std::make_tuple("\\", false, true),
111       std::make_tuple("\\foo", false, true),
112       std::make_tuple("foo", false, false),
113       std::make_tuple("c", false, false),
114       std::make_tuple("c:", false, true),
115       std::make_tuple("c:\\", false, true),
116       std::make_tuple("!:", false, true),
117       std::make_tuple("xx:", false, false),
118       std::make_tuple("c:abc\\", false, true),
119       std::make_tuple(":", false, false)};
120 
121   for (const auto &Path : Paths) {
122     EXPECT_EQ(path::is_absolute_gnu(std::get<0>(Path), path::Style::posix),
123               std::get<1>(Path));
124     EXPECT_EQ(path::is_absolute_gnu(std::get<0>(Path), path::Style::windows),
125               std::get<2>(Path));
126 
127     constexpr int Native = is_style_posix(path::Style::native) ? 1 : 2;
128     EXPECT_EQ(path::is_absolute_gnu(std::get<0>(Path), path::Style::native),
129               std::get<Native>(Path));
130   }
131 }
132 
133 TEST(Support, Path) {
134   SmallVector<StringRef, 40> paths;
135   paths.push_back("");
136   paths.push_back(".");
137   paths.push_back("..");
138   paths.push_back("foo");
139   paths.push_back("/");
140   paths.push_back("/foo");
141   paths.push_back("foo/");
142   paths.push_back("/foo/");
143   paths.push_back("foo/bar");
144   paths.push_back("/foo/bar");
145   paths.push_back("//net");
146   paths.push_back("//net/");
147   paths.push_back("//net/foo");
148   paths.push_back("///foo///");
149   paths.push_back("///foo///bar");
150   paths.push_back("/.");
151   paths.push_back("./");
152   paths.push_back("/..");
153   paths.push_back("../");
154   paths.push_back("foo/.");
155   paths.push_back("foo/..");
156   paths.push_back("foo/./");
157   paths.push_back("foo/./bar");
158   paths.push_back("foo/..");
159   paths.push_back("foo/../");
160   paths.push_back("foo/../bar");
161   paths.push_back("c:");
162   paths.push_back("c:/");
163   paths.push_back("c:foo");
164   paths.push_back("c:/foo");
165   paths.push_back("c:foo/");
166   paths.push_back("c:/foo/");
167   paths.push_back("c:/foo/bar");
168   paths.push_back("prn:");
169   paths.push_back("c:\\");
170   paths.push_back("c:foo");
171   paths.push_back("c:\\foo");
172   paths.push_back("c:foo\\");
173   paths.push_back("c:\\foo\\");
174   paths.push_back("c:\\foo/");
175   paths.push_back("c:/foo\\bar");
176 
177   for (SmallVector<StringRef, 40>::const_iterator i = paths.begin(),
178                                                   e = paths.end();
179                                                   i != e;
180                                                   ++i) {
181     SCOPED_TRACE(*i);
182     SmallVector<StringRef, 5> ComponentStack;
183     for (sys::path::const_iterator ci = sys::path::begin(*i),
184                                    ce = sys::path::end(*i);
185                                    ci != ce;
186                                    ++ci) {
187       EXPECT_FALSE(ci->empty());
188       ComponentStack.push_back(*ci);
189     }
190 
191     SmallVector<StringRef, 5> ReverseComponentStack;
192     for (sys::path::reverse_iterator ci = sys::path::rbegin(*i),
193                                      ce = sys::path::rend(*i);
194                                      ci != ce;
195                                      ++ci) {
196       EXPECT_FALSE(ci->empty());
197       ReverseComponentStack.push_back(*ci);
198     }
199     std::reverse(ReverseComponentStack.begin(), ReverseComponentStack.end());
200     EXPECT_THAT(ComponentStack, testing::ContainerEq(ReverseComponentStack));
201 
202     // Crash test most of the API - since we're iterating over all of our paths
203     // here there isn't really anything reasonable to assert on in the results.
204     (void)path::has_root_path(*i);
205     (void)path::root_path(*i);
206     (void)path::has_root_name(*i);
207     (void)path::root_name(*i);
208     (void)path::has_root_directory(*i);
209     (void)path::root_directory(*i);
210     (void)path::has_parent_path(*i);
211     (void)path::parent_path(*i);
212     (void)path::has_filename(*i);
213     (void)path::filename(*i);
214     (void)path::has_stem(*i);
215     (void)path::stem(*i);
216     (void)path::has_extension(*i);
217     (void)path::extension(*i);
218     (void)path::is_absolute(*i);
219     (void)path::is_absolute_gnu(*i);
220     (void)path::is_relative(*i);
221 
222     SmallString<128> temp_store;
223     temp_store = *i;
224     ASSERT_NO_ERROR(fs::make_absolute(temp_store));
225     temp_store = *i;
226     path::remove_filename(temp_store);
227 
228     temp_store = *i;
229     path::replace_extension(temp_store, "ext");
230     StringRef filename(temp_store.begin(), temp_store.size()), stem, ext;
231     stem = path::stem(filename);
232     ext  = path::extension(filename);
233     EXPECT_EQ(*sys::path::rbegin(filename), (stem + ext).str());
234 
235     path::native(*i, temp_store);
236   }
237 
238   {
239     SmallString<32> Relative("foo.cpp");
240     sys::fs::make_absolute("/root", Relative);
241     Relative[5] = '/'; // Fix up windows paths.
242     ASSERT_EQ("/root/foo.cpp", Relative);
243   }
244 
245   {
246     SmallString<32> Relative("foo.cpp");
247     sys::fs::make_absolute("//root", Relative);
248     Relative[6] = '/'; // Fix up windows paths.
249     ASSERT_EQ("//root/foo.cpp", Relative);
250   }
251 }
252 
253 TEST(Support, PathRoot) {
254   ASSERT_EQ(path::root_name("//net/hello", path::Style::posix).str(), "//net");
255   ASSERT_EQ(path::root_name("c:/hello", path::Style::posix).str(), "");
256   ASSERT_EQ(path::root_name("c:/hello", path::Style::windows).str(), "c:");
257   ASSERT_EQ(path::root_name("/hello", path::Style::posix).str(), "");
258 
259   ASSERT_EQ(path::root_directory("/goo/hello", path::Style::posix).str(), "/");
260   ASSERT_EQ(path::root_directory("c:/hello", path::Style::windows).str(), "/");
261   ASSERT_EQ(path::root_directory("d/file.txt", path::Style::posix).str(), "");
262   ASSERT_EQ(path::root_directory("d/file.txt", path::Style::windows).str(), "");
263 
264   SmallVector<StringRef, 40> paths;
265   paths.push_back("");
266   paths.push_back(".");
267   paths.push_back("..");
268   paths.push_back("foo");
269   paths.push_back("/");
270   paths.push_back("/foo");
271   paths.push_back("foo/");
272   paths.push_back("/foo/");
273   paths.push_back("foo/bar");
274   paths.push_back("/foo/bar");
275   paths.push_back("//net");
276   paths.push_back("//net/");
277   paths.push_back("//net/foo");
278   paths.push_back("///foo///");
279   paths.push_back("///foo///bar");
280   paths.push_back("/.");
281   paths.push_back("./");
282   paths.push_back("/..");
283   paths.push_back("../");
284   paths.push_back("foo/.");
285   paths.push_back("foo/..");
286   paths.push_back("foo/./");
287   paths.push_back("foo/./bar");
288   paths.push_back("foo/..");
289   paths.push_back("foo/../");
290   paths.push_back("foo/../bar");
291   paths.push_back("c:");
292   paths.push_back("c:/");
293   paths.push_back("c:foo");
294   paths.push_back("c:/foo");
295   paths.push_back("c:foo/");
296   paths.push_back("c:/foo/");
297   paths.push_back("c:/foo/bar");
298   paths.push_back("prn:");
299   paths.push_back("c:\\");
300   paths.push_back("c:foo");
301   paths.push_back("c:\\foo");
302   paths.push_back("c:foo\\");
303   paths.push_back("c:\\foo\\");
304   paths.push_back("c:\\foo/");
305   paths.push_back("c:/foo\\bar");
306 
307   for (StringRef p : paths) {
308     ASSERT_EQ(
309       path::root_name(p, path::Style::posix).str() + path::root_directory(p, path::Style::posix).str(),
310       path::root_path(p, path::Style::posix).str());
311 
312     ASSERT_EQ(
313       path::root_name(p, path::Style::windows).str() + path::root_directory(p, path::Style::windows).str(),
314       path::root_path(p, path::Style::windows).str());
315   }
316 }
317 
318 TEST(Support, FilenameParent) {
319   EXPECT_EQ("/", path::filename("/"));
320   EXPECT_EQ("", path::parent_path("/"));
321 
322   EXPECT_EQ("\\", path::filename("c:\\", path::Style::windows));
323   EXPECT_EQ("c:", path::parent_path("c:\\", path::Style::windows));
324 
325   EXPECT_EQ("/", path::filename("///"));
326   EXPECT_EQ("", path::parent_path("///"));
327 
328   EXPECT_EQ("\\", path::filename("c:\\\\", path::Style::windows));
329   EXPECT_EQ("c:", path::parent_path("c:\\\\", path::Style::windows));
330 
331   EXPECT_EQ("bar", path::filename("/foo/bar"));
332   EXPECT_EQ("/foo", path::parent_path("/foo/bar"));
333 
334   EXPECT_EQ("foo", path::filename("/foo"));
335   EXPECT_EQ("/", path::parent_path("/foo"));
336 
337   EXPECT_EQ("foo", path::filename("foo"));
338   EXPECT_EQ("", path::parent_path("foo"));
339 
340   EXPECT_EQ(".", path::filename("foo/"));
341   EXPECT_EQ("foo", path::parent_path("foo/"));
342 
343   EXPECT_EQ("//net", path::filename("//net"));
344   EXPECT_EQ("", path::parent_path("//net"));
345 
346   EXPECT_EQ("/", path::filename("//net/"));
347   EXPECT_EQ("//net", path::parent_path("//net/"));
348 
349   EXPECT_EQ("foo", path::filename("//net/foo"));
350   EXPECT_EQ("//net/", path::parent_path("//net/foo"));
351 
352   // These checks are just to make sure we do something reasonable with the
353   // paths below. They are not meant to prescribe the one true interpretation of
354   // these paths. Other decompositions (e.g. "//" -> "" + "//") are also
355   // possible.
356   EXPECT_EQ("/", path::filename("//"));
357   EXPECT_EQ("", path::parent_path("//"));
358 
359   EXPECT_EQ("\\", path::filename("\\\\", path::Style::windows));
360   EXPECT_EQ("", path::parent_path("\\\\", path::Style::windows));
361 
362   EXPECT_EQ("\\", path::filename("\\\\\\", path::Style::windows));
363   EXPECT_EQ("", path::parent_path("\\\\\\", path::Style::windows));
364 }
365 
366 static std::vector<StringRef>
367 GetComponents(StringRef Path, path::Style S = path::Style::native) {
368   return {path::begin(Path, S), path::end(Path)};
369 }
370 
371 TEST(Support, PathIterator) {
372   EXPECT_THAT(GetComponents("/foo"), testing::ElementsAre("/", "foo"));
373   EXPECT_THAT(GetComponents("/"), testing::ElementsAre("/"));
374   EXPECT_THAT(GetComponents("//"), testing::ElementsAre("/"));
375   EXPECT_THAT(GetComponents("///"), testing::ElementsAre("/"));
376   EXPECT_THAT(GetComponents("c/d/e/foo.txt"),
377               testing::ElementsAre("c", "d", "e", "foo.txt"));
378   EXPECT_THAT(GetComponents(".c/.d/../."),
379               testing::ElementsAre(".c", ".d", "..", "."));
380   EXPECT_THAT(GetComponents("/c/d/e/foo.txt"),
381               testing::ElementsAre("/", "c", "d", "e", "foo.txt"));
382   EXPECT_THAT(GetComponents("/.c/.d/../."),
383               testing::ElementsAre("/", ".c", ".d", "..", "."));
384   EXPECT_THAT(GetComponents("c:\\c\\e\\foo.txt", path::Style::windows),
385               testing::ElementsAre("c:", "\\", "c", "e", "foo.txt"));
386   EXPECT_THAT(GetComponents("//net/"), testing::ElementsAre("//net", "/"));
387   EXPECT_THAT(GetComponents("//net/c/foo.txt"),
388               testing::ElementsAre("//net", "/", "c", "foo.txt"));
389 }
390 
391 TEST(Support, AbsolutePathIteratorEnd) {
392   // Trailing slashes are converted to '.' unless they are part of the root path.
393   SmallVector<std::pair<StringRef, path::Style>, 4> Paths;
394   Paths.emplace_back("/foo/", path::Style::native);
395   Paths.emplace_back("/foo//", path::Style::native);
396   Paths.emplace_back("//net/foo/", path::Style::native);
397   Paths.emplace_back("c:\\foo\\", path::Style::windows);
398 
399   for (auto &Path : Paths) {
400     SCOPED_TRACE(Path.first);
401     StringRef LastComponent = *path::rbegin(Path.first, Path.second);
402     EXPECT_EQ(".", LastComponent);
403   }
404 
405   SmallVector<std::pair<StringRef, path::Style>, 3> RootPaths;
406   RootPaths.emplace_back("/", path::Style::native);
407   RootPaths.emplace_back("//net/", path::Style::native);
408   RootPaths.emplace_back("c:\\", path::Style::windows);
409   RootPaths.emplace_back("//net//", path::Style::native);
410   RootPaths.emplace_back("c:\\\\", path::Style::windows);
411 
412   for (auto &Path : RootPaths) {
413     SCOPED_TRACE(Path.first);
414     StringRef LastComponent = *path::rbegin(Path.first, Path.second);
415     EXPECT_EQ(1u, LastComponent.size());
416     EXPECT_TRUE(path::is_separator(LastComponent[0], Path.second));
417   }
418 }
419 
420 #ifdef _WIN32
421 std::string getEnvWin(const wchar_t *Var) {
422   std::string expected;
423   if (wchar_t const *path = ::_wgetenv(Var)) {
424     auto pathLen = ::wcslen(path);
425     ArrayRef<char> ref{reinterpret_cast<char const *>(path),
426                        pathLen * sizeof(wchar_t)};
427     convertUTF16ToUTF8String(ref, expected);
428   }
429   return expected;
430 }
431 #else
432 // RAII helper to set and restore an environment variable.
433 class WithEnv {
434   const char *Var;
435   llvm::Optional<std::string> OriginalValue;
436 
437 public:
438   WithEnv(const char *Var, const char *Value) : Var(Var) {
439     if (const char *V = ::getenv(Var))
440       OriginalValue.emplace(V);
441     if (Value)
442       ::setenv(Var, Value, 1);
443     else
444       ::unsetenv(Var);
445   }
446   ~WithEnv() {
447     if (OriginalValue)
448       ::setenv(Var, OriginalValue->c_str(), 1);
449     else
450       ::unsetenv(Var);
451   }
452 };
453 #endif
454 
455 TEST(Support, HomeDirectory) {
456   std::string expected;
457 #ifdef _WIN32
458   expected = getEnvWin(L"USERPROFILE");
459 #else
460   if (char const *path = ::getenv("HOME"))
461     expected = path;
462 #endif
463   // Do not try to test it if we don't know what to expect.
464   // On Windows we use something better than env vars.
465   if (!expected.empty()) {
466     SmallString<128> HomeDir;
467     auto status = path::home_directory(HomeDir);
468     EXPECT_TRUE(status);
469     EXPECT_EQ(expected, HomeDir);
470   }
471 }
472 
473 // Apple has their own solution for this.
474 #if defined(LLVM_ON_UNIX) && !defined(__APPLE__)
475 TEST(Support, HomeDirectoryWithNoEnv) {
476   WithEnv Env("HOME", nullptr);
477 
478   // Don't run the test if we have nothing to compare against.
479   struct passwd *pw = getpwuid(getuid());
480   if (!pw || !pw->pw_dir) return;
481   std::string PwDir = pw->pw_dir;
482 
483   SmallString<128> HomeDir;
484   EXPECT_TRUE(path::home_directory(HomeDir));
485   EXPECT_EQ(PwDir, HomeDir);
486 }
487 
488 TEST(Support, ConfigDirectoryWithEnv) {
489   WithEnv Env("XDG_CONFIG_HOME", "/xdg/config");
490 
491   SmallString<128> ConfigDir;
492   EXPECT_TRUE(path::user_config_directory(ConfigDir));
493   EXPECT_EQ("/xdg/config", ConfigDir);
494 }
495 
496 TEST(Support, ConfigDirectoryNoEnv) {
497   WithEnv Env("XDG_CONFIG_HOME", nullptr);
498 
499   SmallString<128> Fallback;
500   ASSERT_TRUE(path::home_directory(Fallback));
501   path::append(Fallback, ".config");
502 
503   SmallString<128> CacheDir;
504   EXPECT_TRUE(path::user_config_directory(CacheDir));
505   EXPECT_EQ(Fallback, CacheDir);
506 }
507 
508 TEST(Support, CacheDirectoryWithEnv) {
509   WithEnv Env("XDG_CACHE_HOME", "/xdg/cache");
510 
511   SmallString<128> CacheDir;
512   EXPECT_TRUE(path::cache_directory(CacheDir));
513   EXPECT_EQ("/xdg/cache", CacheDir);
514 }
515 
516 TEST(Support, CacheDirectoryNoEnv) {
517   WithEnv Env("XDG_CACHE_HOME", nullptr);
518 
519   SmallString<128> Fallback;
520   ASSERT_TRUE(path::home_directory(Fallback));
521   path::append(Fallback, ".cache");
522 
523   SmallString<128> CacheDir;
524   EXPECT_TRUE(path::cache_directory(CacheDir));
525   EXPECT_EQ(Fallback, CacheDir);
526 }
527 #endif
528 
529 #ifdef __APPLE__
530 TEST(Support, ConfigDirectory) {
531   SmallString<128> Fallback;
532   ASSERT_TRUE(path::home_directory(Fallback));
533   path::append(Fallback, "Library/Preferences");
534 
535   SmallString<128> ConfigDir;
536   EXPECT_TRUE(path::user_config_directory(ConfigDir));
537   EXPECT_EQ(Fallback, ConfigDir);
538 }
539 #endif
540 
541 #ifdef _WIN32
542 TEST(Support, ConfigDirectory) {
543   std::string Expected = getEnvWin(L"LOCALAPPDATA");
544   // Do not try to test it if we don't know what to expect.
545   if (!Expected.empty()) {
546     SmallString<128> CacheDir;
547     EXPECT_TRUE(path::user_config_directory(CacheDir));
548     EXPECT_EQ(Expected, CacheDir);
549   }
550 }
551 
552 TEST(Support, CacheDirectory) {
553   std::string Expected = getEnvWin(L"LOCALAPPDATA");
554   // Do not try to test it if we don't know what to expect.
555   if (!Expected.empty()) {
556     SmallString<128> CacheDir;
557     EXPECT_TRUE(path::cache_directory(CacheDir));
558     EXPECT_EQ(Expected, CacheDir);
559   }
560 }
561 #endif
562 
563 TEST(Support, TempDirectory) {
564   SmallString<32> TempDir;
565   path::system_temp_directory(false, TempDir);
566   EXPECT_TRUE(!TempDir.empty());
567   TempDir.clear();
568   path::system_temp_directory(true, TempDir);
569   EXPECT_TRUE(!TempDir.empty());
570 }
571 
572 #ifdef _WIN32
573 static std::string path2regex(std::string Path) {
574   size_t Pos = 0;
575   while ((Pos = Path.find('\\', Pos)) != std::string::npos) {
576     Path.replace(Pos, 1, "\\\\");
577     Pos += 2;
578   }
579   return Path;
580 }
581 
582 /// Helper for running temp dir test in separated process. See below.
583 #define EXPECT_TEMP_DIR(prepare, expected)                                     \
584   EXPECT_EXIT(                                                                 \
585       {                                                                        \
586         prepare;                                                               \
587         SmallString<300> TempDir;                                              \
588         path::system_temp_directory(true, TempDir);                            \
589         raw_os_ostream(std::cerr) << TempDir;                                  \
590         std::exit(0);                                                          \
591       },                                                                       \
592       ::testing::ExitedWithCode(0), path2regex(expected))
593 
594 TEST(SupportDeathTest, TempDirectoryOnWindows) {
595   // In this test we want to check how system_temp_directory responds to
596   // different values of specific env vars. To prevent corrupting env vars of
597   // the current process all checks are done in separated processes.
598   EXPECT_TEMP_DIR(_wputenv_s(L"TMP", L"C:\\OtherFolder"), "C:\\OtherFolder");
599   EXPECT_TEMP_DIR(_wputenv_s(L"TMP", L"C:/Unix/Path/Seperators"),
600                   "C:\\Unix\\Path\\Seperators");
601   EXPECT_TEMP_DIR(_wputenv_s(L"TMP", L"Local Path"), ".+\\Local Path$");
602   EXPECT_TEMP_DIR(_wputenv_s(L"TMP", L"F:\\TrailingSep\\"), "F:\\TrailingSep");
603   EXPECT_TEMP_DIR(
604       _wputenv_s(L"TMP", L"C:\\2\x03C0r-\x00B5\x00B3\\\x2135\x2080"),
605       "C:\\2\xCF\x80r-\xC2\xB5\xC2\xB3\\\xE2\x84\xB5\xE2\x82\x80");
606 
607   // Test $TMP empty, $TEMP set.
608   EXPECT_TEMP_DIR(
609       {
610         _wputenv_s(L"TMP", L"");
611         _wputenv_s(L"TEMP", L"C:\\Valid\\Path");
612       },
613       "C:\\Valid\\Path");
614 
615   // All related env vars empty
616   EXPECT_TEMP_DIR(
617   {
618     _wputenv_s(L"TMP", L"");
619     _wputenv_s(L"TEMP", L"");
620     _wputenv_s(L"USERPROFILE", L"");
621   },
622     "C:\\Temp");
623 
624   // Test evn var / path with 260 chars.
625   SmallString<270> Expected{"C:\\Temp\\AB\\123456789"};
626   while (Expected.size() < 260)
627     Expected.append("\\DirNameWith19Charss");
628   ASSERT_EQ(260U, Expected.size());
629   EXPECT_TEMP_DIR(_putenv_s("TMP", Expected.c_str()), Expected.c_str());
630 }
631 #endif
632 
633 class FileSystemTest : public testing::Test {
634 protected:
635   /// Unique temporary directory in which all created filesystem entities must
636   /// be placed. It is removed at the end of each test (must be empty).
637   SmallString<128> TestDirectory;
638   SmallString<128> NonExistantFile;
639 
640   void SetUp() override {
641     ASSERT_NO_ERROR(
642         fs::createUniqueDirectory("file-system-test", TestDirectory));
643     // We don't care about this specific file.
644     errs() << "Test Directory: " << TestDirectory << '\n';
645     errs().flush();
646     NonExistantFile = TestDirectory;
647 
648     // Even though this value is hardcoded, is a 128-bit GUID, so we should be
649     // guaranteed that this file will never exist.
650     sys::path::append(NonExistantFile, "1B28B495C16344CB9822E588CD4C3EF0");
651   }
652 
653   void TearDown() override { ASSERT_NO_ERROR(fs::remove(TestDirectory.str())); }
654 };
655 
656 TEST_F(FileSystemTest, Unique) {
657   // Create a temp file.
658   int FileDescriptor;
659   SmallString<64> TempPath;
660   ASSERT_NO_ERROR(
661       fs::createTemporaryFile("prefix", "temp", FileDescriptor, TempPath));
662 
663   // The same file should return an identical unique id.
664   fs::UniqueID F1, F2;
665   ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath), F1));
666   ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath), F2));
667   ASSERT_EQ(F1, F2);
668 
669   // Different files should return different unique ids.
670   int FileDescriptor2;
671   SmallString<64> TempPath2;
672   ASSERT_NO_ERROR(
673       fs::createTemporaryFile("prefix", "temp", FileDescriptor2, TempPath2));
674 
675   fs::UniqueID D;
676   ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath2), D));
677   ASSERT_NE(D, F1);
678   ::close(FileDescriptor2);
679 
680   ASSERT_NO_ERROR(fs::remove(Twine(TempPath2)));
681 
682   // Two paths representing the same file on disk should still provide the
683   // same unique id.  We can test this by making a hard link.
684   ASSERT_NO_ERROR(fs::create_link(Twine(TempPath), Twine(TempPath2)));
685   fs::UniqueID D2;
686   ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath2), D2));
687   ASSERT_EQ(D2, F1);
688 
689   ::close(FileDescriptor);
690 
691   SmallString<128> Dir1;
692   ASSERT_NO_ERROR(
693      fs::createUniqueDirectory("dir1", Dir1));
694   ASSERT_NO_ERROR(fs::getUniqueID(Dir1.c_str(), F1));
695   ASSERT_NO_ERROR(fs::getUniqueID(Dir1.c_str(), F2));
696   ASSERT_EQ(F1, F2);
697 
698   SmallString<128> Dir2;
699   ASSERT_NO_ERROR(
700      fs::createUniqueDirectory("dir2", Dir2));
701   ASSERT_NO_ERROR(fs::getUniqueID(Dir2.c_str(), F2));
702   ASSERT_NE(F1, F2);
703   ASSERT_NO_ERROR(fs::remove(Dir1));
704   ASSERT_NO_ERROR(fs::remove(Dir2));
705   ASSERT_NO_ERROR(fs::remove(TempPath2));
706   ASSERT_NO_ERROR(fs::remove(TempPath));
707 }
708 
709 TEST_F(FileSystemTest, RealPath) {
710   ASSERT_NO_ERROR(
711       fs::create_directories(Twine(TestDirectory) + "/test1/test2/test3"));
712   ASSERT_TRUE(fs::exists(Twine(TestDirectory) + "/test1/test2/test3"));
713 
714   SmallString<64> RealBase;
715   SmallString<64> Expected;
716   SmallString<64> Actual;
717 
718   // TestDirectory itself might be under a symlink or have been specified with
719   // a different case than the existing temp directory.  In such cases real_path
720   // on the concatenated path will differ in the TestDirectory portion from
721   // how we specified it.  Make sure to compare against the real_path of the
722   // TestDirectory, and not just the value of TestDirectory.
723   ASSERT_NO_ERROR(fs::real_path(TestDirectory, RealBase));
724   path::native(Twine(RealBase) + "/test1/test2", Expected);
725 
726   ASSERT_NO_ERROR(fs::real_path(
727       Twine(TestDirectory) + "/././test1/../test1/test2/./test3/..", Actual));
728 
729   EXPECT_EQ(Expected, Actual);
730 
731   SmallString<64> HomeDir;
732 
733   // This can fail if $HOME is not set and getpwuid fails.
734   bool Result = llvm::sys::path::home_directory(HomeDir);
735   if (Result) {
736     ASSERT_NO_ERROR(fs::real_path(HomeDir, Expected));
737     ASSERT_NO_ERROR(fs::real_path("~", Actual, true));
738     EXPECT_EQ(Expected, Actual);
739     ASSERT_NO_ERROR(fs::real_path("~/", Actual, true));
740     EXPECT_EQ(Expected, Actual);
741   }
742 
743   ASSERT_NO_ERROR(fs::remove_directories(Twine(TestDirectory) + "/test1"));
744 }
745 
746 TEST_F(FileSystemTest, ExpandTilde) {
747   SmallString<64> Expected;
748   SmallString<64> Actual;
749   SmallString<64> HomeDir;
750 
751   // This can fail if $HOME is not set and getpwuid fails.
752   bool Result = llvm::sys::path::home_directory(HomeDir);
753   if (Result) {
754     fs::expand_tilde(HomeDir, Expected);
755 
756     fs::expand_tilde("~", Actual);
757     EXPECT_EQ(Expected, Actual);
758 
759 #ifdef _WIN32
760     Expected += "\\foo";
761     fs::expand_tilde("~\\foo", Actual);
762 #else
763     Expected += "/foo";
764     fs::expand_tilde("~/foo", Actual);
765 #endif
766 
767     EXPECT_EQ(Expected, Actual);
768   }
769 }
770 
771 #ifdef LLVM_ON_UNIX
772 TEST_F(FileSystemTest, RealPathNoReadPerm) {
773   SmallString<64> Expanded;
774 
775   ASSERT_NO_ERROR(
776     fs::create_directories(Twine(TestDirectory) + "/noreadperm"));
777   ASSERT_TRUE(fs::exists(Twine(TestDirectory) + "/noreadperm"));
778 
779   fs::setPermissions(Twine(TestDirectory) + "/noreadperm", fs::no_perms);
780   fs::setPermissions(Twine(TestDirectory) + "/noreadperm", fs::all_exe);
781 
782   ASSERT_NO_ERROR(fs::real_path(Twine(TestDirectory) + "/noreadperm", Expanded,
783                                 false));
784 
785   ASSERT_NO_ERROR(fs::remove_directories(Twine(TestDirectory) + "/noreadperm"));
786 }
787 #endif
788 
789 
790 TEST_F(FileSystemTest, TempFileKeepDiscard) {
791   // We can keep then discard.
792   auto TempFileOrError = fs::TempFile::create(TestDirectory + "/test-%%%%");
793   ASSERT_TRUE((bool)TempFileOrError);
794   fs::TempFile File = std::move(*TempFileOrError);
795   ASSERT_EQ(-1, TempFileOrError->FD);
796   ASSERT_FALSE((bool)File.keep(TestDirectory + "/keep"));
797   ASSERT_FALSE((bool)File.discard());
798   ASSERT_TRUE(fs::exists(TestDirectory + "/keep"));
799   ASSERT_NO_ERROR(fs::remove(TestDirectory + "/keep"));
800 }
801 
802 TEST_F(FileSystemTest, TempFileDiscardDiscard) {
803   // We can discard twice.
804   auto TempFileOrError = fs::TempFile::create(TestDirectory + "/test-%%%%");
805   ASSERT_TRUE((bool)TempFileOrError);
806   fs::TempFile File = std::move(*TempFileOrError);
807   ASSERT_EQ(-1, TempFileOrError->FD);
808   ASSERT_FALSE((bool)File.discard());
809   ASSERT_FALSE((bool)File.discard());
810   ASSERT_FALSE(fs::exists(TestDirectory + "/keep"));
811 }
812 
813 TEST_F(FileSystemTest, TempFiles) {
814   // Create a temp file.
815   int FileDescriptor;
816   SmallString<64> TempPath;
817   ASSERT_NO_ERROR(
818       fs::createTemporaryFile("prefix", "temp", FileDescriptor, TempPath));
819 
820   // Make sure it exists.
821   ASSERT_TRUE(sys::fs::exists(Twine(TempPath)));
822 
823   // Create another temp tile.
824   int FD2;
825   SmallString<64> TempPath2;
826   ASSERT_NO_ERROR(fs::createTemporaryFile("prefix", "temp", FD2, TempPath2));
827   ASSERT_TRUE(TempPath2.endswith(".temp"));
828   ASSERT_NE(TempPath.str(), TempPath2.str());
829 
830   fs::file_status A, B;
831   ASSERT_NO_ERROR(fs::status(Twine(TempPath), A));
832   ASSERT_NO_ERROR(fs::status(Twine(TempPath2), B));
833   EXPECT_FALSE(fs::equivalent(A, B));
834 
835   ::close(FD2);
836 
837   // Remove Temp2.
838   ASSERT_NO_ERROR(fs::remove(Twine(TempPath2)));
839   ASSERT_NO_ERROR(fs::remove(Twine(TempPath2)));
840   ASSERT_EQ(fs::remove(Twine(TempPath2), false),
841             errc::no_such_file_or_directory);
842 
843   std::error_code EC = fs::status(TempPath2.c_str(), B);
844   EXPECT_EQ(EC, errc::no_such_file_or_directory);
845   EXPECT_EQ(B.type(), fs::file_type::file_not_found);
846 
847   // Make sure Temp2 doesn't exist.
848   ASSERT_EQ(fs::access(Twine(TempPath2), sys::fs::AccessMode::Exist),
849             errc::no_such_file_or_directory);
850 
851   SmallString<64> TempPath3;
852   ASSERT_NO_ERROR(fs::createTemporaryFile("prefix", "", TempPath3));
853   ASSERT_FALSE(TempPath3.endswith("."));
854   FileRemover Cleanup3(TempPath3);
855 
856   // Create a hard link to Temp1.
857   ASSERT_NO_ERROR(fs::create_link(Twine(TempPath), Twine(TempPath2)));
858   bool equal;
859   ASSERT_NO_ERROR(fs::equivalent(Twine(TempPath), Twine(TempPath2), equal));
860   EXPECT_TRUE(equal);
861   ASSERT_NO_ERROR(fs::status(Twine(TempPath), A));
862   ASSERT_NO_ERROR(fs::status(Twine(TempPath2), B));
863   EXPECT_TRUE(fs::equivalent(A, B));
864 
865   // Remove Temp1.
866   ::close(FileDescriptor);
867   ASSERT_NO_ERROR(fs::remove(Twine(TempPath)));
868 
869   // Remove the hard link.
870   ASSERT_NO_ERROR(fs::remove(Twine(TempPath2)));
871 
872   // Make sure Temp1 doesn't exist.
873   ASSERT_EQ(fs::access(Twine(TempPath), sys::fs::AccessMode::Exist),
874             errc::no_such_file_or_directory);
875 
876 #ifdef _WIN32
877   // Path name > 260 chars should get an error.
878   const char *Path270 =
879     "abcdefghijklmnopqrstuvwxyz9abcdefghijklmnopqrstuvwxyz8"
880     "abcdefghijklmnopqrstuvwxyz7abcdefghijklmnopqrstuvwxyz6"
881     "abcdefghijklmnopqrstuvwxyz5abcdefghijklmnopqrstuvwxyz4"
882     "abcdefghijklmnopqrstuvwxyz3abcdefghijklmnopqrstuvwxyz2"
883     "abcdefghijklmnopqrstuvwxyz1abcdefghijklmnopqrstuvwxyz0";
884   EXPECT_EQ(fs::createUniqueFile(Path270, FileDescriptor, TempPath),
885             errc::invalid_argument);
886   // Relative path < 247 chars, no problem.
887   const char *Path216 =
888     "abcdefghijklmnopqrstuvwxyz7abcdefghijklmnopqrstuvwxyz6"
889     "abcdefghijklmnopqrstuvwxyz5abcdefghijklmnopqrstuvwxyz4"
890     "abcdefghijklmnopqrstuvwxyz3abcdefghijklmnopqrstuvwxyz2"
891     "abcdefghijklmnopqrstuvwxyz1abcdefghijklmnopqrstuvwxyz0";
892   ASSERT_NO_ERROR(fs::createTemporaryFile(Path216, "", TempPath));
893   ASSERT_NO_ERROR(fs::remove(Twine(TempPath)));
894 #endif
895 }
896 
897 TEST_F(FileSystemTest, TempFileCollisions) {
898   SmallString<128> TestDirectory;
899   ASSERT_NO_ERROR(
900       fs::createUniqueDirectory("CreateUniqueFileTest", TestDirectory));
901   FileRemover Cleanup(TestDirectory);
902   SmallString<128> Model = TestDirectory;
903   path::append(Model, "%.tmp");
904   SmallString<128> Path;
905   std::vector<fs::TempFile> TempFiles;
906 
907   auto TryCreateTempFile = [&]() {
908     Expected<fs::TempFile> T = fs::TempFile::create(Model);
909     if (T) {
910       TempFiles.push_back(std::move(*T));
911       return true;
912     } else {
913       logAllUnhandledErrors(T.takeError(), errs(),
914                             "Failed to create temporary file: ");
915       return false;
916     }
917   };
918 
919   // Our single-character template allows for 16 unique names. Check that
920   // calling TryCreateTempFile repeatedly results in 16 successes.
921   // Because the test depends on random numbers, it could theoretically fail.
922   // However, the probability of this happening is tiny: with 32 calls, each
923   // of which will retry up to 128 times, to not get a given digit we would
924   // have to fail at least 15 + 17 * 128 = 2191 attempts. The probability of
925   // 2191 attempts not producing a given hexadecimal digit is
926   // (1 - 1/16) ** 2191 or 3.88e-62.
927   int Successes = 0;
928   for (int i = 0; i < 32; ++i)
929     if (TryCreateTempFile()) ++Successes;
930   EXPECT_EQ(Successes, 16);
931 
932   for (fs::TempFile &T : TempFiles)
933     cantFail(T.discard());
934 }
935 
936 TEST_F(FileSystemTest, CreateDir) {
937   ASSERT_NO_ERROR(fs::create_directory(Twine(TestDirectory) + "foo"));
938   ASSERT_NO_ERROR(fs::create_directory(Twine(TestDirectory) + "foo"));
939   ASSERT_EQ(fs::create_directory(Twine(TestDirectory) + "foo", false),
940             errc::file_exists);
941   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "foo"));
942 
943 #ifdef LLVM_ON_UNIX
944   // Set a 0000 umask so that we can test our directory permissions.
945   mode_t OldUmask = ::umask(0000);
946 
947   fs::file_status Status;
948   ASSERT_NO_ERROR(
949       fs::create_directory(Twine(TestDirectory) + "baz500", false,
950                            fs::perms::owner_read | fs::perms::owner_exe));
951   ASSERT_NO_ERROR(fs::status(Twine(TestDirectory) + "baz500", Status));
952   ASSERT_EQ(Status.permissions() & fs::perms::all_all,
953             fs::perms::owner_read | fs::perms::owner_exe);
954   ASSERT_NO_ERROR(fs::create_directory(Twine(TestDirectory) + "baz777", false,
955                                        fs::perms::all_all));
956   ASSERT_NO_ERROR(fs::status(Twine(TestDirectory) + "baz777", Status));
957   ASSERT_EQ(Status.permissions() & fs::perms::all_all, fs::perms::all_all);
958 
959   // Restore umask to be safe.
960   ::umask(OldUmask);
961 #endif
962 
963 #ifdef _WIN32
964   // Prove that create_directories() can handle a pathname > 248 characters,
965   // which is the documented limit for CreateDirectory().
966   // (248 is MAX_PATH subtracting room for an 8.3 filename.)
967   // Generate a directory path guaranteed to fall into that range.
968   size_t TmpLen = TestDirectory.size();
969   const char *OneDir = "\\123456789";
970   size_t OneDirLen = strlen(OneDir);
971   ASSERT_LT(OneDirLen, 12U);
972   size_t NLevels = ((248 - TmpLen) / OneDirLen) + 1;
973   SmallString<260> LongDir(TestDirectory);
974   for (size_t I = 0; I < NLevels; ++I)
975     LongDir.append(OneDir);
976   ASSERT_NO_ERROR(fs::create_directories(Twine(LongDir)));
977   ASSERT_NO_ERROR(fs::create_directories(Twine(LongDir)));
978   ASSERT_EQ(fs::create_directories(Twine(LongDir), false),
979             errc::file_exists);
980   // Tidy up, "recursively" removing the directories.
981   StringRef ThisDir(LongDir);
982   for (size_t J = 0; J < NLevels; ++J) {
983     ASSERT_NO_ERROR(fs::remove(ThisDir));
984     ThisDir = path::parent_path(ThisDir);
985   }
986 
987   // Also verify that paths with Unix separators are handled correctly.
988   std::string LongPathWithUnixSeparators(TestDirectory.str());
989   // Add at least one subdirectory to TestDirectory, and replace slashes with
990   // backslashes
991   do {
992     LongPathWithUnixSeparators.append("/DirNameWith19Charss");
993   } while (LongPathWithUnixSeparators.size() < 260);
994   std::replace(LongPathWithUnixSeparators.begin(),
995                LongPathWithUnixSeparators.end(),
996                '\\', '/');
997   ASSERT_NO_ERROR(fs::create_directories(Twine(LongPathWithUnixSeparators)));
998   // cleanup
999   ASSERT_NO_ERROR(fs::remove_directories(Twine(TestDirectory) +
1000                                          "/DirNameWith19Charss"));
1001 
1002   // Similarly for a relative pathname.  Need to set the current directory to
1003   // TestDirectory so that the one we create ends up in the right place.
1004   char PreviousDir[260];
1005   size_t PreviousDirLen = ::GetCurrentDirectoryA(260, PreviousDir);
1006   ASSERT_GT(PreviousDirLen, 0U);
1007   ASSERT_LT(PreviousDirLen, 260U);
1008   ASSERT_NE(::SetCurrentDirectoryA(TestDirectory.c_str()), 0);
1009   LongDir.clear();
1010   // Generate a relative directory name with absolute length > 248.
1011   size_t LongDirLen = 249 - TestDirectory.size();
1012   LongDir.assign(LongDirLen, 'a');
1013   ASSERT_NO_ERROR(fs::create_directory(Twine(LongDir)));
1014   // While we're here, prove that .. and . handling works in these long paths.
1015   const char *DotDotDirs = "\\..\\.\\b";
1016   LongDir.append(DotDotDirs);
1017   ASSERT_NO_ERROR(fs::create_directory("b"));
1018   ASSERT_EQ(fs::create_directory(Twine(LongDir), false), errc::file_exists);
1019   // And clean up.
1020   ASSERT_NO_ERROR(fs::remove("b"));
1021   ASSERT_NO_ERROR(fs::remove(
1022     Twine(LongDir.substr(0, LongDir.size() - strlen(DotDotDirs)))));
1023   ASSERT_NE(::SetCurrentDirectoryA(PreviousDir), 0);
1024 #endif
1025 }
1026 
1027 TEST_F(FileSystemTest, DirectoryIteration) {
1028   std::error_code ec;
1029   for (fs::directory_iterator i(".", ec), e; i != e; i.increment(ec))
1030     ASSERT_NO_ERROR(ec);
1031 
1032   // Create a known hierarchy to recurse over.
1033   ASSERT_NO_ERROR(
1034       fs::create_directories(Twine(TestDirectory) + "/recursive/a0/aa1"));
1035   ASSERT_NO_ERROR(
1036       fs::create_directories(Twine(TestDirectory) + "/recursive/a0/ab1"));
1037   ASSERT_NO_ERROR(fs::create_directories(Twine(TestDirectory) +
1038                                          "/recursive/dontlookhere/da1"));
1039   ASSERT_NO_ERROR(
1040       fs::create_directories(Twine(TestDirectory) + "/recursive/z0/za1"));
1041   ASSERT_NO_ERROR(
1042       fs::create_directories(Twine(TestDirectory) + "/recursive/pop/p1"));
1043   typedef std::vector<std::string> v_t;
1044   v_t visited;
1045   for (fs::recursive_directory_iterator i(Twine(TestDirectory)
1046          + "/recursive", ec), e; i != e; i.increment(ec)){
1047     ASSERT_NO_ERROR(ec);
1048     if (path::filename(i->path()) == "p1") {
1049       i.pop();
1050       // FIXME: recursive_directory_iterator should be more robust.
1051       if (i == e) break;
1052     }
1053     if (path::filename(i->path()) == "dontlookhere")
1054       i.no_push();
1055     visited.push_back(std::string(path::filename(i->path())));
1056   }
1057   v_t::const_iterator a0 = find(visited, "a0");
1058   v_t::const_iterator aa1 = find(visited, "aa1");
1059   v_t::const_iterator ab1 = find(visited, "ab1");
1060   v_t::const_iterator dontlookhere = find(visited, "dontlookhere");
1061   v_t::const_iterator da1 = find(visited, "da1");
1062   v_t::const_iterator z0 = find(visited, "z0");
1063   v_t::const_iterator za1 = find(visited, "za1");
1064   v_t::const_iterator pop = find(visited, "pop");
1065   v_t::const_iterator p1 = find(visited, "p1");
1066 
1067   // Make sure that each path was visited correctly.
1068   ASSERT_NE(a0, visited.end());
1069   ASSERT_NE(aa1, visited.end());
1070   ASSERT_NE(ab1, visited.end());
1071   ASSERT_NE(dontlookhere, visited.end());
1072   ASSERT_EQ(da1, visited.end()); // Not visited.
1073   ASSERT_NE(z0, visited.end());
1074   ASSERT_NE(za1, visited.end());
1075   ASSERT_NE(pop, visited.end());
1076   ASSERT_EQ(p1, visited.end()); // Not visited.
1077 
1078   // Make sure that parents were visited before children. No other ordering
1079   // guarantees can be made across siblings.
1080   ASSERT_LT(a0, aa1);
1081   ASSERT_LT(a0, ab1);
1082   ASSERT_LT(z0, za1);
1083 
1084   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/a0/aa1"));
1085   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/a0/ab1"));
1086   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/a0"));
1087   ASSERT_NO_ERROR(
1088       fs::remove(Twine(TestDirectory) + "/recursive/dontlookhere/da1"));
1089   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/dontlookhere"));
1090   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/pop/p1"));
1091   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/pop"));
1092   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/z0/za1"));
1093   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/z0"));
1094   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive"));
1095 
1096   // Test recursive_directory_iterator level()
1097   ASSERT_NO_ERROR(
1098       fs::create_directories(Twine(TestDirectory) + "/reclevel/a/b/c"));
1099   fs::recursive_directory_iterator I(Twine(TestDirectory) + "/reclevel", ec), E;
1100   for (int l = 0; I != E; I.increment(ec), ++l) {
1101     ASSERT_NO_ERROR(ec);
1102     EXPECT_EQ(I.level(), l);
1103   }
1104   EXPECT_EQ(I, E);
1105   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel/a/b/c"));
1106   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel/a/b"));
1107   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel/a"));
1108   ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel"));
1109 }
1110 
1111 TEST_F(FileSystemTest, DirectoryNotExecutable) {
1112   ASSERT_EQ(fs::access(TestDirectory, sys::fs::AccessMode::Execute),
1113             errc::permission_denied);
1114 }
1115 
1116 #ifdef LLVM_ON_UNIX
1117 TEST_F(FileSystemTest, BrokenSymlinkDirectoryIteration) {
1118   // Create a known hierarchy to recurse over.
1119   ASSERT_NO_ERROR(fs::create_directories(Twine(TestDirectory) + "/symlink"));
1120   ASSERT_NO_ERROR(
1121       fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/a"));
1122   ASSERT_NO_ERROR(
1123       fs::create_directories(Twine(TestDirectory) + "/symlink/b/bb"));
1124   ASSERT_NO_ERROR(
1125       fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/b/ba"));
1126   ASSERT_NO_ERROR(
1127       fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/b/bc"));
1128   ASSERT_NO_ERROR(
1129       fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/c"));
1130   ASSERT_NO_ERROR(
1131       fs::create_directories(Twine(TestDirectory) + "/symlink/d/dd/ddd"));
1132   ASSERT_NO_ERROR(fs::create_link(Twine(TestDirectory) + "/symlink/d/dd",
1133                                   Twine(TestDirectory) + "/symlink/d/da"));
1134   ASSERT_NO_ERROR(
1135       fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/e"));
1136 
1137   typedef std::vector<std::string> v_t;
1138   v_t VisitedNonBrokenSymlinks;
1139   v_t VisitedBrokenSymlinks;
1140   std::error_code ec;
1141   using testing::UnorderedElementsAre;
1142   using testing::UnorderedElementsAreArray;
1143 
1144   // Broken symbol links are expected to throw an error.
1145   for (fs::directory_iterator i(Twine(TestDirectory) + "/symlink", ec), e;
1146        i != e; i.increment(ec)) {
1147     ASSERT_NO_ERROR(ec);
1148     if (i->status().getError() ==
1149         std::make_error_code(std::errc::no_such_file_or_directory)) {
1150       VisitedBrokenSymlinks.push_back(std::string(path::filename(i->path())));
1151       continue;
1152     }
1153     VisitedNonBrokenSymlinks.push_back(std::string(path::filename(i->path())));
1154   }
1155   EXPECT_THAT(VisitedNonBrokenSymlinks, UnorderedElementsAre("b", "d"));
1156   VisitedNonBrokenSymlinks.clear();
1157 
1158   EXPECT_THAT(VisitedBrokenSymlinks, UnorderedElementsAre("a", "c", "e"));
1159   VisitedBrokenSymlinks.clear();
1160 
1161   // Broken symbol links are expected to throw an error.
1162   for (fs::recursive_directory_iterator i(
1163       Twine(TestDirectory) + "/symlink", ec), e; i != e; i.increment(ec)) {
1164     ASSERT_NO_ERROR(ec);
1165     if (i->status().getError() ==
1166         std::make_error_code(std::errc::no_such_file_or_directory)) {
1167       VisitedBrokenSymlinks.push_back(std::string(path::filename(i->path())));
1168       continue;
1169     }
1170     VisitedNonBrokenSymlinks.push_back(std::string(path::filename(i->path())));
1171   }
1172   EXPECT_THAT(VisitedNonBrokenSymlinks,
1173               UnorderedElementsAre("b", "bb", "d", "da", "dd", "ddd", "ddd"));
1174   VisitedNonBrokenSymlinks.clear();
1175 
1176   EXPECT_THAT(VisitedBrokenSymlinks,
1177               UnorderedElementsAre("a", "ba", "bc", "c", "e"));
1178   VisitedBrokenSymlinks.clear();
1179 
1180   for (fs::recursive_directory_iterator i(
1181       Twine(TestDirectory) + "/symlink", ec, /*follow_symlinks=*/false), e;
1182        i != e; i.increment(ec)) {
1183     ASSERT_NO_ERROR(ec);
1184     if (i->status().getError() ==
1185         std::make_error_code(std::errc::no_such_file_or_directory)) {
1186       VisitedBrokenSymlinks.push_back(std::string(path::filename(i->path())));
1187       continue;
1188     }
1189     VisitedNonBrokenSymlinks.push_back(std::string(path::filename(i->path())));
1190   }
1191   EXPECT_THAT(VisitedNonBrokenSymlinks,
1192               UnorderedElementsAreArray({"a", "b", "ba", "bb", "bc", "c", "d",
1193                                          "da", "dd", "ddd", "e"}));
1194   VisitedNonBrokenSymlinks.clear();
1195 
1196   EXPECT_THAT(VisitedBrokenSymlinks, UnorderedElementsAre());
1197   VisitedBrokenSymlinks.clear();
1198 
1199   ASSERT_NO_ERROR(fs::remove_directories(Twine(TestDirectory) + "/symlink"));
1200 }
1201 #endif
1202 
1203 #ifdef _WIN32
1204 TEST_F(FileSystemTest, UTF8ToUTF16DirectoryIteration) {
1205   // The Windows filesystem support uses UTF-16 and converts paths from the
1206   // input UTF-8. The UTF-16 equivalent of the input path can be shorter in
1207   // length.
1208 
1209   // This test relies on TestDirectory not being so long such that MAX_PATH
1210   // would be exceeded (see widenPath). If that were the case, the UTF-16
1211   // path is likely to be longer than the input.
1212   const char *Pi = "\xcf\x80"; // UTF-8 lower case pi.
1213   std::string RootDir = (TestDirectory + "/" + Pi).str();
1214 
1215   // Create test directories.
1216   ASSERT_NO_ERROR(fs::create_directories(Twine(RootDir) + "/a"));
1217   ASSERT_NO_ERROR(fs::create_directories(Twine(RootDir) + "/b"));
1218 
1219   std::error_code EC;
1220   unsigned Count = 0;
1221   for (fs::directory_iterator I(Twine(RootDir), EC), E; I != E;
1222        I.increment(EC)) {
1223     ASSERT_NO_ERROR(EC);
1224     StringRef DirName = path::filename(I->path());
1225     EXPECT_TRUE(DirName == "a" || DirName == "b");
1226     ++Count;
1227   }
1228   EXPECT_EQ(Count, 2U);
1229 
1230   ASSERT_NO_ERROR(fs::remove(Twine(RootDir) + "/a"));
1231   ASSERT_NO_ERROR(fs::remove(Twine(RootDir) + "/b"));
1232   ASSERT_NO_ERROR(fs::remove(Twine(RootDir)));
1233 }
1234 #endif
1235 
1236 TEST_F(FileSystemTest, Remove) {
1237   SmallString<64> BaseDir;
1238   SmallString<64> Paths[4];
1239   int fds[4];
1240   ASSERT_NO_ERROR(fs::createUniqueDirectory("fs_remove", BaseDir));
1241 
1242   ASSERT_NO_ERROR(fs::create_directories(Twine(BaseDir) + "/foo/bar/baz"));
1243   ASSERT_NO_ERROR(fs::create_directories(Twine(BaseDir) + "/foo/bar/buzz"));
1244   ASSERT_NO_ERROR(fs::createUniqueFile(
1245       Twine(BaseDir) + "/foo/bar/baz/%%%%%%.tmp", fds[0], Paths[0]));
1246   ASSERT_NO_ERROR(fs::createUniqueFile(
1247       Twine(BaseDir) + "/foo/bar/baz/%%%%%%.tmp", fds[1], Paths[1]));
1248   ASSERT_NO_ERROR(fs::createUniqueFile(
1249       Twine(BaseDir) + "/foo/bar/buzz/%%%%%%.tmp", fds[2], Paths[2]));
1250   ASSERT_NO_ERROR(fs::createUniqueFile(
1251       Twine(BaseDir) + "/foo/bar/buzz/%%%%%%.tmp", fds[3], Paths[3]));
1252 
1253   for (int fd : fds)
1254     ::close(fd);
1255 
1256   EXPECT_TRUE(fs::exists(Twine(BaseDir) + "/foo/bar/baz"));
1257   EXPECT_TRUE(fs::exists(Twine(BaseDir) + "/foo/bar/buzz"));
1258   EXPECT_TRUE(fs::exists(Paths[0]));
1259   EXPECT_TRUE(fs::exists(Paths[1]));
1260   EXPECT_TRUE(fs::exists(Paths[2]));
1261   EXPECT_TRUE(fs::exists(Paths[3]));
1262 
1263   ASSERT_NO_ERROR(fs::remove_directories("D:/footest"));
1264 
1265   ASSERT_NO_ERROR(fs::remove_directories(BaseDir));
1266   ASSERT_FALSE(fs::exists(BaseDir));
1267 }
1268 
1269 #ifdef _WIN32
1270 TEST_F(FileSystemTest, CarriageReturn) {
1271   SmallString<128> FilePathname(TestDirectory);
1272   std::error_code EC;
1273   path::append(FilePathname, "test");
1274 
1275   {
1276     raw_fd_ostream File(FilePathname, EC, sys::fs::OF_TextWithCRLF);
1277     ASSERT_NO_ERROR(EC);
1278     File << '\n';
1279   }
1280   {
1281     auto Buf = MemoryBuffer::getFile(FilePathname.str());
1282     EXPECT_TRUE((bool)Buf);
1283     EXPECT_EQ(Buf.get()->getBuffer(), "\r\n");
1284   }
1285 
1286   {
1287     raw_fd_ostream File(FilePathname, EC, sys::fs::OF_None);
1288     ASSERT_NO_ERROR(EC);
1289     File << '\n';
1290   }
1291   {
1292     auto Buf = MemoryBuffer::getFile(FilePathname.str());
1293     EXPECT_TRUE((bool)Buf);
1294     EXPECT_EQ(Buf.get()->getBuffer(), "\n");
1295   }
1296   ASSERT_NO_ERROR(fs::remove(Twine(FilePathname)));
1297 }
1298 #endif
1299 
1300 TEST_F(FileSystemTest, Resize) {
1301   int FD;
1302   SmallString<64> TempPath;
1303   ASSERT_NO_ERROR(fs::createTemporaryFile("prefix", "temp", FD, TempPath));
1304   ASSERT_NO_ERROR(fs::resize_file(FD, 123));
1305   fs::file_status Status;
1306   ASSERT_NO_ERROR(fs::status(FD, Status));
1307   ASSERT_EQ(Status.getSize(), 123U);
1308   ::close(FD);
1309   ASSERT_NO_ERROR(fs::remove(TempPath));
1310 }
1311 
1312 TEST_F(FileSystemTest, ResizeBeforeMapping) {
1313   // Create a temp file.
1314   int FD;
1315   SmallString<64> TempPath;
1316   ASSERT_NO_ERROR(fs::createTemporaryFile("prefix", "temp", FD, TempPath));
1317   ASSERT_NO_ERROR(fs::resize_file_before_mapping_readwrite(FD, 123));
1318 
1319   // Map in temp file. On Windows, fs::resize_file_before_mapping_readwrite is
1320   // a no-op and the mapping itself will resize the file.
1321   std::error_code EC;
1322   {
1323     fs::mapped_file_region mfr(fs::convertFDToNativeFile(FD),
1324                                fs::mapped_file_region::readwrite, 123, 0, EC);
1325     ASSERT_NO_ERROR(EC);
1326     // Unmap temp file
1327   }
1328 
1329   // Check the size.
1330   fs::file_status Status;
1331   ASSERT_NO_ERROR(fs::status(FD, Status));
1332   ASSERT_EQ(Status.getSize(), 123U);
1333   ::close(FD);
1334   ASSERT_NO_ERROR(fs::remove(TempPath));
1335 }
1336 
1337 TEST_F(FileSystemTest, MD5) {
1338   int FD;
1339   SmallString<64> TempPath;
1340   ASSERT_NO_ERROR(fs::createTemporaryFile("prefix", "temp", FD, TempPath));
1341   StringRef Data("abcdefghijklmnopqrstuvwxyz");
1342   ASSERT_EQ(write(FD, Data.data(), Data.size()), static_cast<ssize_t>(Data.size()));
1343   lseek(FD, 0, SEEK_SET);
1344   auto Hash = fs::md5_contents(FD);
1345   ::close(FD);
1346   ASSERT_NO_ERROR(Hash.getError());
1347 
1348   EXPECT_STREQ("c3fcd3d76192e4007dfb496cca67e13b", Hash->digest().c_str());
1349 }
1350 
1351 TEST_F(FileSystemTest, FileMapping) {
1352   // Create a temp file.
1353   int FileDescriptor;
1354   SmallString<64> TempPath;
1355   ASSERT_NO_ERROR(
1356       fs::createTemporaryFile("prefix", "temp", FileDescriptor, TempPath));
1357   unsigned Size = 4096;
1358   ASSERT_NO_ERROR(
1359       fs::resize_file_before_mapping_readwrite(FileDescriptor, Size));
1360 
1361   // Map in temp file and add some content
1362   std::error_code EC;
1363   StringRef Val("hello there");
1364   fs::mapped_file_region MaybeMFR;
1365   EXPECT_FALSE(MaybeMFR);
1366   {
1367     fs::mapped_file_region mfr(fs::convertFDToNativeFile(FileDescriptor),
1368                                fs::mapped_file_region::readwrite, Size, 0, EC);
1369     ASSERT_NO_ERROR(EC);
1370     std::copy(Val.begin(), Val.end(), mfr.data());
1371     // Explicitly add a 0.
1372     mfr.data()[Val.size()] = 0;
1373 
1374     // Move it out of the scope and confirm mfr is reset.
1375     MaybeMFR = std::move(mfr);
1376     EXPECT_FALSE(mfr);
1377 #if !defined(NDEBUG) && GTEST_HAS_DEATH_TEST
1378     EXPECT_DEATH(mfr.data(), "Mapping failed but used anyway!");
1379     EXPECT_DEATH(mfr.size(), "Mapping failed but used anyway!");
1380 #endif
1381   }
1382 
1383   // Check that the moved-to region is still valid.
1384   EXPECT_EQ(Val, StringRef(MaybeMFR.data()));
1385   EXPECT_EQ(Size, MaybeMFR.size());
1386 
1387   // Unmap temp file.
1388   MaybeMFR.unmap();
1389 
1390   ASSERT_EQ(close(FileDescriptor), 0);
1391 
1392   // Map it back in read-only
1393   {
1394     int FD;
1395     EC = fs::openFileForRead(Twine(TempPath), FD);
1396     ASSERT_NO_ERROR(EC);
1397     fs::mapped_file_region mfr(fs::convertFDToNativeFile(FD),
1398                                fs::mapped_file_region::readonly, Size, 0, EC);
1399     ASSERT_NO_ERROR(EC);
1400 
1401     // Verify content
1402     EXPECT_EQ(StringRef(mfr.const_data()), Val);
1403 
1404     // Unmap temp file
1405     fs::mapped_file_region m(fs::convertFDToNativeFile(FD),
1406                              fs::mapped_file_region::readonly, Size, 0, EC);
1407     ASSERT_NO_ERROR(EC);
1408     ASSERT_EQ(close(FD), 0);
1409   }
1410   ASSERT_NO_ERROR(fs::remove(TempPath));
1411 }
1412 
1413 TEST(Support, NormalizePath) {
1414   //                           Input,        Expected Win, Expected Posix
1415   using TestTuple = std::tuple<const char *, const char *, const char *>;
1416   std::vector<TestTuple> Tests;
1417   Tests.emplace_back("a", "a", "a");
1418   Tests.emplace_back("a/b", "a\\b", "a/b");
1419   Tests.emplace_back("a\\b", "a\\b", "a/b");
1420   Tests.emplace_back("a\\\\b", "a\\\\b", "a//b");
1421   Tests.emplace_back("\\a", "\\a", "/a");
1422   Tests.emplace_back("a\\", "a\\", "a/");
1423   Tests.emplace_back("a\\t", "a\\t", "a/t");
1424 
1425   for (auto &T : Tests) {
1426     SmallString<64> Win(std::get<0>(T));
1427     SmallString<64> Posix(Win);
1428     path::native(Win, path::Style::windows);
1429     path::native(Posix, path::Style::posix);
1430     EXPECT_EQ(std::get<1>(T), Win);
1431     EXPECT_EQ(std::get<2>(T), Posix);
1432   }
1433 
1434 #if defined(_WIN32)
1435   SmallString<64> PathHome;
1436   path::home_directory(PathHome);
1437 
1438   const char *Path7a = "~/aaa";
1439   SmallString<64> Path7(Path7a);
1440   path::native(Path7);
1441   EXPECT_TRUE(Path7.endswith("\\aaa"));
1442   EXPECT_TRUE(Path7.startswith(PathHome));
1443   EXPECT_EQ(Path7.size(), PathHome.size() + strlen(Path7a + 1));
1444 
1445   const char *Path8a = "~";
1446   SmallString<64> Path8(Path8a);
1447   path::native(Path8);
1448   EXPECT_EQ(Path8, PathHome);
1449 
1450   const char *Path9a = "~aaa";
1451   SmallString<64> Path9(Path9a);
1452   path::native(Path9);
1453   EXPECT_EQ(Path9, "~aaa");
1454 
1455   const char *Path10a = "aaa/~/b";
1456   SmallString<64> Path10(Path10a);
1457   path::native(Path10);
1458   EXPECT_EQ(Path10, "aaa\\~\\b");
1459 #endif
1460 }
1461 
1462 TEST(Support, RemoveLeadingDotSlash) {
1463   StringRef Path1("././/foolz/wat");
1464   StringRef Path2("./////");
1465 
1466   Path1 = path::remove_leading_dotslash(Path1);
1467   EXPECT_EQ(Path1, "foolz/wat");
1468   Path2 = path::remove_leading_dotslash(Path2);
1469   EXPECT_EQ(Path2, "");
1470 }
1471 
1472 static std::string remove_dots(StringRef path, bool remove_dot_dot,
1473                                path::Style style) {
1474   SmallString<256> buffer(path);
1475   path::remove_dots(buffer, remove_dot_dot, style);
1476   return std::string(buffer.str());
1477 }
1478 
1479 TEST(Support, RemoveDots) {
1480   EXPECT_EQ("foolz\\wat",
1481             remove_dots(".\\.\\\\foolz\\wat", false, path::Style::windows));
1482   EXPECT_EQ("", remove_dots(".\\\\\\\\\\", false, path::Style::windows));
1483 
1484   EXPECT_EQ("a\\..\\b\\c",
1485             remove_dots(".\\a\\..\\b\\c", false, path::Style::windows));
1486   EXPECT_EQ("b\\c", remove_dots(".\\a\\..\\b\\c", true, path::Style::windows));
1487   EXPECT_EQ("c", remove_dots(".\\.\\c", true, path::Style::windows));
1488   EXPECT_EQ("..\\a\\c",
1489             remove_dots("..\\a\\b\\..\\c", true, path::Style::windows));
1490   EXPECT_EQ("..\\..\\a\\c",
1491             remove_dots("..\\..\\a\\b\\..\\c", true, path::Style::windows));
1492   EXPECT_EQ("C:\\a\\c", remove_dots("C:\\foo\\bar//..\\..\\a\\c", true,
1493                                     path::Style::windows));
1494 
1495   // FIXME: These leading forward slashes are emergent behavior. VFS depends on
1496   // this behavior now.
1497   EXPECT_EQ("C:/bar",
1498             remove_dots("C:/foo/../bar", true, path::Style::windows));
1499   EXPECT_EQ("C:/foo\\bar",
1500             remove_dots("C:/foo/bar", true, path::Style::windows));
1501   EXPECT_EQ("C:/foo\\bar",
1502             remove_dots("C:/foo\\bar", true, path::Style::windows));
1503   EXPECT_EQ("/", remove_dots("/", true, path::Style::windows));
1504   EXPECT_EQ("C:/", remove_dots("C:/", true, path::Style::windows));
1505 
1506   // Some clients of remove_dots expect it to remove trailing slashes. Again,
1507   // this is emergent behavior that VFS relies on, and not inherently part of
1508   // the specification.
1509   EXPECT_EQ("C:\\foo\\bar",
1510             remove_dots("C:\\foo\\bar\\", true, path::Style::windows));
1511   EXPECT_EQ("/foo/bar",
1512             remove_dots("/foo/bar/", true, path::Style::posix));
1513 
1514   // A double separator is rewritten.
1515   EXPECT_EQ("C:/foo\\bar", remove_dots("C:/foo//bar", true, path::Style::windows));
1516 
1517   SmallString<64> Path1(".\\.\\c");
1518   EXPECT_TRUE(path::remove_dots(Path1, true, path::Style::windows));
1519   EXPECT_EQ("c", Path1);
1520 
1521   EXPECT_EQ("foolz/wat",
1522             remove_dots("././/foolz/wat", false, path::Style::posix));
1523   EXPECT_EQ("", remove_dots("./////", false, path::Style::posix));
1524 
1525   EXPECT_EQ("a/../b/c", remove_dots("./a/../b/c", false, path::Style::posix));
1526   EXPECT_EQ("b/c", remove_dots("./a/../b/c", true, path::Style::posix));
1527   EXPECT_EQ("c", remove_dots("././c", true, path::Style::posix));
1528   EXPECT_EQ("../a/c", remove_dots("../a/b/../c", true, path::Style::posix));
1529   EXPECT_EQ("../../a/c",
1530             remove_dots("../../a/b/../c", true, path::Style::posix));
1531   EXPECT_EQ("/a/c", remove_dots("/../../a/c", true, path::Style::posix));
1532   EXPECT_EQ("/a/c",
1533             remove_dots("/../a/b//../././/c", true, path::Style::posix));
1534   EXPECT_EQ("/", remove_dots("/", true, path::Style::posix));
1535 
1536   // FIXME: Leaving behind this double leading slash seems like a bug.
1537   EXPECT_EQ("//foo/bar",
1538             remove_dots("//foo/bar/", true, path::Style::posix));
1539 
1540   SmallString<64> Path2("././c");
1541   EXPECT_TRUE(path::remove_dots(Path2, true, path::Style::posix));
1542   EXPECT_EQ("c", Path2);
1543 }
1544 
1545 TEST(Support, ReplacePathPrefix) {
1546   SmallString<64> Path1("/foo");
1547   SmallString<64> Path2("/old/foo");
1548   SmallString<64> Path3("/oldnew/foo");
1549   SmallString<64> Path4("C:\\old/foo\\bar");
1550   SmallString<64> OldPrefix("/old");
1551   SmallString<64> OldPrefixSep("/old/");
1552   SmallString<64> OldPrefixWin("c:/oLD/F");
1553   SmallString<64> NewPrefix("/new");
1554   SmallString<64> NewPrefix2("/longernew");
1555   SmallString<64> EmptyPrefix("");
1556   bool Found;
1557 
1558   SmallString<64> Path = Path1;
1559   Found = path::replace_path_prefix(Path, OldPrefix, NewPrefix);
1560   EXPECT_FALSE(Found);
1561   EXPECT_EQ(Path, "/foo");
1562   Path = Path2;
1563   Found = path::replace_path_prefix(Path, OldPrefix, NewPrefix);
1564   EXPECT_TRUE(Found);
1565   EXPECT_EQ(Path, "/new/foo");
1566   Path = Path2;
1567   Found = path::replace_path_prefix(Path, OldPrefix, NewPrefix2);
1568   EXPECT_TRUE(Found);
1569   EXPECT_EQ(Path, "/longernew/foo");
1570   Path = Path1;
1571   Found = path::replace_path_prefix(Path, EmptyPrefix, NewPrefix);
1572   EXPECT_TRUE(Found);
1573   EXPECT_EQ(Path, "/new/foo");
1574   Path = Path2;
1575   Found = path::replace_path_prefix(Path, OldPrefix, EmptyPrefix);
1576   EXPECT_TRUE(Found);
1577   EXPECT_EQ(Path, "/foo");
1578   Path = Path2;
1579   Found = path::replace_path_prefix(Path, OldPrefixSep, EmptyPrefix);
1580   EXPECT_TRUE(Found);
1581   EXPECT_EQ(Path, "foo");
1582   Path = Path3;
1583   Found = path::replace_path_prefix(Path, OldPrefix, NewPrefix);
1584   EXPECT_TRUE(Found);
1585   EXPECT_EQ(Path, "/newnew/foo");
1586   Path = Path3;
1587   Found = path::replace_path_prefix(Path, OldPrefix, NewPrefix2);
1588   EXPECT_TRUE(Found);
1589   EXPECT_EQ(Path, "/longernewnew/foo");
1590   Path = Path1;
1591   Found = path::replace_path_prefix(Path, EmptyPrefix, NewPrefix);
1592   EXPECT_TRUE(Found);
1593   EXPECT_EQ(Path, "/new/foo");
1594   Path = OldPrefix;
1595   Found = path::replace_path_prefix(Path, OldPrefix, NewPrefix);
1596   EXPECT_TRUE(Found);
1597   EXPECT_EQ(Path, "/new");
1598   Path = OldPrefixSep;
1599   Found = path::replace_path_prefix(Path, OldPrefix, NewPrefix);
1600   EXPECT_TRUE(Found);
1601   EXPECT_EQ(Path, "/new/");
1602   Path = OldPrefix;
1603   Found = path::replace_path_prefix(Path, OldPrefixSep, NewPrefix);
1604   EXPECT_FALSE(Found);
1605   EXPECT_EQ(Path, "/old");
1606   Path = Path4;
1607   Found = path::replace_path_prefix(Path, OldPrefixWin, NewPrefix,
1608                                     path::Style::windows);
1609   EXPECT_TRUE(Found);
1610   EXPECT_EQ(Path, "/newoo\\bar");
1611   Path = Path4;
1612   Found = path::replace_path_prefix(Path, OldPrefixWin, NewPrefix,
1613                                     path::Style::posix);
1614   EXPECT_FALSE(Found);
1615   EXPECT_EQ(Path, "C:\\old/foo\\bar");
1616 }
1617 
1618 TEST_F(FileSystemTest, OpenFileForRead) {
1619   // Create a temp file.
1620   int FileDescriptor;
1621   SmallString<64> TempPath;
1622   ASSERT_NO_ERROR(
1623       fs::createTemporaryFile("prefix", "temp", FileDescriptor, TempPath));
1624   FileRemover Cleanup(TempPath);
1625 
1626   // Make sure it exists.
1627   ASSERT_TRUE(sys::fs::exists(Twine(TempPath)));
1628 
1629   // Open the file for read
1630   int FileDescriptor2;
1631   SmallString<64> ResultPath;
1632   ASSERT_NO_ERROR(fs::openFileForRead(Twine(TempPath), FileDescriptor2,
1633                                       fs::OF_None, &ResultPath))
1634 
1635   // If we succeeded, check that the paths are the same (modulo case):
1636   if (!ResultPath.empty()) {
1637     // The paths returned by createTemporaryFile and getPathFromOpenFD
1638     // should reference the same file on disk.
1639     fs::UniqueID D1, D2;
1640     ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath), D1));
1641     ASSERT_NO_ERROR(fs::getUniqueID(Twine(ResultPath), D2));
1642     ASSERT_EQ(D1, D2);
1643   }
1644   ::close(FileDescriptor);
1645   ::close(FileDescriptor2);
1646 
1647 #ifdef _WIN32
1648   // Since Windows Vista, file access time is not updated by default.
1649   // This is instead updated manually by openFileForRead.
1650   // https://blogs.technet.microsoft.com/filecab/2006/11/07/disabling-last-access-time-in-windows-vista-to-improve-ntfs-performance/
1651   // This part of the unit test is Windows specific as the updating of
1652   // access times can be disabled on Linux using /etc/fstab.
1653 
1654   // Set access time to UNIX epoch.
1655   ASSERT_NO_ERROR(sys::fs::openFileForWrite(Twine(TempPath), FileDescriptor,
1656                                             fs::CD_OpenExisting));
1657   TimePoint<> Epoch(std::chrono::milliseconds(0));
1658   ASSERT_NO_ERROR(fs::setLastAccessAndModificationTime(FileDescriptor, Epoch));
1659   ::close(FileDescriptor);
1660 
1661   // Open the file and ensure access time is updated, when forced.
1662   ASSERT_NO_ERROR(fs::openFileForRead(Twine(TempPath), FileDescriptor,
1663                                       fs::OF_UpdateAtime, &ResultPath));
1664 
1665   sys::fs::file_status Status;
1666   ASSERT_NO_ERROR(sys::fs::status(FileDescriptor, Status));
1667   auto FileAccessTime = Status.getLastAccessedTime();
1668 
1669   ASSERT_NE(Epoch, FileAccessTime);
1670   ::close(FileDescriptor);
1671 
1672   // Ideally this test would include a case when ATime is not forced to update,
1673   // however the expected behaviour will differ depending on the configuration
1674   // of the Windows file system.
1675 #endif
1676 }
1677 
1678 static void createFileWithData(const Twine &Path, bool ShouldExistBefore,
1679                                fs::CreationDisposition Disp, StringRef Data) {
1680   int FD;
1681   ASSERT_EQ(ShouldExistBefore, fs::exists(Path));
1682   ASSERT_NO_ERROR(fs::openFileForWrite(Path, FD, Disp));
1683   FileDescriptorCloser Closer(FD);
1684   ASSERT_TRUE(fs::exists(Path));
1685 
1686   ASSERT_EQ(Data.size(), (size_t)write(FD, Data.data(), Data.size()));
1687 }
1688 
1689 static void verifyFileContents(const Twine &Path, StringRef Contents) {
1690   auto Buffer = MemoryBuffer::getFile(Path);
1691   ASSERT_TRUE((bool)Buffer);
1692   StringRef Data = Buffer.get()->getBuffer();
1693   ASSERT_EQ(Data, Contents);
1694 }
1695 
1696 TEST_F(FileSystemTest, CreateNew) {
1697   int FD;
1698   Optional<FileDescriptorCloser> Closer;
1699 
1700   // Succeeds if the file does not exist.
1701   ASSERT_FALSE(fs::exists(NonExistantFile));
1702   ASSERT_NO_ERROR(fs::openFileForWrite(NonExistantFile, FD, fs::CD_CreateNew));
1703   ASSERT_TRUE(fs::exists(NonExistantFile));
1704 
1705   FileRemover Cleanup(NonExistantFile);
1706   Closer.emplace(FD);
1707 
1708   // And creates a file of size 0.
1709   sys::fs::file_status Status;
1710   ASSERT_NO_ERROR(sys::fs::status(FD, Status));
1711   EXPECT_EQ(0ULL, Status.getSize());
1712 
1713   // Close this first, before trying to re-open the file.
1714   Closer.reset();
1715 
1716   // But fails if the file does exist.
1717   ASSERT_ERROR(fs::openFileForWrite(NonExistantFile, FD, fs::CD_CreateNew));
1718 }
1719 
1720 TEST_F(FileSystemTest, CreateAlways) {
1721   int FD;
1722   Optional<FileDescriptorCloser> Closer;
1723 
1724   // Succeeds if the file does not exist.
1725   ASSERT_FALSE(fs::exists(NonExistantFile));
1726   ASSERT_NO_ERROR(
1727       fs::openFileForWrite(NonExistantFile, FD, fs::CD_CreateAlways));
1728 
1729   Closer.emplace(FD);
1730 
1731   ASSERT_TRUE(fs::exists(NonExistantFile));
1732 
1733   FileRemover Cleanup(NonExistantFile);
1734 
1735   // And creates a file of size 0.
1736   uint64_t FileSize;
1737   ASSERT_NO_ERROR(sys::fs::file_size(NonExistantFile, FileSize));
1738   ASSERT_EQ(0ULL, FileSize);
1739 
1740   // If we write some data to it re-create it with CreateAlways, it succeeds and
1741   // truncates to 0 bytes.
1742   ASSERT_EQ(4, write(FD, "Test", 4));
1743 
1744   Closer.reset();
1745 
1746   ASSERT_NO_ERROR(sys::fs::file_size(NonExistantFile, FileSize));
1747   ASSERT_EQ(4ULL, FileSize);
1748 
1749   ASSERT_NO_ERROR(
1750       fs::openFileForWrite(NonExistantFile, FD, fs::CD_CreateAlways));
1751   Closer.emplace(FD);
1752   ASSERT_NO_ERROR(sys::fs::file_size(NonExistantFile, FileSize));
1753   ASSERT_EQ(0ULL, FileSize);
1754 }
1755 
1756 TEST_F(FileSystemTest, OpenExisting) {
1757   int FD;
1758 
1759   // Fails if the file does not exist.
1760   ASSERT_FALSE(fs::exists(NonExistantFile));
1761   ASSERT_ERROR(fs::openFileForWrite(NonExistantFile, FD, fs::CD_OpenExisting));
1762   ASSERT_FALSE(fs::exists(NonExistantFile));
1763 
1764   // Make a dummy file now so that we can try again when the file does exist.
1765   createFileWithData(NonExistantFile, false, fs::CD_CreateNew, "Fizz");
1766   FileRemover Cleanup(NonExistantFile);
1767   uint64_t FileSize;
1768   ASSERT_NO_ERROR(sys::fs::file_size(NonExistantFile, FileSize));
1769   ASSERT_EQ(4ULL, FileSize);
1770 
1771   // If we re-create it with different data, it overwrites rather than
1772   // appending.
1773   createFileWithData(NonExistantFile, true, fs::CD_OpenExisting, "Buzz");
1774   verifyFileContents(NonExistantFile, "Buzz");
1775 }
1776 
1777 TEST_F(FileSystemTest, OpenAlways) {
1778   // Succeeds if the file does not exist.
1779   createFileWithData(NonExistantFile, false, fs::CD_OpenAlways, "Fizz");
1780   FileRemover Cleanup(NonExistantFile);
1781   uint64_t FileSize;
1782   ASSERT_NO_ERROR(sys::fs::file_size(NonExistantFile, FileSize));
1783   ASSERT_EQ(4ULL, FileSize);
1784 
1785   // Now re-open it and write again, verifying the contents get over-written.
1786   createFileWithData(NonExistantFile, true, fs::CD_OpenAlways, "Bu");
1787   verifyFileContents(NonExistantFile, "Buzz");
1788 }
1789 
1790 TEST_F(FileSystemTest, AppendSetsCorrectFileOffset) {
1791   fs::CreationDisposition Disps[] = {fs::CD_CreateAlways, fs::CD_OpenAlways,
1792                                      fs::CD_OpenExisting};
1793 
1794   // Write some data and re-open it with every possible disposition (this is a
1795   // hack that shouldn't work, but is left for compatibility.  OF_Append
1796   // overrides
1797   // the specified disposition.
1798   for (fs::CreationDisposition Disp : Disps) {
1799     int FD;
1800     Optional<FileDescriptorCloser> Closer;
1801 
1802     createFileWithData(NonExistantFile, false, fs::CD_CreateNew, "Fizz");
1803 
1804     FileRemover Cleanup(NonExistantFile);
1805 
1806     uint64_t FileSize;
1807     ASSERT_NO_ERROR(sys::fs::file_size(NonExistantFile, FileSize));
1808     ASSERT_EQ(4ULL, FileSize);
1809     ASSERT_NO_ERROR(
1810         fs::openFileForWrite(NonExistantFile, FD, Disp, fs::OF_Append));
1811     Closer.emplace(FD);
1812     ASSERT_NO_ERROR(sys::fs::file_size(NonExistantFile, FileSize));
1813     ASSERT_EQ(4ULL, FileSize);
1814 
1815     ASSERT_EQ(4, write(FD, "Buzz", 4));
1816     Closer.reset();
1817 
1818     verifyFileContents(NonExistantFile, "FizzBuzz");
1819   }
1820 }
1821 
1822 static void verifyRead(int FD, StringRef Data, bool ShouldSucceed) {
1823   std::vector<char> Buffer;
1824   Buffer.resize(Data.size());
1825   int Result = ::read(FD, Buffer.data(), Buffer.size());
1826   if (ShouldSucceed) {
1827     ASSERT_EQ((size_t)Result, Data.size());
1828     ASSERT_EQ(Data, StringRef(Buffer.data(), Buffer.size()));
1829   } else {
1830     ASSERT_EQ(-1, Result);
1831     ASSERT_EQ(EBADF, errno);
1832   }
1833 }
1834 
1835 static void verifyWrite(int FD, StringRef Data, bool ShouldSucceed) {
1836   int Result = ::write(FD, Data.data(), Data.size());
1837   if (ShouldSucceed)
1838     ASSERT_EQ((size_t)Result, Data.size());
1839   else {
1840     ASSERT_EQ(-1, Result);
1841     ASSERT_EQ(EBADF, errno);
1842   }
1843 }
1844 
1845 TEST_F(FileSystemTest, ReadOnlyFileCantWrite) {
1846   createFileWithData(NonExistantFile, false, fs::CD_CreateNew, "Fizz");
1847   FileRemover Cleanup(NonExistantFile);
1848 
1849   int FD;
1850   ASSERT_NO_ERROR(fs::openFileForRead(NonExistantFile, FD));
1851   FileDescriptorCloser Closer(FD);
1852 
1853   verifyWrite(FD, "Buzz", false);
1854   verifyRead(FD, "Fizz", true);
1855 }
1856 
1857 TEST_F(FileSystemTest, WriteOnlyFileCantRead) {
1858   createFileWithData(NonExistantFile, false, fs::CD_CreateNew, "Fizz");
1859   FileRemover Cleanup(NonExistantFile);
1860 
1861   int FD;
1862   ASSERT_NO_ERROR(
1863       fs::openFileForWrite(NonExistantFile, FD, fs::CD_OpenExisting));
1864   FileDescriptorCloser Closer(FD);
1865   verifyRead(FD, "Fizz", false);
1866   verifyWrite(FD, "Buzz", true);
1867 }
1868 
1869 TEST_F(FileSystemTest, ReadWriteFileCanReadOrWrite) {
1870   createFileWithData(NonExistantFile, false, fs::CD_CreateNew, "Fizz");
1871   FileRemover Cleanup(NonExistantFile);
1872 
1873   int FD;
1874   ASSERT_NO_ERROR(fs::openFileForReadWrite(NonExistantFile, FD,
1875                                            fs::CD_OpenExisting, fs::OF_None));
1876   FileDescriptorCloser Closer(FD);
1877   verifyRead(FD, "Fizz", true);
1878   verifyWrite(FD, "Buzz", true);
1879 }
1880 
1881 TEST_F(FileSystemTest, readNativeFile) {
1882   createFileWithData(NonExistantFile, false, fs::CD_CreateNew, "01234");
1883   FileRemover Cleanup(NonExistantFile);
1884   const auto &Read = [&](size_t ToRead) -> Expected<std::string> {
1885     std::string Buf(ToRead, '?');
1886     Expected<fs::file_t> FD = fs::openNativeFileForRead(NonExistantFile);
1887     if (!FD)
1888       return FD.takeError();
1889     auto Close = make_scope_exit([&] { fs::closeFile(*FD); });
1890     if (Expected<size_t> BytesRead = fs::readNativeFile(
1891             *FD, makeMutableArrayRef(&*Buf.begin(), Buf.size())))
1892       return Buf.substr(0, *BytesRead);
1893     else
1894       return BytesRead.takeError();
1895   };
1896   EXPECT_THAT_EXPECTED(Read(5), HasValue("01234"));
1897   EXPECT_THAT_EXPECTED(Read(3), HasValue("012"));
1898   EXPECT_THAT_EXPECTED(Read(6), HasValue("01234"));
1899 }
1900 
1901 TEST_F(FileSystemTest, readNativeFileSlice) {
1902   createFileWithData(NonExistantFile, false, fs::CD_CreateNew, "01234");
1903   FileRemover Cleanup(NonExistantFile);
1904   Expected<fs::file_t> FD = fs::openNativeFileForRead(NonExistantFile);
1905   ASSERT_THAT_EXPECTED(FD, Succeeded());
1906   auto Close = make_scope_exit([&] { fs::closeFile(*FD); });
1907   const auto &Read = [&](size_t Offset,
1908                          size_t ToRead) -> Expected<std::string> {
1909     std::string Buf(ToRead, '?');
1910     if (Expected<size_t> BytesRead = fs::readNativeFileSlice(
1911             *FD, makeMutableArrayRef(&*Buf.begin(), Buf.size()), Offset))
1912       return Buf.substr(0, *BytesRead);
1913     else
1914       return BytesRead.takeError();
1915   };
1916   EXPECT_THAT_EXPECTED(Read(0, 5), HasValue("01234"));
1917   EXPECT_THAT_EXPECTED(Read(0, 3), HasValue("012"));
1918   EXPECT_THAT_EXPECTED(Read(2, 3), HasValue("234"));
1919   EXPECT_THAT_EXPECTED(Read(0, 6), HasValue("01234"));
1920   EXPECT_THAT_EXPECTED(Read(2, 6), HasValue("234"));
1921   EXPECT_THAT_EXPECTED(Read(5, 5), HasValue(""));
1922 }
1923 
1924 TEST_F(FileSystemTest, is_local) {
1925   bool TestDirectoryIsLocal;
1926   ASSERT_NO_ERROR(fs::is_local(TestDirectory, TestDirectoryIsLocal));
1927   EXPECT_EQ(TestDirectoryIsLocal, fs::is_local(TestDirectory));
1928 
1929   int FD;
1930   SmallString<128> TempPath;
1931   ASSERT_NO_ERROR(
1932       fs::createUniqueFile(Twine(TestDirectory) + "/temp", FD, TempPath));
1933   FileRemover Cleanup(TempPath);
1934 
1935   // Make sure it exists.
1936   ASSERT_TRUE(sys::fs::exists(Twine(TempPath)));
1937 
1938   bool TempFileIsLocal;
1939   ASSERT_NO_ERROR(fs::is_local(FD, TempFileIsLocal));
1940   EXPECT_EQ(TempFileIsLocal, fs::is_local(FD));
1941   ::close(FD);
1942 
1943   // Expect that the file and its parent directory are equally local or equally
1944   // remote.
1945   EXPECT_EQ(TestDirectoryIsLocal, TempFileIsLocal);
1946 }
1947 
1948 TEST_F(FileSystemTest, getUmask) {
1949 #ifdef _WIN32
1950   EXPECT_EQ(fs::getUmask(), 0U) << "Should always be 0 on Windows.";
1951 #else
1952   unsigned OldMask = ::umask(0022);
1953   unsigned CurrentMask = fs::getUmask();
1954   EXPECT_EQ(CurrentMask, 0022U)
1955       << "getUmask() didn't return previously set umask()";
1956   EXPECT_EQ(::umask(OldMask), mode_t(0022U))
1957       << "getUmask() may have changed umask()";
1958 #endif
1959 }
1960 
1961 TEST_F(FileSystemTest, RespectUmask) {
1962 #ifndef _WIN32
1963   unsigned OldMask = ::umask(0022);
1964 
1965   int FD;
1966   SmallString<128> TempPath;
1967   ASSERT_NO_ERROR(fs::createTemporaryFile("prefix", "temp", FD, TempPath));
1968 
1969   fs::perms AllRWE = static_cast<fs::perms>(0777);
1970 
1971   ASSERT_NO_ERROR(fs::setPermissions(TempPath, AllRWE));
1972 
1973   ErrorOr<fs::perms> Perms = fs::getPermissions(TempPath);
1974   ASSERT_TRUE(!!Perms);
1975   EXPECT_EQ(Perms.get(), AllRWE) << "Should have ignored umask by default";
1976 
1977   ASSERT_NO_ERROR(fs::setPermissions(TempPath, AllRWE));
1978 
1979   Perms = fs::getPermissions(TempPath);
1980   ASSERT_TRUE(!!Perms);
1981   EXPECT_EQ(Perms.get(), AllRWE) << "Should have ignored umask";
1982 
1983   ASSERT_NO_ERROR(
1984       fs::setPermissions(FD, static_cast<fs::perms>(AllRWE & ~fs::getUmask())));
1985   Perms = fs::getPermissions(TempPath);
1986   ASSERT_TRUE(!!Perms);
1987   EXPECT_EQ(Perms.get(), static_cast<fs::perms>(0755))
1988       << "Did not respect umask";
1989 
1990   (void)::umask(0057);
1991 
1992   ASSERT_NO_ERROR(
1993       fs::setPermissions(FD, static_cast<fs::perms>(AllRWE & ~fs::getUmask())));
1994   Perms = fs::getPermissions(TempPath);
1995   ASSERT_TRUE(!!Perms);
1996   EXPECT_EQ(Perms.get(), static_cast<fs::perms>(0720))
1997       << "Did not respect umask";
1998 
1999   (void)::umask(OldMask);
2000   (void)::close(FD);
2001 #endif
2002 }
2003 
2004 TEST_F(FileSystemTest, set_current_path) {
2005   SmallString<128> path;
2006 
2007   ASSERT_NO_ERROR(fs::current_path(path));
2008   ASSERT_NE(TestDirectory, path);
2009 
2010   struct RestorePath {
2011     SmallString<128> path;
2012     RestorePath(const SmallString<128> &path) : path(path) {}
2013     ~RestorePath() { fs::set_current_path(path); }
2014   } restore_path(path);
2015 
2016   ASSERT_NO_ERROR(fs::set_current_path(TestDirectory));
2017 
2018   ASSERT_NO_ERROR(fs::current_path(path));
2019 
2020   fs::UniqueID D1, D2;
2021   ASSERT_NO_ERROR(fs::getUniqueID(TestDirectory, D1));
2022   ASSERT_NO_ERROR(fs::getUniqueID(path, D2));
2023   ASSERT_EQ(D1, D2) << "D1: " << TestDirectory << "\nD2: " << path;
2024 }
2025 
2026 TEST_F(FileSystemTest, permissions) {
2027   int FD;
2028   SmallString<64> TempPath;
2029   ASSERT_NO_ERROR(fs::createTemporaryFile("prefix", "temp", FD, TempPath));
2030   FileRemover Cleanup(TempPath);
2031 
2032   // Make sure it exists.
2033   ASSERT_TRUE(fs::exists(Twine(TempPath)));
2034 
2035   auto CheckPermissions = [&](fs::perms Expected) {
2036     ErrorOr<fs::perms> Actual = fs::getPermissions(TempPath);
2037     return Actual && *Actual == Expected;
2038   };
2039 
2040   std::error_code NoError;
2041   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_all), NoError);
2042   EXPECT_TRUE(CheckPermissions(fs::all_all));
2043 
2044   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_read | fs::all_exe), NoError);
2045   EXPECT_TRUE(CheckPermissions(fs::all_read | fs::all_exe));
2046 
2047 #if defined(_WIN32)
2048   fs::perms ReadOnly = fs::all_read | fs::all_exe;
2049   EXPECT_EQ(fs::setPermissions(TempPath, fs::no_perms), NoError);
2050   EXPECT_TRUE(CheckPermissions(ReadOnly));
2051 
2052   EXPECT_EQ(fs::setPermissions(TempPath, fs::owner_read), NoError);
2053   EXPECT_TRUE(CheckPermissions(ReadOnly));
2054 
2055   EXPECT_EQ(fs::setPermissions(TempPath, fs::owner_write), NoError);
2056   EXPECT_TRUE(CheckPermissions(fs::all_all));
2057 
2058   EXPECT_EQ(fs::setPermissions(TempPath, fs::owner_exe), NoError);
2059   EXPECT_TRUE(CheckPermissions(ReadOnly));
2060 
2061   EXPECT_EQ(fs::setPermissions(TempPath, fs::owner_all), NoError);
2062   EXPECT_TRUE(CheckPermissions(fs::all_all));
2063 
2064   EXPECT_EQ(fs::setPermissions(TempPath, fs::group_read), NoError);
2065   EXPECT_TRUE(CheckPermissions(ReadOnly));
2066 
2067   EXPECT_EQ(fs::setPermissions(TempPath, fs::group_write), NoError);
2068   EXPECT_TRUE(CheckPermissions(fs::all_all));
2069 
2070   EXPECT_EQ(fs::setPermissions(TempPath, fs::group_exe), NoError);
2071   EXPECT_TRUE(CheckPermissions(ReadOnly));
2072 
2073   EXPECT_EQ(fs::setPermissions(TempPath, fs::group_all), NoError);
2074   EXPECT_TRUE(CheckPermissions(fs::all_all));
2075 
2076   EXPECT_EQ(fs::setPermissions(TempPath, fs::others_read), NoError);
2077   EXPECT_TRUE(CheckPermissions(ReadOnly));
2078 
2079   EXPECT_EQ(fs::setPermissions(TempPath, fs::others_write), NoError);
2080   EXPECT_TRUE(CheckPermissions(fs::all_all));
2081 
2082   EXPECT_EQ(fs::setPermissions(TempPath, fs::others_exe), NoError);
2083   EXPECT_TRUE(CheckPermissions(ReadOnly));
2084 
2085   EXPECT_EQ(fs::setPermissions(TempPath, fs::others_all), NoError);
2086   EXPECT_TRUE(CheckPermissions(fs::all_all));
2087 
2088   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_read), NoError);
2089   EXPECT_TRUE(CheckPermissions(ReadOnly));
2090 
2091   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_write), NoError);
2092   EXPECT_TRUE(CheckPermissions(fs::all_all));
2093 
2094   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_exe), NoError);
2095   EXPECT_TRUE(CheckPermissions(ReadOnly));
2096 
2097   EXPECT_EQ(fs::setPermissions(TempPath, fs::set_uid_on_exe), NoError);
2098   EXPECT_TRUE(CheckPermissions(ReadOnly));
2099 
2100   EXPECT_EQ(fs::setPermissions(TempPath, fs::set_gid_on_exe), NoError);
2101   EXPECT_TRUE(CheckPermissions(ReadOnly));
2102 
2103   EXPECT_EQ(fs::setPermissions(TempPath, fs::sticky_bit), NoError);
2104   EXPECT_TRUE(CheckPermissions(ReadOnly));
2105 
2106   EXPECT_EQ(fs::setPermissions(TempPath, fs::set_uid_on_exe |
2107                                              fs::set_gid_on_exe |
2108                                              fs::sticky_bit),
2109             NoError);
2110   EXPECT_TRUE(CheckPermissions(ReadOnly));
2111 
2112   EXPECT_EQ(fs::setPermissions(TempPath, ReadOnly | fs::set_uid_on_exe |
2113                                              fs::set_gid_on_exe |
2114                                              fs::sticky_bit),
2115             NoError);
2116   EXPECT_TRUE(CheckPermissions(ReadOnly));
2117 
2118   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_perms), NoError);
2119   EXPECT_TRUE(CheckPermissions(fs::all_all));
2120 #else
2121   EXPECT_EQ(fs::setPermissions(TempPath, fs::no_perms), NoError);
2122   EXPECT_TRUE(CheckPermissions(fs::no_perms));
2123 
2124   EXPECT_EQ(fs::setPermissions(TempPath, fs::owner_read), NoError);
2125   EXPECT_TRUE(CheckPermissions(fs::owner_read));
2126 
2127   EXPECT_EQ(fs::setPermissions(TempPath, fs::owner_write), NoError);
2128   EXPECT_TRUE(CheckPermissions(fs::owner_write));
2129 
2130   EXPECT_EQ(fs::setPermissions(TempPath, fs::owner_exe), NoError);
2131   EXPECT_TRUE(CheckPermissions(fs::owner_exe));
2132 
2133   EXPECT_EQ(fs::setPermissions(TempPath, fs::owner_all), NoError);
2134   EXPECT_TRUE(CheckPermissions(fs::owner_all));
2135 
2136   EXPECT_EQ(fs::setPermissions(TempPath, fs::group_read), NoError);
2137   EXPECT_TRUE(CheckPermissions(fs::group_read));
2138 
2139   EXPECT_EQ(fs::setPermissions(TempPath, fs::group_write), NoError);
2140   EXPECT_TRUE(CheckPermissions(fs::group_write));
2141 
2142   EXPECT_EQ(fs::setPermissions(TempPath, fs::group_exe), NoError);
2143   EXPECT_TRUE(CheckPermissions(fs::group_exe));
2144 
2145   EXPECT_EQ(fs::setPermissions(TempPath, fs::group_all), NoError);
2146   EXPECT_TRUE(CheckPermissions(fs::group_all));
2147 
2148   EXPECT_EQ(fs::setPermissions(TempPath, fs::others_read), NoError);
2149   EXPECT_TRUE(CheckPermissions(fs::others_read));
2150 
2151   EXPECT_EQ(fs::setPermissions(TempPath, fs::others_write), NoError);
2152   EXPECT_TRUE(CheckPermissions(fs::others_write));
2153 
2154   EXPECT_EQ(fs::setPermissions(TempPath, fs::others_exe), NoError);
2155   EXPECT_TRUE(CheckPermissions(fs::others_exe));
2156 
2157   EXPECT_EQ(fs::setPermissions(TempPath, fs::others_all), NoError);
2158   EXPECT_TRUE(CheckPermissions(fs::others_all));
2159 
2160   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_read), NoError);
2161   EXPECT_TRUE(CheckPermissions(fs::all_read));
2162 
2163   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_write), NoError);
2164   EXPECT_TRUE(CheckPermissions(fs::all_write));
2165 
2166   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_exe), NoError);
2167   EXPECT_TRUE(CheckPermissions(fs::all_exe));
2168 
2169   EXPECT_EQ(fs::setPermissions(TempPath, fs::set_uid_on_exe), NoError);
2170   EXPECT_TRUE(CheckPermissions(fs::set_uid_on_exe));
2171 
2172   EXPECT_EQ(fs::setPermissions(TempPath, fs::set_gid_on_exe), NoError);
2173   EXPECT_TRUE(CheckPermissions(fs::set_gid_on_exe));
2174 
2175   // Modern BSDs require root to set the sticky bit on files.
2176   // AIX and Solaris without root will mask off (i.e., lose) the sticky bit
2177   // on files.
2178 #if !defined(__FreeBSD__) && !defined(__NetBSD__) && !defined(__OpenBSD__) &&  \
2179     !defined(_AIX) && !(defined(__sun__) && defined(__svr4__))
2180   EXPECT_EQ(fs::setPermissions(TempPath, fs::sticky_bit), NoError);
2181   EXPECT_TRUE(CheckPermissions(fs::sticky_bit));
2182 
2183   EXPECT_EQ(fs::setPermissions(TempPath, fs::set_uid_on_exe |
2184                                              fs::set_gid_on_exe |
2185                                              fs::sticky_bit),
2186             NoError);
2187   EXPECT_TRUE(CheckPermissions(fs::set_uid_on_exe | fs::set_gid_on_exe |
2188                                fs::sticky_bit));
2189 
2190   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_read | fs::set_uid_on_exe |
2191                                              fs::set_gid_on_exe |
2192                                              fs::sticky_bit),
2193             NoError);
2194   EXPECT_TRUE(CheckPermissions(fs::all_read | fs::set_uid_on_exe |
2195                                fs::set_gid_on_exe | fs::sticky_bit));
2196 
2197   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_perms), NoError);
2198   EXPECT_TRUE(CheckPermissions(fs::all_perms));
2199 #endif // !FreeBSD && !NetBSD && !OpenBSD && !AIX
2200 
2201   EXPECT_EQ(fs::setPermissions(TempPath, fs::all_perms & ~fs::sticky_bit),
2202                                NoError);
2203   EXPECT_TRUE(CheckPermissions(fs::all_perms & ~fs::sticky_bit));
2204 #endif
2205 }
2206 
2207 #ifdef _WIN32
2208 TEST_F(FileSystemTest, widenPath) {
2209   const std::wstring LongPathPrefix(L"\\\\?\\");
2210 
2211   // Test that the length limit is checked against the UTF-16 length and not the
2212   // UTF-8 length.
2213   std::string Input("C:\\foldername\\");
2214   const std::string Pi("\xcf\x80"); // UTF-8 lower case pi.
2215   // Add Pi up to the MAX_PATH limit.
2216   const size_t NumChars = MAX_PATH - Input.size() - 1;
2217   for (size_t i = 0; i < NumChars; ++i)
2218     Input += Pi;
2219   // Check that UTF-8 length already exceeds MAX_PATH.
2220   EXPECT_TRUE(Input.size() > MAX_PATH);
2221   SmallVector<wchar_t, MAX_PATH + 16> Result;
2222   ASSERT_NO_ERROR(windows::widenPath(Input, Result));
2223   // Result should not start with the long path prefix.
2224   EXPECT_TRUE(std::wmemcmp(Result.data(), LongPathPrefix.c_str(),
2225                            LongPathPrefix.size()) != 0);
2226   EXPECT_EQ(Result.size(), (size_t)MAX_PATH - 1);
2227 
2228   // Add another Pi to exceed the MAX_PATH limit.
2229   Input += Pi;
2230   // Construct the expected result.
2231   SmallVector<wchar_t, MAX_PATH + 16> Expected;
2232   ASSERT_NO_ERROR(windows::UTF8ToUTF16(Input, Expected));
2233   Expected.insert(Expected.begin(), LongPathPrefix.begin(),
2234                   LongPathPrefix.end());
2235 
2236   ASSERT_NO_ERROR(windows::widenPath(Input, Result));
2237   EXPECT_EQ(Result, Expected);
2238 
2239   // Test that UNC paths are handled correctly.
2240   const std::string ShareName("\\\\sharename\\");
2241   const std::string FileName("\\filename");
2242   // Initialize directory name so that the input is within the MAX_PATH limit.
2243   const char DirChar = 'x';
2244   std::string DirName(MAX_PATH - ShareName.size() - FileName.size() - 1,
2245                       DirChar);
2246 
2247   Input = ShareName + DirName + FileName;
2248   ASSERT_NO_ERROR(windows::widenPath(Input, Result));
2249   // Result should not start with the long path prefix.
2250   EXPECT_TRUE(std::wmemcmp(Result.data(), LongPathPrefix.c_str(),
2251                            LongPathPrefix.size()) != 0);
2252   EXPECT_EQ(Result.size(), (size_t)MAX_PATH - 1);
2253 
2254   // Extend the directory name so the input exceeds the MAX_PATH limit.
2255   DirName += DirChar;
2256   Input = ShareName + DirName + FileName;
2257   // Construct the expected result.
2258   ASSERT_NO_ERROR(windows::UTF8ToUTF16(StringRef(Input).substr(2), Expected));
2259   const std::wstring UNCPrefix(LongPathPrefix + L"UNC\\");
2260   Expected.insert(Expected.begin(), UNCPrefix.begin(), UNCPrefix.end());
2261 
2262   ASSERT_NO_ERROR(windows::widenPath(Input, Result));
2263   EXPECT_EQ(Result, Expected);
2264 
2265   // Check that Unix separators are handled correctly.
2266   std::replace(Input.begin(), Input.end(), '\\', '/');
2267   ASSERT_NO_ERROR(windows::widenPath(Input, Result));
2268   EXPECT_EQ(Result, Expected);
2269 
2270   // Check the removal of "dots".
2271   Input = ShareName + DirName + "\\.\\foo\\.\\.." + FileName;
2272   ASSERT_NO_ERROR(windows::widenPath(Input, Result));
2273   EXPECT_EQ(Result, Expected);
2274 }
2275 #endif
2276 
2277 #ifdef _WIN32
2278 // Windows refuses lock request if file region is already locked by the same
2279 // process. POSIX system in this case updates the existing lock.
2280 TEST_F(FileSystemTest, FileLocker) {
2281   using namespace std::chrono;
2282   int FD;
2283   std::error_code EC;
2284   SmallString<64> TempPath;
2285   EC = fs::createTemporaryFile("test", "temp", FD, TempPath);
2286   ASSERT_NO_ERROR(EC);
2287   FileRemover Cleanup(TempPath);
2288   raw_fd_ostream Stream(TempPath, EC);
2289 
2290   EC = fs::tryLockFile(FD);
2291   ASSERT_NO_ERROR(EC);
2292   EC = fs::unlockFile(FD);
2293   ASSERT_NO_ERROR(EC);
2294 
2295   if (auto L = Stream.lock()) {
2296     ASSERT_ERROR(fs::tryLockFile(FD));
2297     ASSERT_NO_ERROR(L->unlock());
2298     ASSERT_NO_ERROR(fs::tryLockFile(FD));
2299     ASSERT_NO_ERROR(fs::unlockFile(FD));
2300   } else {
2301     ADD_FAILURE();
2302     handleAllErrors(L.takeError(), [&](ErrorInfoBase &EIB) {});
2303   }
2304 
2305   ASSERT_NO_ERROR(fs::tryLockFile(FD));
2306   ASSERT_NO_ERROR(fs::unlockFile(FD));
2307 
2308   {
2309     Expected<fs::FileLocker> L1 = Stream.lock();
2310     ASSERT_THAT_EXPECTED(L1, Succeeded());
2311     raw_fd_ostream Stream2(FD, false);
2312     Expected<fs::FileLocker> L2 = Stream2.tryLockFor(250ms);
2313     ASSERT_THAT_EXPECTED(L2, Failed());
2314     ASSERT_NO_ERROR(L1->unlock());
2315     Expected<fs::FileLocker> L3 = Stream.tryLockFor(0ms);
2316     ASSERT_THAT_EXPECTED(L3, Succeeded());
2317   }
2318 
2319   ASSERT_NO_ERROR(fs::tryLockFile(FD));
2320   ASSERT_NO_ERROR(fs::unlockFile(FD));
2321 }
2322 #endif
2323 
2324 TEST_F(FileSystemTest, CopyFile) {
2325   unittest::TempDir RootTestDirectory("CopyFileTest", /*Unique=*/true);
2326 
2327   SmallVector<std::string> Data;
2328   SmallVector<SmallString<128>> Sources;
2329   for (int I = 0, E = 3; I != E; ++I) {
2330     Data.push_back(Twine(I).str());
2331     Sources.emplace_back(RootTestDirectory.path());
2332     path::append(Sources.back(), "source" + Data.back() + ".txt");
2333     createFileWithData(Sources.back(), /*ShouldExistBefore=*/false,
2334                        fs::CD_CreateNew, Data.back());
2335   }
2336 
2337   // Copy the first file to a non-existing file.
2338   SmallString<128> Destination(RootTestDirectory.path());
2339   path::append(Destination, "destination");
2340   ASSERT_FALSE(fs::exists(Destination));
2341   fs::copy_file(Sources[0], Destination);
2342   verifyFileContents(Destination, Data[0]);
2343 
2344   // Copy the second file to an existing file.
2345   fs::copy_file(Sources[1], Destination);
2346   verifyFileContents(Destination, Data[1]);
2347 
2348   // Note: The remaining logic is targeted at a potential failure case related
2349   // to file cloning and symlinks on Darwin. On Windows, fs::create_link() does
2350   // not return success here so the test is skipped.
2351 #if !defined(_WIN32)
2352   // Set up a symlink to the third file.
2353   SmallString<128> Symlink(RootTestDirectory.path());
2354   path::append(Symlink, "symlink");
2355   ASSERT_NO_ERROR(fs::create_link(path::filename(Sources[2]), Symlink));
2356   verifyFileContents(Symlink, Data[2]);
2357 
2358   // fs::getUniqueID() should follow symlinks. Otherwise, this isn't good test
2359   // coverage.
2360   fs::UniqueID SymlinkID;
2361   fs::UniqueID Data2ID;
2362   ASSERT_NO_ERROR(fs::getUniqueID(Symlink, SymlinkID));
2363   ASSERT_NO_ERROR(fs::getUniqueID(Sources[2], Data2ID));
2364   ASSERT_EQ(SymlinkID, Data2ID);
2365 
2366   // Copy the third file through the symlink.
2367   fs::copy_file(Symlink, Destination);
2368   verifyFileContents(Destination, Data[2]);
2369 
2370   // Confirm the destination is not a link to the original file, and not a
2371   // symlink.
2372   bool IsDestinationSymlink;
2373   ASSERT_NO_ERROR(fs::is_symlink_file(Destination, IsDestinationSymlink));
2374   ASSERT_FALSE(IsDestinationSymlink);
2375   fs::UniqueID DestinationID;
2376   ASSERT_NO_ERROR(fs::getUniqueID(Destination, DestinationID));
2377   ASSERT_NE(SymlinkID, DestinationID);
2378 #endif
2379 }
2380 
2381 } // anonymous namespace
2382