From 1a9fc18e830dc57731e2976edb5c5f0fabc5019c Mon Sep 17 00:00:00 2001 From: Ralf Jung <post@ralfj.de> Date: Mon, 9 Mar 2020 11:16:23 +0100 Subject: [PATCH] panic_bounds_check: use caller_location, like PanicFnLangItem --- src/libcore/panicking.rs | 18 ++++++++++++++++++ src/librustc_codegen_ssa/mir/block.rs | 6 +++++- 2 files changed, 23 insertions(+), 1 deletion(-) diff --git a/src/libcore/panicking.rs b/src/libcore/panicking.rs index 61b764f2d62..d58a7cfec95 100644 --- a/src/libcore/panicking.rs +++ b/src/libcore/panicking.rs @@ -52,6 +52,24 @@ pub fn panic(expr: &str) -> ! { panic_fmt(fmt::Arguments::new_v1(&[expr], &[]), Location::caller()) } +#[cfg(not(bootstrap))] +#[cold] +#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never))] +#[track_caller] +#[lang = "panic_bounds_check"] // needed by codegen for panic on OOB array/slice access +fn panic_bounds_check(index: usize, len: usize) -> ! { + if cfg!(feature = "panic_immediate_abort") { + unsafe { super::intrinsics::abort() } + } + + panic_fmt( + format_args!("index out of bounds: the len is {} but the index is {}", len, index), + Location::caller(), + ) +} + +// For bootstrap, we need a variant with the old argument order. +#[cfg(bootstrap)] #[cold] #[cfg_attr(not(feature = "panic_immediate_abort"), inline(never))] #[lang = "panic_bounds_check"] // needed by codegen for panic on OOB array/slice access diff --git a/src/librustc_codegen_ssa/mir/block.rs b/src/librustc_codegen_ssa/mir/block.rs index a1b54607b80..f22c0216a78 100644 --- a/src/librustc_codegen_ssa/mir/block.rs +++ b/src/librustc_codegen_ssa/mir/block.rs @@ -415,11 +415,15 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> { AssertKind::BoundsCheck { ref len, ref index } => { let len = self.codegen_operand(&mut bx, len).immediate(); let index = self.codegen_operand(&mut bx, index).immediate(); - (lang_items::PanicBoundsCheckFnLangItem, vec![location, index, len]) + // It's `fn panic_bounds_check(index: usize, len: usize)`, and + // `#[track_caller]` adds an implicit third argument. + (lang_items::PanicBoundsCheckFnLangItem, vec![index, len, location]) } _ => { let msg_str = Symbol::intern(msg.description()); let msg = bx.const_str(msg_str); + // It's `pub fn panic(expr: &str)`, with the wide reference being passed + // as two arguments, and `#[track_caller]` adds an implicit third argument. (lang_items::PanicFnLangItem, vec![msg.0, msg.1, location]) } };