@@ -25,12 +25,60 @@ let copy_lock_dir ~target ~lock_dir ~deps ~files =
2525 |> action_builder_with_dir_targets ~directory_targets: [ target ]
2626;;
2727
28- let setup_copy_rules ~dir :target ~lock_dir =
29- let + deps, files = Source_deps. files (Path. source lock_dir) in
28+ let files dir =
29+ let rec recurse dir =
30+ match Path.Untracked. readdir_unsorted_with_kinds dir with
31+ | Ok entries ->
32+ entries
33+ |> List. fold_left
34+ ~init: (Path.Set. empty, Path.Set. empty)
35+ ~f: (fun (files , empty_directories ) (entry , kind ) ->
36+ let path = Path. relative dir entry in
37+ match (kind : Unix.file_kind ) with
38+ | S_REG ->
39+ let files = Path.Set. add files path in
40+ files, empty_directories
41+ | S_DIR ->
42+ let files', empty_directories' = recurse path in
43+ (match Path.Set. is_empty files', Path.Set. is_empty empty_directories' with
44+ | true , true ->
45+ let empty_directories = Path.Set. add empty_directories path in
46+ files, empty_directories
47+ | _ , _ ->
48+ let files = Path.Set. union files files' in
49+ let empty_directories =
50+ Path.Set. union empty_directories empty_directories'
51+ in
52+ files, empty_directories)
53+ | otherwise ->
54+ Code_error. raise
55+ " unsupported kind of file in folder"
56+ [ " path" , Path. to_dyn path; " kind" , File_kind. to_dyn otherwise ])
57+ | Error (ENOENT, _ , _ ) -> Path.Set. empty, Path.Set. empty
58+ | Error unix_error ->
59+ User_error. raise
60+ [ Pp. textf
61+ " Failed to read lock dir files of %s:"
62+ (Path. to_string_maybe_quoted dir)
63+ ; Pp. text (Unix_error.Detailed. to_string_hum unix_error)
64+ ]
65+ in
66+ let files, empty_directories = recurse dir in
67+ Dep.Set. of_source_files ~files ~empty_directories , files
68+ ;;
69+
70+ let setup_copy_rules ~dir :target ~assume_src_exists ~lock_dir =
71+ let + () = Memo. return () in
72+ let deps, files = files (Path. source lock_dir) in
3073 let directory_targets, rules =
3174 match Path.Set. is_empty files with
3275 | true -> Path.Build.Map. empty, Rules. empty
3376 | false ->
77+ let deps =
78+ match assume_src_exists with
79+ | false -> deps
80+ | true -> Dep.Set. empty
81+ in
3482 let directory_targets = Path.Build.Map. singleton target Loc. none in
3583 let { Action_builder.With_targets. build; targets } =
3684 copy_lock_dir ~target ~lock_dir ~deps ~files
@@ -44,15 +92,17 @@ let setup_copy_rules ~dir:target ~lock_dir =
4492let setup_lock_rules (workspace : Workspace.t ) ~dir ~lock_dir =
4593 let dir = Path.Build. append_local dir lock_dir in
4694 let lock_dir = Path.Source. append_local workspace.dir lock_dir in
47- setup_copy_rules ~dir ~lock_dir
95+ setup_copy_rules ~dir ~assume_src_exists: false ~ lock_dir
4896;;
4997
5098let setup_dev_tool_lock_rules ~dir dev_tool =
5199 let package_name = Dune_pkg.Dev_tool. package_name dev_tool in
52100 let dev_tool_name = Dune_lang.Package_name. to_string package_name in
53101 let dir = Path.Build. relative dir dev_tool_name in
54102 let lock_dir = Lock_dir. dev_tool_source_lock_dir dev_tool in
55- setup_copy_rules ~dir ~lock_dir
103+ (* dev tool lock files are created in _build outside of the build system
104+ so we have to tell the build system not to try to create them *)
105+ setup_copy_rules ~dir ~assume_src_exists: true ~lock_dir
56106;;
57107
58108let lock_dirs_of_workspace (workspace : Workspace.t ) =
0 commit comments