Skip to content

Commit efce07d

Browse files
author
David Lomas
committed
Reset READONLY if rename fails
Signed-off-by: David Lomas <[email protected]>
1 parent 4a1821d commit efce07d

File tree

1 file changed

+17
-6
lines changed

1 file changed

+17
-6
lines changed

compat/mingw.c

Lines changed: 17 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2700,7 +2700,7 @@ int mingw_accept(int sockfd1, struct sockaddr *sa, socklen_t *sz)
27002700
#undef rename
27012701
int mingw_rename(const char *pold, const char *pnew)
27022702
{
2703-
DWORD attrs = INVALID_FILE_ATTRIBUTES, gle;
2703+
DWORD attrs = INVALID_FILE_ATTRIBUTES, gle, attrsold;
27042704
int tries = 0;
27052705
wchar_t wpold[MAX_LONG_PATH], wpnew[MAX_LONG_PATH];
27062706
if (xutftowcs_long_path(wpold, pold) < 0 ||
@@ -2713,11 +2713,22 @@ int mingw_rename(const char *pold, const char *pnew)
27132713
return 0;
27142714
gle = GetLastError();
27152715

2716-
if (gle == ERROR_ACCESS_DENIED && is_inside_windows_container()) {
2717-
/* Fall back to copy to destination & remove source */
2718-
if (CopyFileW(wpold, wpnew, FALSE) && !mingw_unlink(pold))
2719-
return 0;
2720-
gle = GetLastError();
2716+
if (gle == ERROR_ACCESS_DENIED) {
2717+
if (is_inside_windows_container()) {
2718+
/* Fall back to copy to destination & remove source */
2719+
if (CopyFileW(wpold, wpnew, FALSE) && !mingw_unlink(pold))
2720+
return 0;
2721+
gle = GetLastError();
2722+
} else if ((attrsold = GetFileAttributesW(wpold)) & FILE_ATTRIBUTE_READONLY) {
2723+
/* if file is read-only, change and retry */
2724+
SetFileAttributesW(wpold, attrsold & ~FILE_ATTRIBUTE_READONLY);
2725+
if (MoveFileExW(wpold, wpnew,
2726+
MOVEFILE_REPLACE_EXISTING | MOVEFILE_COPY_ALLOWED)) {
2727+
SetFileAttributesW(wpnew, attrsold);
2728+
return 0;
2729+
}
2730+
gle = GetLastError();
2731+
}
27212732
}
27222733

27232734
/* revert file attributes on failure */

0 commit comments

Comments
 (0)