diff options
author | Hein-Pieter van Braam <hp@tmm.cx> | 2018-02-24 17:34:10 +0100 |
---|---|---|
committer | RĂ©mi Verschelde <rverschelde@gmail.com> | 2018-02-24 18:09:20 +0100 |
commit | 8cde69f5f2fa78ebd7651186eb8bd3abae9dfdd5 (patch) | |
tree | 0abe8847d38e35a339011f46d126914e9df36f7c /drivers | |
parent | bc4b7bc82e9a68975849de92ab6bdcd3f5ef4e62 (diff) |
Fix Windows file case changing
Windows APIs don't really provide a way to change a filename case. This
implements a little juggling to make this work. We first create a
guaranteed unique temporary file, we then replace the original file with
the temporary file and we finally rename it to the desired filename
case.
(cherry picked from commit d69d58deeaa523c6c38958b3956423ae8f814909)
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/windows/dir_access_windows.cpp | 27 |
1 files changed, 22 insertions, 5 deletions
diff --git a/drivers/windows/dir_access_windows.cpp b/drivers/windows/dir_access_windows.cpp index 2e64b55430..cf4d82fb07 100644 --- a/drivers/windows/dir_access_windows.cpp +++ b/drivers/windows/dir_access_windows.cpp @@ -261,13 +261,30 @@ Error DirAccessWindows::rename(String p_path, String p_new_path) { p_new_path = fix_path(p_new_path); - if (file_exists(p_new_path)) { - if (remove(p_new_path) != OK) { + // If we're only changing file name case we need to do a little juggling + if (p_path.to_lower() == p_new_path.to_lower()) { + WCHAR tmpfile[MAX_PATH]; + + if (!GetTempFileNameW(fix_path(get_current_dir()).c_str(), NULL, 0, tmpfile)) { return FAILED; - }; - }; + } + + if (!::ReplaceFileW(tmpfile, p_path.c_str(), NULL, 0, NULL, NULL)) { + DeleteFileW(tmpfile); + return FAILED; + } - return ::_wrename(p_path.c_str(), p_new_path.c_str()) == 0 ? OK : FAILED; + return ::_wrename(tmpfile, p_new_path.c_str()) == 0 ? OK : FAILED; + + } else { + if (file_exists(p_new_path)) { + if (remove(p_new_path) != OK) { + return FAILED; + } + } + + return ::_wrename(p_path.c_str(), p_new_path.c_str()) == 0 ? OK : FAILED; + } } Error DirAccessWindows::remove(String p_path) { |