[llvm] r273262 - Switch to using an API that handles non-ASCII paths appropriately on Windows.

Aaron Ballman via llvm-commits llvm-commits at lists.llvm.org
Tue Jun 21 07:24:48 PDT 2016


Author: aaronballman
Date: Tue Jun 21 09:24:48 2016
New Revision: 273262

URL: http://llvm.org/viewvc/llvm-project?rev=273262&view=rev
Log:
Switch to using an API that handles non-ASCII paths appropriately on Windows.

Modified:
    llvm/trunk/lib/Support/Windows/Path.inc
    llvm/trunk/unittests/Support/Path.cpp

Modified: llvm/trunk/lib/Support/Windows/Path.inc
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Support/Windows/Path.inc?rev=273262&r1=273261&r2=273262&view=diff
==============================================================================
--- llvm/trunk/lib/Support/Windows/Path.inc (original)
+++ llvm/trunk/lib/Support/Windows/Path.inc Tue Jun 21 09:24:48 2016
@@ -820,33 +820,34 @@ std::error_code getPathFromOpenFD(int FD
     return make_error_code(errc::bad_file_descriptor);
 
   DWORD CharCount;
+  SmallVector<wchar_t, 1024> TempPath;
   do {
-    // FIXME: We should be using the W version of this API and converting the
-    // resulting path to UTF-8 to handle non-ASCII file paths.
-    CharCount = ::GetFinalPathNameByHandleA(FileHandle, ResultPath.begin(),
-                                            ResultPath.capacity(),
+    CharCount = ::GetFinalPathNameByHandleW(FileHandle, TempPath.begin(),
+                                            TempPath.capacity(),
                                             FILE_NAME_NORMALIZED);
-    if (CharCount < ResultPath.capacity())
+    if (CharCount < TempPath.capacity())
       break;
 
     // Reserve sufficient space for the path as well as the null character. Even
     // though the API does not document that it is required, if we reserve just
     // CharCount space, the function call will not store the resulting path and
     // still report success.
-    ResultPath.reserve(CharCount + 1);
+    TempPath.reserve(CharCount + 1);
   } while (true);
 
   if (CharCount == 0)
     return mapWindowsError(::GetLastError());
 
-  ResultPath.set_size(CharCount);
+  TempPath.set_size(CharCount);
 
   // On earlier Windows releases, the character count includes the terminating
   // null.
-  if (ResultPath.back() == '\0')
-    ResultPath.pop_back();
+  if (TempPath.back() == L'\0') {
+    --CharCount;
+    TempPath.pop_back();
+  }
 
-  return std::error_code();
+  return windows::UTF16ToUTF8(TempPath.data(), CharCount, ResultPath);
 }
 } // end namespace fs
 

Modified: llvm/trunk/unittests/Support/Path.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/Support/Path.cpp?rev=273262&r1=273261&r2=273262&view=diff
==============================================================================
--- llvm/trunk/unittests/Support/Path.cpp (original)
+++ llvm/trunk/unittests/Support/Path.cpp Tue Jun 21 09:24:48 2016
@@ -1057,6 +1057,32 @@ TEST_F(FileSystemTest, PathFromFDWin32)
   ::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;




More information about the llvm-commits mailing list