Skip to content

Commit 040e71a

Browse files
committed
Auto merge of rust-lang#116054 - matthiaskrgr:rollup-3pusno6, r=matthiaskrgr
Rollup of 7 pull requests Successful merges: - rust-lang#114379 (Command: also print removed env vars) - rust-lang#116034 (add UI test for delimiter errors) - rust-lang#116036 (tests/ui: Split large_moves.rs and move to lint/large_assignments) - rust-lang#116038 (Fall back to _SC_NPROCESSORS_ONLN if sched_getaffinity returns an empty mask) - rust-lang#116039 (Account for nested `impl Trait` in TAIT) - rust-lang#116041 (Add note to `is_known_rigid`) - rust-lang#116049 (give FutureIncompatibilityReason variants more explicit names) r? `@ghost` `@rustbot` modify labels: rollup
2 parents 9695dcf + fc02a0e commit 040e71a

File tree

5 files changed

+87
-8
lines changed

5 files changed

+87
-8
lines changed

std/src/process.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -789,7 +789,7 @@ impl Command {
789789
/// or [`Command::envs`]. In addition, it will prevent the spawned child process from inheriting
790790
/// any environment variable from its parent process.
791791
///
792-
/// After calling [`Command::env_remove`], the iterator from [`Command::get_envs`] will be
792+
/// After calling [`Command::env_clear`], the iterator from [`Command::get_envs`] will be
793793
/// empty.
794794
///
795795
/// You can use [`Command::env_remove`] to clear a single mapping.

std/src/process/tests.rs

Lines changed: 46 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -537,7 +537,7 @@ fn env_empty() {
537537
#[test]
538538
#[cfg(not(windows))]
539539
#[cfg_attr(any(target_os = "emscripten", target_env = "sgx"), ignore)]
540-
fn main() {
540+
fn debug_print() {
541541
const PIDFD: &'static str =
542542
if cfg!(target_os = "linux") { " create_pidfd: false,\n" } else { "" };
543543

@@ -623,6 +623,51 @@ fn main() {
623623
cwd: Some(
624624
"/some/path",
625625
),
626+
{PIDFD}}}"#
627+
)
628+
);
629+
630+
let mut command_with_removed_env = Command::new("boring-name");
631+
command_with_removed_env.env_remove("FOO").env_remove("BAR");
632+
assert_eq!(format!("{command_with_removed_env:?}"), r#"env -u BAR -u FOO "boring-name""#);
633+
assert_eq!(
634+
format!("{command_with_removed_env:#?}"),
635+
format!(
636+
r#"Command {{
637+
program: "boring-name",
638+
args: [
639+
"boring-name",
640+
],
641+
env: CommandEnv {{
642+
clear: false,
643+
vars: {{
644+
"BAR": None,
645+
"FOO": None,
646+
}},
647+
}},
648+
{PIDFD}}}"#
649+
)
650+
);
651+
652+
let mut command_with_cleared_env = Command::new("boring-name");
653+
command_with_cleared_env.env_clear().env("BAR", "val").env_remove("FOO");
654+
assert_eq!(format!("{command_with_cleared_env:?}"), r#"env -i BAR="val" "boring-name""#);
655+
assert_eq!(
656+
format!("{command_with_cleared_env:#?}"),
657+
format!(
658+
r#"Command {{
659+
program: "boring-name",
660+
args: [
661+
"boring-name",
662+
],
663+
env: CommandEnv {{
664+
clear: true,
665+
vars: {{
666+
"BAR": Some(
667+
"val",
668+
),
669+
}},
670+
}},
626671
{PIDFD}}}"#
627672
)
628673
);

std/src/sys/unix/process/process_common.rs

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -586,6 +586,23 @@ impl fmt::Debug for Command {
586586
if let Some(ref cwd) = self.cwd {
587587
write!(f, "cd {cwd:?} && ")?;
588588
}
589+
if self.env.does_clear() {
590+
write!(f, "env -i ")?;
591+
// Altered env vars will be printed next, that should exactly work as expected.
592+
} else {
593+
// Removed env vars need the command to be wrapped in `env`.
594+
let mut any_removed = false;
595+
for (key, value_opt) in self.get_envs() {
596+
if value_opt.is_none() {
597+
if !any_removed {
598+
write!(f, "env ")?;
599+
any_removed = true;
600+
}
601+
write!(f, "-u {} ", key.to_string_lossy())?;
602+
}
603+
}
604+
}
605+
// Altered env vars can just be added in front of the program.
589606
for (key, value_opt) in self.get_envs() {
590607
if let Some(value) = value_opt {
591608
write!(f, "{}={value:?} ", key.to_string_lossy())?;

std/src/sys/unix/thread.rs

Lines changed: 19 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -318,25 +318,38 @@ pub fn available_parallelism() -> io::Result<NonZeroUsize> {
318318
target_os = "solaris",
319319
target_os = "illumos",
320320
))] {
321+
#[allow(unused_assignments)]
322+
#[allow(unused_mut)]
323+
let mut quota = usize::MAX;
324+
321325
#[cfg(any(target_os = "android", target_os = "linux"))]
322326
{
323-
let quota = cgroups::quota().max(1);
327+
quota = cgroups::quota().max(1);
324328
let mut set: libc::cpu_set_t = unsafe { mem::zeroed() };
325329
unsafe {
326330
if libc::sched_getaffinity(0, mem::size_of::<libc::cpu_set_t>(), &mut set) == 0 {
327331
let count = libc::CPU_COUNT(&set) as usize;
328332
let count = count.min(quota);
329-
// reported to occur on MIPS kernels older than our minimum supported kernel version for those targets
330-
let count = NonZeroUsize::new(count)
331-
.expect("CPU count must be > 0. This may be a bug in sched_getaffinity(); try upgrading the kernel.");
332-
return Ok(count);
333+
334+
// According to sched_getaffinity's API it should always be non-zero, but
335+
// some old MIPS kernels were buggy and zero-initialized the mask if
336+
// none was explicitly set.
337+
// In that case we use the sysconf fallback.
338+
if let Some(count) = NonZeroUsize::new(count) {
339+
return Ok(count)
340+
}
333341
}
334342
}
335343
}
336344
match unsafe { libc::sysconf(libc::_SC_NPROCESSORS_ONLN) } {
337345
-1 => Err(io::Error::last_os_error()),
338346
0 => Err(io::const_io_error!(io::ErrorKind::NotFound, "The number of hardware threads is not known for the target platform")),
339-
cpus => Ok(unsafe { NonZeroUsize::new_unchecked(cpus as usize) }),
347+
cpus => {
348+
let count = cpus as usize;
349+
// Cover the unusual situation where we were able to get the quota but not the affinity mask
350+
let count = count.min(quota);
351+
Ok(unsafe { NonZeroUsize::new_unchecked(count) })
352+
}
340353
}
341354
} else if #[cfg(any(target_os = "freebsd", target_os = "dragonfly", target_os = "netbsd"))] {
342355
use crate::ptr;

std/src/sys_common/process.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -80,6 +80,10 @@ impl CommandEnv {
8080
self.vars.clear();
8181
}
8282

83+
pub fn does_clear(&self) -> bool {
84+
self.clear
85+
}
86+
8387
pub fn have_changed_path(&self) -> bool {
8488
self.saw_path || self.clear
8589
}

0 commit comments

Comments
 (0)