Skip to content
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

Be more obvious when suggesting dereference #45947

Merged
merged 3 commits into from
Nov 26, 2017

Conversation

estebank
Copy link
Contributor

@estebank estebank commented Nov 12, 2017

Include & span when suggesting dereference on a span that is already a reference:

error: non-reference pattern used to match a reference (see issue #42640)
  --> dont-suggest-dereference-on-arg.rs:16:19
   |
16 |         .filter(|&(ref a, _)| foo(a))
   |                  ^^^^^^^^^^^ help: consider using: `&&(ref k, _)`
   |
   = help: add #![feature(match_default_bindings)] to the crate attributes to enable

Fix #45925.

@mark-i-m
Copy link
Member

I'm still not quite sure I understand the error... Isn't &(ref k, _) a reference pattern used to match a reference? What does it mean by "non-reference pattern"?

@estebank
Copy link
Contributor Author

This PR is not a full solution, do not merge.

@mark-i-m the type checker sees the closure's argument as a pattern match, I believed that behavior was introduced as part of RFC 2005 (tracked in #42640).

@mark-i-m
Copy link
Member

It is a pattern match, though, right? I was under the impression that in Rust all arguments to functions and closures are actually patterns, which can bind new names, just as in an if let or match. Is this not true?

Another way of asking the question is to ask if &(ref k, _) is actually wrong. I believe the types are correct, and I don't think I was violating the borrow rules or anything. So IIUC I should not have gotten any error at all; it should have just compiled, right?

@mark-i-m
Copy link
Member

Ah, I see. The correct pattern would be &&(ref k, _) but the "type mismatch" error is covered over by the "match bindings" error... So the code should not have compiled...

@mark-i-m
Copy link
Member

Hmm... so the hint was actually on the right track. It suggests replacing (ref k, _) with &(ref k, _) in &(ref k, _), which would have lead to &&(ref k, _). It is just not at all clear that's what it means...

@kennytm kennytm added the S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. label Nov 13, 2017
@arielb1
Copy link
Contributor

arielb1 commented Nov 13, 2017

@estebank

Can't we just adjust our error message until it includes all the surrounding reference patterns, so we'll get this:

error: non-reference pattern used to match a reference (see issue #42640)
   --> src/coord.rs:194:23
    |
194 |             .filter(|&(ref k, _)| self.hash(k) == server)
    |                      ^^^^^^^^^^^ help: consider using: `&&(ref k, _)`
    |
    = help: add #![feature(match_default_bindings)] to the crate attributes to enable

error: aborting due to previous error

error: Could not compile `kv_2pc`.

To learn more, run the command again with --verbose.

@estebank
Copy link
Contributor Author

@arielb1 yeah, I think that's a better approach.

@kennytm
Copy link
Member

kennytm commented Nov 22, 2017

Hi @estebank, what is the status of this PR?

@estebank estebank force-pushed the match_default_bindings-arg-hint branch 3 times, most recently from 8b8dbaa to 8ca6925 Compare November 23, 2017 03:01
@estebank
Copy link
Contributor Author

@kennytm @arielb1 I've modified the PR to do some span fiddling to see if there's a & right before. I'm not entirely happy with doing that, but it should be enough to handle the presented situation.

@estebank estebank changed the title Don't suggest dereference on tuple argument Be more obvious when suggesting dereference Nov 23, 2017
@mark-i-m
Copy link
Member

@estebank

I'm not entirely happy with doing that

What problems do you foresee with it?

let lo = if span_lo == 0 {
0
} else {
span_lo - 1
Copy link
Member

@mark-i-m mark-i-m Nov 23, 2017

Choose a reason for hiding this comment

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

Doesn't this mean we now have the same problem with the following case:

let x = &&&0;
let &&x = x;

IIUC, the error message would suggest using &&, right?

let span = self.data();
let span_lo = span.lo.0;
let lo = if span_lo == 0 {
0
Copy link
Contributor

Choose a reason for hiding this comment

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

This looks likely to introduce an infinite loop in some case, where we go up to the start of the file. You can return an Option<Span> instead.

@arielb1
Copy link
Contributor

arielb1 commented Nov 23, 2017

@estebank

Please don't fiddle with spans, it causes very weird situations with macros. You can use tcx.hir.get_parent_node to go up the pattern tree and find the reference patterns until you find something that is not a reference pattern, and then you span the last reference pattern.

@estebank estebank force-pushed the match_default_bindings-arg-hint branch 2 times, most recently from b28b38e to f1a672c Compare November 23, 2017 20:29
@@ -120,15 +120,33 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
.pat_adjustments_mut()
.insert(pat.hir_id, pat_adjustments);
} else {
let mut ref_sp = pat.span;
let mut id = pat.id;
loop { // make span include all enclosing `&` to avoid confusing diag output
Copy link
Contributor

Choose a reason for hiding this comment

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

nit: s/loop/while let/

Copy link
Contributor

Choose a reason for hiding this comment

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

ok a while-let would be ugly too. Why can't we have a do-while loop?

@arielb1
Copy link
Contributor

arielb1 commented Nov 23, 2017

@bors r+

@bors
Copy link
Contributor

bors commented Nov 23, 2017

📌 Commit f1a672c has been approved by arielb1

@kennytm
Copy link
Member

kennytm commented Nov 24, 2017

@bors r-

CI failed, the UI test ui/suggestions/dont-suggest-dereference-on-arg.rs’s output needs to be updated.

@bors
Copy link
Contributor

bors commented Nov 24, 2017

☔ The latest upstream changes (presumably #46116) made this pull request unmergeable. Please resolve the merge conflicts.

Include enclosing span when suggesting dereference on a span that is
already a reference:

```
error: non-reference pattern used to match a reference (see issue rust-lang#42640)
  --> dont-suggest-dereference-on-arg.rs:16:19
   |
16 |         .filter(|&(ref a, _)| foo(a))
   |                  ^^^^^^^^^^^ help: consider using: `&&(ref k, _)`
   |
   = help: add #![feature(match_default_bindings)] to the crate attributes to enable
```
@estebank estebank force-pushed the match_default_bindings-arg-hint branch 3 times, most recently from 33f0684 to 48d291a Compare November 25, 2017 15:52
x.iter()
.filter(|&(ref a, _)| foo(a))
//~^ ERROR non-reference pattern used to match a reference
//~| HELP consider using a reference
Copy link
Member

Choose a reason for hiding this comment

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

[00:47:09] error: /checkout/src/test/ui/suggestions/dont-suggest-dereference-on-arg.rs:16: unexpected help message: '16:18: 16:29: add #![feature(match_default_bindings)] to the crate attributes to enable'

Needs one more //~| HELP.

@estebank estebank force-pushed the match_default_bindings-arg-hint branch from 48d291a to 15dfd7e Compare November 25, 2017 18:16
@estebank
Copy link
Contributor Author

@bors r=arielb1

@bors
Copy link
Contributor

bors commented Nov 25, 2017

📌 Commit 15dfd7e has been approved by arielb1

@kennytm kennytm added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. labels Nov 25, 2017
bors added a commit that referenced this pull request Nov 26, 2017
…ielb1

Be more obvious when suggesting dereference

Include `&` span when suggesting dereference on a span that is already a reference:

```
error: non-reference pattern used to match a reference (see issue #42640)
  --> dont-suggest-dereference-on-arg.rs:16:19
   |
16 |         .filter(|&(ref a, _)| foo(a))
   |                  ^^^^^^^^^^^ help: consider using: `&&(ref k, _)`
   |
   = help: add #![feature(match_default_bindings)] to the crate attributes to enable
```

Fix #45925.
@bors
Copy link
Contributor

bors commented Nov 26, 2017

⌛ Testing commit 15dfd7e with merge 693bb0d...

@bors
Copy link
Contributor

bors commented Nov 26, 2017

☀️ Test successful - status-appveyor, status-travis
Approved by: arielb1
Pushing 693bb0d to master...

@bors bors merged commit 15dfd7e into rust-lang:master Nov 26, 2017
@estebank estebank deleted the match_default_bindings-arg-hint branch November 9, 2023 05:25
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants