Skip to content

Commit 1048974

Browse files
committed
Auto merge of rust-lang#129063 - the8472:cold-opt-size, r=Amanieu
Apply size optimizations to panic machinery and some cold functions * std dependencies gimli and addr2line are now built with opt-level=s * various panic-related methods and `#[cold]` methods are now marked `#[optimize(size)]` Panics should be cold enough that it doesn't make sense to optimize them for speed. The only tradeoff here is if someone does a lot of backtrace captures (without panics) and printing then the opt-level change might impact their perf. Seems to be the first use of the optimize attribute. Tracking issue rust-lang#54882
2 parents 4074d49 + 79b5cfd commit 1048974

File tree

10 files changed

+26
-9
lines changed

10 files changed

+26
-9
lines changed

library/Cargo.toml

+2
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,10 @@ codegen-units = 10000
3131
# helps to improve link times a little bit.
3232
[profile.release.package]
3333
addr2line.debug = 0
34+
addr2line.opt-level = "s"
3435
adler.debug = 0
3536
gimli.debug = 0
37+
gimli.opt-level = "s"
3638
miniz_oxide.debug = 0
3739
object.debug = 0
3840
rustc-demangle.debug = 0

library/alloc/src/alloc.rs

+1
Original file line numberDiff line numberDiff line change
@@ -372,6 +372,7 @@ extern "Rust" {
372372
#[rustc_const_unstable(feature = "const_alloc_error", issue = "92523")]
373373
#[cfg(all(not(no_global_oom_handling), not(test)))]
374374
#[cold]
375+
#[optimize(size)]
375376
pub const fn handle_alloc_error(layout: Layout) -> ! {
376377
const fn ct_error(_: Layout) -> ! {
377378
panic!("allocation failed");

library/alloc/src/lib.rs

+1
Original file line numberDiff line numberDiff line change
@@ -184,6 +184,7 @@
184184
#![feature(multiple_supertrait_upcastable)]
185185
#![feature(negative_impls)]
186186
#![feature(never_type)]
187+
#![feature(optimize_attribute)]
187188
#![feature(rustc_allow_const_fn_unstable)]
188189
#![feature(rustc_attrs)]
189190
#![feature(slice_internals)]

library/alloc/src/raw_vec.rs

+1
Original file line numberDiff line numberDiff line change
@@ -782,6 +782,7 @@ where
782782
// Central function for reserve error handling.
783783
#[cfg(not(no_global_oom_handling))]
784784
#[cold]
785+
#[optimize(size)]
785786
fn handle_error(e: TryReserveError) -> ! {
786787
match e.kind() {
787788
CapacityOverflow => capacity_overflow(),

library/alloc/src/vec/mod.rs

+4
Original file line numberDiff line numberDiff line change
@@ -1520,6 +1520,7 @@ impl<T, A: Allocator> Vec<T, A> {
15201520
#[cold]
15211521
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never))]
15221522
#[track_caller]
1523+
#[optimize(size)]
15231524
fn assert_failed(index: usize, len: usize) -> ! {
15241525
panic!("swap_remove index (is {index}) should be < len (is {len})");
15251526
}
@@ -1568,6 +1569,7 @@ impl<T, A: Allocator> Vec<T, A> {
15681569
#[cold]
15691570
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never))]
15701571
#[track_caller]
1572+
#[optimize(size)]
15711573
fn assert_failed(index: usize, len: usize) -> ! {
15721574
panic!("insertion index (is {index}) should be <= len (is {len})");
15731575
}
@@ -1630,6 +1632,7 @@ impl<T, A: Allocator> Vec<T, A> {
16301632
#[cold]
16311633
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never))]
16321634
#[track_caller]
1635+
#[optimize(size)]
16331636
fn assert_failed(index: usize, len: usize) -> ! {
16341637
panic!("removal index (is {index}) should be < len (is {len})");
16351638
}
@@ -2318,6 +2321,7 @@ impl<T, A: Allocator> Vec<T, A> {
23182321
#[cold]
23192322
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never))]
23202323
#[track_caller]
2324+
#[optimize(size)]
23212325
fn assert_failed(at: usize, len: usize) -> ! {
23222326
panic!("`at` split index (is {at}) should be <= len (is {len})");
23232327
}

library/core/src/lib.rs

+1
Original file line numberDiff line numberDiff line change
@@ -233,6 +233,7 @@
233233
#![feature(never_type)]
234234
#![feature(no_core)]
235235
#![feature(no_sanitize)]
236+
#![feature(optimize_attribute)]
236237
#![feature(prelude_import)]
237238
#![feature(repr_simd)]
238239
#![feature(rustc_allow_const_fn_unstable)]

library/core/src/panicking.rs

+7-7
Original file line numberDiff line numberDiff line change
@@ -264,7 +264,7 @@ pub const fn panic_display<T: fmt::Display>(x: &T) -> ! {
264264
panic_fmt(format_args!("{}", *x));
265265
}
266266

267-
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold)]
267+
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold, optimize(size))]
268268
#[cfg_attr(feature = "panic_immediate_abort", inline)]
269269
#[track_caller]
270270
#[lang = "panic_bounds_check"] // needed by codegen for panic on OOB array/slice access
@@ -276,7 +276,7 @@ fn panic_bounds_check(index: usize, len: usize) -> ! {
276276
panic!("index out of bounds: the len is {len} but the index is {index}")
277277
}
278278

