Skip to content

Commit 10e5363

Browse files
committed
Auto merge of #100782 - thomcc:fix-android-sigaddset, r=Mark-Simulacrum
Align android `sigaddset` impl with the reference impl from Bionic In rust-lang/rust#100737 I noticed we were treating the sigset_t as an array of bytes, while referencing code from android (https://github.com/aosp-mirror/platform_bionic/blob/ad8dcd6023294b646e5a8288c0ed431b0845da49/libc/include/android/legacy_signal_inlines.h) which treats it as an array of unsigned long. That said, the behavior difference is so subtle here that it's not hard to see why nobody noticed. This fixes the implementation to be equivalent to the one in bionic.
2 parents 12b491a + 770b2c3 commit 10e5363

File tree

1 file changed

+23
-3
lines changed

1 file changed

+23
-3
lines changed

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

+23-3
Original file line numberDiff line numberDiff line change
@@ -45,11 +45,31 @@ cfg_if::cfg_if! {
4545
}
4646
#[allow(dead_code)]
4747
pub unsafe fn sigaddset(set: *mut libc::sigset_t, signum: libc::c_int) -> libc::c_int {
48-
use crate::{slice, mem};
48+
use crate::{
49+
mem::{align_of, size_of},
50+
slice,
51+
};
52+
use libc::{c_ulong, sigset_t};
53+
54+
// The implementations from bionic (android libc) type pun `sigset_t` as an
55+
// array of `c_ulong`. This works, but lets add a smoke check to make sure
56+
// that doesn't change.
57+
const _: () = assert!(
58+
align_of::<c_ulong>() == align_of::<sigset_t>()
59+
&& (size_of::<sigset_t>() % size_of::<c_ulong>()) == 0
60+
);
4961

50-
let raw = slice::from_raw_parts_mut(set as *mut u8, mem::size_of::<libc::sigset_t>());
5162
let bit = (signum - 1) as usize;
52-
raw[bit / 8] |= 1 << (bit % 8);
63+
if set.is_null() || bit >= (8 * size_of::<sigset_t>()) {
64+
crate::sys::unix::os::set_errno(libc::EINVAL);
65+
return -1;
66+
}
67+
let raw = slice::from_raw_parts_mut(
68+
set as *mut c_ulong,
69+
size_of::<sigset_t>() / size_of::<c_ulong>(),
70+
);
71+
const LONG_BIT: usize = size_of::<c_ulong>() * 8;
72+
raw[bit / LONG_BIT] |= 1 << (bit % LONG_BIT);
5373
return 0;
5474
}
5575
} else {

0 commit comments

Comments
 (0)