Rollup merge of #85920 - luqmana:wasm-linker-tweaks, r=petrochenkov

Tweak wasm_base target spec to indicate linker is not GNU and update linker inferring logic for wasm-ld.

Reported via [Zulip](https://rust-lang.zulipchat.com/#narrow/stream/131828-t-compiler/topic/wasi.20linker.20unknown.20argument.3A.20--as-needed): we try passing `--as-needed` to the linker if it's GNU ld which `wasm-ld` is not. Usually this isn't an issue for wasm as we would use the WasmLd linker driver but because the linker in question (`wasm32-unknown-wasi-wasm-ld`) ended with `-ld` our linker inferring [logic](f64503eb55/compiler/rustc_codegen_ssa/src/back/link.rs (L957-L1040)) used the `GccLinker` implementations. (UPD: The linker inferring logic actually didn't apply in this case because the linker is actually invoked through gcc in the reported issue. But it's still worth updating the logic I think.)

This change then has 2 parts:
1. Update wasm_base target spec to indicate `linker_is_gnu: false` plus a few additions of `target.is_like_wasm` to handle flags `wasm-ld` does in fact support.
2. Improve the linker detection logic to properly determine the correct flavor of wasm linker we're using when we can.

We need to add the new `target.is_like_wasm` branches to handle the case where the "linker" used could be something like clang which would then under the hood call wasm-ld.
This commit is contained in:
Yuki Okushi 2021-06-06 19:11:18 +09:00 committed by GitHub
commit 679a1d1ac1
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 8 additions and 3 deletions

View file

@ -1199,6 +1199,8 @@ fn linker_and_flavor(sess: &Session) -> (PathBuf, LinkerFlavor) {
|| stem.ends_with("-clang")
{
LinkerFlavor::Gcc
} else if stem == "wasm-ld" || stem.ends_with("-wasm-ld") {
LinkerFlavor::Lld(LldFlavor::Wasm)
} else if stem == "ld" || stem == "ld.lld" || stem.ends_with("-ld") {
LinkerFlavor::Ld
} else if stem == "link" || stem == "lld-link" {

View file

@ -476,7 +476,9 @@ impl<'a> Linker for GccLinker<'a> {
// eliminate the metadata. If we're building an executable, however,
// --gc-sections drops the size of hello world from 1.8MB to 597K, a 67%
// reduction.
} else if self.sess.target.linker_is_gnu && !keep_metadata {
} else if (self.sess.target.linker_is_gnu || self.sess.target.is_like_wasm)
&& !keep_metadata
{
self.linker_arg("--gc-sections");
}
}
@ -484,13 +486,13 @@ impl<'a> Linker for GccLinker<'a> {
fn no_gc_sections(&mut self) {
if self.sess.target.is_like_osx {
self.linker_arg("-no_dead_strip");
} else if self.sess.target.linker_is_gnu {
} else if self.sess.target.linker_is_gnu || self.sess.target.is_like_wasm {
self.linker_arg("--no-gc-sections");
}
}
fn optimize(&mut self) {
if !self.sess.target.linker_is_gnu {
if !self.sess.target.linker_is_gnu && !self.sess.target.is_like_wasm {
return;
}

View file

@ -102,6 +102,7 @@ pub fn options() -> TargetOptions {
// we use the LLD shipped with the Rust toolchain by default
linker: Some("rust-lld".to_owned()),
lld_flavor: LldFlavor::Wasm,
linker_is_gnu: false,
pre_link_args,