diff --git a/src/irmin-pack/unix/gc_worker.ml b/src/irmin-pack/unix/gc_worker.ml index 6d1c6c4cd5..6ba178b70f 100644 --- a/src/irmin-pack/unix/gc_worker.ml +++ b/src/irmin-pack/unix/gc_worker.ml @@ -353,7 +353,8 @@ module Make (Args : Gc_args.S) = struct let out = Irmin.Type.to_json_string gc_output_t output in let* () = Io.write_string io ~off:Int63.zero out in let* () = Io.fsync io in - Io.close io + let* () = Io.close io in + Io.fsync_dir root (* No one catches errors when this function terminates. Write the result in a file and terminate. *) diff --git a/src/irmin-pack/unix/io.ml b/src/irmin-pack/unix/io.ml index 29cfa7af17..13fdbe0bba 100644 --- a/src/irmin-pack/unix/io.ml +++ b/src/irmin-pack/unix/io.ml @@ -284,4 +284,17 @@ module Unix = struct Sys.remove path; Ok () with Sys_error msg -> Error (`Sys_error msg) + + let fsync_dir path = + try + let dirfd = Unix.openfile path Unix.[ O_RDONLY ] default_open_perm in + let fsync_result = + try + Unix.fsync dirfd; + Ok () + with Unix.Unix_error (e, s1, s2) -> Error (`Io_misc (e, s1, s2)) + in + Unix.close dirfd; + fsync_result + with Unix.Unix_error (e, s1, s2) -> Error (`Io_misc (e, s1, s2)) end diff --git a/src/irmin-pack/unix/io_intf.ml b/src/irmin-pack/unix/io_intf.ml index f33aa1d635..45a376f1ce 100644 --- a/src/irmin-pack/unix/io_intf.ml +++ b/src/irmin-pack/unix/io_intf.ml @@ -140,6 +140,11 @@ module type S = sig val catch_misc_error : (unit -> 'a) -> ('a, [> `Io_misc of misc_error ]) result + + val fsync_dir : string -> (unit, [> `Io_misc of misc_error ]) result + (** [fsync path] persists to the file system the directory in [path]. Note + that separate fsyncs are needed for persisting the files in the directory + [path]. *) end module type Sigs = sig