Skip to content

Account for desugaring in method call move errors - #160006

Open
estebank wants to merge 3 commits into
rust-lang:mainfrom
estebank:issue-89567
Open

Account for desugaring in method call move errors#160006
estebank wants to merge 3 commits into
rust-lang:mainfrom
estebank:issue-89567

Conversation

@estebank

@estebank estebank commented Jul 27, 2026

Copy link
Copy Markdown
Contributor

When encountering a move error caused by a desugared method call, talk about the user-facing feature (await/?/for-loop), instead of only the internal API it got desugared to.

error[E0382]: use of moved value: `entry`
  --> $DIR/moved-into-question-mark.rs:11:18
   |
LL |     for entry in fs::read_dir(".")? {
   |         ----- move occurs because `entry` has type `Result<DirEntry, std::io::Error>`, which does not implement the `Copy` trait
LL |
LL |         let file_type = entry?.file_type()?;
   |                         ------ `entry` moved due to usage in the question mark operator
...
LL |             dbg!(entry?.file_name());
   |                  ^^^^^ value used here after move
   |
note: the question mark operator is expanded into a call to `branch`, which takes ownership of the receiver `self`, which moves `entry`
  --> $SRC_DIR/core/src/ops/try_trait.rs:LL:COL
help: you could `clone` the value and consume it, if the following trait bounds could be satisfied: `DirEntry: Clone` and `std::io::Error: Clone`
   |
LL |         let file_type = entry.clone()?.file_type()?;
   |                              ++++++++

Fix #89567.

When encountering a move error caused by a desugared method call, talk about the user-facing feature (`await`/`?`/`for`-loop), instead of only the internal API it got desugared to.

```
error[E0382]: use of moved value: `entry`
  --> $DIR/moved-into-question-mark.rs:11:18
   |
LL |     for entry in fs::read_dir(".")? {
   |         ----- move occurs because `entry` has type `Result<DirEntry, std::io::Error>`, which does not implement the `Copy` trait
LL |
LL |         let file_type = entry?.file_type()?;
   |                         ------ `entry` moved due to usage in the question mark operator
...
LL |             dbg!(entry?.file_name());
   |                  ^^^^^ value used here after move
   |
note: the question mark operator is expanded into a call to `branch`, which takes ownership of the receiver `self`, which moves `entry`
  --> $SRC_DIR/core/src/ops/try_trait.rs:LL:COL
help: you could `clone` the value and consume it, if the following trait bounds could be satisfied: `DirEntry: Clone` and `std::io::Error: Clone`
   |
LL |         let file_type = entry.clone()?.file_type()?;
   |                              ++++++++
```
@rustbot rustbot added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. labels Jul 27, 2026
@rustbot

rustbot commented Jul 27, 2026

Copy link
Copy Markdown
Collaborator

r? @chenyukang

rustbot has assigned @chenyukang.
They will have a look at your PR within the next two weeks and either review your PR or reassign to another reviewer.

Use r? to explicitly pick a reviewer

Why was this reviewer chosen?

The reviewer was selected based on:

  • Owners of files modified in this PR: borrowck, compiler
  • borrowck, compiler expanded to 74 candidates
  • Random selection from 18 candidates

LL | dbg!(entry?.file_name());
| ^^^^^ value used here after move
|
note: the question mark operator is expanded into a call to `branch`, which takes ownership of the receiver `self`, which moves `entry`

@chenyukang chenyukang Jul 28, 2026

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

is it better to use desugarded than expanded, not sure.

View changes since the review

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Changed, as well as a few other tweaks in the second commit. I think that using the full path to the item makes more sense in this case (it is unlikely to be too long, and the clarity gain is high). LMKWYT.

| ^^^^ value used here after move
|
note: `into_async_iter` takes ownership of the receiver `self`, which moves `iter`
note: `std::async_iter::IntoAsyncIterator::into_async_iter` takes ownership of the receiver `self`, which moves `iter`

@chenyukang chenyukang Jul 30, 2026

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

it's better we point out the for await here?
maybe:

note: the for await loop is desugared into a call to std::async_iter::IntoAsyncIterator::into_async_iter, which takes ownership of the receiver self and moves iter

View changes since the review

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

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

Done

@chenyukang

Copy link
Copy Markdown
Member

r=me after a nit.

@rustbot

rustbot commented Jul 30, 2026

Copy link
Copy Markdown
Collaborator

Some changes occurred to the CTFE machinery

cc @RalfJung, @oli-obk, @lcnr

Some changes occurred to constck

cc @fee1-dead

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Diagnostics: confusing terminology when moves occur due to ? operator

3 participants