From 510992a924f343a8e6bb574a57cf706c3099ee47 Mon Sep 17 00:00:00 2001 From: David Allsopp Date: Thu, 17 Oct 2024 13:18:35 +0100 Subject: [PATCH] Fix inclusion of libraries when partial linking ld -r (certainly in GNU binutils) has an empty search path - co-opt the MSVC search code and always resolve libraries when partial linking, except this time _ignore_ the ones which are missing. This seems to fit the rest of -output-complete-obj, given that the _standard_ C libraries are also omitted (-lm, -lpthread, etc.) --- testsuite/tools/test_in_prefix.ml | 11 ++++------- utils/ccomp.ml | 30 +++++++++++++++++------------- 2 files changed, 21 insertions(+), 20 deletions(-) diff --git a/testsuite/tools/test_in_prefix.ml b/testsuite/tools/test_in_prefix.ml index 32425a055012..78bacbadbb5c 100644 --- a/testsuite/tools/test_in_prefix.ml +++ b/testsuite/tools/test_in_prefix.ml @@ -865,14 +865,11 @@ let compile_test ~original env bindir = | Output_complete_obj(C_ocamlc, Shared) -> true, false, ["-output-complete-obj"], true, None | Output_complete_obj(C_ocamlopt, Static) -> - (* At the moment, the partial linker will pass -lzstd to ld -r which - will (normally) fail). Until this is done, pass the libraries - manually. *) - false, true, ["-output-complete-obj"; "-noautolink"], true, - Some ocamlcommon_native_c_libraries + false, true, ["-output-complete-obj"], true, + Some Config.comprmarsh_c_libraries | Output_complete_obj(C_ocamlopt, Shared) -> - true, true, ["-output-complete-obj"; "-noautolink"], true, - Some ocamlcommon_native_c_libraries + true, true, ["-output-complete-obj"], true, + Some Config.comprmarsh_c_libraries | Output_complete_exe Static -> false, false, ["-output-complete-exe"], false, None | Output_complete_exe Shared -> diff --git a/utils/ccomp.ml b/utils/ccomp.ml index defe4d2a4b92..96dd7ade1c1a 100644 --- a/utils/ccomp.ml +++ b/utils/ccomp.ml @@ -147,16 +147,15 @@ let create_archive archive file_list = (quote_files ~response_files:Config.ar_supports_response_files file_list)) -let expand_libname cclibs = - cclibs |> List.map (fun cclib -> - if String.starts_with ~prefix:"-l" cclib then - let libname = - "lib" ^ String.sub cclib 2 (String.length cclib - 2) ^ Config.ext_lib in - try - Load_path.find libname - with Not_found -> - libname - else cclib) +let expand_libname cclib = + if String.starts_with ~prefix:"-l" cclib then + let libname = + "lib" ^ String.sub cclib 2 (String.length cclib - 2) ^ Config.ext_lib in + try + Some (Load_path.find libname) + with Not_found -> + None + else Some cclib type link_mode = | Exe @@ -176,11 +175,16 @@ let call_linker mode output_name files extra = Profile.record_call "c-linker" (fun () -> let cmd = if mode = Partial then - let (l_prefix, files) = + let l_prefix = match Config.ccomp_type with - | "msvc" -> ("/libpath:", expand_libname files) - | _ -> ("-L", files) + | "msvc" -> "/libpath:" + | _ -> "-L" in + (* For partial linking, only include -llib if -llib can be found in the + current search path. For ld -r, this PATH is (usually) limited to the + -L directories. This should cause OCaml libraries to be linked, but + not any system libraries mentioned in .cma/.cmxa files. *) + let files = List.filter_map expand_libname files in Printf.sprintf "%s%s %s %s %s" Config.native_pack_linker (Filename.quote output_name)