-
Notifications
You must be signed in to change notification settings - Fork 13.9k
Description
I believe that the semantics of let _ = foo() should be that the destructor for the value returned by foo() runs at the end of the block. The reason for this is a consequence of a couple of other rules that I worked out as part of the temporary lifetime stuff.
In general, let <pat> = <rvalue> where <pat> is not a single identifier is equivalent to:
let _tmp = <rvalue>;
let <path> = _tmp;
In this case, that means that let _ = <rvalue> should be:
let _tmp = <rvalue>;
let _ = tmp;
and since the _ pattern just ignores the thing it matches against, this means that _tmp is unaffected and drops at the end of the block.
However, the following test case suggests that this is not what we do today:
struct Foo;
impl Drop for Foo {
fn drop(&mut self) {
println!("Hi2!");
}
}
fn main() {
let _ = Foo;
println!("Hi1!");
}
This should print Hi1 and then Hi2 but in fact it prints the opposite. This is probably a hold-over from the special code that was in trans to special case the treatment of let _ vs other patterns, but I could be wrong.