Skip to content

Conversation

@james7132
Copy link
Contributor

@james7132 james7132 commented Sep 2, 2025

Fixes #83. Fixes #66. Partially fixes #78.

This PR gets rid of the extra boxing in spawn_unchecked that results in extra monomorphization and overhead of allocating and moving into a Pin<Box<Fut>>. The boxing causes an extra copy onto the stack before moving onto the heap. This negates only one of the two stack copies made on lower optimization builds, and requires an extra indirection on every access, so we get rid of it.

Instead, this PR turns spawn_unchecked into a macro to avoid creating extra stack frames, effectively forcibly inlining the code regardless of what optimization level. This PR also opts to replace the abort_on_panic implementation with a manual one to avoid the extra stack copy there.

@james7132 james7132 requested review from notgull and taiki-e September 3, 2025 00:10
@james7132
Copy link
Contributor Author

I'm not sure where the CI failures are coming from. I don't think they're related to the changes here, and they show up in #87 as well. @taiki-e FYI.

Copy link
Collaborator

@taiki-e taiki-e left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@james7132
Copy link
Contributor Author

@taiki-e any thoughts on the CI failures? I'm not sure where the leaks are coming from.

@taiki-e
Copy link
Collaborator

taiki-e commented Sep 12, 2025

All errors come from doctest, so I think it's likely because doctest-xcompile has stabilized in 1.89 and doctests are now tested even when runner is set. (So it's not due to this PR.)

failures:
    src/lib.rs - (line 25)
    src/runnable.rs - runnable::Runnable<M>::schedule (line 727)
    src/runnable.rs - runnable::Runnable<M>::waker (line 790)

All "definitely lost" indicate a leak of allocation from flume::unbounded that is captured in the closure, so this is probably due to the task being scheduled but not polled.

==6502== 248 (152 direct, 96 indirect) bytes in 1 blocks are definitely lost in loss record 3 of 4
==6502==    at 0x48C480F: malloc (vg_replace_malloc.c:446)
==6502==    by 0x402D07D: alloc::alloc::Global::alloc_impl (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x402CF59: alloc::alloc::exchange_malloc (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x402CD51: alloc::sync::Arc<T>::new (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x402F523: flume::unbounded (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x402FCDB: rust_out::main::_doctest_main_src_runnable_rs_790_0 (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x402FCA5: rust_out::main (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x402A512: core::ops::function::FnOnce::call_once (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x4029E95: std::sys::backtrace::__rust_begin_short_backtrace (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x4029E78: std::rt::lang_start::{{closure}} (in /tmp/rustdoctest3ICG2R/rust_out)
==6502==    by 0x404249F: call_once<(), (dyn core::ops::function::Fn<(), Output=i32> + core::marker::Sync + core::panic::unwind_safe::RefUnwindSafe)> (function.rs:290)
==6502==    by 0x404249F: do_call<&(dyn core::ops::function::Fn<(), Output=i32> + core::marker::Sync + core::panic::unwind_safe::RefUnwindSafe), i32> (panicking.rs:590)
==6502==    by 0x404249F: catch_unwind<i32, &(dyn core::ops::function::Fn<(), Output=i32> + core::marker::Sync + core::panic::unwind_safe::RefUnwindSafe)> (panicking.rs:553)
==6502==    by 0x404249F: catch_unwind<&(dyn core::ops::function::Fn<(), Output=i32> + core::marker::Sync + core::panic::unwind_safe::RefUnwindSafe), i32> (panic.rs:359)
==6502==    by 0x404249F: {closure#0} (rt.rs:175)
==6502==    by 0x404249F: do_call<std::rt::lang_start_internal::{closure_env#0}, isize> (panicking.rs:590)
==6502==    by 0x404249F: catch_unwind<isize, std::rt::lang_start_internal::{closure_env#0}> (panicking.rs:553)
==6502==    by 0x404249F: catch_unwind<std::rt::lang_start_internal::{closure_env#0}, isize> (panic.rs:359)
==6502==    by 0x404249F: std::rt::lang_start_internal (rt.rs:171)
==6502==    by 0x4029E60: std::rt::lang_start (in /tmp/rustdoctest3ICG2R/rust_out)

@taiki-e taiki-e mentioned this pull request Sep 12, 2025
@james7132 james7132 merged commit e4e8216 into smol-rs:master Sep 12, 2025
8 checks passed
@james7132 james7132 deleted the no-box branch September 16, 2025 09:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

2 participants