Skip to content

Commit

Permalink
signal: add SignalKind::info on illumos
Browse files Browse the repository at this point in the history
illumos has supported SIGINFO for a long time; see illumos/illumos-gate@19d32b9.
  • Loading branch information
sunshowers committed Dec 3, 2024
1 parent c07257f commit c69052a
Show file tree
Hide file tree
Showing 2 changed files with 53 additions and 2 deletions.
17 changes: 15 additions & 2 deletions tokio/src/signal/unix.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,13 +23,25 @@ pub(crate) type OsStorage = Box<[SignalInfo]>;
impl Init for OsStorage {
fn init() -> Self {
// There are reliable signals ranging from 1 to 33 available on every Unix platform.
#[cfg(not(target_os = "linux"))]
#[cfg(not(any(target_os = "linux", target_os = "illumos")))]
let possible = 0..=33;

// On Linux, there are additional real-time signals available.
#[cfg(target_os = "linux")]
let possible = 0..=libc::SIGRTMAX();

// On illumos, signal numbers go up to 41 (SIGINFO). The list of signals
// hasn't changed since 2013. See
// https://github.com/illumos/illumos-gate/blob/master/usr/src/uts/common/sys/iso/signal_iso.h.
//
// illumos also has real-time signals, but (a) the number of real-time
// signals is actually configurable at runtime and (b) this capability
// isn't exposed by libc as of 0.2.167, so we don't support them at the
// moment. If support for real-time signals on illumos is desired, this
// code would have to be changed to accommodate that.
#[cfg(target_os = "illumos")]
let possible = 0..=41;

possible.map(|_| SignalInfo::default()).collect()
}
}
Expand Down Expand Up @@ -130,7 +142,8 @@ impl SignalKind {
target_os = "freebsd",
target_os = "macos",
target_os = "netbsd",
target_os = "openbsd"
target_os = "openbsd",
target_os = "illumos"
))]
pub const fn info() -> Self {
Self(libc::SIGINFO)
Expand Down
38 changes: 38 additions & 0 deletions tokio/tests/signal_info.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
#![warn(rust_2018_idioms)]
#![cfg(feature = "full")]
#![cfg(any(
target_os = "dragonfly",
target_os = "freebsd",
target_os = "macos",
target_os = "netbsd",
target_os = "openbsd",
target_os = "illumos"
))]
#![cfg(not(miri))] // No `sigaction` on Miri

mod support {
pub mod signal;
}
use support::signal::send_signal;

use tokio::signal;
use tokio::signal::unix::SignalKind;
use tokio::sync::oneshot;

#[tokio::test]
async fn siginfo() {
let mut sig = signal::unix::signal(SignalKind::info()).expect("installed signal handler");

let (fire, wait) = oneshot::channel();

// NB: simulate a signal coming in by exercising our signal handler
// to avoid complications with sending SIGINFO to the test process
tokio::spawn(async {
wait.await.expect("wait failed");
send_signal(libc::SIGINFO);
});

let _ = fire.send(());

sig.recv().await.expect("received SIGINFO signal");
}

0 comments on commit c69052a

Please sign in to comment.