@@ -726,28 +726,26 @@ func setFD_CLOEXEC(_ flag: Bool, onFileDescriptor fd: CInt) throws {
726
726
/// platforms, it is always equal to `"/"`.
727
727
let rootDirectoryPath : String = {
728
728
#if os(Windows)
729
- if let systemDrive = Environment . variable ( named: " SYSTEMDRIVE " ) ? . utf16 {
730
- // Copy the system drive string with room for up to "C:\" and a NUL.
731
- var buffer = UnsafeMutableBufferPointer< wchar_t> . allocate( capacity: systemDrive. count + 4 )
732
- defer {
733
- buffer. deallocate ( )
729
+ var result : String ?
730
+
731
+ // The boot volume is, except in some legacy scenarios, the volume that
732
+ // contains the system Windows directory. For an explanation of the difference
733
+ // between the Windows directory and the _system_ Windows directory, see
734
+ // https://devblogs.microsoft.com/oldnewthing/20140723-00/?p=423 .
735
+ let count = GetSystemWindowsDirectoryW ( nil , 0 )
736
+ if count > 0 {
737
+ withUnsafeTemporaryAllocation ( of: wchar_t. self, capacity: Int ( count) + 1 ) { buffer in
738
+ _ = GetSystemWindowsDirectoryW ( buffer. baseAddress!, UINT ( buffer. count) )
739
+ let rStrip = PathCchStripToRoot ( buffer. baseAddress!, buffer. count)
740
+ if rStrip == S_OK || rStrip == S_FALSE {
741
+ result = String . decodeCString ( buffer. baseAddress!, as: UTF16 . self) ? . result
742
+ }
734
743
}
735
- buffer. initialize ( fromContentsOf: systemDrive)
736
- buffer [ systemDrive. count] = 0
737
744
738
- // On the assumption that the value of %SYSTEMDRIVE% is "C:" or similar,
739
- // ensure a trailing slash is added to refer to the root directory. If
740
- // somebody decides to set this environment variable to something
741
- // nonsensical or to a deeper path, we should accept it silently.
742
- let rAddBackslash = PathCchAddBackslashEx ( buffer. baseAddress!, buffer. count, nil , nil )
743
- if rAddBackslash == S_OK || rAddBackslash == S_FALSE,
744
- let result = String . decodeCString ( buffer. baseAddress!, as: UTF16 . self) ? . result {
745
- return result
746
- }
745
+ // If we weren't able to get a path, fall back to "C:\" on the assumption
746
+ // that it's the common case and most likely correct.
747
+ return result ?? #"C:\"#
747
748
}
748
- // We weren't able to get a path, so fall back to "C:\" on the assumption that
749
- // it's the common case and most likely correct.
750
- return #"C:\"#
751
749
#else
752
750
return " / "
753
751
#endif
0 commit comments