diff options
author | Bram Moolenaar <Bram@vim.org> | 2011-05-05 16:41:24 +0200 |
---|---|---|
committer | Bram Moolenaar <Bram@vim.org> | 2011-05-05 16:41:24 +0200 |
commit | 1c32dff7d6b4cf00d1e63ac79968e9deb8b90e2e (patch) | |
tree | 2d78aad10e6cfc81acfcac846501a99d719933d5 /src/os_win32.c | |
parent | 85de20665f3ed48345b79cd0920af41397544141 (diff) | |
download | vim-git-1c32dff7d6b4cf00d1e63ac79968e9deb8b90e2e.tar.gz |
updated for version 7.3.172v7.3.172
Problem: MS-Windows: rename() might delete the file if the name differs but
it's actually the same file.
Solution: Use the file handle to check if it's the same file. (Yukihiro
Nakadaira)
Diffstat (limited to 'src/os_win32.c')
-rw-r--r-- | src/os_win32.c | 40 |
1 files changed, 30 insertions, 10 deletions
diff --git a/src/os_win32.c b/src/os_win32.c index 90664e626..bf51d2473 100644 --- a/src/os_win32.c +++ b/src/os_win32.c @@ -2645,25 +2645,44 @@ mch_isdir(char_u *name) int mch_is_linked(char_u *fname) { + BY_HANDLE_FILE_INFORMATION info; + + return win32_fileinfo(fname, &info) == FILEINFO_OK + && info.nNumberOfLinks > 1; +} + +/* + * Get the by-handle-file-information for "fname". + * Returns FILEINFO_OK when OK. + * returns FILEINFO_ENC_FAIL when enc_to_utf16() failed. + * Returns FILEINFO_READ_FAIL when CreateFile() failed. + * Returns FILEINFO_INFO_FAIL when GetFileInformationByHandle() failed. + */ + int +win32_fileinfo(char_u *fname, BY_HANDLE_FILE_INFORMATION *info) +{ HANDLE hFile; - int res = 0; - BY_HANDLE_FILE_INFORMATION inf; + int res = FILEINFO_READ_FAIL; #ifdef FEAT_MBYTE WCHAR *wn = NULL; if (enc_codepage >= 0 && (int)GetACP() != enc_codepage) + { wn = enc_to_utf16(fname, NULL); + if (wn == NULL) + res = FILEINFO_ENC_FAIL; + } if (wn != NULL) { hFile = CreateFileW(wn, /* file name */ GENERIC_READ, /* access mode */ - 0, /* share mode */ + FILE_SHARE_READ | FILE_SHARE_WRITE, /* share mode */ NULL, /* security descriptor */ OPEN_EXISTING, /* creation disposition */ - 0, /* file attributes */ + FILE_FLAG_BACKUP_SEMANTICS, /* file attributes */ NULL); /* handle to template file */ if (hFile == INVALID_HANDLE_VALUE - && GetLastError() == ERROR_CALL_NOT_IMPLEMENTED) + && GetLastError() == ERROR_CALL_NOT_IMPLEMENTED) { /* Retry with non-wide function (for Windows 98). */ vim_free(wn); @@ -2674,17 +2693,18 @@ mch_is_linked(char_u *fname) #endif hFile = CreateFile(fname, /* file name */ GENERIC_READ, /* access mode */ - 0, /* share mode */ + FILE_SHARE_READ | FILE_SHARE_WRITE, /* share mode */ NULL, /* security descriptor */ OPEN_EXISTING, /* creation disposition */ - 0, /* file attributes */ + FILE_FLAG_BACKUP_SEMANTICS, /* file attributes */ NULL); /* handle to template file */ if (hFile != INVALID_HANDLE_VALUE) { - if (GetFileInformationByHandle(hFile, &inf) != 0 - && inf.nNumberOfLinks > 1) - res = 1; + if (GetFileInformationByHandle(hFile, info) != 0) + res = FILEINFO_OK; + else + res = FILEINFO_INFO_FAIL; CloseHandle(hFile); } |