jmp_scape/glibc_compat.rs
1use core::marker::PhantomData;
2
3// glibc `__jmp_buf` is architecture-specific (see e.g. sysdeps/*/bits/setjmp.h).
4// Linux aarch64 uses `unsigned long long __jmp_buf[22]`; x86_64 uses `long long[8]`.
5// This module is only used as `struct_defs` on Linux (`lib.rs`); other OSes still
6// compile it with a placeholder length.
7#[cfg(all(target_os = "linux", target_arch = "aarch64"))]
8const JMP_BUF_U64_LEN: usize = 22;
9#[cfg(all(target_os = "linux", not(target_arch = "aarch64")))]
10const JMP_BUF_U64_LEN: usize = 8;
11#[cfg(not(target_os = "linux"))]
12const JMP_BUF_U64_LEN: usize = 8;
13
14/// `JmpBufFields` are the accessible fields when viewed via a JmpBuf pointer.
15/// But also: You shouldn't be poking at these!
16#[repr(C)]
17pub struct JmpBufFields {
18 _buf: [u64; JMP_BUF_U64_LEN],
19 _neither_send_nor_sync: PhantomData<*const u8>,
20}
21
22/// `SigJmpBufFields` are the accessible fields when viewed via a SigJmpBuf pointer.
23/// But also: You shouldn't be poking at these!
24#[repr(C)]
25pub struct SigJmpBufFields {
26 // This *must* be the first field. We allow `SigJmpBuf` to be transmuted to
27 // a `JmpBuf` and then back again depending on the host libc. (e.g. glibc
28 // has setjmp as a shallow wrapper around sigsetjmp, and will write to
29 // fields past the `__jmp_buf`).
30 __jmp_buf: JmpBufFields,
31 __mask_was_saved: isize,
32 __saved_mask: libc::sigset_t,
33}
34
35/// This is the type you use to allocate a JmpBuf on the stack.
36/// (Glibc puns the two.)
37pub type JmpBufStruct = SigJmpBufFields;
38
39/// This is the type you use to allocate a SigJmpBuf on the stack.
40pub type SigJmpBufStruct = SigJmpBufFields;