diff --git a/.depend b/.depend index 8a2dd0deff0..2d8fb662dc2 100644 --- a/.depend +++ b/.depend @@ -744,6 +744,7 @@ typing/datarepr.cmx : \ parsing/asttypes.cmi \ typing/datarepr.cmi typing/datarepr.cmi : \ + parsing/unit_info.cmi \ typing/types.cmi \ typing/path.cmi \ typing/ident.cmi \ @@ -1449,6 +1450,7 @@ typing/printtyped.cmx : \ typing/printtyped.cmi : \ typing/typedtree.cmi typing/shape.cmo : \ + parsing/unit_info.cmi \ typing/path.cmi \ utils/misc.cmi \ utils/identifiable.cmi \ @@ -1456,6 +1458,7 @@ typing/shape.cmo : \ utils/compilation_unit.cmi \ typing/shape.cmi typing/shape.cmx : \ + parsing/unit_info.cmx \ typing/path.cmx \ utils/misc.cmx \ utils/identifiable.cmx \ @@ -1463,6 +1466,7 @@ typing/shape.cmx : \ utils/compilation_unit.cmx \ typing/shape.cmi typing/shape.cmi : \ + parsing/unit_info.cmi \ typing/path.cmi \ utils/identifiable.cmi \ typing/ident.cmi \ diff --git a/Changes b/Changes index 7e0c9c2fbfd..a9352fea1c3 100644 --- a/Changes +++ b/Changes @@ -661,6 +661,15 @@ OCaml 5.2.0 usages index (Ulysse Gérard, review by Gabriel Scherer and Nathanaëlle Courant) +- #13286: Distinguish unique identifiers `Shape.Uid.t` according to their + provenance: either an implementation or an interface. + (Ulysse Gérard, review by Florian Angeletti and Leo White) + +- #13308: keep track of relations between declaration in the cmt files. This is + useful information for external tools for navigation and analysis purposis. + (Ulysse Gérard, Florian Angeletti, review by Florian Angeletti and Gabriel + Scherer) + ### Build system: - #12198, #12321, #12586, #12616, #12706, #13048: continue the merge of the diff --git a/boot/ocamlc b/boot/ocamlc new file mode 100755 index 00000000000..3fb10ea2e00 Binary files /dev/null and b/boot/ocamlc differ diff --git a/bytecomp/bytepackager.ml b/bytecomp/bytepackager.ml index 398242755ac..d1c803d1e9e 100644 --- a/bytecomp/bytepackager.ml +++ b/bytecomp/bytepackager.ml @@ -355,7 +355,7 @@ let package_files ~ppf_dump initial_env files targetfile = CU.create (CU.Prefix.from_clflags ()) (Unit_info.Artifact.modname target |> CU.Name.of_string) in - CU.set_current (Some comp_unit); + CU.set_current (Some (comp_unit, Impl)); Misc.try_finally (fun () -> let coercion = Typemod.package_units initial_env files (Unit_info.companion_cmi target) diff --git a/driver/compile.ml b/driver/compile.ml index 8aabea0df7a..3ceb0781326 100644 --- a/driver/compile.ml +++ b/driver/compile.ml @@ -22,7 +22,7 @@ let with_info = Compile_common.with_info ~native:false ~tool_name let interface ~source_file ~output_prefix = - with_info ~source_file ~output_prefix ~dump_ext:"cmi" + with_info ~source_file ~kind:Intf ~output_prefix ~dump_ext:"cmi" ~compilation_unit:Inferred_from_output_prefix @@ fun info -> Compile_common.interface @@ -101,7 +101,8 @@ let starting_point_of_compiler_pass start_from = let implementation_aux ~start_from ~source_file ~output_prefix ~keep_symbol_tables:_ ~(compilation_unit : Compile_common.compilation_unit_or_inferred) = - with_info ~source_file ~output_prefix ~dump_ext:"cmo" ~compilation_unit + with_info ~source_file ~kind:Impl ~output_prefix + ~dump_ext:"cmo" ~compilation_unit @@ fun info -> match start_from with | Parsing -> diff --git a/driver/compile_common.ml b/driver/compile_common.ml index ed200f90e85..6543e039976 100644 --- a/driver/compile_common.ml +++ b/driver/compile_common.ml @@ -28,11 +28,11 @@ type compilation_unit_or_inferred = | Exactly of Compilation_unit.t | Inferred_from_output_prefix -let with_info ~native ~tool_name ~source_file ~output_prefix +let with_info ~native ~tool_name ~source_file ~kind ~output_prefix ~compilation_unit ~dump_ext k = Compmisc.init_path (); Compmisc.init_parameters (); - let target = Unit_info.make ~source_file output_prefix in + let target = Unit_info.make ~source_file output_prefix in let compilation_unit = match compilation_unit with | Exactly compilation_unit -> compilation_unit @@ -42,8 +42,8 @@ let with_info ~native ~tool_name ~source_file ~output_prefix Compilation_unit.create for_pack_prefix (module_name |> Compilation_unit.Name.of_string) in - Compilation_unit.set_current (Some compilation_unit); - Env.set_unit_name (Some compilation_unit); + Compilation_unit.set_current (Some (compilation_unit, kind)); + Env.set_unit_name (Some (compilation_unit, kind)); let env = Compmisc.initial_env() in let dump_file = String.concat "." [output_prefix; dump_ext] in Compmisc.with_ppf_dump ~file_prefix:dump_file (fun ppf_dump -> @@ -85,7 +85,7 @@ let typecheck_intf info ast = Format.(fprintf std_formatter) "%a@." (Printtyp.printed_signature (Unit_info.source_file info.target)) sg); - ignore (Includemod.signatures info.env ~mark:Mark_both + ignore (Includemod.signatures info.env ~mark:true ~modes:(Legacy None) sg sg); Typecore.force_delayed_checks (); Builtin_attributes.warn_unused (); diff --git a/driver/compile_common.mli b/driver/compile_common.mli index 3a3f756f8f8..b4cdb4ff984 100644 --- a/driver/compile_common.mli +++ b/driver/compile_common.mli @@ -34,6 +34,7 @@ val with_info : native:bool -> tool_name:string -> source_file:string -> + kind:Compilation_unit.intf_or_impl -> output_prefix:string -> compilation_unit:compilation_unit_or_inferred -> dump_ext:string -> diff --git a/driver/optcompile.ml b/driver/optcompile.ml index 569a53ff941..7901373339b 100644 --- a/driver/optcompile.ml +++ b/driver/optcompile.ml @@ -23,7 +23,7 @@ let tool_name = "ocamlopt" let with_info = Compile_common.with_info ~native:true ~tool_name let interface ~source_file ~output_prefix = - with_info ~source_file ~output_prefix ~dump_ext:"cmi" + with_info ~source_file ~kind:Intf ~output_prefix ~dump_ext:"cmi" ~compilation_unit:Inferred_from_output_prefix @@ fun info -> Compile_common.interface @@ -115,7 +115,8 @@ let implementation_aux unix ~(flambda2 : flambda2) ~start_from let pipeline : Asmgen.pipeline = Direct_to_cmm (flambda2 ~keep_symbol_tables) in - with_info ~source_file ~output_prefix ~dump_ext:"cmx" ~compilation_unit + with_info ~source_file ~kind:Impl ~output_prefix + ~dump_ext:"cmx" ~compilation_unit @@ fun info -> if !Flambda_backend_flags.internal_assembler then Emitaux.binary_backend_available := true; diff --git a/file_formats/cms_format.ml b/file_formats/cms_format.ml index 6b75dc4f401..82b33ccfcf3 100644 --- a/file_formats/cms_format.ml +++ b/file_formats/cms_format.ml @@ -17,6 +17,8 @@ (** cms and cmsi files format. *) +module Uid = Shape.Uid + let read_magic_number ic = let len_magic_number = String.length Config.cms_magic_number in really_input_string ic len_magic_number @@ -32,7 +34,9 @@ type cms_infos = { cms_uid_to_attributes : Parsetree.attributes Shape.Uid.Tbl.t; cms_impl_shape : Shape.t option; (* None for mli *) cms_ident_occurrences : - (Longident.t Location.loc * Shape_reduce.result) array + (Longident.t Location.loc * Shape_reduce.result) array; + cms_declaration_dependencies : + (Cmt_format.dependency_kind * Uid.t * Uid.t) list; } type error = @@ -114,6 +118,9 @@ let save_cms target modname binary_annots initial_env shape = let cms_uid_to_loc, cms_uid_to_attributes = uid_tables_of_binary_annots binary_annots in + let cms_declaration_dependencies = + Cmt_format.get_declaration_dependencies () + in let cms = { cms_modname = modname; @@ -125,7 +132,8 @@ let save_cms target modname binary_annots initial_env shape = cms_uid_to_loc; cms_uid_to_attributes; cms_impl_shape = shape; - cms_ident_occurrences + cms_ident_occurrences; + cms_declaration_dependencies; } in output_cms oc cms) diff --git a/file_formats/cms_format.mli b/file_formats/cms_format.mli index af1dcba9884..4c172ddee5f 100644 --- a/file_formats/cms_format.mli +++ b/file_formats/cms_format.mli @@ -17,6 +17,8 @@ (** cms and cmsi files format. *) +module Uid = Shape.Uid + type cms_infos = { cms_modname : Compilation_unit.t; cms_comments : (string * Location.t) list; @@ -28,7 +30,9 @@ type cms_infos = { cms_uid_to_attributes : Parsetree.attributes Shape.Uid.Tbl.t; cms_impl_shape : Shape.t option; (* None for mli *) cms_ident_occurrences : - (Longident.t Location.loc * Shape_reduce.result) array + (Longident.t Location.loc * Shape_reduce.result) array; + cms_declaration_dependencies : + (Cmt_format.dependency_kind * Uid.t * Uid.t) list; } type error = diff --git a/file_formats/cmt_format.ml b/file_formats/cmt_format.ml index 89b7638721e..9d8c5f3a9ca 100644 --- a/file_formats/cmt_format.ml +++ b/file_formats/cmt_format.ml @@ -45,11 +45,11 @@ and binary_part = | Partial_signature_item of signature_item | Partial_module_type of module_type +type dependency_kind = Definition_to_declaration | Declaration_to_declaration type cmt_infos = { cmt_modname : Compilation_unit.t; cmt_annots : binary_annots; - cmt_value_dependencies : - (Types.value_description * Types.value_description) list; + cmt_declaration_dependencies : (dependency_kind * Uid.t * Uid.t) list; cmt_comments : (string * Location.t) list; cmt_args : string array; cmt_sourcefile : string option; @@ -452,19 +452,19 @@ let read_cmi filename = | Some cmi, _ -> cmi let saved_types = ref [] -let value_deps = ref [] +let uids_deps : (dependency_kind * Uid.t * Uid.t) list ref = ref [] let clear () = saved_types := []; - value_deps := [] + uids_deps := [] let add_saved_type b = saved_types := b :: !saved_types let get_saved_types () = !saved_types let set_saved_types l = saved_types := l -let record_value_dependency vd1 vd2 = - if vd1.Types.val_loc <> vd2.Types.val_loc then - value_deps := (vd1, vd2) :: !value_deps +let record_declaration_dependency (rk, uid1, uid2) = + if not (Uid.equal uid1 uid2) then + uids_deps := (rk, uid1, uid2) :: !uids_deps let save_cmt target cu binary_annots initial_env cmi shape = if !Clflags.binary_annotations && not !Clflags.print_types then begin @@ -499,7 +499,7 @@ let save_cmt target cu binary_annots initial_env cmi shape = let cmt = { cmt_modname = cu; cmt_annots; - cmt_value_dependencies = !value_deps; + cmt_declaration_dependencies = !uids_deps; cmt_comments = Lexer.comments (); cmt_args = Sys.argv; cmt_sourcefile = sourcefile; @@ -518,3 +518,5 @@ let save_cmt target cu binary_annots initial_env cmi shape = output_cmt oc cmt) end; clear () + +let get_declaration_dependencies () = !uids_deps diff --git a/file_formats/cmt_format.mli b/file_formats/cmt_format.mli index a58d24c6ef2..06e4fbde1fe 100644 --- a/file_formats/cmt_format.mli +++ b/file_formats/cmt_format.mli @@ -48,11 +48,11 @@ and binary_part = | Partial_signature_item of signature_item | Partial_module_type of module_type +type dependency_kind = Definition_to_declaration | Declaration_to_declaration type cmt_infos = { cmt_modname : Compilation_unit.t; cmt_annots : binary_annots; - cmt_value_dependencies : - (Types.value_description * Types.value_description) list; + cmt_declaration_dependencies : (dependency_kind * Uid.t * Uid.t) list; cmt_comments : (string * Location.t) list; cmt_args : string array; cmt_sourcefile : string option; @@ -108,8 +108,7 @@ val add_saved_type : binary_part -> unit val get_saved_types : unit -> binary_part list val set_saved_types : binary_part list -> unit -val record_value_dependency: - Types.value_description -> Types.value_description -> unit +val record_declaration_dependency: dependency_kind * Uid.t * Uid.t -> unit val index_occurrences : binary_annots -> (Longident.t Location.loc * Shape_reduce.result) array @@ -134,3 +133,6 @@ val need_to_clear_env : bool val read_signature : 'a -> string -> Types.signature * 'b list * 'c list *) + +val get_declaration_dependencies : + unit -> (dependency_kind * Uid.t * Uid.t) list diff --git a/lambda/translprim.ml b/lambda/translprim.ml index 158e2ac4a74..a61b51c8434 100644 --- a/lambda/translprim.ml +++ b/lambda/translprim.ml @@ -1610,7 +1610,7 @@ let lambda_of_loc kind sloc = let module_name = match name with | None -> "//"^filename^"//" - | Some comp_unit -> + | Some (comp_unit, _) -> Compilation_unit.name_as_string comp_unit in Lconst (Const_immstring module_name) diff --git a/middle_end/compilenv.ml b/middle_end/compilenv.ml index 6200880d2c1..986a7a51d39 100644 --- a/middle_end/compilenv.ml +++ b/middle_end/compilenv.ml @@ -68,7 +68,7 @@ let current_unit = let reset compilation_unit = Infos_table.clear global_infos_table; Zero_alloc_info.reset cached_zero_alloc_info; - CU.set_current (Some compilation_unit); + CU.set_current (Some (compilation_unit, Impl)); current_unit.ui_unit <- compilation_unit; current_unit.ui_defines <- [compilation_unit]; current_unit.ui_arg_descr <- None; diff --git a/middle_end/flambda2/cmx/flambda_cmx.ml b/middle_end/flambda2/cmx/flambda_cmx.ml index 43ec1943e59..2292fb72863 100644 --- a/middle_end/flambda2/cmx/flambda_cmx.ml +++ b/middle_end/flambda2/cmx/flambda_cmx.ml @@ -83,7 +83,7 @@ let all_predefined_exception_symbols () = let predefined_exception_typing_env () = let comp_unit = Compilation_unit.get_current () in - Compilation_unit.set_current (Some Compilation_unit.predef_exn); + Compilation_unit.set_current (Some (Compilation_unit.predef_exn, Impl)); let typing_env = TE.Serializable.predefined_exceptions (all_predefined_exception_symbols ()) in diff --git a/middle_end/flambda2/cmx/flambda_cmx_format.ml b/middle_end/flambda2/cmx/flambda_cmx_format.ml index ac28a8d62b3..4069379fef9 100644 --- a/middle_end/flambda2/cmx/flambda_cmx_format.ml +++ b/middle_end/flambda2/cmx/flambda_cmx_format.ml @@ -213,7 +213,7 @@ let merge t1_opt t2_opt = let print0 ~sections ~print_typing_env ~print_code ~print_offsets ppf t = Format.fprintf ppf "@[Original unit:@ %a@]@;" Compilation_unit.print t.original_compilation_unit; - Compilation_unit.set_current (Some t.original_compilation_unit); + Compilation_unit.set_current (Some (t.original_compilation_unit, Impl)); let typing_env, code = import_typing_env_and_code0 ~sections t in if print_typing_env then diff --git a/middle_end/flambda2/parser/parse_flambda.ml b/middle_end/flambda2/parser/parse_flambda.ml index 6fdd0ddbc02..1cff65e6415 100644 --- a/middle_end/flambda2/parser/parse_flambda.ml +++ b/middle_end/flambda2/parser/parse_flambda.ml @@ -154,7 +154,7 @@ let parse filename = |> Result.map (fun fexpr -> let comp_unit = make_compilation_unit ~extension:".fl" ~filename () in let old_comp_unit = Compilation_unit.get_current () in - Compilation_unit.set_current (Some comp_unit); + Compilation_unit.set_current (Some (comp_unit, Impl)); let flambda = Fexpr_to_flambda.conv comp_unit fexpr in Compilation_unit.set_current old_comp_unit; flambda) diff --git a/middle_end/flambda2/tests/api_tests/extension_meet.ml b/middle_end/flambda2/tests/api_tests/extension_meet.ml index c2d3d1b07a3..5eab05c3c7a 100644 --- a/middle_end/flambda2/tests/api_tests/extension_meet.ml +++ b/middle_end/flambda2/tests/api_tests/extension_meet.ml @@ -188,5 +188,5 @@ let _ = let linkage_name = Compilation_unit.Name.of_string "camlTest" in Compilation_unit.create Compilation_unit.Prefix.empty linkage_name in - Compilation_unit.set_current (Some comp_unit); + Compilation_unit.set_current (Some (comp_unit, Impl)); test_double_recursion () diff --git a/middle_end/flambda2/tests/meet_test.ml b/middle_end/flambda2/tests/meet_test.ml index 0af29852d5a..bf0f831ee4e 100644 --- a/middle_end/flambda2/tests/meet_test.ml +++ b/middle_end/flambda2/tests/meet_test.ml @@ -260,7 +260,7 @@ let test_meet_bottom_after_alias () = let () = let comp_unit = "Meet_test" |> Compilation_unit.of_string in - Compilation_unit.set_current (Some comp_unit); + Compilation_unit.set_current (Some (comp_unit, Impl)); Format.eprintf "MEET CHAINS WITH TWO VARS@\n@."; test_meet_chains_two_vars (); Format.eprintf "@.MEET CHAINS WITH THREE VARS@\n@."; diff --git a/middle_end/flambda2/tests/tools/fldiff.ml b/middle_end/flambda2/tests/tools/fldiff.ml index 9dca939ef92..7e2d886a0be 100644 --- a/middle_end/flambda2/tests/tools/fldiff.ml +++ b/middle_end/flambda2/tests/tools/fldiff.ml @@ -9,7 +9,7 @@ let _ = let modname1 = Parse_flambda.make_compilation_unit ~filename:file1 ~extension:".fl" () in - Compilation_unit.set_current (Some modname1); + Compilation_unit.set_current (Some (modname1, Impl)); Format.printf "%a@." (Compare.Comparison.print Flambda_unit.print) (Compare.flambda_units unit1 unit2) diff --git a/middle_end/flambda2/tests/tools/flexpect.ml b/middle_end/flambda2/tests/tools/flexpect.ml index 63cfc7f4cbc..6791c74a209 100644 --- a/middle_end/flambda2/tests/tools/flexpect.ml +++ b/middle_end/flambda2/tests/tools/flexpect.ml @@ -35,7 +35,7 @@ end let run_expect_test ~get_module_info ~extension ~filename ({ before; after = expected } : Fexpr.expect_test_spec) : Test_outcome.t = let comp_unit = Parse_flambda.make_compilation_unit ~extension ~filename () in - Compilation_unit.set_current (Some comp_unit); + Compilation_unit.set_current (Some (comp_unit, Impl)); let before_fl = Fexpr_to_flambda.conv comp_unit before in check_invariants before_fl; let cmx_loader = Flambda_cmx.create_loader ~get_module_info in diff --git a/middle_end/flambda2/tests/tools/parseflambda.ml b/middle_end/flambda2/tests/tools/parseflambda.ml index 5223e016c70..e6d777c134f 100644 --- a/middle_end/flambda2/tests/tools/parseflambda.ml +++ b/middle_end/flambda2/tests/tools/parseflambda.ml @@ -15,7 +15,7 @@ let parse_flambda filename = let comp_unit = Parse_flambda.make_compilation_unit ~extension:".fl" ~filename () in - Compilation_unit.set_current comp_unit; + Compilation_unit.set_current (Some (comp_unit, Impl)); Format.printf "%a@.@." Print_fexpr.flambda_unit unit; let fl2 = Fexpr_to_flambda.conv comp_unit unit in Format.printf "flambda:@.%a@.@." Flambda_unit.print fl2; diff --git a/middle_end/flambda2/tests/tools/roundtrip.ml b/middle_end/flambda2/tests/tools/roundtrip.ml index 8774d6fa813..f53048561fe 100644 --- a/middle_end/flambda2/tests/tools/roundtrip.ml +++ b/middle_end/flambda2/tests/tools/roundtrip.ml @@ -30,7 +30,7 @@ let () = in (* Need to get this right or the conversion will complain about binding non-local symbols *) - Compilation_unit.set_current (Some modname); + Compilation_unit.set_current (Some (modname, Impl)); let unit = match Parse_flambda.parse file with | Ok unit -> unit diff --git a/ocamldoc/odoc_analyse.ml b/ocamldoc/odoc_analyse.ml index f79d78ddffc..0f9cbf47def 100644 --- a/ocamldoc/odoc_analyse.ml +++ b/ocamldoc/odoc_analyse.ml @@ -30,7 +30,7 @@ let init_path () = Compmisc.init_path () let initial_env () = let current = match Env.get_unit_name () with - | Some cu -> cu |> Compilation_unit.full_path_as_string + | Some (cu, _) -> cu |> Compilation_unit.full_path_as_string | None -> "" in let initial = !Odoc_global.initially_opened_module in @@ -81,7 +81,7 @@ let process_implementation_file sourcefile = Compilation_unit.create (Compilation_unit.Prefix.from_clflags ()) (Unit_info.modname source |> Compilation_unit.Name.of_string) in - Env.set_unit_name (Some compilation_unit); + Env.set_unit_name (Some (compilation_unit, Impl)); let inputfile = preprocess sourcefile in let env = initial_env () in try @@ -119,7 +119,7 @@ let process_interface_file sourcefile = Compilation_unit.create (Compilation_unit.Prefix.from_clflags ()) (modulename |> Compilation_unit.Name.of_string) in - Env.set_unit_name (Some compilation_unit); + Env.set_unit_name (Some (compilation_unit, Intf)); let inputfile = preprocess sourcefile in let ast = Pparse.file ~tool_name inputfile diff --git a/testsuite/tests/shape-index/index.reference b/testsuite/tests/shape-index/index.reference index ab08854ebe2..e62b460632b 100644 --- a/testsuite/tests/shape-index/index.reference +++ b/testsuite/tests/shape-index/index.reference @@ -34,30 +34,30 @@ Resolved: Index.3 : t (File "index.ml", line 25, characters 11-12) Resolved: Index.0 : t (File "index.ml", line 20, characters 10-11) Uid of decls: -Index.10: y (File "index.ml", line 40, characters 4-5) -Index.21: MS (File "index.ml", line 51, characters 12-14) -Index.5: A (File "index.ml", line 23, characters 7-8) -Index.15: G (File "index.ml", line 48, characters 7-8) Index.0: t (File "index.ml", line 19, characters 7-8) -Index.28: MSB (File "index.ml", line 65, characters 12-15) -Index.3: t (File "index.ml", line 24, characters 7-8) -Index.17: MT (File "index.ml", line 52, characters 14-16) -Index.11: a (File "index.ml", line 44, characters 4-5) -Index.25: u (File "index.ml", line 66, characters 7-8) -Index.24: MSA (File "index.ml", line 57, characters 12-15) Index.1: x (File "index.ml", line 20, characters 6-7) -Index.16: u (File "index.ml", line 49, characters 5-6) +Index.2: AS (File "index.ml", line 18, characters 12-14) +Index.3: t (File "index.ml", line 24, characters 7-8) +Index.4: x (File "index.ml", line 25, characters 7-8) +Index.5: A (File "index.ml", line 23, characters 7-8) +Index.6: B (File "index.ml", line 28, characters 7-8) +Index.7: c (File "index.ml", line 35, characters 6-7) Index.8: c (File "index.ml", line 32, characters 6-7) Index.9: C (File "index.ml", line 30, characters 7-8) -Index.23: u (File "index.ml", line 60, characters 11-12) -Index.14: F (File "index.ml", line 47, characters 7-8) +Index.10: y (File "index.ml", line 40, characters 4-5) +Index.11: a (File "index.ml", line 44, characters 4-5) Index.12: _ (File "index.ml", line 45, characters 7-8) -Index.27: G (File "index.ml", line 68, characters 9-10) +Index.14: F (File "index.ml", line 47, characters 7-8) +Index.15: G (File "index.ml", line 48, characters 7-8) +Index.16: u (File "index.ml", line 49, characters 5-6) +Index.17: MT (File "index.ml", line 52, characters 14-16) +Index.18: M (File "index.ml", line 53, characters 9-10) +Index.19: X (File "index.ml", line 54, characters 9-10) Index.20: u (File "index.ml", line 55, characters 7-8) +Index.21: MS (File "index.ml", line 51, characters 12-14) +Index.23: u (File "index.ml", line 60, characters 11-12) +Index.24: MSA (File "index.ml", line 57, characters 12-15) +Index.25: u (File "index.ml", line 66, characters 7-8) Index.26: t (File "index.ml", line 67, characters 23-24) -Index.19: X (File "index.ml", line 54, characters 9-10) -Index.6: B (File "index.ml", line 28, characters 7-8) -Index.4: x (File "index.ml", line 25, characters 7-8) -Index.18: M (File "index.ml", line 53, characters 9-10) -Index.7: c (File "index.ml", line 35, characters 6-7) -Index.2: AS (File "index.ml", line 18, characters 12-14) +Index.27: G (File "index.ml", line 68, characters 9-10) +Index.28: MSB (File "index.ml", line 65, characters 12-15) diff --git a/testsuite/tests/shape-index/index_aliases.reference b/testsuite/tests/shape-index/index_aliases.reference index e433d55b2a8..ca456ec6fb1 100644 --- a/testsuite/tests/shape-index/index_aliases.reference +++ b/testsuite/tests/shape-index/index_aliases.reference @@ -38,29 +38,29 @@ Resolved: Index_aliases.1 : A (File "index_aliases.ml", line 19, characters 11-12) Uid of decls: -Index_aliases.12: M (File "index_aliases.ml", line 32, characters 9-10) +Index_aliases.0: t (File "index_aliases.ml", line 18, characters 23-24) Index_aliases.1: A (File "index_aliases.ml", line 18, characters 7-8) Index_aliases.2: B (File "index_aliases.ml", line 19, characters 7-8) -Index_aliases.18: s (File "index_aliases.ml", line 36, characters 26-27) -Index_aliases.17: x (File "index_aliases.ml", line 35, characters 4-5) +Index_aliases.3: t (File "index_aliases.ml", line 21, characters 23-24) Index_aliases.5: F (File "index_aliases.ml", line 21, characters 7-8) -Index_aliases.26: FArg (File "index_aliases.ml", line 48, characters 7-11) +Index_aliases.6: F' (File "index_aliases.ml", line 22, characters 7-9) Index_aliases.7: C (File "index_aliases.ml", line 23, characters 7-8) -Index_aliases.24: Z (File "index_aliases.ml", line 42, characters 7-8) -Index_aliases.20: t (File "index_aliases.ml", line 37, characters 41-42) +Index_aliases.8: C' (File "index_aliases.ml", line 25, characters 7-9) Index_aliases.9: D (File "index_aliases.ml", line 26, characters 7-8) +Index_aliases.10: G (File "index_aliases.ml", line 28, characters 7-8) +Index_aliases.11: s (File "index_aliases.ml", line 32, characters 21-22) +Index_aliases.12: M (File "index_aliases.ml", line 32, characters 9-10) +Index_aliases.14: t (File "index_aliases.ml", line 33, characters 48-49) Index_aliases.15: F (File "index_aliases.ml", line 33, characters 9-10) +Index_aliases.16: S (File "index_aliases.ml", line 31, characters 12-13) +Index_aliases.17: x (File "index_aliases.ml", line 35, characters 4-5) +Index_aliases.18: s (File "index_aliases.ml", line 36, characters 26-27) Index_aliases.19: M (File "index_aliases.ml", line 36, characters 11-12) -Index_aliases.8: C' (File "index_aliases.ml", line 25, characters 7-9) -Index_aliases.23: Y (File "index_aliases.ml", line 41, characters 7-8) -Index_aliases.14: t (File "index_aliases.ml", line 33, characters 48-49) -Index_aliases.10: G (File "index_aliases.ml", line 28, characters 7-8) -Index_aliases.27: u (File "index_aliases.ml", line 52, characters 5-6) +Index_aliases.20: t (File "index_aliases.ml", line 37, characters 41-42) +Index_aliases.21: F (File "index_aliases.ml", line 37, characters 11-12) Index_aliases.22: X (File "index_aliases.ml", line 40, characters 7-8) -Index_aliases.16: S (File "index_aliases.ml", line 31, characters 12-13) +Index_aliases.23: Y (File "index_aliases.ml", line 41, characters 7-8) +Index_aliases.24: Z (File "index_aliases.ml", line 42, characters 7-8) Index_aliases.25: Arg (File "index_aliases.ml", line 47, characters 7-10) -Index_aliases.21: F (File "index_aliases.ml", line 37, characters 11-12) -Index_aliases.6: F' (File "index_aliases.ml", line 22, characters 7-9) -Index_aliases.3: t (File "index_aliases.ml", line 21, characters 23-24) -Index_aliases.11: s (File "index_aliases.ml", line 32, characters 21-22) -Index_aliases.0: t (File "index_aliases.ml", line 18, characters 23-24) +Index_aliases.26: FArg (File "index_aliases.ml", line 48, characters 7-11) +Index_aliases.27: u (File "index_aliases.ml", line 52, characters 5-6) diff --git a/testsuite/tests/shape-index/index_bindingops.reference b/testsuite/tests/shape-index/index_bindingops.reference index 38c4f70b4d1..8892fd4ecf8 100644 --- a/testsuite/tests/shape-index/index_bindingops.reference +++ b/testsuite/tests/shape-index/index_bindingops.reference @@ -39,9 +39,9 @@ Unresolved: CU Stdlib . "Option"[module] . "map"[value] : Option.map (File "index_bindingops.ml", line 17, characters 17-27) Uid of decls: -Index_bindingops.8: - minus_three (File "index_bindingops.ml", line 23, characters 4-15) Index_bindingops.0: let+ (File "index_bindingops.ml", line 17, characters 4-10) Index_bindingops.3: and+ (File "index_bindingops.ml", line 19, characters 4-10) +Index_bindingops.8: + minus_three (File "index_bindingops.ml", line 23, characters 4-15) diff --git a/testsuite/tests/shape-index/index_constrs.reference b/testsuite/tests/shape-index/index_constrs.reference index 3fe533e8b6b..c8cec480385 100644 --- a/testsuite/tests/shape-index/index_constrs.reference +++ b/testsuite/tests/shape-index/index_constrs.reference @@ -17,10 +17,10 @@ Resolved: Index_constrs.0 : E (File "index_constrs.ml", line 20, characters 16-17) Uid of decls: -Index_constrs.6: f (File "index_constrs.ml", line 27, characters 4-5) -Index_constrs.5: x_ (File "index_constrs.ml", line 25, characters 4-6) Index_constrs.0: E (File "index_constrs.ml", line 18, characters 10-11) -Index_constrs.2: M (File "index_constrs.ml", line 19, characters 7-8) Index_constrs.1: F (File "index_constrs.ml", line 20, characters 12-13) +Index_constrs.2: M (File "index_constrs.ml", line 19, characters 7-8) Index_constrs.3: t (File "index_constrs.ml", line 23, characters 5-6) Index_constrs.4: E (File "index_constrs.ml", line 23, characters 9-10) +Index_constrs.5: x_ (File "index_constrs.ml", line 25, characters 4-6) +Index_constrs.6: f (File "index_constrs.ml", line 27, characters 4-5) diff --git a/testsuite/tests/shape-index/index_constrs_records.reference b/testsuite/tests/shape-index/index_constrs_records.reference index e876416599e..e4a6f808fb4 100644 --- a/testsuite/tests/shape-index/index_constrs_records.reference +++ b/testsuite/tests/shape-index/index_constrs_records.reference @@ -57,37 +57,37 @@ Resolved: Index_constrs_records.4 : A (File "index_constrs_records.ml", line 22, characters 10-11) Uid of decls: -Index_constrs_records.4: - A (File "index_constrs_records.ml", line 21, characters 11-12) -Index_constrs_records.12: - l_c (File "index_constrs_records.ml", line 19, characters 18-21) +Index_constrs_records.0: + l (File "index_constrs_records.ml", line 17, characters 5-6) +Index_constrs_records.1: + lbl (File "index_constrs_records.ml", line 17, characters 11-14) Index_constrs_records.2: t (File "index_constrs_records.ml", line 21, characters 7-8) -Index_constrs_records.34: - l_exn (File "index_constrs_records.ml", line 39, characters 18-23) -Index_constrs_records.29: - Ext (File "index_constrs_records.ml", line 33, characters 10-13) Index_constrs_records.3: l_c (File "index_constrs_records.ml", line 21, characters 18-21) -Index_constrs_records.21: - M (File "index_constrs_records.ml", line 18, characters 7-8) -Index_constrs_records.35: - Exn (File "index_constrs_records.ml", line 39, characters 10-13) -Index_constrs_records.13: - A (File "index_constrs_records.ml", line 19, characters 11-12) -Index_constrs_records.37: - e (File "index_constrs_records.ml", line 41, characters 4-5) -Index_constrs_records.31: - f (File "index_constrs_records.ml", line 35, characters 4-5) +Index_constrs_records.4: + A (File "index_constrs_records.ml", line 21, characters 11-12) Index_constrs_records.11: t (File "index_constrs_records.ml", line 19, characters 7-8) +Index_constrs_records.12: + l_c (File "index_constrs_records.ml", line 19, characters 18-21) +Index_constrs_records.13: + A (File "index_constrs_records.ml", line 19, characters 11-12) +Index_constrs_records.21: + M (File "index_constrs_records.ml", line 18, characters 7-8) +Index_constrs_records.23: + f (File "index_constrs_records.ml", line 30, characters 4-5) Index_constrs_records.27: u (File "index_constrs_records.ml", line 32, characters 5-6) Index_constrs_records.28: l_ext (File "index_constrs_records.ml", line 33, characters 19-24) -Index_constrs_records.0: - l (File "index_constrs_records.ml", line 17, characters 5-6) -Index_constrs_records.23: - f (File "index_constrs_records.ml", line 30, characters 4-5) -Index_constrs_records.1: - lbl (File "index_constrs_records.ml", line 17, characters 11-14) +Index_constrs_records.29: + Ext (File "index_constrs_records.ml", line 33, characters 10-13) +Index_constrs_records.31: + f (File "index_constrs_records.ml", line 35, characters 4-5) +Index_constrs_records.34: + l_exn (File "index_constrs_records.ml", line 39, characters 18-23) +Index_constrs_records.35: + Exn (File "index_constrs_records.ml", line 39, characters 10-13) +Index_constrs_records.37: + e (File "index_constrs_records.ml", line 41, characters 4-5) diff --git a/testsuite/tests/shape-index/index_functor.reference b/testsuite/tests/shape-index/index_functor.reference index 89867f0bafe..04746c8d555 100644 --- a/testsuite/tests/shape-index/index_functor.reference +++ b/testsuite/tests/shape-index/index_functor.reference @@ -11,7 +11,7 @@ Resolved: Index_functor.0 : X (File "index_functor.ml", line 18, characters 43-44) Uid of decls: +Index_functor.1: M (File "index_functor.ml", line 18, characters 39-40) +Index_functor.2: F (File "index_functor.ml", line 18, characters 7-8) Index_functor.3: N (File "index_functor.ml", line 19, characters 7-8) Index_functor.4: O (File "index_functor.ml", line 20, characters 7-8) -Index_functor.2: F (File "index_functor.ml", line 18, characters 7-8) -Index_functor.1: M (File "index_functor.ml", line 18, characters 39-40) diff --git a/testsuite/tests/shape-index/index_labels.reference b/testsuite/tests/shape-index/index_labels.reference index 797744dfe31..ae84539a8ef 100644 --- a/testsuite/tests/shape-index/index_labels.reference +++ b/testsuite/tests/shape-index/index_labels.reference @@ -17,9 +17,9 @@ Resolved: Index_labels.1 : a (File "index_labels.ml", line 20, characters 10-11) Uid of decls: -Index_labels.5: f (File "index_labels.ml", line 25, characters 4-5) +Index_labels.0: t (File "index_labels.ml", line 18, characters 5-6) +Index_labels.1: a (File "index_labels.ml", line 18, characters 19-20) Index_labels.2: b (File "index_labels.ml", line 18, characters 27-28) Index_labels.3: x (File "index_labels.ml", line 20, characters 4-5) -Index_labels.1: a (File "index_labels.ml", line 18, characters 19-20) Index_labels.4: _y (File "index_labels.ml", line 21, characters 4-6) -Index_labels.0: t (File "index_labels.ml", line 18, characters 5-6) +Index_labels.5: f (File "index_labels.ml", line 25, characters 4-5) diff --git a/testsuite/tests/shape-index/index_objects.reference b/testsuite/tests/shape-index/index_objects.reference index 1a0b3a3ab25..4d44a656558 100644 --- a/testsuite/tests/shape-index/index_objects.reference +++ b/testsuite/tests/shape-index/index_objects.reference @@ -23,10 +23,10 @@ Resolved: Index_objects.0 : o (File "index_objects.ml", line 23, characters 9-10) Uid of decls: +Index_objects.0: o (File "index_objects.ml", line 18, characters 4-5) +Index_objects.5: c (File "index_objects.ml", line 25, characters 6-7) Index_objects.10: d (File "index_objects.ml", line 31, characters 6-7) -Index_objects.15: M (File "index_objects.ml", line 35, characters 12-13) +Index_objects.13: ct (File "index_objects.ml", line 36, characters 8-10) Index_objects.14: dt (File "index_objects.ml", line 40, characters 8-10) -Index_objects.5: c (File "index_objects.ml", line 25, characters 6-7) -Index_objects.0: o (File "index_objects.ml", line 18, characters 4-5) +Index_objects.15: M (File "index_objects.ml", line 35, characters 12-13) Index_objects.16: ins_var (File "index_objects.ml", line 43, characters 6-13) -Index_objects.13: ct (File "index_objects.ml", line 36, characters 8-10) diff --git a/testsuite/tests/shape-index/index_types.reference b/testsuite/tests/shape-index/index_types.reference index 330c8e29244..b7887fa3be3 100644 --- a/testsuite/tests/shape-index/index_types.reference +++ b/testsuite/tests/shape-index/index_types.reference @@ -12,15 +12,15 @@ Resolved: Index_types.0 : t (File "index_types.ml", line 20, characters 8-9) Resolved: Index_types.0 : t (File "index_types.ml", line 20, characters 8-9) Uid of decls: -Index_types.11: u (File "index_types.ml", line 41, characters 5-6) -Index_types.3: poly (File "index_types.ml", line 27, characters 5-9) +Index_types.0: t (File "index_types.ml", line 18, characters 5-6) +Index_types.1: x (File "index_types.ml", line 20, characters 4-5) Index_types.2: M (File "index_types.ml", line 22, characters 7-8) -Index_types.6: S (File "index_types.ml", line 31, characters 12-13) -Index_types.10: N (File "index_types.ml", line 40, characters 7-8) -Index_types.5: B (File "index_types.ml", line 33, characters 13-14) -Index_types.9: t (File "index_types.ml", line 40, characters 23-24) +Index_types.3: poly (File "index_types.ml", line 27, characters 5-9) Index_types.4: t2 (File "index_types.ml", line 32, characters 7-9) -Index_types.1: x (File "index_types.ml", line 20, characters 4-5) -Index_types.8: B (File "index_types.ml", line 37, characters 11-12) -Index_types.0: t (File "index_types.ml", line 18, characters 5-6) +Index_types.5: B (File "index_types.ml", line 33, characters 13-14) +Index_types.6: S (File "index_types.ml", line 31, characters 12-13) Index_types.7: t1 (File "index_types.ml", line 36, characters 5-7) +Index_types.8: B (File "index_types.ml", line 37, characters 11-12) +Index_types.9: t (File "index_types.ml", line 40, characters 23-24) +Index_types.10: N (File "index_types.ml", line 40, characters 7-8) +Index_types.11: u (File "index_types.ml", line 41, characters 5-6) diff --git a/testsuite/tests/shape-index/index_unboxed_labels.reference b/testsuite/tests/shape-index/index_unboxed_labels.reference index ad75879c736..701e06820b1 100644 --- a/testsuite/tests/shape-index/index_unboxed_labels.reference +++ b/testsuite/tests/shape-index/index_unboxed_labels.reference @@ -29,35 +29,35 @@ Resolved: Index_unboxed_labels.1 : a (File "index_unboxed_labels.ml", line 21, characters 10-11) Uid of decls: -Index_unboxed_labels.2: - b (File "index_unboxed_labels.ml", line 18, characters 19-20) -Index_unboxed_labels.16: - f (File "index_unboxed_labels.ml", line 40, characters 4-5) -Index_unboxed_labels.7: - f (File "index_unboxed_labels.ml", line 24, characters 4-5) +Index_unboxed_labels.0: + t (File "index_unboxed_labels.ml", line 18, characters 5-6) Index_unboxed_labels.1: a (File "index_unboxed_labels.ml", line 18, characters 11-12) -Index_unboxed_labels.13: - b (File "index_unboxed_labels.ml", line 35, characters 12-13) -Index_unboxed_labels.6: - _y (File "index_unboxed_labels.ml", line 22, characters 4-6) -Index_unboxed_labels.4: - a (File "index_unboxed_labels.ml", line 19, characters 13-14) +Index_unboxed_labels.2: + b (File "index_unboxed_labels.ml", line 18, characters 19-20) Index_unboxed_labels.3: tu (File "index_unboxed_labels.ml", line 19, characters 5-7) -Index_unboxed_labels.11: - f (File "index_unboxed_labels.ml", line 31, characters 4-5) +Index_unboxed_labels.4: + a (File "index_unboxed_labels.ml", line 19, characters 13-14) Index_unboxed_labels.5: x (File "index_unboxed_labels.ml", line 21, characters 4-5) +Index_unboxed_labels.6: + _y (File "index_unboxed_labels.ml", line 22, characters 4-6) +Index_unboxed_labels.7: + f (File "index_unboxed_labels.ml", line 24, characters 4-5) +Index_unboxed_labels.9: + x (File "index_unboxed_labels.ml", line 28, characters 4-5) +Index_unboxed_labels.10: + _y (File "index_unboxed_labels.ml", line 29, characters 4-6) +Index_unboxed_labels.11: + f (File "index_unboxed_labels.ml", line 31, characters 4-5) +Index_unboxed_labels.12: + tb (File "index_unboxed_labels.ml", line 35, characters 5-7) +Index_unboxed_labels.13: + b (File "index_unboxed_labels.ml", line 35, characters 12-13) Index_unboxed_labels.14: x (File "index_unboxed_labels.ml", line 37, characters 4-5) Index_unboxed_labels.15: _y (File "index_unboxed_labels.ml", line 38, characters 4-6) -Index_unboxed_labels.12: - tb (File "index_unboxed_labels.ml", line 35, characters 5-7) -Index_unboxed_labels.0: - t (File "index_unboxed_labels.ml", line 18, characters 5-6) -Index_unboxed_labels.10: - _y (File "index_unboxed_labels.ml", line 29, characters 4-6) -Index_unboxed_labels.9: - x (File "index_unboxed_labels.ml", line 28, characters 4-5) +Index_unboxed_labels.16: + f (File "index_unboxed_labels.ml", line 40, characters 4-5) diff --git a/testsuite/tests/shape-index/index_vb.reference b/testsuite/tests/shape-index/index_vb.reference index a48f72fff64..cb96c56c3d4 100644 --- a/testsuite/tests/shape-index/index_vb.reference +++ b/testsuite/tests/shape-index/index_vb.reference @@ -16,9 +16,9 @@ Resolved: Index_vb.2 : b (File "index_vb.ml", line 20, characters 9-10) Resolved: Index_vb.1 : a (File "index_vb.ml", line 20, characters 6-7) Uid of decls: -Index_vb.3: a (File "index_vb.ml", line 20, characters 6-7) -Index_vb.1: a (File "index_vb.ml", line 18, characters 11-12) Index_vb.0: t (File "index_vb.ml", line 18, characters 5-6) +Index_vb.1: a (File "index_vb.ml", line 18, characters 11-12) Index_vb.2: b (File "index_vb.ml", line 18, characters 20-21) -Index_vb.5: a (File "index_vb.ml", line 20, characters 6-7) +Index_vb.3: a (File "index_vb.ml", line 20, characters 6-7) Index_vb.4: a (File "index_vb.ml", line 20, characters 6-7) +Index_vb.5: a (File "index_vb.ml", line 20, characters 6-7) diff --git a/testsuite/tests/uid-deps/link_intf_impl.ml b/testsuite/tests/uid-deps/link_intf_impl.ml new file mode 100644 index 00000000000..6d2090a1313 --- /dev/null +++ b/testsuite/tests/uid-deps/link_intf_impl.ml @@ -0,0 +1,59 @@ +(* TEST + +flags = "-bin-annot -bin-annot-occurrences"; +compile_only = "true"; +setup-ocamlc.byte-build-env; +all_modules = "link_intf_impl.mli link_intf_impl.ml"; +ocamlc.byte; +check-ocamlc.byte-output; + +program = "-quiet -uid-deps link_intf_impl.cmt"; +output = "out_objinfo"; +ocamlobjinfo; + +check-program-output; +*) + +let x (* 0 *) = 42 + +type t (* 1 *) = int + +module type S (* 3 *) = sig + val y (* 2 *) : t +end + +module M (* 5 *) : S = struct + let y (* 4 *) = 36 +end + +module N (* 8 *) : sig + val y (* 7 *) : int +end = struct + let y (* 6 *) = 2 +end + +let _ = (module N : S) + +module P (* 10 *)= struct + let y (* 9 *) = 12 +end + +module F (* 12 *) (X (* 11 *) : S) = X + +module G (* 13 *) = F(P) + +module type Initial (* 16 *) = sig + module type Nested (* 15 *) = sig + type t (* 14 *) + end +end + +module MF (* 23 *) : sig + module F (* 22 *) (X (* 21 *) : sig val x (* 20 *) : int end) : sig end +end = struct + module F (* 19 *) (X (* 18 *) : sig val x (* 17 *) : int end) = struct end +end + +module FMT (* 27 *) (X (* 26 *) : sig + module type MT (* 25 *) = sig val x (* 24 *) : int end +end) : sig end = struct end diff --git a/testsuite/tests/uid-deps/link_intf_impl.mli b/testsuite/tests/uid-deps/link_intf_impl.mli new file mode 100644 index 00000000000..fa4403c9c10 --- /dev/null +++ b/testsuite/tests/uid-deps/link_intf_impl.mli @@ -0,0 +1,19 @@ +type t (* 0 *) + +val x (* 1 *) : t + +module type S (* 3 *) = sig + val y (* 2 *) : t +end + +module M (* 4 *) : S + +module type Initial (* 7 *) = sig + module type Nested (* 6 *) = sig + type t (* 5 *) + end +end + +module FMT (* 11 *) (X (* 10 *) : sig + module type MT (* 9 *) = sig val x (* 8 *) : int end +end) : sig end diff --git a/testsuite/tests/uid-deps/link_intf_impl.reference b/testsuite/tests/uid-deps/link_intf_impl.reference new file mode 100644 index 00000000000..3e6ffa226ad --- /dev/null +++ b/testsuite/tests/uid-deps/link_intf_impl.reference @@ -0,0 +1,19 @@ + +Uid dependencies: +Link_intf_impl.0 <- [intf]Link_intf_impl.1 +Link_intf_impl.1 <- [intf]Link_intf_impl.0 +Link_intf_impl.2 <-> [intf]Link_intf_impl.2 +Link_intf_impl.3 <- [intf]Link_intf_impl.3 +Link_intf_impl.4 <- Link_intf_impl.2 +Link_intf_impl.5 <- [intf]Link_intf_impl.4 +Link_intf_impl.6 <- Link_intf_impl.7 +Link_intf_impl.7 <-> Link_intf_impl.2 +Link_intf_impl.9 <-> Link_intf_impl.2 +Link_intf_impl.14 <-> [intf]Link_intf_impl.5 +Link_intf_impl.15 <-> [intf]Link_intf_impl.6 +Link_intf_impl.16 <- [intf]Link_intf_impl.7 +Link_intf_impl.17 <-> Link_intf_impl.20 +Link_intf_impl.19 <- Link_intf_impl.22 +Link_intf_impl.24 <-> [intf]Link_intf_impl.8 +Link_intf_impl.25 <-> [intf]Link_intf_impl.9 +Link_intf_impl.27 <- [intf]Link_intf_impl.11 diff --git a/testsuite/tests/uids/intf_uids.ml b/testsuite/tests/uids/intf_uids.ml new file mode 100644 index 00000000000..af315bf6033 --- /dev/null +++ b/testsuite/tests/uids/intf_uids.ml @@ -0,0 +1,3 @@ +type u (* has uid Intf_uids.0 *) + +type t (* has uid Intf_uids.1 *) diff --git a/testsuite/tests/uids/intf_uids.mli b/testsuite/tests/uids/intf_uids.mli new file mode 100644 index 00000000000..21cfde35a94 --- /dev/null +++ b/testsuite/tests/uids/intf_uids.mli @@ -0,0 +1,3 @@ +type t (* has uid [intf]Intf_uids.0 *) + +type u (* has uid [intf]Intf_uids.1 *) diff --git a/testsuite/tests/uids/intf_uids_test.ml b/testsuite/tests/uids/intf_uids_test.ml new file mode 100644 index 00000000000..a5faf8e2c99 --- /dev/null +++ b/testsuite/tests/uids/intf_uids_test.ml @@ -0,0 +1,22 @@ +(* TEST + +flags = "-bin-annot"; +compile_only = "true"; +modules = "intf_uids.ml"; + +setup-ocamlc.byte-build-env; +all_modules = "intf_uids.mli intf_uids.ml"; +ocamlc.byte; +check-ocamlc.byte-output; + +program = "-quiet -decls intf_uids.cmti intf_uids.cmt"; +output = "out_objinfo"; +ocamlobjinfo; + +check-program-output; +*) + +(* This test illustrates the fact that uids are tagged to indicate if they + originate from an interface of an implementation: it prints the delcarations + written in the cmt file for the interface and then for the implementation. + These should not overlap. *) diff --git a/testsuite/tests/uids/intf_uids_test.reference b/testsuite/tests/uids/intf_uids_test.reference new file mode 100644 index 00000000000..a1963210cec --- /dev/null +++ b/testsuite/tests/uids/intf_uids_test.reference @@ -0,0 +1,8 @@ + +Uid of decls: +[intf]Intf_uids.0: t (File "intf_uids.mli", line 1, characters 5-6) +[intf]Intf_uids.1: u (File "intf_uids.mli", line 3, characters 5-6) + +Uid of decls: +Intf_uids.0: u (File "intf_uids.ml", line 1, characters 5-6) +Intf_uids.1: t (File "intf_uids.ml", line 3, characters 5-6) diff --git a/tools/objinfo.ml b/tools/objinfo.ml index 49cbc43f607..61b76418af2 100644 --- a/tools/objinfo.ml +++ b/tools/objinfo.ml @@ -39,6 +39,7 @@ let no_crc = ref false let shape = ref false let index = ref false let decls = ref false +let uid_deps = ref false module Magic_number = Misc.Magic_number module String = Misc.Stdlib.String @@ -213,9 +214,32 @@ let print_cmt_infos cmt = cmt.cmt_ident_occurrences; Format.print_flush () end; + if !uid_deps then begin + printf "\nUid dependencies:\n"; + let arr = Array.of_list cmt.cmt_declaration_dependencies in + let () = + Array.sort (fun (_tr, u1, u2) (_tr', u1', u2') -> + match Shape.Uid.compare u1 u1' with + | 0 -> Shape.Uid.compare u2 u2' + | n -> n) arr + in + Format.printf "@["; + Array.iter (fun (rk, u1, u2) -> + let rk = match rk with + | Definition_to_declaration -> "<-" + | Declaration_to_declaration -> "<->" + in + Format.printf "@[%a %s %a@]@;" + Shape.Uid.print u1 + rk + Shape.Uid.print u2) arr; + Format.printf "@]"; + end; if !decls then begin printf "\nUid of decls:\n"; - Shape.Uid.Tbl.iter (fun uid item -> + let decls = Array.of_list (Shape.Uid.Tbl.to_list cmt.cmt_uid_to_decl) in + Array.sort (fun (uid, _) (uid', _) -> Shape.Uid.compare uid uid') decls; + Array.iter (fun (uid, item) -> let loc = match (item : Typedtree.item_declaration) with | Value vd -> vd.val_name | Value_binding vb -> @@ -245,8 +269,8 @@ let print_cmt_infos cmt = Format.printf "@[%a:@ %a@]@;" Shape.Uid.print uid pp_loc loc) - cmt.cmt_uid_to_decl; - Format.print_flush () + decls; + Format.print_flush () end let print_cms_infos cms = @@ -569,6 +593,8 @@ let arg_list = [ " Print a list of all usages of values, types, etc. in the module"; "-decls", Arg.Set decls, " Print a list of all declarations in the module"; + "-uid-deps", Arg.Set uid_deps, + " Print the declarations' uids dependencies of the module"; "-null-crc", Arg.Set no_crc, " Print a null CRC for imported interfaces"; "-args", Arg.Expand Arg.read_arg, " Read additional newline separated command line arguments \n\ diff --git a/toplevel/byte/topeval.ml b/toplevel/byte/topeval.ml index 6c4d051e12a..1922fa12238 100644 --- a/toplevel/byte/topeval.ml +++ b/toplevel/byte/topeval.ml @@ -125,8 +125,7 @@ let execute_phrase print_outcome ppf phr = in if !Clflags.dump_typedtree then Printtyped.implementation ppf str; let sg' = Typemod.Signature_names.simplify newenv sn sg in - ignore (Includemod.signatures ~mark:Mark_positive oldenv - ~modes:(Legacy None) sg sg'); + Includemod.check_implementation oldenv ~modes:(Legacy None) sg sg'; Typecore.force_delayed_checks (); let shape = Shape_reduce.local_reduce Env.empty shape in if !Clflags.dump_shape then Shape.print ppf shape; diff --git a/toplevel/native/opttoploop.ml b/toplevel/native/opttoploop.ml index 0316c3b85e7..5082c51f0af 100644 --- a/toplevel/native/opttoploop.ml +++ b/toplevel/native/opttoploop.ml @@ -401,7 +401,7 @@ let execute_phrase print_outcome ppf phr = if !Clflags.dump_typedtree then Printtyped.implementation ppf str; let sg' = Typemod.Signature_names.simplify newenv names sg in let coercion = - Includemod.signatures oldenv ~mark:Mark_positive + Includemod.signatures oldenv ~mark:true ~modes:(Legacy None) sg sg' in Typecore.force_delayed_checks (); diff --git a/toplevel/native/topeval.ml b/toplevel/native/topeval.ml index 22b6a9c2475..fdfb4a1cc1e 100644 --- a/toplevel/native/topeval.ml +++ b/toplevel/native/topeval.ml @@ -185,7 +185,7 @@ let execute_phrase print_outcome ppf phr = in if !Clflags.dump_typedtree then Printtyped.implementation ppf str; let sg' = Typemod.Signature_names.simplify newenv names sg in - ignore (Includemod.signatures oldenv ~mark:Mark_positive sg sg'); + Includemod.check_implementation oldenv ~modes:(Legacy None) sg sg'; Typecore.force_delayed_checks (); let shape = Shape_reduce.local_reduce Env.empty shape in if !Clflags.dump_shape then Shape.print ppf shape; diff --git a/typing/datarepr.mli b/typing/datarepr.mli index 606fa6eab1b..0a1d507174f 100644 --- a/typing/datarepr.mli +++ b/typing/datarepr.mli @@ -19,8 +19,8 @@ open Types val extension_descr: - current_unit:Compilation_unit.t option -> Path.t -> extension_constructor -> - constructor_description + current_unit:Compilation_unit.with_kind option -> + Path.t -> extension_constructor -> constructor_description val labels_of_type: Path.t -> type_declaration -> @@ -29,8 +29,8 @@ val unboxed_labels_of_type: Path.t -> type_declaration -> (Ident.t * unboxed_label_description) list val constructors_of_type: - current_unit:Compilation_unit.t option -> Path.t -> type_declaration -> - (Ident.t * constructor_description) list + current_unit:Compilation_unit.with_kind option -> Path.t -> + type_declaration -> (Ident.t * constructor_description) list exception Constr_not_found diff --git a/typing/env.ml b/typing/env.ml index 9222de63292..0f550efaec8 100644 --- a/typing/env.ml +++ b/typing/env.ml @@ -1007,8 +1007,8 @@ let rec address_head = function (* The name of the compilation unit currently compiled. *) module Current_unit_name : sig - val get : unit -> Compilation_unit.t option - val set : Compilation_unit.t option -> unit + val get : unit -> (Compilation_unit.with_kind) option + val set : (Compilation_unit.with_kind) option -> unit val is : string -> bool val is_ident : Ident.t -> bool val is_path : Path.t -> bool @@ -1018,7 +1018,7 @@ end = struct let set comp_unit = Compilation_unit.set_current comp_unit let get_name () = - Option.map Compilation_unit.name (get ()) + Option.map (fun (cu, _) -> Compilation_unit.name cu) (get ()) let is name = let current_name_string = Option.map Compilation_unit.Name.to_string (get_name ()) diff --git a/typing/env.mli b/typing/env.mli index 507ce49d348..36d2d092d6e 100644 --- a/typing/env.mli +++ b/typing/env.mli @@ -518,8 +518,8 @@ val reset_cache: preserve_persistent_env:bool -> unit val reset_cache_toplevel: unit -> unit (* Remember the name of the current compilation unit. *) -val set_unit_name: Compilation_unit.t option -> unit -val get_unit_name: unit -> Compilation_unit.t option +val set_unit_name: (Compilation_unit.with_kind) option -> unit +val get_unit_name: unit -> (Compilation_unit.with_kind) option (* Read, save a signature to/from a file. *) val read_signature: diff --git a/typing/includemod.ml b/typing/includemod.ml index e097fbc8245..bb8717aad81 100644 --- a/typing/includemod.ml +++ b/typing/includemod.ml @@ -120,21 +120,88 @@ module Error = struct end -type mark = +module Directionality = struct + + + type mark = | Mark_both | Mark_positive - | Mark_negative | Mark_neither -let negate_mark = function - | Mark_both -> Mark_both - | Mark_positive -> Mark_negative - | Mark_negative -> Mark_positive - | Mark_neither -> Mark_neither + type pos = + | Strictly_positive + (** Strictly positive positions are notable for tools since they are the + the case where we match a implementation definition with an interface + declaration. Oherwise in the positive case we are matching + declatations inside functor arguments at even level of nesting.*) + | Positive + | Negative + + +(** + When checking inclusion, the [Directionality.t] type tracks the + subtyping direction at the syntactic level. + + The [posivity] field is used in the [cmt_declaration_dependencies] to + distinguish between directed and undirected edges, and to avoid recording + matched declarations twice. + + The [mark_as_used] field describes if we should record only positive use, + any use (because there is no clear implementation side), or none (because we + are inside an auxiliary check function.) + + The [in_eq] field is [true] when we are checking both directions inside of + module types which allows optimizing module type equality checks. The module + subtyping relation [A <: B] checks that [A.T = B.T] when [A] and [B] define a + module type [T]. The relation [A.T = B.T] is equivalent to [(A.T <: B.T) and + (B.T <: A.T)], but checking both recursively would lead to an exponential + slowdown (see #10598 and #10616). To avoid this issue, when [in_eq] is + [true], we compute a coarser relation [A << B] which is the same as [A <: B] + except that module types [T] are checked only for [A.T << B.T] and not the + reverse. Thus, we can implement a cheap module type equality check [A.T = + B.T] by computing [(A.T << B.T) and (B.T << A.T)], avoiding the exponential + slowdown described above. +*) + type t = { + in_eq:bool; + mark_as_used:mark; + pos:pos; + } + + let strictly_positive ~mark = + let mark_as_used = if mark then Mark_positive else Mark_neither in + { in_eq=false; pos=Strictly_positive; mark_as_used } + + let unknown ~mark = + let mark_as_used = if mark then Mark_both else Mark_neither in + { in_eq=false; pos=Positive; mark_as_used } -let mark_positive = function - | Mark_both | Mark_positive -> true - | Mark_negative | Mark_neither -> false + let negate_pos = function + | Positive | Strictly_positive -> Negative + | Negative -> Positive + + let negate d = { d with pos = negate_pos d.pos } + + let at_most_positive = function + | Strictly_positive -> Positive + | Positive | Negative as non_strict -> non_strict + + let enter_eq d = + { + in_eq = true; + pos = at_most_positive d.pos; + mark_as_used = d.mark_as_used + } + + let mark_as_used d = match d.mark_as_used with + | Mark_neither -> false + | Mark_both -> true + | Mark_positive -> + match d.pos with + | Positive | Strictly_positive -> true + | Negative -> false + +end (* All functions "blah env x1 x2" check that x1 is included in x2, i.e. that x1 is the type of an implementation that fulfills the @@ -153,9 +220,8 @@ let append_ldot s = function (* Inclusion between value descriptions *) -let value_descriptions ~loc env ~mark subst id ~mmodes vd1 vd2 = - Cmt_format.record_value_dependency vd1 vd2; - if mark_positive mark then +let value_descriptions ~loc env ~direction subst id ~mmodes vd1 vd2 = + if Directionality.mark_as_used direction then Env.mark_value_used vd1.val_uid; let vd2 = Subst.value_description subst vd2 in try @@ -165,8 +231,8 @@ let value_descriptions ~loc env ~mark subst id ~mmodes vd1 vd2 = (* Inclusion between type declarations *) -let type_declarations ~loc env ~mark subst id decl1 decl2 = - let mark = mark_positive mark in +let type_declarations ~loc env ~direction subst id decl1 decl2 = + let mark = Directionality.mark_as_used direction in if mark then Env.mark_type_used decl1.type_uid; let decl2 = Subst.type_declaration subst decl2 in @@ -180,8 +246,8 @@ let type_declarations ~loc env ~mark subst id decl1 decl2 = (* Inclusion between extension constructors *) -let extension_constructors ~loc env ~mark subst id ext1 ext2 = - let mark = mark_positive mark in +let extension_constructors ~loc env ~direction subst id ext1 ext2 = + let mark = Directionality.mark_as_used direction in let ext2 = Subst.extension_constructor subst ext2 in match Includecore.extension_constructors ~loc env ~mark id ext1 ext2 with | None -> Ok Tcoerce_none @@ -505,24 +571,8 @@ and shallow_module_paths env subst p1 mty2 p2 = | Mty_alias _ | Mty_ident _ | Mty_signature _ | Mty_functor _ | exception Not_found -> false -(** - In the group of mutual functions below, the [~in_eq] argument is [true] when - we are in fact checking equality of module types. - - The module subtyping relation [A <: B] checks that [A.T = B.T] when [A] - and [B] define a module type [T]. The relation [A.T = B.T] is equivalent - to [(A.T <: B.T) and (B.T <: A.T)], but checking both recursively would lead - to an exponential slowdown (see #10598 and #10616). - To avoid this issue, when [~in_eq] is [true], we compute a coarser relation - [A << B] which is the same as [A <: B] except that module types [T] are - checked only for [A.T << B.T] and not the reverse. - Thus, we can implement a cheap module type equality check [A.T = B.T] by - computing [(A.T << B.T) and (B.T << A.T)], avoiding the exponential slowdown - described above. -*) - -let rec modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 shape = - match try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 shape with +let rec modtypes ~direction ~loc env subst ~modes mty1 mty2 shape = + match try_modtypes ~direction ~loc env subst ~modes mty1 mty2 shape with | Ok _ as ok -> ok | Error reason -> let mty1 = Subst.Lazy.force_modtype mty1 in @@ -531,7 +581,7 @@ let rec modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 shape = in Error Error.(diff mty1 mty2 reason) -and try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 orig_shape = +and try_modtypes ~direction ~loc env subst ~modes mty1 mty2 orig_shape = let open Subst.Lazy in (* Do a quick nominal comparison for simple types and if that fails, try to unfold one of them. For structured types, do a deep comparison. *) @@ -553,7 +603,7 @@ and try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 orig_shape = | p1 -> begin match Env.find_module_lazy p1 env with | md -> begin - match strengthened_modtypes ~in_eq ~loc ~aliasable:true env ~mark + match strengthened_modtypes ~direction ~loc ~aliasable:true env subst ~modes md.md_type p1 mty2 orig_shape with | Ok _ as x -> x @@ -565,7 +615,7 @@ and try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 orig_shape = end | (Mty_signature sig1, Mty_signature sig2) -> begin match - signatures ~in_eq ~loc env ~mark subst ~modes sig1 sig2 orig_shape + signatures ~direction ~loc env subst ~modes sig1 sig2 orig_shape with | Ok _ as ok -> ok | Error e -> Error (Error.Signature e) @@ -574,7 +624,8 @@ and try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 orig_shape = | Mty_functor (param1, res1), Mty_functor (param2, res2) -> walk_locks ~env ~item:Module modes; let cc_arg, env, subst = - functor_param ~in_eq ~loc env ~mark:(negate_mark mark) + let direction = Directionality.negate direction in + functor_param ~direction ~loc env subst param1 param2 in let var, res_shape = @@ -592,7 +643,7 @@ and try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 orig_shape = var, Shape.app orig_shape ~arg:shape_var in let cc_res = - modtypes ~in_eq ~loc env ~mark subst res1 res2 res_shape + modtypes ~direction ~loc env subst res1 res2 res_shape ~modes:(Legacy None) in begin match cc_arg, cc_res with @@ -650,7 +701,7 @@ and try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 orig_shape = in match red with | Some (mty1,mty2) -> - try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 orig_shape + try_modtypes ~direction ~loc env subst ~modes mty1 mty2 orig_shape | None -> (* Report error *) match mty1, mty2 with @@ -682,7 +733,7 @@ and try_modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 orig_shape = (* Functor parameters *) -and functor_param ~in_eq ~loc env ~mark subst param1 param2 = +and functor_param ~direction ~loc env subst param1 param2 = let open Subst.Lazy in match param1, param2 with | Unit, Unit -> @@ -691,7 +742,7 @@ and functor_param ~in_eq ~loc env ~mark subst param1 param2 = let arg2' = Subst.Lazy.modtype Keep subst arg2 in let cc_arg = match - modtypes ~in_eq ~loc env ~mark Subst.identity arg2' arg1 + modtypes ~direction ~loc env Subst.identity arg2' arg1 Shape.dummy_mod ~modes:(Legacy None) with | Ok (cc, _) -> Ok cc @@ -721,22 +772,22 @@ and equate_one_functor_param subst env arg2' name1 name2 = | None, None -> env, subst -and strengthened_modtypes ~in_eq ~loc ~aliasable env ~mark +and strengthened_modtypes ~direction ~loc ~aliasable env subst ~modes mty1 path1 mty2 shape = let mty1 = Mtype.strengthen_lazy ~aliasable mty1 path1 in - modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 shape + modtypes ~direction ~loc env subst ~modes mty1 mty2 shape -and strengthened_module_decl ~loc ~aliasable env ~mark +and strengthened_module_decl ~loc ~aliasable ~direction env subst ~mmodes md1 path1 md2 shape = let md1 = Subst.Lazy.of_module_decl md1 in let md1 = Mtype.strengthen_lazy_decl ~aliasable md1 path1 in let mty2 = Subst.Lazy.of_modtype md2.md_type in let modes = mmodes in - modtypes ~in_eq:false ~loc env ~mark subst ~modes md1.md_type mty2 shape + modtypes ~direction ~loc env subst ~modes md1.md_type mty2 shape (* Inclusion between signatures *) -and signatures ~in_eq ~loc env ~mark subst ~modes sig1 sig2 mod_shape = +and signatures ~direction ~loc env subst ~modes sig1 sig2 mod_shape = let open Subst.Lazy in (* Environment used to check inclusion of components *) let sig1 = force_signature_once sig1 in @@ -764,7 +815,7 @@ and signatures ~in_eq ~loc env ~mark subst ~modes sig1 sig2 mod_shape = (* Do the pairing and checking, and return the final coercion *) let paired, unpaired, subst = pair_components subst comps1 sig2 in let d = - signature_components ~in_eq ~loc ~mark new_env subst mod_shape + signature_components ~direction ~loc new_env subst mod_shape Shape.Map.empty ~mmodes:modes (List.rev paired) in @@ -789,19 +840,19 @@ and signatures ~in_eq ~loc env ~mark subst ~modes sig1 sig2 mod_shape = (* Inclusion between signature components *) and signature_components : - 'a. in_eq:_ -> loc:_ -> mark:_ -> _ -> _ -> _ -> _ -> mmodes:_ -> (_ * _ * 'a) list -> 'a Sign_diff.t = - fun ~in_eq ~loc ~mark env subst orig_shape shape_map ~mmodes paired -> + 'a. direction:_ -> loc:_ -> _ -> _ -> _ -> _ -> mmodes:_ -> (_ * _ * 'a) list -> 'a Sign_diff.t = + fun ~direction ~loc env subst orig_shape shape_map ~mmodes paired -> let open Subst.Lazy in match paired with | [] -> Sign_diff.{ empty with shape_map } | (sigi1, sigi2, pos) :: rem -> let shape_modified = ref false in - let id, item, shape_map, present_at_runtime = + let id, item, paired_uids, shape_map, present_at_runtime = match sigi1, sigi2 with | Sig_value(id1, valdecl1, _) ,Sig_value(_id2, valdecl2, _) -> let mmodes = append_ldot (Ident.name id1) mmodes in let item = - value_descriptions ~loc env ~mark subst id1 ~mmodes + value_descriptions ~loc ~direction env subst id1 ~mmodes (Subst.Lazy.force_value_description valdecl1) (Subst.Lazy.force_value_description valdecl2) in @@ -811,25 +862,26 @@ and signature_components : | _ -> true in let shape_map = Shape.Map.add_value_proj shape_map id1 orig_shape in - id1, item, shape_map, present_at_runtime + let paired_uids = (valdecl1.val_uid, valdecl2.val_uid) in + id1, item, paired_uids, shape_map, present_at_runtime | Sig_type(id1, tydec1, _, _), Sig_type(_id2, tydec2, _, _) -> let item = - type_declarations ~loc env ~mark subst id1 tydec1 tydec2 + type_declarations ~loc ~direction env subst id1 tydec1 tydec2 in let item = mark_error_as_unrecoverable item in (* Right now we don't filter hidden constructors / labels from the shape. *) let shape_map = Shape.Map.add_type_proj shape_map id1 orig_shape in - id1, item, shape_map, false + id1, item, (tydec1.type_uid, tydec2.type_uid), shape_map, false | Sig_typext(id1, ext1, _, _), Sig_typext(_id2, ext2, _, _) -> let item = - extension_constructors ~loc env ~mark subst id1 ext1 ext2 + extension_constructors ~loc ~direction env subst id1 ext1 ext2 in let item = mark_error_as_unrecoverable item in let shape_map = Shape.Map.add_extcons_proj shape_map id1 orig_shape in - id1, item, shape_map, true + id1, item, (ext1.ext_uid, ext2.ext_uid), shape_map, true | Sig_module(id1, pres1, mty1, _, _), Sig_module(_, pres2, mty2, _, _) -> begin let mmodes = append_ldot (Ident.name id1) mmodes in @@ -837,7 +889,7 @@ and signature_components : Shape.(proj orig_shape (Item.module_ id1)) in let item = - module_declarations ~in_eq ~loc env ~mark subst id1 mty1 mty2 + module_declarations ~direction ~loc env subst id1 mty1 mty2 ~mmodes orig_shape in let item, shape_map = @@ -862,17 +914,18 @@ and signature_components : | Mp_absent, Mp_present, _ -> assert false in let item = mark_error_as_unrecoverable item in - id1, item, shape_map, present_at_runtime + let paired_uids = (mty1.md_uid, mty2.md_uid) in + id1, item, paired_uids, shape_map, present_at_runtime end | Sig_modtype(id1, info1, _), Sig_modtype(_id2, info2, _) -> let item = - modtype_infos ~in_eq ~loc env ~mark subst id1 info1 info2 + modtype_infos ~direction ~loc env subst id1 info1 info2 in let shape_map = Shape.Map.add_module_type_proj shape_map id1 orig_shape in let item = mark_error_as_unrecoverable item in - id1, item, shape_map, false + id1, item, (info1.mtd_uid, info2.mtd_uid), shape_map, false | Sig_class(id1, decl1, _, _), Sig_class(_id2, decl2, _, _) -> walk_locks ~env ~item:Class (append_ldot (Ident.name id1) mmodes); let item = @@ -882,7 +935,7 @@ and signature_components : Shape.Map.add_class_proj shape_map id1 orig_shape in let item = mark_error_as_unrecoverable item in - id1, item, shape_map, true + id1, item, (decl1.cty_uid, decl2.cty_uid), shape_map, true | Sig_class_type(id1, info1, _, _), Sig_class_type(_id2, info2, _, _) -> let item = class_type_declarations ~loc env subst info1 info2 @@ -891,7 +944,7 @@ and signature_components : let shape_map = Shape.Map.add_class_type_proj shape_map id1 orig_shape in - id1, item, shape_map, false + id1, item, (info1.clty_uid, info2.clty_uid), shape_map, false | _ -> assert false in @@ -899,6 +952,25 @@ and signature_components : let first = match item with | Ok x -> + begin match direction with + | { Directionality.in_eq = true; pos = Negative } + | { Directionality.mark_as_used = Mark_neither; _ } -> + (* We do not store paired uids when checking for reverse + module-type inclusion as it would introduce duplicates. *) + () + | { Directionality.pos; _} -> + let paired_uids = + let elt1, elt2 = paired_uids in + match pos with + | Negative -> + (Cmt_format.Declaration_to_declaration, elt2, elt1) + | Positive -> + (Cmt_format.Declaration_to_declaration, elt1, elt2) + | Strictly_positive -> + (Cmt_format. Definition_to_declaration, elt1, elt2) + in + Cmt_format.record_declaration_dependency paired_uids + end; let runtime_coercions = if present_at_runtime then [pos,x] else [] in @@ -912,7 +984,7 @@ and signature_components : in let rest = if continue then - signature_components ~in_eq ~loc ~mark env subst + signature_components ~direction ~loc env subst orig_shape shape_map ~mmodes rem else let rem = List.map @@ -926,7 +998,7 @@ and signature_components : in Sign_diff.merge first rest -and module_declarations ~in_eq ~loc env ~mark subst id1 ~mmodes md1 md2 orig_shape = +and module_declarations ~direction ~loc env subst id1 ~mmodes md1 md2 orig_shape = let open Subst.Lazy in Builtin_attributes.check_alerts_inclusion ~def:md1.md_loc @@ -935,15 +1007,15 @@ and module_declarations ~in_eq ~loc env ~mark subst id1 ~mmodes md1 md2 orig_s md1.md_attributes md2.md_attributes (Ident.name id1); let p1 = Path.Pident id1 in - if mark_positive mark then + if Directionality.mark_as_used direction then Env.mark_module_used md1.md_uid; let modes = mmodes in - strengthened_modtypes ~in_eq ~loc ~aliasable:true env ~mark subst ~modes + strengthened_modtypes ~direction ~loc ~aliasable:true env subst ~modes md1.md_type p1 md2.md_type orig_shape (* Inclusion between module type specifications *) -and modtype_infos ~in_eq ~loc env ~mark subst id info1 info2 = +and modtype_infos ~direction ~loc env subst id info1 info2 = let open Subst.Lazy in Builtin_attributes.check_alerts_inclusion ~def:info1.mtd_loc @@ -957,10 +1029,10 @@ and modtype_infos ~in_eq ~loc env ~mark subst id info1 info2 = (None, None) -> Ok Tcoerce_none | (Some _, None) -> Ok Tcoerce_none | (Some mty1, Some mty2) -> - check_modtype_equiv ~in_eq ~loc env ~mark mty1 mty2 + check_modtype_equiv ~direction ~loc env mty1 mty2 | (None, Some mty2) -> let mty1 = Mty_ident(Path.Pident id) in - check_modtype_equiv ~in_eq ~loc env ~mark mty1 mty2 in + check_modtype_equiv ~direction ~loc env mty1 mty2 in match r with | Ok _ as ok -> ok | Error e -> @@ -968,9 +1040,11 @@ and modtype_infos ~in_eq ~loc env ~mark subst id info1 info2 = let info2 = Subst.Lazy.force_modtype_decl info2 in Error Error.(Module_type_declaration (diff info1 info2 e)) -and check_modtype_equiv ~in_eq ~loc env ~mark mty1 mty2 = +and check_modtype_equiv ~direction ~loc env mty1 mty2 = + let nested_eq = direction.Directionality.in_eq in + let direction = Directionality.enter_eq direction in let c1 = - modtypes ~in_eq:true ~loc env ~mark Subst.identity mty1 mty2 Shape.dummy_mod + modtypes ~direction ~loc env Subst.identity mty1 mty2 Shape.dummy_mod ~modes:All in let c2 = @@ -978,11 +1052,11 @@ and check_modtype_equiv ~in_eq ~loc env ~mark mty1 mty2 = the outer module type is the one responsible for checking the other side of the equivalence. *) - if in_eq then None + if nested_eq then None else - let mark = negate_mark mark in + let direction = Directionality.negate direction in Some ( - modtypes ~in_eq:true ~loc env ~mark Subst.identity ~modes:All + modtypes ~direction ~loc env Subst.identity ~modes:All mty2 mty1 Shape.dummy_mod ) in @@ -997,10 +1071,10 @@ and check_modtype_equiv ~in_eq ~loc env ~mark mty1 mty2 = | Error less_than, Some Error greater_than -> Error Error.(Incomparable {less_than; greater_than}) -let include_functor_signatures ~loc env ~mark subst sig1 sig2 mod_shape = +let include_functor_signatures ~direction ~loc env subst sig1 sig2 mod_shape = let _, _, comps1 = build_component_table (fun _pos name -> name) sig1 in let paired, unpaired, subst = pair_components subst comps1 sig2 in - let d = signature_components ~in_eq:false ~loc ~mark env subst mod_shape + let d = signature_components ~direction ~loc env subst mod_shape Shape.Map.empty ~mmodes:(Legacy None) (List.rev paired) in @@ -1021,21 +1095,21 @@ let can_alias env path = no_apply path && not (Env.is_functor_arg path env) -let signatures ~in_eq ~loc env ~mark subst sig1 sig2 mod_shape = +let signatures ~direction ~loc env subst sig1 sig2 mod_shape = let sig1 = Subst.Lazy.of_signature sig1 in let sig2 = Subst.Lazy.of_signature sig2 in - signatures ~in_eq ~loc env ~mark subst sig1 sig2 mod_shape + signatures ~direction ~loc env subst sig1 sig2 mod_shape -let modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 shape = +let modtypes ~direction ~loc env subst ~modes mty1 mty2 shape = let mty1 = Subst.Lazy.of_modtype mty1 in let mty2 = Subst.Lazy.of_modtype mty2 in - modtypes ~in_eq ~loc env ~mark subst ~modes mty1 mty2 shape + modtypes ~direction ~loc env subst ~modes mty1 mty2 shape -let strengthened_modtypes ~in_eq ~loc ~aliasable env ~mark +let strengthened_modtypes ~direction ~loc ~aliasable env subst mty1 path1 mty2 shape = let mty1 = Subst.Lazy.of_modtype mty1 in let mty2 = Subst.Lazy.of_modtype mty2 in - strengthened_modtypes ~in_eq ~loc ~aliasable env ~mark subst mty1 + strengthened_modtypes ~direction ~loc ~aliasable env subst mty1 path1 mty2 shape type explanation = Env.t * Error.all @@ -1055,7 +1129,8 @@ exception Apply_error of { let check_modtype_inclusion_raw ~loc env mty1 path1 mty2 = let aliasable = can_alias env path1 in - strengthened_modtypes ~in_eq:false ~loc ~aliasable env ~mark:Mark_both + let direction = Directionality.unknown ~mark:true in + strengthened_modtypes ~direction ~loc ~aliasable env Subst.identity ~modes:(Legacy None) mty1 path1 mty2 Shape.dummy_mod |> Result.map fst @@ -1092,8 +1167,9 @@ let () = let compunit0 ~comparison env ~mark impl_name impl_sig intf_name intf_sig unit_shape = + let direction = Directionality.strictly_positive ~mark in match - signatures ~in_eq:false ~loc:(Location.in_file impl_name) env ~mark + signatures ~direction ~loc:(Location.in_file impl_name) env Subst.identity ~modes:(Legacy None) impl_sig intf_sig unit_shape with Result.Error reasons -> let diff = Error.diff impl_name intf_name reasons in @@ -1110,7 +1186,7 @@ let compunit = compunit0 ~comparison:Implementation_vs_interface let compunit_as_argument env arg_name arg_sig param_name param_sig = let cc, _shape = compunit0 env arg_name arg_sig param_name param_sig Shape.dummy_mod - ~comparison:Argument_vs_parameter ~mark:Mark_positive + ~comparison:Argument_vs_parameter ~mark:true in cc @@ -1214,7 +1290,8 @@ module Functor_inclusion_diff = struct let res, _, _ = let mty1 = Subst.Lazy.of_functor_parameter mty1 in let mty2 = Subst.Lazy.of_functor_parameter mty2 in - functor_param ~in_eq:false ~loc st.env ~mark:Mark_neither + let direction = Directionality.unknown ~mark:false in + functor_param ~direction ~loc st.env st.subst mty1 mty2 in res @@ -1308,8 +1385,9 @@ module Functor_app_diff = struct | Unit, Named _ | (Anonymous | Named _), Unit -> Result.Error (Error.Incompatible_params(arg,param)) | ( Anonymous | Named _ | Empty_struct ), Named (_, param) -> + let direction = Directionality.unknown ~mark:false in match - modtypes ~in_eq:false ~loc state.env ~mark:Mark_neither + modtypes ~direction ~loc state.env state.subst ~modes:(Legacy None) arg_mty param Shape.dummy_mod with @@ -1332,44 +1410,58 @@ end (* Hide the context and substitution parameters to the outside world *) let modtypes_with_shape ~shape ~loc env ~mark ~modes mty1 mty2 = - match modtypes ~in_eq:false ~loc env ~mark + (* modtypes with shape is used when typing module expressions in [Typemod] *) + let direction = Directionality.strictly_positive ~mark in + match modtypes ~direction ~loc env Subst.identity ~modes mty1 mty2 shape with | Ok (cc, shape) -> cc, shape | Error reason -> raise (Error (env, Error.(In_Module_type reason))) let modtypes ~loc env ~mark ~modes mty1 mty2 = - match modtypes ~in_eq:false ~loc env ~mark + let direction = Directionality.unknown ~mark in + match modtypes ~direction ~loc env Subst.identity ~modes mty1 mty2 Shape.dummy_mod with | Ok (cc, _) -> cc | Error reason -> raise (Error (env, Error.(In_Module_type reason))) -let signatures env ~mark ~modes sig1 sig2 = - match signatures ~in_eq:false ~loc:Location.none env ~mark +let gen_signatures env ~direction ~modes sig1 sig2 = + match signatures ~direction ~loc:Location.none env Subst.identity ~modes sig1 sig2 Shape.dummy_mod with | Ok (cc, _) -> cc | Error reason -> raise (Error(env,Error.(In_Signature reason))) +let signatures env ~mark ~modes sig1 sig2 = + let direction = Directionality.unknown ~mark in + gen_signatures env ~direction ~modes sig1 sig2 + +let check_implementation env ~modes impl intf = + let direction = Directionality.strictly_positive ~mark:true in + ignore (gen_signatures env ~direction ~modes impl intf) + let include_functor_signatures env ~mark sig1 sig2 = let sig1 = List.map Subst.Lazy.of_signature_item sig1 in let sig2 = List.map Subst.Lazy.of_signature_item sig2 in - match include_functor_signatures ~loc:Location.none env ~mark + let direction = Directionality.unknown ~mark in + match include_functor_signatures ~direction ~loc:Location.none env Subst.identity sig1 sig2 Shape.dummy_mod with | Ok cc -> cc | Error reason -> raise (Error(env,Error.(In_Include_functor_signature reason))) let type_declarations ~loc env ~mark id decl1 decl2 = - match type_declarations ~loc env ~mark Subst.identity id decl1 decl2 with + let direction = Directionality.unknown ~mark in + match type_declarations ~loc env ~direction Subst.identity id decl1 decl2 with | Ok _ -> () | Error (Error.Core reason) -> raise (Error(env,Error.(In_Type_declaration(id,reason)))) | Error _ -> assert false let strengthened_module_decl ~loc ~aliasable env ~mark ~mmodes md1 path1 md2 = - match strengthened_module_decl ~loc ~aliasable env ~mark Subst.identity + let direction = Directionality.unknown ~mark in + match strengthened_module_decl ~loc ~aliasable ~direction env Subst.identity ~mmodes md1 path1 md2 Shape.dummy_mod with | Ok (x, _shape) -> x | Error mdiff -> @@ -1384,7 +1476,8 @@ let expand_module_alias ~strengthen env path = let check_modtype_equiv ~loc env id mty1 mty2 = let mty1' = Subst.Lazy.of_modtype mty1 in let mty2' = Subst.Lazy.of_modtype mty2 in - match check_modtype_equiv ~in_eq:false ~loc env ~mark:Mark_both mty1' mty2' with + let direction = Directionality.unknown ~mark:true in + match check_modtype_equiv ~direction ~loc env mty1' mty2' with | Ok _ -> () | Error e -> raise (Error(env, diff --git a/typing/includemod.mli b/typing/includemod.mli index 4100f806d98..7f476404851 100644 --- a/typing/includemod.mli +++ b/typing/includemod.mli @@ -18,18 +18,6 @@ open Typedtree open Types -(** Type describing which arguments of an inclusion to consider as used - for the usage warnings. [Mark_both] is the default. *) -type mark = - | Mark_both - (** Mark definitions used from both arguments *) - | Mark_positive - (** Mark definitions used from the positive (first) argument *) - | Mark_negative - (** Mark definitions used from the negative (second) argument *) - | Mark_neither - (** Do not mark definitions used from either argument *) - module Error: sig type ('elt,'explanation) diff = { @@ -155,15 +143,15 @@ type modes = Includecore.mmodes (* Typechecking *) val modtypes: - loc:Location.t -> Env.t -> mark:mark -> modes:modes -> + loc:Location.t -> Env.t -> mark:bool -> modes:modes -> module_type -> module_type -> module_coercion val modtypes_with_shape: - shape:Shape.t -> loc:Location.t -> Env.t -> mark:mark -> modes:modes -> + shape:Shape.t -> loc:Location.t -> Env.t -> mark:bool -> modes:modes -> module_type -> module_type -> module_coercion * Shape.t val strengthened_module_decl: - loc:Location.t -> aliasable:bool -> Env.t -> mark:mark -> mmodes:modes -> + loc:Location.t -> aliasable:bool -> Env.t -> mark:bool -> mmodes:modes -> module_declaration -> Path.t -> module_declaration -> module_coercion val check_modtype_inclusion : @@ -176,21 +164,24 @@ val check_modtype_inclusion : val check_modtype_equiv: loc:Location.t -> Env.t -> Ident.t -> module_type -> module_type -> unit -val signatures: Env.t -> mark:mark -> modes:modes -> +val signatures: Env.t -> mark:bool -> modes:modes -> signature -> signature -> module_coercion -val include_functor_signatures : Env.t -> mark:mark -> +val include_functor_signatures : Env.t -> mark:bool -> signature -> signature -> (Ident.t * module_coercion) list +val check_implementation: Env.t -> modes:modes -> signature -> signature -> unit +(** Check an implementation against an interface *) + val compunit: - Env.t -> mark:mark -> string -> signature -> + Env.t -> mark:bool -> string -> signature -> string -> signature -> Shape.t -> module_coercion * Shape.t val compunit_as_argument: Env.t -> string -> signature -> string -> signature -> module_coercion val type_declarations: - loc:Location.t -> Env.t -> mark:mark -> + loc:Location.t -> Env.t -> mark:bool -> Ident.t -> type_declaration -> type_declaration -> unit val print_coercion: Format.formatter -> module_coercion -> unit diff --git a/typing/persistent_env.ml b/typing/persistent_env.ml index 5b21ff835a2..e0e1eb50426 100644 --- a/typing/persistent_env.ml +++ b/typing/persistent_env.ml @@ -349,7 +349,7 @@ let acknowledge_import penv ~check modname pers_sig = | Opaque -> register_import_as_opaque penv modname) flags; begin match kind, CU.get_current () with - | Normal { cmi_impl = imported_unit }, Some current_unit -> + | Normal { cmi_impl = imported_unit }, Some (current_unit, _) -> let access_allowed = CU.can_access_by_name imported_unit ~accessed_by:current_unit in @@ -500,7 +500,7 @@ let rec approximate_global_by_name penv global_name = let current_unit_is_aux name ~allow_args = match CU.get_current () with | None -> false - | Some current -> + | Some (current, _) -> match CU.to_global_name current with | Some { head; args } -> (args = [] || allow_args) diff --git a/typing/shape.ml b/typing/shape.ml index af15989695d..26dc7a1e5ce 100644 --- a/typing/shape.ml +++ b/typing/shape.ml @@ -16,7 +16,10 @@ module Uid = struct type t = | Compilation_unit of string - | Item of { comp_unit: string; id: int } + | Item of { + comp_unit: string; + id: int; + from: Compilation_unit.intf_or_impl } | Internal | Predef of string | Unboxed_version of t @@ -29,7 +32,10 @@ module Uid = struct | Compilation_unit s1, Compilation_unit s2 -> String.compare s1 s2 | Item c1, Item c2 -> let c = Int.compare c1.id c2.id in - if c <> 0 then c else String.compare c1.comp_unit c2.comp_unit + let c = + if c <> 0 then c else String.compare c1.comp_unit c2.comp_unit + in + if c <> 0 then c else Stdlib.compare c1.from c2.from | Internal, Internal -> 0 | Predef s1, Predef s2 -> String.compare s1 s2 | Unboxed_version t1, Unboxed_version t2 -> compare t1 t2 @@ -50,11 +56,16 @@ module Uid = struct let hash (x : t) = Hashtbl.hash x + let pp_intf_or_impl fmt = function + | Compilation_unit.Intf -> Format.pp_print_string fmt "[intf]" + | Compilation_unit.Impl -> () + let rec print fmt = function | Internal -> Format.pp_print_string fmt "" | Predef name -> Format.fprintf fmt "" name | Compilation_unit s -> Format.pp_print_string fmt s - | Item { comp_unit; id } -> Format.fprintf fmt "%s.%d" comp_unit id + | Item { comp_unit; id; from } -> + Format.fprintf fmt "%a%s.%d" pp_intf_or_impl from comp_unit id | Unboxed_version t -> Format.fprintf fmt "%a#" print t let output oc t = @@ -67,13 +78,13 @@ module Uid = struct let reinit () = id := (-1) let mk ~current_unit = - incr id; - let comp_unit = + let comp_unit, from = match current_unit with - | Some cu -> cu |> Compilation_unit.full_path_as_string - | None -> "" + | None -> "", Compilation_unit.Impl + | Some (cu, kind) -> Compilation_unit.full_path_as_string cu, kind in - Item { comp_unit; id = !id } + incr id; + Item { comp_unit; id = !id; from } let of_compilation_unit_id id = Compilation_unit (id |> Compilation_unit.full_path_as_string) diff --git a/typing/shape.mli b/typing/shape.mli index 53f0d818d47..37aec51de96 100644 --- a/typing/shape.mli +++ b/typing/shape.mli @@ -43,9 +43,9 @@ [cmt_format.cmt_uid_to_decl] table of the corresponding compilation unit. See: - - {{: https://icfp22.sigplan.org/details/mlfamilyworkshop-2022-papers/10/Module-Shapes-for-Modern-Tooling } + - {{:https://icfp22.sigplan.org/details/mlfamilyworkshop-2022-papers/10/Module-Shapes-for-Modern-Tooling} the design document} - - {{: https://www.lix.polytechnique.fr/Labo/Gabriel.Scherer/research/shapes/2022-ml-workshop-shapes-talk.pdf } + - {{:https://www.lix.polytechnique.fr/Labo/Gabriel.Scherer/research/shapes/2022-ml-workshop-shapes-talk.pdf} a talk about the reduction strategy *) @@ -57,14 +57,18 @@ module Uid : sig type t = private | Compilation_unit of string - | Item of { comp_unit: string; id: int } + | Item of { + comp_unit: string; + id: int; + from: Compilation_unit.intf_or_impl } | Internal | Predef of string | Unboxed_version of t val reinit : unit -> unit - val mk : current_unit:Compilation_unit.t option -> t + val mk : + current_unit:(Compilation_unit.with_kind) option -> t val of_compilation_unit_id : Compilation_unit.t -> t val of_compilation_unit_name : Compilation_unit.Name.t -> t val of_predef_id : Ident.t -> t diff --git a/typing/typemod.ml b/typing/typemod.ml index 741d198ca98..77c4360bad4 100644 --- a/typing/typemod.ml +++ b/typing/typemod.ml @@ -147,7 +147,7 @@ let extract_sig_functor_open funct_body env loc mty sig_acc = in let coercion = try - Includemod.include_functor_signatures ~mark:Mark_both env + Includemod.include_functor_signatures ~mark:true env sig_acc sg_param with Includemod.Error msg -> raise (Error(loc, env, Not_included_functor msg)) @@ -316,7 +316,7 @@ let check_type_decl env sg loc id row_id newdecl decl = | Some fresh_row_id -> Env.add_type ~check:false fresh_row_id newdecl env in let env = Env.add_signature sg env in - Includemod.type_declarations ~mark:Mark_both ~loc env fresh_id newdecl decl; + Includemod.type_declarations ~mark:true ~loc env fresh_id newdecl decl; ignore (Typedecl.check_coherence env loc path newdecl) let make_variance p n i = @@ -833,7 +833,7 @@ let merge_constraint initial_env loc sg lid constr = in let md'' = { md' with md_type = mty } in let newmd = Mtype.strengthen_decl ~aliasable:false md'' path in - ignore(Includemod.modtypes ~mark:Mark_both ~loc sig_env + ignore(Includemod.modtypes ~mark:true ~loc sig_env ~modes:(Legacy None) newmd.md_type md.md_type); return ~replace_by:(Some(Sig_module(id, pres, newmd, rs, priv))) @@ -843,7 +843,7 @@ let merge_constraint initial_env loc sg lid constr = let sig_env = Env.add_signature sg_for_env outer_sig_env in let aliasable = not (Env.is_functor_arg path sig_env) in ignore - (Includemod.strengthened_module_decl ~loc ~mark:Mark_both + (Includemod.strengthened_module_decl ~loc ~mark:true ~aliasable sig_env ~mmodes:(Legacy None) md' path md); real_ids := [Pident id]; return ~replace_by:None @@ -1732,7 +1732,7 @@ and transl_modtype_aux env smty = try ignore (Includemod.modtypes ~loc env ~modes:(Legacy None) - ~mark:Includemod.Mark_both md.md_type tmty.mty_type); + ~mark:true md.md_type tmty.mty_type); mkmty (Tmty_strengthen (tmty, path, mod_id)) (Mty_strengthen @@ -2426,7 +2426,7 @@ let check_recmodule_inclusion env bindings = let coercion, shape = try Includemod.modtypes_with_shape ~shape - ~loc:modl.mod_loc ~mark:Mark_both + ~loc:modl.mod_loc ~mark:true env ~modes:(Legacy None) mty_actual' mty_decl' with Includemod.Error msg -> raise(Error(modl.mod_loc, env, Not_included msg)) in @@ -2517,14 +2517,13 @@ let package_subtype env p1 fl1 p2 fl2 = | exception Error(_, _, Cannot_scrape_package_type _) -> false | mty1, mty2 -> let loc = Location.none in - match Includemod.modtypes ~loc ~mark:Mark_both env ~modes:All mty1 mty2 with + match Includemod.modtypes ~loc ~mark:true env ~modes:All mty1 mty2 with | Tcoerce_none -> true | _ | exception Includemod.Error _ -> false let () = Ctype.package_subtype := package_subtype let wrap_constraint_package env mark arg held_locks mty explicit = - let mark = if mark then Includemod.Mark_both else Includemod.Mark_neither in let mty1 = Subst.modtype Keep Subst.identity arg.mod_type in let mty2 = Subst.modtype Keep Subst.identity mty in let coercion = @@ -2540,7 +2539,6 @@ let wrap_constraint_package env mark arg held_locks mty explicit = let wrap_constraint_with_shape env mark arg held_locks mty shape explicit = - let mark = if mark then Includemod.Mark_both else Includemod.Mark_neither in let coercion, shape = try Includemod.modtypes_with_shape ~shape ~loc:arg.mod_loc env ~mark @@ -2896,7 +2894,7 @@ and type_one_application ~ctx:(apply_loc,sfunct,md_f,args) arg = Some { shape = arg_shape; path = arg_path; arg; held_locks } } -> let coercion = try Includemod.modtypes - ~loc:arg.mod_loc ~mark:Mark_both env arg.mod_type mty_param + ~loc:arg.mod_loc ~mark:true env arg.mod_type mty_param ~modes:(Legacy held_locks) with Includemod.Error _ -> apply_error () in @@ -2928,7 +2926,7 @@ and type_one_application ~ctx:(apply_loc,sfunct,md_f,args) in begin match Includemod.modtypes - ~loc:app_loc ~mark:Mark_neither env mty_res nondep_mty + ~loc:app_loc ~mark:false env mty_res nondep_mty ~modes:(Legacy None) with | Tcoerce_none -> () @@ -3860,7 +3858,7 @@ let type_implementation target modulename initial_env ast = old_arg_type = arg_type_from_cmi }); let coercion, shape = Profile.record_call "check_sig" (fun () -> - Includemod.compunit initial_env ~mark:Mark_positive + Includemod.compunit initial_env ~mark:true sourcefile sg compiled_intf_file_name dclsig shape) in (* Check the _mli_ against the argument type, since the mli determines @@ -3896,7 +3894,7 @@ let type_implementation target modulename initial_env ast = Warnings.Missing_mli; let coercion, shape = Profile.record_call "check_sig" (fun () -> - Includemod.compunit initial_env ~mark:Mark_positive + Includemod.compunit initial_env ~mark:true sourcefile sg "(inferred signature)" simple_sg shape) in check_nongen_signature finalenv simple_sg; @@ -4067,7 +4065,7 @@ let package_units initial_env objfiles target_cmi modulename = let name = Compilation_unit.to_global_name_without_prefix modulename in let dclsig = Env.read_signature name target_cmi in let cc, _shape = - Includemod.compunit initial_env ~mark:Mark_both + Includemod.compunit initial_env ~mark:true "(obtained by packing)" sg mli dclsig shape in Cmt_format.save_cmt (Unit_info.companion_cmt target_cmi) modulename diff --git a/utils/compilation_unit.ml b/utils/compilation_unit.ml index a172da7ab71..93ad77d762a 100644 --- a/utils/compilation_unit.ml +++ b/utils/compilation_unit.ml @@ -637,17 +637,25 @@ let print_debug ppf t = "@[(@[(for_pack_prefix@ %a)@]@;@[(name@ %a)@]" Prefix.print for_pack_prefix Name.print name +type intf_or_impl = + | Intf + | Impl + +type with_kind = t * intf_or_impl + let current = ref None let set_current t_opt = current := t_opt let get_current () = !current -let get_current_or_dummy () = Option.value !current ~default:dummy +let get_current_or_dummy () = + Option.value !current ~default:(dummy, Impl) |> fst let get_current_exn () = match !current with - | Some t -> t + | Some (t, _) -> t | None -> Misc.fatal_error "No compilation unit set" -let is_current t = match !current with None -> false | Some t' -> equal t t' +let is_current t = + match !current with None -> false | Some (t', _) -> equal t t' diff --git a/utils/compilation_unit.mli b/utils/compilation_unit.mli index 5e42151075a..d09aa94b511 100644 --- a/utils/compilation_unit.mli +++ b/utils/compilation_unit.mli @@ -297,9 +297,21 @@ type error = private (** The exception raised by conversion functions in this module. *) exception Error of error -val set_current : t option -> unit +(* CR ugerard: there might be a cleaner way to do that. Upstream this info is + part of a `Unit_info.t` record that is stored as the "current unit" in the + environement. But here in flambda-backend `Compilation_unit.t` instead. This + looks like conflicting refactorings that it would be useful to reconcile. -val get_current : unit -> t option + Here, for the prototype, we use a tuple to add that information. *) +type intf_or_impl = + | Intf + | Impl + +type with_kind = t * intf_or_impl + +val set_current : with_kind option -> unit + +val get_current : unit -> with_kind option val get_current_or_dummy : unit -> t