"sandwich" rlibs between native deps in linker order #1333
Merged
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
This is part of the work on #1268.
Consider a case where we have a rust binary B that depends on a rust library R that depends on a native library N. With a recent nightly rustc that passes the native library via
-l
to the linker (not using--whole-archive
as it used to) and a linker that checks for backward references, we can run into backward reference errors when N appears before R on the linker invocation. Example at rust-lang/rust#81490 (comment).We came up with two approaches to deal with such cases: a "sandwich" one and one where we'd pass appropriate
-l
flags to rustc when building rust_libraries. This PR implements the "sandwich" one.Under the "sandwich" approach, we modify the rustc command link for building B in a way that the native libraries section on the linker invocation is repeated once more after the rlib section:
By doing this, we allow the linker to resolve a dependency from an rlib to a native lib from
Y
toZ
.This should allow us to remove the
experimental_use_whole_archive_for_native_deps
stopgap feature, while additionally allowing us to take advantage of the new rustc no-whole-archive behaviour.The approach to pass appropriate
-l
when building rust_libraries also seems plausible, but we've got some concerns about scaling in some cases, e.g., where we have deeply nested "ladder-like" dependency graphs composed of mixed rust and native libraries. Embedding the transitive set of native library names in the rlib also means we may need to build multiple variants of rlibs to work, e.g., in pic/no-pic mode, whereas now a single rlib is sufficient for both modes. We'll continue to investigate.