Repository navigation
Closed
Labels
B-unstableBlocker: Implemented in the nightly compiler and unstable.Blocker: Implemented in the nightly compiler and unstable.C-tracking-issueCategory: An issue tracking the progress of sth. like the implementation of an RFCCategory: An issue tracking the progress of sth. like the implementation of an RFCT-langRelevant to the language teamRelevant to the language teamT-libs-api[DEPRECATED; DO NOT USE][DEPRECATED; DO NOT USE]disposition-closeThis PR / issue is in PFCP or FCP with a disposition to close it.This PR / issue is in PFCP or FCP with a disposition to close it.finished-final-comment-periodThe final comment period is finished for this PR / Issue.The final comment period is finished for this PR / Issue.
Description
This is a tracking issue for the fn_box feature and FnBox trait, which allows a Box<FnOnce(...) -> _> closure to be invoked via the "rust-call" sugar.
I'm not sure what the primary concerns are. All I know is it'd be really, really nice if we could invoke a Box<FnOnce()> somehow in safe Rust. This may or may not be the best approach.
@eddyb feel free to CC anyone who might want to comment or edit this issue to add any pertinent information.
Reacted by Jan Hohenheim, Ben Berman, Stepan Koltsov and Rodrigo
Metadata
Metadata
Assignees
Labels
B-unstableBlocker: Implemented in the nightly compiler and unstable.Blocker: Implemented in the nightly compiler and unstable.C-tracking-issueCategory: An issue tracking the progress of sth. like the implementation of an RFCCategory: An issue tracking the progress of sth. like the implementation of an RFCT-langRelevant to the language teamRelevant to the language teamT-libs-api[DEPRECATED; DO NOT USE][DEPRECATED; DO NOT USE]disposition-closeThis PR / issue is in PFCP or FCP with a disposition to close it.This PR / issue is in PFCP or FCP with a disposition to close it.finished-final-comment-periodThe final comment period is finished for this PR / Issue.The final comment period is finished for this PR / Issue.
Activity
eefriedman commentedon Oct 1, 2015
The reason we don't want to stabilize
FnBoxis because we would prefer to makeBox<FnOnce()>just work.Making
Box<FnOnce()>work isn't exactly controversial (there's only one obvious way to handle the construct), but it's sort of tied up with rust-lang/rfcs#997, and more generally the issue that we want to remove the special cases forBoxfrom the compiler.charlesetc commentedon Oct 2, 2015
So in the stable version of rust it's impossible to call
Box<FnOnce()>and it's impossible to return a closure that's not in a box, judging from the book, because it doesn't have a known size. So how does one return a closure and call it?abonander commentedon Oct 2, 2015
@charlesetc
Box<Fn()>andBox<FnMut()>can both be called without a problem, because they don't require destructuring the box they're in; they only need&selfor&mut self, respectively, which totally works with the current deref coercions. Which of the closure traits,Fn(), FnMut(),orFnOnce(), is implemented for a specific closure is determined by inference.Box<FnOnce()>is a challenge because it takesselfby-value, which means it needs to be moved out of theBoxand onto the stack to be executed, but this doesn't work in current Rust because there's no stable way to move out of (destructure) aBox. TheDerefMovetrait proposed in the RFC @eefriedman linked would make this work, but the design of it is still being worked on.The key here is that
Box<FnOnce()>does have a known size, but it's hidden behind theBoxpointer so that anything implementingFnOnce, regardless of its size, can fit in the same spot. The v-table in the trait object directs the processor to the concrete implementation of the trait (in this case, the closure body) for that specific object. All the details about the object, its size, fields, etc., are coded into that implementation.charlesetc commentedon Oct 2, 2015
Oh that makes more sense, thanks!
kosta commentedon Oct 2, 2015
I don't want to be pushy, but I think this is really a major missing piece in Rusts "Closures" story - and not really mentioned on in the rust book.
I understand that you want to remove special-cases for Box in the compiler and I agree that that's a worthy goal. But when will that land?
If we can have Box<FnOnce> right now for the price of "a bit more Box magic" until the no-special-case-for-Box story is complete, then is that maybe the right price to pay?
(I couldn't say, I would just profit from it as a Rust user)
alexcrichton commentedon Nov 4, 2015
Nominating for discussion in 1.6
nikomatsakis commentedon Nov 4, 2015
cc me
alexcrichton commentedon Nov 5, 2015
🔔 This issue is now entering its cycle-long final comment period 🔔
The libs team discussed this and we have two possible routes for this right now:
FnBox1,FnBox2, etc. This has the benefit of not polluting the standard library but is less ergonomic to use.We're a little undecided on which route to take, so some comments would be welcome!
abonander commentedon Nov 5, 2015
I'd vote for the former. We have enough micro-crates in the ecosystem and this is a common enough pattern that it's worth supporting in the stdlib.
Edit: I want to add that I do have a use for this. I need it for one-off callbacks in wingui. Right now I'm having to wrap
FnOncecallbacks in anOptionand move it into anFnMutclosure so I can call it from a box. It's not very ergonomic.I don't want to have to add another crate to my build because that seems like a very heavyweight solution just to get a trait or two.
sfackler commentedon Nov 5, 2015
@cybergeek94 you can do a bit better than that with some boilerplate: https://github.com/sfackler/r2d2/blob/master/src/thunk.rs but it's a bit of a pain.
97 remaining items
Make closure of challenge phase FnOnce.
Rollup merge of rust-lang#62043 - Centril:remove-fnbox, r=cramertj
Rollup merge of rust-lang#62043 - Centril:remove-fnbox, r=cramertj
Rollup merge of rust-lang#62043 - Centril:remove-fnbox, r=cramertj
Rollup merge of rust-lang#62043 - Centril:remove-fnbox, r=cramertj
Rollup merge of rust-lang#62043 - Centril:remove-fnbox, r=cramertj
Rollup merge of rust-lang#62043 - Centril:remove-fnbox, r=cramertj
Remove workaround for boxed FnOnce in Rust <1.35
Remove workaround for boxed FnOnce in Rust <1.35
Make closure of challenge phase FnOnce.
Make closure of challenge phase FnOnce.
Make closure of challenge phase FnOnce.
Make closure of challenge phase FnOnce. (#276)
Switch RPC callback to FnOnce, add "idle proc" to RPC mainloop