Skip to content

Commit 6a3005f

Browse files
Auto merge of #148105 - Noratrieb:personality-panicking, r=<try>
Ensure the personality does not panic try-job: x86_64-msvc-1 try-job: i686-msvc-1 try-job: x86_64-mingw-1 try-job: test-various try-job: armhf-gnu try-job: aarch64-apple
2 parents a8664a1 + 82ad235 commit 6a3005f

File tree

7 files changed

+46
-17
lines changed

7 files changed

+46
-17
lines changed

library/std/src/sys/personality/gcc.rs

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,9 +37,12 @@
3737
//! and the last personality routine transfers control to the catch block.
3838
#![forbid(unsafe_op_in_unsafe_fn)]
3939

40+
mod dwarf;
41+
mod eh;
42+
4043
use unwind as uw;
4144

42-
use super::dwarf::eh::{self, EHAction, EHContext};
45+
use self::eh::{EHAction, EHContext};
4346
use crate::ffi::c_int;
4447

4548
// Register ids were lifted from LLVM's TargetLowering::getExceptionPointerRegister()
@@ -332,8 +335,7 @@ unsafe fn find_eh_action(context: *mut uw::_Unwind_Context) -> Result<EHAction,
332335
// `ip = -1` has special meaning, so use wrapping sub to allow for that
333336
ip: if ip_before_instr != 0 { ip } else { ip.wrapping_sub(1) },
334337
func_start: uw::_Unwind_GetRegionStart(context),
335-
get_text_start: &|| uw::_Unwind_GetTextRelBase(context),
336-
get_data_start: &|| uw::_Unwind_GetDataRelBase(context),
338+
raw_context: context,
337339
};
338340
eh::find_eh_action(lsda, &eh_context)
339341
}

library/std/src/sys/personality/dwarf/mod.rs renamed to library/std/src/sys/personality/gcc/dwarf.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,6 @@
1010
#[cfg(test)]
1111
mod tests;
1212

13-
pub mod eh;
14-
1513
pub struct DwarfReader {
1614
pub ptr: *const u8,
1715
}

library/std/src/sys/personality/dwarf/eh.rs renamed to library/std/src/sys/personality/gcc/eh.rs

Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,9 @@
1414

1515
use core::ptr;
1616

17-
use super::DwarfReader;
17+
use unwind as uw;
18+
19+
use super::dwarf::DwarfReader;
1820

1921
pub const DW_EH_PE_omit: u8 = 0xFF;
2022
pub const DW_EH_PE_absptr: u8 = 0x00;
@@ -37,11 +39,10 @@ pub const DW_EH_PE_aligned: u8 = 0x50;
3739
pub const DW_EH_PE_indirect: u8 = 0x80;
3840

3941
#[derive(Copy, Clone)]
40-
pub struct EHContext<'a> {
41-
pub ip: *const u8, // Current instruction pointer
42-
pub func_start: *const u8, // Pointer to the current function
43-
pub get_text_start: &'a dyn Fn() -> *const u8, // Get pointer to the code section
44-
pub get_data_start: &'a dyn Fn() -> *const u8, // Get pointer to the data section
42+
pub struct EHContext {
43+
pub(crate) ip: *const u8, // Current instruction pointer
44+
pub(crate) func_start: *const u8, // Pointer to the current function
45+
pub(crate) raw_context: *mut uw::_Unwind_Context,
4546
}
4647

4748
/// Landing pad.
@@ -63,7 +64,7 @@ pub enum EHAction {
6364
pub const USING_SJLJ_EXCEPTIONS: bool =
6465
cfg!(all(target_vendor = "apple", not(target_os = "watchos"), target_arch = "arm"));
6566

66-
pub unsafe fn find_eh_action(lsda: *const u8, context: &EHContext<'_>) -> Result<EHAction, ()> {
67+
pub unsafe fn find_eh_action(lsda: *const u8, context: &EHContext) -> Result<EHAction, ()> {
6768
if lsda.is_null() {
6869
return Ok(EHAction::None);
6970
}
@@ -224,7 +225,7 @@ unsafe fn read_encoded_offset(reader: &mut DwarfReader, encoding: u8) -> Result<
224225
/// [LSB-dwarf-ext]: https://refspecs.linuxfoundation.org/LSB_5.0.0/LSB-Core-generic/LSB-Core-generic/dwarfext.html
225226
unsafe fn read_encoded_pointer(
226227
reader: &mut DwarfReader,
227-
context: &EHContext<'_>,
228+
context: &EHContext,
228229
encoding: u8,
229230
) -> Result<*const u8, ()> {
230231
if encoding == DW_EH_PE_omit {
@@ -241,8 +242,8 @@ unsafe fn read_encoded_pointer(
241242
}
242243
context.func_start
243244
}
244-
DW_EH_PE_textrel => (*context.get_text_start)(),
245-
DW_EH_PE_datarel => (*context.get_data_start)(),
245+
DW_EH_PE_textrel => unsafe { uw::_Unwind_GetTextRelBase(context.raw_context) },
246+
DW_EH_PE_datarel => unsafe { uw::_Unwind_GetDataRelBase(context.raw_context) },
246247
// aligned means the value is aligned to the size of a pointer
247248
DW_EH_PE_aligned => {
248249
reader.ptr = reader.ptr.with_addr(round_up(reader.ptr.addr(), size_of::<*const u8>())?);

library/std/src/sys/personality/mod.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,6 @@
1010
//! Additionally, ARM EHABI uses the personality function when generating
1111
//! backtraces.
1212
13-
mod dwarf;
14-
1513
#[cfg(not(any(test, doctest)))]
1614
cfg_select! {
1715
target_os = "emscripten" => {
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
#![crate_type = "cdylib"]
2+
3+
pub extern "C" fn add(a: u64, b: u64) -> u64 {
4+
a + b
5+
}
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
// This ensures that a cdylib that uses std and panic=unwind but does not
2+
// have any panics itself will not have *any* panic-related code in the final
3+
// binary, at least when using fat LTO
4+
// (since all the necessary nounwind propagation requires fat LTO).
5+
//
6+
// This code used to be pulled in via a landing pad in the personality function,
7+
// (since that is `extern "C"` and therefore panics if something unwinds), so
8+
// if this failed because you modified the personality function, ensure it contains
9+
// no potentially unwinding calls.
10+
11+
use run_make_support::{dynamic_lib_name, llvm_nm, rustc};
12+
13+
fn main() {
14+
rustc().input("add.rs").edition("2024").lto("fat").opt_level("3").run();
15+
16+
llvm_nm()
17+
.input(dynamic_lib_name("add"))
18+
.run()
19+
// a collection of panic-related strings. if this appears in the output
20+
// for other reasons than having panic symbols, I am sorry.
21+
.assert_stdout_not_contains("panic")
22+
.assert_stdout_not_contains("addr2line")
23+
.assert_stdout_not_contains("backtrace")
24+
.assert_stdout_not_contains("gimli");
25+
}

0 commit comments

Comments
 (0)