diff --git a/Cargo.toml b/Cargo.toml index 23807c7ad4..3e8a74df81 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -163,6 +163,16 @@ wildcard_imports = "warn" name = "rustup" path = "src/lib.rs" +[[bin]] +name = "rustup-init" +path = "src/bin/rustup-init.rs" +# The binary has no unit tests or benchmarks. Its empty test and bench harnesses +# would otherwise be linked with the binary's delay-load list (see `build.rs`) but +# without the code that imports those DLLs, which `/WX` turns into a link error +# (LNK4199). +test = false +bench = false + [profile.release] codegen-units = 1 lto = true diff --git a/build.rs b/build.rs index e6e6a69197..07bca81f20 100644 --- a/build.rs +++ b/build.rs @@ -70,6 +70,16 @@ fn main() { for dll in delay_load_dlls { println!("cargo::rustc-link-arg-bin=rustup-init=/delayload:{dll}.dll"); } + // Also delay load system DLLs that the proxies never call. Every `cargo`, + // `rustc` etc. started through rustup is a separate process on Windows, and + // each of these DLLs (with what it pulls in, such as gdi32 for user32) costs + // start-up time when it is loaded eagerly. + let delay_load_for_startup = [ + "user32", "shell32", "ole32", "oleaut32", "crypt32", "secur32", "ws2_32", + ]; + for dll in delay_load_for_startup { + println!("cargo::rustc-link-arg-bin=rustup-init=/delayload:{dll}.dll"); + } // When using delayload, it's necessary to also link delayimp.lib // https://learn.microsoft.com/en-us/cpp/build/reference/dependentloadflag?view=msvc-170 println!("cargo::rustc-link-arg-bin=rustup-init=delayimp.lib");