1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
// src/signal.rs
//! Provides signal handling for graceful shutdown.
use crateCancellationToken;
use ;
/// Sets up a handler for Ctrl+C (SIGINT).
///
/// This function registers a handler that listens for the interrupt signal.
/// When the signal is caught, it flips the value of the returned `AtomicBool`
/// from `true` to `false`. Long-running operations in the application can
/// periodically check this boolean to gracefully terminate.
///
/// # Returns
/// A `CancellationToken` that will be cancelled when the signal is caught.
///
/// # Errors
/// Returns an error if the signal handler cannot be set.
///
/// # Examples
///
/// ```no_run
/// use dircat::signal::setup_signal_handler;
/// use std::thread;
/// use std::time::Duration;
///
/// # fn main() -> anyhow::Result<()> {
/// // In a real app, you would call this once at the start.
/// let token = setup_signal_handler()?;
///
/// // Simulate a long-running task
/// while !token.is_cancelled() {
/// println!("Working...");
/// thread::sleep(Duration::from_secs(1));
/// }
///
/// println!("Work cancelled, shutting down.");
/// # Ok(())
/// # }
/// ```
// Note: Testing signal handlers directly is complex and often skipped
// or handled via integration tests that send signals to the process.