Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Try removing the RO bit when unlinking files on Windows #849

Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 23 additions & 1 deletion src/unix/lwt_io.ml
Original file line number Diff line number Diff line change
Expand Up @@ -1470,6 +1470,28 @@ let create_temp_dir
in
attempt 0

let win32_unlink fn =
Lwt.catch
(fun () -> Lwt_unix.unlink fn)
(function
| Unix.Unix_error (Unix.EACCES, _, _) ->
Lwt_unix.lstat fn >>= fun {st_perm; _} ->
(* Try removing the read-only attribute *)
Lwt_unix.chmod fn 0o666 >>= fun () ->
Lwt.catch
(fun () -> Lwt_unix.unlink fn)
(function exn ->
(* Restore original permissions *)
Lwt_unix.chmod fn st_perm >>= fun () ->
Lwt.fail exn)
| exn -> Lwt.fail exn)

let unlink =
if Sys.win32 then
win32_unlink
else
Lwt_unix.unlink

(* This is likely VERY slow for directories with many files. That is probably
best addressed by switching to blocking calls run inside a worker thread,
i.e. with Lwt_preemptive. *)
Expand All @@ -1485,7 +1507,7 @@ let rec delete_recursively directory =
if stat.Lwt_unix.st_kind = Lwt_unix.S_DIR then
delete_recursively path
else
Lwt_unix.unlink path
unlink path
end >>= fun () ->
Lwt_unix.rmdir directory

Expand Down