Skip to content

Commit

Permalink
Merge pull request #136 from ecnelises/aix
Browse files Browse the repository at this point in the history
Support AIX signal handler types
  • Loading branch information
vorner authored Feb 11, 2023
2 parents a4d5e35 + 5dc385f commit 1b8cafa
Show file tree
Hide file tree
Showing 4 changed files with 28 additions and 5 deletions.
8 changes: 7 additions & 1 deletion signal-hook-registry/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,10 @@ impl Slot {
fn new(signal: libc::c_int) -> Result<Self, Error> {
// C data structure, expected to be zeroed out.
let mut new: libc::sigaction = unsafe { mem::zeroed() };
new.sa_sigaction = handler as usize;
#[cfg(not(target_os = "aix"))]
{ new.sa_sigaction = handler as usize; }
#[cfg(target_os = "aix")]
{ new.sa_union.__su_sigaction = handler; }
// Android is broken and uses different int types than the rest (and different depending on
// the pointer width). This converts the flags to the proper type no matter what it is on
// the given platform.
Expand Down Expand Up @@ -232,7 +235,10 @@ impl Prev {

#[cfg(not(windows))]
unsafe fn execute(&self, sig: c_int, info: *mut siginfo_t, data: *mut c_void) {
#[cfg(not(target_os = "aix"))]
let fptr = self.info.sa_sigaction;
#[cfg(target_os = "aix")]
let fptr = self.info.sa_union.__su_sigaction as usize;
if fptr != 0 && fptr != libc::SIG_DFL && fptr != libc::SIG_IGN {
// Android is broken and uses different int types than the rest (and different
// depending on the pointer width). This converts the flags to the proper type no
Expand Down
6 changes: 5 additions & 1 deletion src/iterator/backend.rs
Original file line number Diff line number Diff line change
Expand Up @@ -309,11 +309,15 @@ where
// should not be something like closed file descriptor. It could EAGAIN, but
// that's OK in case we say MSG_DONTWAIT. If it's EINTR, then it's OK too,
// it'll only create a spurious wakeup.
#[cfg(target_os = "aix")]
let nowait_flag = libc::MSG_NONBLOCK;
#[cfg(not(target_os = "aix"))]
let nowait_flag = libc::MSG_DONTWAIT;
while libc::recv(
self.read.as_raw_fd(),
buff.as_mut_ptr() as *mut libc::c_void,
SIZE,
libc::MSG_DONTWAIT,
nowait_flag,
) > 0
{}
}
Expand Down
9 changes: 7 additions & 2 deletions src/low_level/pipe.rs
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,11 @@ use libc::{self, c_int};

use crate::SigId;

#[cfg(target_os = "aix")]
const MSG_NOWAIT: i32 = libc::MSG_NONBLOCK;
#[cfg(not(target_os = "aix"))]
const MSG_NOWAIT: i32 = libc::MSG_DONTWAIT;

#[derive(Copy, Clone)]
pub(crate) enum WakeMethod {
Send,
Expand Down Expand Up @@ -141,7 +146,7 @@ pub(crate) fn wake(pipe: RawFd, method: WakeMethod) {
let data = b"X" as *const _ as *const _;
match method {
WakeMethod::Write => libc::write(pipe, data, 1),
WakeMethod::Send => libc::send(pipe, data, 1, libc::MSG_DONTWAIT),
WakeMethod::Send => libc::send(pipe, data, 1, MSG_NOWAIT),
};
}
}
Expand Down Expand Up @@ -170,7 +175,7 @@ pub(crate) fn wake(pipe: RawFd, method: WakeMethod) {
/// * If it is not possible, the [`O_NONBLOCK`][libc::O_NONBLOCK] will be set on the file
/// descriptor and [`write`][libc::write] will be used instead.
pub fn register_raw(signal: c_int, pipe: RawFd) -> Result<SigId, Error> {
let res = unsafe { libc::send(pipe, &[] as *const _, 0, libc::MSG_DONTWAIT) };
let res = unsafe { libc::send(pipe, &[] as *const _, 0, MSG_NOWAIT) };
let fd = match (res, Error::last_os_error().kind()) {
(0, _) | (-1, ErrorKind::WouldBlock) => WakeFd {
fd: pipe,
Expand Down
10 changes: 9 additions & 1 deletion src/low_level/signal_details.rs
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,15 @@ fn restore_default(signal: c_int) -> Result<(), Error> {
unsafe {
// A C structure, supposed to be memset to 0 before use.
let mut action: libc::sigaction = mem::zeroed();
action.sa_sigaction = libc::SIG_DFL as _;
#[cfg(target_os = "aix")]
{
action.sa_union.__su_sigaction = mem::transmute::<
usize,
extern "C" fn(libc::c_int, *mut libc::siginfo_t, *mut libc::c_void),
>(libc::SIG_DFL);
}
#[cfg(not(target_os = "aix"))]
{ action.sa_sigaction = libc::SIG_DFL as _; }
if libc::sigaction(signal, &action, ptr::null_mut()) == 0 {
Ok(())
} else {
Expand Down

0 comments on commit 1b8cafa

Please sign in to comment.