diff options
Diffstat (limited to 'unittests/Support/Path.cpp')
-rw-r--r-- | unittests/Support/Path.cpp | 190 |
1 files changed, 177 insertions, 13 deletions
diff --git a/unittests/Support/Path.cpp b/unittests/Support/Path.cpp index 3f626f87888a3..1a6ffa50e983e 100644 --- a/unittests/Support/Path.cpp +++ b/unittests/Support/Path.cpp @@ -17,6 +17,7 @@ #include "gtest/gtest.h" #ifdef LLVM_ON_WIN32 +#include "llvm/ADT/ArrayRef.h" #include <windows.h> #include <winerror.h> #endif @@ -416,7 +417,7 @@ TEST(SupportDeathTest, TempDirectoryOnWindows) { SmallString<270> Expected{"C:\\Temp\\AB\\123456789"}; while (Expected.size() < 260) Expected.append("\\DirNameWith19Charss"); - ASSERT_EQ(260, Expected.size()); + ASSERT_EQ(260U, Expected.size()); EXPECT_TEMP_DIR(_putenv_s("TMP", Expected.c_str()), Expected.c_str()); } #endif @@ -715,6 +716,20 @@ TEST_F(FileSystemTest, DirectoryIteration) { ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/z0/za1")); ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive/z0")); ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/recursive")); + + // Test recursive_directory_iterator level() + ASSERT_NO_ERROR( + fs::create_directories(Twine(TestDirectory) + "/reclevel/a/b/c")); + fs::recursive_directory_iterator I(Twine(TestDirectory) + "/reclevel", ec), E; + for (int l = 0; I != E; I.increment(ec), ++l) { + ASSERT_NO_ERROR(ec); + EXPECT_EQ(I.level(), l); + } + EXPECT_EQ(I, E); + ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel/a/b/c")); + ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel/a/b")); + ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel/a")); + ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel")); } const char archive[] = "!<arch>\x0A"; @@ -725,22 +740,30 @@ const char coff_bigobj[] = "\x00\x00\xff\xff\x00\x02......" const char coff_import_library[] = "\x00\x00\xff\xff...."; const char elf_relocatable[] = { 0x7f, 'E', 'L', 'F', 1, 2, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1 }; -const char macho_universal_binary[] = "\xca\xfe\xba\xbe...\0x00"; -const char macho_object[] = "\xfe\xed\xfa\xce..........\x00\x01"; -const char macho_executable[] = "\xfe\xed\xfa\xce..........\x00\x02"; +const char macho_universal_binary[] = "\xca\xfe\xba\xbe...\x00"; +const char macho_object[] = + "\xfe\xed\xfa\xce........\x00\x00\x00\x01............"; +const char macho_executable[] = + "\xfe\xed\xfa\xce........\x00\x00\x00\x02............"; const char macho_fixed_virtual_memory_shared_lib[] = - "\xfe\xed\xfa\xce..........\x00\x03"; -const char macho_core[] = "\xfe\xed\xfa\xce..........\x00\x04"; -const char macho_preload_executable[] = "\xfe\xed\xfa\xce..........\x00\x05"; + "\xfe\xed\xfa\xce........\x00\x00\x00\x03............"; +const char macho_core[] = + "\xfe\xed\xfa\xce........\x00\x00\x00\x04............"; +const char macho_preload_executable[] = + "\xfe\xed\xfa\xce........\x00\x00\x00\x05............"; const char macho_dynamically_linked_shared_lib[] = - "\xfe\xed\xfa\xce..........\x00\x06"; -const char macho_dynamic_linker[] = "\xfe\xed\xfa\xce..........\x00\x07"; -const char macho_bundle[] = "\xfe\xed\xfa\xce..........\x00\x08"; -const char macho_dsym_companion[] = "\xfe\xed\xfa\xce..........\x00\x0a"; -const char macho_kext_bundle[] = "\xfe\xed\xfa\xce..........\x00\x0b"; + "\xfe\xed\xfa\xce........\x00\x00\x00\x06............"; +const char macho_dynamic_linker[] = + "\xfe\xed\xfa\xce........\x00\x00\x00\x07............"; +const char macho_bundle[] = + "\xfe\xed\xfa\xce........\x00\x00\x00\x08............"; +const char macho_dsym_companion[] = + "\xfe\xed\xfa\xce........\x00\x00\x00\x0a............"; +const char macho_kext_bundle[] = + "\xfe\xed\xfa\xce........\x00\x00\x00\x0b............"; const char windows_resource[] = "\x00\x00\x00\x00\x020\x00\x00\x00\xff"; const char macho_dynamically_linked_shared_lib_stub[] = - "\xfe\xed\xfa\xce..........\x00\x09"; + "\xfe\xed\xfa\xce........\x00\x00\x00\x09............"; TEST_F(FileSystemTest, Magic) { struct type { @@ -947,4 +970,145 @@ TEST(Support, RemoveDots) { EXPECT_EQ("c", Path1); #endif } + +TEST(Support, ReplacePathPrefix) { + SmallString<64> Path1("/foo"); + SmallString<64> Path2("/old/foo"); + SmallString<64> OldPrefix("/old"); + SmallString<64> NewPrefix("/new"); + SmallString<64> NewPrefix2("/longernew"); + SmallString<64> EmptyPrefix(""); + + SmallString<64> Path = Path1; + path::replace_path_prefix(Path, OldPrefix, NewPrefix); + EXPECT_EQ(Path, "/foo"); + Path = Path2; + path::replace_path_prefix(Path, OldPrefix, NewPrefix); + EXPECT_EQ(Path, "/new/foo"); + Path = Path2; + path::replace_path_prefix(Path, OldPrefix, NewPrefix2); + EXPECT_EQ(Path, "/longernew/foo"); + Path = Path1; + path::replace_path_prefix(Path, EmptyPrefix, NewPrefix); + EXPECT_EQ(Path, "/new/foo"); + Path = Path2; + path::replace_path_prefix(Path, OldPrefix, EmptyPrefix); + EXPECT_EQ(Path, "/foo"); +} + +TEST_F(FileSystemTest, PathFromFD) { + // Create a temp file. + int FileDescriptor; + SmallString<64> TempPath; + ASSERT_NO_ERROR( + fs::createTemporaryFile("prefix", "temp", FileDescriptor, TempPath)); + + // Make sure it exists. + ASSERT_TRUE(sys::fs::exists(Twine(TempPath))); + + // Try to get the path from the file descriptor + SmallString<64> ResultPath; + std::error_code ErrorCode = + fs::getPathFromOpenFD(FileDescriptor, ResultPath); + + // If we succeeded, check that the paths are the same (modulo case): + if (!ErrorCode) { + // The paths returned by createTemporaryFile and getPathFromOpenFD + // should reference the same file on disk. + fs::UniqueID D1, D2; + ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath), D1)); + ASSERT_NO_ERROR(fs::getUniqueID(Twine(ResultPath), D2)); + ASSERT_EQ(D1, D2); + } + + ::close(FileDescriptor); +} + +TEST_F(FileSystemTest, PathFromFDWin32) { + // Create a temp file. + int FileDescriptor; + SmallString<64> TempPath; + ASSERT_NO_ERROR( + fs::createTemporaryFile("prefix", "temp", FileDescriptor, TempPath)); + + // Make sure it exists. + ASSERT_TRUE(sys::fs::exists(Twine(TempPath))); + + SmallVector<char, 8> ResultPath; + std::error_code ErrorCode = + fs::getPathFromOpenFD(FileDescriptor, ResultPath); + + if (!ErrorCode) { + // Now that we know how much space is required for the path, create a path + // buffer with exactly enough space (sans null terminator, which should not + // be present), and call getPathFromOpenFD again to ensure that the API + // properly handles exactly-sized buffers. + SmallVector<char, 8> ExactSizedPath(ResultPath.size()); + ErrorCode = fs::getPathFromOpenFD(FileDescriptor, ExactSizedPath); + ResultPath = ExactSizedPath; + } + + if (!ErrorCode) { + fs::UniqueID D1, D2; + ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath), D1)); + ASSERT_NO_ERROR(fs::getUniqueID(Twine(ResultPath), D2)); + ASSERT_EQ(D1, D2); + } + ::close(FileDescriptor); +} + +TEST_F(FileSystemTest, PathFromFDUnicode) { + // Create a temp file. + int FileDescriptor; + SmallString<64> TempPath; + + // Test Unicode: "<temp directory>/(pi)r^2<temp rand chars>.aleth.0" + ASSERT_NO_ERROR( + fs::createTemporaryFile("\xCF\x80r\xC2\xB2", + "\xE2\x84\xB5.0", FileDescriptor, TempPath)); + + // Make sure it exists. + ASSERT_TRUE(sys::fs::exists(Twine(TempPath))); + + SmallVector<char, 8> ResultPath; + std::error_code ErrorCode = + fs::getPathFromOpenFD(FileDescriptor, ResultPath); + + if (!ErrorCode) { + fs::UniqueID D1, D2; + ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath), D1)); + ASSERT_NO_ERROR(fs::getUniqueID(Twine(ResultPath), D2)); + ASSERT_EQ(D1, D2); + } + ::close(FileDescriptor); +} + +TEST_F(FileSystemTest, OpenFileForRead) { + // Create a temp file. + int FileDescriptor; + SmallString<64> TempPath; + ASSERT_NO_ERROR( + fs::createTemporaryFile("prefix", "temp", FileDescriptor, TempPath)); + + // Make sure it exists. + ASSERT_TRUE(sys::fs::exists(Twine(TempPath))); + + // Open the file for read + int FileDescriptor2; + SmallString<64> ResultPath; + ASSERT_NO_ERROR( + fs::openFileForRead(Twine(TempPath), FileDescriptor2, &ResultPath)) + + // If we succeeded, check that the paths are the same (modulo case): + if (!ResultPath.empty()) { + // The paths returned by createTemporaryFile and getPathFromOpenFD + // should reference the same file on disk. + fs::UniqueID D1, D2; + ASSERT_NO_ERROR(fs::getUniqueID(Twine(TempPath), D1)); + ASSERT_NO_ERROR(fs::getUniqueID(Twine(ResultPath), D2)); + ASSERT_EQ(D1, D2); + } + + ::close(FileDescriptor); +} } // anonymous namespace |