Skip to content

Commit f61e6a5

Browse files
authored
Rollup merge of #139080 - m-ou-se:super-let-gate, r=traviscross
Experimental feature gate for `super let` This adds an experimental feature gate, `#![feature(super_let)]`, for the `super let` experiment. Tracking issue: rust-lang/rust#139076 Liaison: ``@nikomatsakis`` ## Description There's a rough (inaccurate) description here: https://blog.m-ou.se/super-let/ In short, `super let` allows you to define something that lives long enough to be borrowed by the tail expression of the block. For example: ```rust let a = { super let b = temp(); &b }; ``` Here, `b` is extended to live as long as `a`, similar to how in `let a = &temp();`, the temporary will be extended to live as long as `a`. ## Properties During the temporary lifetimes work we did last year, we explored the properties of "super let" and concluded that the fundamental property should be that these two are always equivalent in any context: 1. `& $expr` 2. `{ super let a = & $expr; a }` And, additionally, that these are equivalent in any context when `$expr` is a temporary (aka rvalue): 1. `& $expr` 2. `{ super let a = $expr; & a }` This makes it possible to give a name to a temporary without affecting how temporary lifetimes work, such that a macro can transparently use a block in its expansion, without that having any effect on the outside. ## Implementing pin!() correctly With `super let`, we can properly implement the `pin!()` macro without hacks: ✨ ```rust pub macro pin($value:expr $(,)?) { { super let mut pinned = $value; unsafe { $crate::pin::Pin::new_unchecked(&mut pinned) } } } ``` This is important, as there is currently no way to express it without hacks in Rust 2021 and before (see [hacky definition](https://github.com/rust-lang/rust/blob/2a06022951893fe5b5384f8dbd75b4e6e3b5cee0/library/core/src/pin.rs#L1947)), and no way to express it at all in Rust 2024 (see [issue](rust-lang/rust#138718)). ## Fixing format_args!() This will also allow us to express `format_args!()` in a way where one can assign the result to a variable, fixing a [long standing issue](rust-lang/rust#92698): ```rust let f = format_args!("Hello {name}!"); // error today, but accepted in the future! (after separate FCP) ``` ## Experiment The precise definition of `super let`, what happens for `super let x;` (without initializer), and whether to accept `super let _ = _ else { .. }` are still open questions, to be answered by the experiment. Furthermore, once we have a more complete understanding of the feature, we might be able to come up with a better syntax. (Which could be just a different keywords, or an entirely different way of naming temporaries that doesn't involve a block and a (super) let statement.)
2 parents 9720c5c + eb6d674 commit f61e6a5

File tree

0 file changed

+0
-0
lines changed

    0 file changed

    +0
    -0
    lines changed

    0 commit comments

    Comments
     (0)