@@ -217,7 +217,7 @@ impl<'a> Toolchain<'a> {
217
217
new_path. push ( PathBuf :: from ( "/usr/lib" ) ) ;
218
218
}
219
219
220
- env_var:: prepend_path ( sysenv:: LOADER_PATH , new_path, cmd, self . cfg . process ) ;
220
+ env_var:: insert_path ( sysenv:: LOADER_PATH , new_path, None , cmd, self . cfg . process ) ;
221
221
222
222
// Prepend CARGO_HOME/bin to the PATH variable so that we're sure to run
223
223
// cargo/rustc via the proxy bins. There is no fallback case for if the
@@ -228,30 +228,50 @@ impl<'a> Toolchain<'a> {
228
228
path_entries. push ( cargo_home. join ( "bin" ) ) ;
229
229
}
230
230
231
- // Historically rustup included the bin directory in PATH to
232
- // work around some bugs (see
233
- // https://github.com/rust-lang/rustup/pull/3178 for more
234
- // information). This shouldn't be needed anymore, and it causes
231
+ // On Windows, we append the "bin" directory to PATH by default.
232
+ // Windows loads DLLs from PATH and the "bin" directory contains DLLs
233
+ // that proc macros and other tools not in the sysroot use.
234
+ // It's appended rather than prepended so that the exe files in "bin"
235
+ // do not take precedence over anything else in PATH.
236
+ //
237
+ // Historically rustup prepended the bin directory in PATH but doing so causes
235
238
// problems because calling tools recursively (like `cargo
236
239
// +nightly metadata` from within a cargo subcommand). The
237
240
// recursive call won't work because it is not executing the
238
241
// proxy, so the `+` toolchain override doesn't work.
242
+ // See: https://github.com/rust-lang/rustup/pull/3178
239
243
//
240
- // The RUSTUP_WINDOWS_PATH_ADD_BIN env var was added to opt-in to
241
- // testing the fix. The default is now off, but this is left here
242
- // just in case there are problems. Consider removing in the
243
- // future if it doesn't seem necessary.
244
- #[ cfg( target_os = "windows" ) ]
245
- if self
246
- . cfg
247
- . process
248
- . var_os ( "RUSTUP_WINDOWS_PATH_ADD_BIN" )
249
- . is_some_and ( |s| s == "1" )
250
- {
251
- path_entries. push ( self . path . join ( "bin" ) ) ;
252
- }
244
+ // This behaviour was then changed to not add the bin directory at all.
245
+ // But this caused another set of problems due to the sysroot DLLs
246
+ // not being found by the loader, e.g. for proc macros.
247
+ // See: https://github.com/rust-lang/rustup/issues/3825
248
+ //
249
+ // Which is how we arrived at the current default described above.
250
+ //
251
+ // The `RUSTUP_WINDOWS_PATH_ADD_BIN` environment variable allows
252
+ // users to opt-in to one of the old behaviours in case the new
253
+ // default causes any new issues.
254
+ //
255
+ // FIXME: The `RUSTUP_WINDOWS_PATH_ADD_BIN` environment variable can
256
+ // be removed once we're confident that the default behaviour works.
257
+ let append = if cfg ! ( target_os = "windows" ) {
258
+ let add_bin = self . cfg . process . var ( "RUSTUP_WINDOWS_PATH_ADD_BIN" ) ;
259
+ match add_bin. as_deref ( ) . unwrap_or ( "append" ) {
260
+ // Don't add to PATH at all
261
+ "0" => None ,
262
+ // Prepend to PATH
263
+ "1" => {
264
+ path_entries. push ( self . path . join ( "bin" ) ) ;
265
+ None
266
+ }
267
+ // Append to PATH (the default)
268
+ _ => Some ( self . path . join ( "bin" ) ) ,
269
+ }
270
+ } else {
271
+ None
272
+ } ;
253
273
254
- env_var:: prepend_path ( "PATH" , path_entries, cmd, self . cfg . process ) ;
274
+ env_var:: insert_path ( "PATH" , path_entries, append , cmd, self . cfg . process ) ;
255
275
}
256
276
257
277
/// Infallible function that describes the version of rustc in an installed distribution
0 commit comments