279-
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold)]
279+
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold, optimize(size))]
280280
#[cfg_attr(feature = "panic_immediate_abort", inline)]
281281
#[track_caller]
282282
#[lang = "panic_misaligned_pointer_dereference"] // needed by codegen for panic on misaligned pointer deref
@@ -301,7 +301,7 @@ fn panic_misaligned_pointer_dereference(required: usize, found: usize) -> ! {
301301
///
302302
/// This function is called directly by the codegen backend, and must not have
303303
/// any extra arguments (including those synthesized by track_caller).
304-
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold)]
304+
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold, optimize(size))]
305305
#[cfg_attr(feature = "panic_immediate_abort", inline)]
306306
#[lang = "panic_cannot_unwind"] // needed by codegen for panic in nounwind function
307307
#[rustc_nounwind]
@@ -317,7 +317,7 @@ fn panic_cannot_unwind() -> ! {
317317
///
318318
/// This function is called directly by the codegen backend, and must not have
319319
/// any extra arguments (including those synthesized by track_caller).
320-
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold)]
320+
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold, optimize(size))]
321321
#[cfg_attr(feature = "panic_immediate_abort", inline)]
322322
#[lang = "panic_in_cleanup"] // needed by codegen for panic in nounwind function
323323
#[rustc_nounwind]
@@ -350,7 +350,7 @@ pub enum AssertKind {
350350
}
351351

352352
/// Internal function for `assert_eq!` and `assert_ne!` macros
353-
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold)]
353+
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold, optimize(size))]
354354
#[cfg_attr(feature = "panic_immediate_abort", inline)]
355355
#[track_caller]
356356
#[doc(hidden)]
@@ -368,7 +368,7 @@ where
368368
}
369369

370370
/// Internal function for `assert_match!`
371-
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold)]
371+
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold, optimize(size))]
372372
#[cfg_attr(feature = "panic_immediate_abort", inline)]
373373
#[track_caller]
374374
#[doc(hidden)]
@@ -388,7 +388,7 @@ pub fn assert_matches_failed<T: fmt::Debug + ?Sized>(
388388
}
389389

390390
/// Non-generic version of the above functions, to avoid code bloat.
391-
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold)]
391+
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold, optimize(size))]
392392
#[cfg_attr(feature = "panic_immediate_abort", inline)]
393393
#[track_caller]
394394
fn assert_failed_inner(

library/std/src/lib.rs

+2
Original file line numberDiff line numberDiff line change
@@ -306,10 +306,12 @@
306306
#![feature(negative_impls)]
307307
#![feature(never_type)]
308308
#![feature(no_sanitize)]
309+
#![feature(optimize_attribute)]
309310
#![feature(prelude_import)]
310311
#![feature(rustc_attrs)]
311312
#![feature(rustdoc_internals)]
312313
#![feature(staged_api)]
314+
#![feature(stmt_expr_attributes)]
313315
#![feature(thread_local)]
314316
#![feature(try_blocks)]
315317
#![feature(type_alias_impl_trait)]

library/std/src/panicking.rs

+6-2
Original file line numberDiff line numberDiff line change
@@ -231,6 +231,7 @@ where
231231
}
232232

233233
/// The default panic handler.
234+
#[optimize(size)]
234235
fn default_hook(info: &PanicHookInfo<'_>) {
235236
// If this is a double panic, make sure that we print a backtrace
236237
// for this panic. Otherwise only print it if logging is enabled.
@@ -249,7 +250,8 @@ fn default_hook(info: &PanicHookInfo<'_>) {
249250
let thread = thread::try_current();
250251
let name = thread.as_ref().and_then(|t| t.name()).unwrap_or("<unnamed>");
251252

252-
let write = |err: &mut dyn crate::io::Write| {
253+
let write = #[optimize(size)]
254+
|err: &mut dyn crate::io::Write| {
253255
// Use a lock to prevent mixed output in multithreading context.
254256
// Some platforms also require it when printing a backtrace, like `SymFromAddr` on Windows.
255257
let mut lock = backtrace::lock();
@@ -527,6 +529,7 @@ pub unsafe fn r#try<R, F: FnOnce() -> R>(f: F) -> Result<R, Box<dyn Any + Send>>
527529
// optimizer (in most cases this function is not inlined even as a normal,
528530
// non-cold function, though, as of the writing of this comment).
529531
#[cold]
532+
#[optimize(size)]
530533
unsafe fn cleanup(payload: *mut u8) -> Box<dyn Any + Send + 'static> {
531534
// SAFETY: The whole unsafe block hinges on a correct implementation of
532535
// the panic handler `__rust_panic_cleanup`. As such we can only
@@ -686,7 +689,7 @@ pub fn begin_panic_handler(info: &core::panic::PanicInfo<'_>) -> ! {
686689
// lang item for CTFE panic support
687690
// never inline unless panic_immediate_abort to avoid code
688691
// bloat at the call sites as much as possible
689-
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold)]
692+
#[cfg_attr(not(feature = "panic_immediate_abort"), inline(never), cold, optimize(size))]
690693
#[cfg_attr(feature = "panic_immediate_abort", inline)]
691694
#[track_caller]
692695
#[rustc_do_not_const_check] // hooked by const-eval
@@ -756,6 +759,7 @@ fn payload_as_str(payload: &dyn Any) -> &str {
756759
/// Executes the primary logic for a panic, including checking for recursive
757760
/// panics, panic hooks, and finally dispatching to the panic runtime to either
758761
/// abort or unwind.
762+
#[optimize(size)]
759763
fn rust_panic_with_hook(
760764
payload: &mut dyn PanicPayload,
761765
location: &Location<'_>,

library/std/src/sync/once_lock.rs

+1
Original file line numberDiff line numberDiff line change
@@ -498,6 +498,7 @@ impl<T> OnceLock<T> {
498498
}
499499

500500
#[cold]
501+
#[optimize(size)]
501502
fn initialize<F, E>(&self, f: F) -> Result<(), E>
502503
where
503504
F: FnOnce() -> Result<T, E>,

0 commit comments

Comments
 (0)