-
Notifications
You must be signed in to change notification settings - Fork 12.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Temporary does not live long enough in let chains #103476
Comments
Minimized: #![feature(let_chains)]
struct Pd<T>(std::marker::PhantomData<T>);
impl<T> Pd<T> {
fn iter(&self) -> Iter<T> {
todo!()
}
}
pub struct Iter<'a, T: 'a> {
inner: Box<dyn IterTrait<'a, T> + 'a>,
}
trait IterTrait<'a, T: 'a> {
fn clone_box(&self) -> Box<dyn IterTrait<'a, T> + 'a>;
}
fn f(m: Option<Pd<()>>) -> bool {
if let Some(n) = m
&& let it = n.iter()
/* other stuff */
{
}
true
} #![feature(let_chains)]
struct Pd;
impl Pd {
fn it(&self) -> It {
todo!()
}
}
pub struct It<'a>(Box<dyn Tr<'a>>);
trait Tr<'a> {}
fn f(m: Option<Pd>) {
if let Some(n) = m && let it = n.iter() {};
} |
Even more minimized: #![feature(let_chains)]
#![allow(irrefutable_let_patterns)]
fn it(_: &()) -> Box<dyn Tr<'_>> { todo!() }
trait Tr<'a> {}
fn f() {
if let n = () && let _ = it(&n) {};
}
Weirdly, I couldn't replace |
Box's |
Good point about the lang item. I've tried it with This also still reproduces: #![feature(let_chains)]
#![allow(irrefutable_let_patterns)]
struct B<T: ?Sized> { _t: std::marker::PhantomData<T>, }
impl<T: ?Sized> std::ops::Drop for B<T> {
fn drop(&mut self) {}
}
fn it(_: &()) -> B<dyn Tr<'_>> { todo!() }
trait Tr<'a> {}
fn f() {
if let n = () && let _ = it(&n) {};
} |
This reproduces as well: #![feature(let_chains)]
#![allow(irrefutable_let_patterns)]
struct B<'a>(&'a ());
impl<'a> std::ops::Drop for B<'a> {
fn drop(&mut self) {}
}
fn f() {
if let n = () && let _ = B(&n) {};
} If you remove the |
The reason why |
There is no |
@est31 that's the point? @nathanwhit's example can use |
Good point, you are right about #![feature(dropck_eyepatch)]
#![feature(let_chains)]
#![allow(irrefutable_let_patterns)]
struct B<T: ?Sized> { _t: *const T, }
unsafe impl<#[may_dangle] T: ?Sized> std::ops::Drop for B<T> {
fn drop(&mut self) {}
}
fn it(_: &()) -> B<&()> { todo!() }
trait Tr<'a> {}
fn f() {
if let n = () && let _ = it(&n) {};
} |
Does this still block the stabilization of let chains? |
@WiSaGaN it would probably be very useful for this issue to get input by a borrow checking expert on whether this issue is fixable without doing breaking changes, and whether a fix is easy/feasible, or hard. Also, there are plans to rewrite large parts of let chains. |
As for your question: I wouldn't delay let chains for this indefinitely, esp as there is limited progress, but it would be sad that "there was not enough attention from the right people on this" is the reason why some issue can't get fixed indefinitely. Atm there are also other blockers too like #104843 and #104893. Especially latter would greatly benefit from input from third parties: try out let chains in your own code, and report bugs you find. |
This doesn't reproduce on edition 2024 any more, while still reproducing on edition 2021. I would say it's fixed by if let rescoping (#124085). I've tried both the "a bit further minimized" snippet as well as the snippet right below by @WaffleLapkin. As to the original snippet provided by @Alexendoo , same behaviour there, although note that latest syn (v1.0.109) does not reproduce the issue while an older version like 1.0.80 reproduces it. I suppose this can be closed now once we have a test for it in the testsuite. |
Let chains tests Filing this as this marks off two of the open issues in rust-lang#132833: * extending the tests for `move-guard-if-let-chain.rs` and `conflicting_bindings.rs` to have chains with multiple let's (one implementation could for example search for the first `let` and then terminate). * An instance where a temporary lives shorter than with nested ifs, breaking compilation: rust-lang#103476. This was fixed in the end by the if let rescoping work. Closes rust-lang#103476
Rollup merge of rust-lang#133093 - est31:let_chains_tests, r=traviscross Let chains tests Filing this as this marks off two of the open issues in rust-lang#132833: * extending the tests for `move-guard-if-let-chain.rs` and `conflicting_bindings.rs` to have chains with multiple let's (one implementation could for example search for the first `let` and then terminate). * An instance where a temporary lives shorter than with nested ifs, breaking compilation: rust-lang#103476. This was fixed in the end by the if let rescoping work. Closes rust-lang#103476
I tried this code, playground:
I expected to see this happen: code compiles
Instead, this happened: errors due to
name_value.path.segments does not live long enough
It compiles when expressed as nested ifs, playground:
The code compiled previously, but no longer does after #103034 (confirmed with a
cargo bisect-rustc
)cc @nathanwhit
The text was updated successfully, but these errors were encountered: