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

Type inference failure with Borrow<Vec<Foo>> leads to false positive type mismatch errors #13761

Open
cyqsimon opened this issue Dec 12, 2022 · 3 comments
Labels
A-ty type system / type inference / traits / method resolution C-bug Category: bug

Comments

@cyqsimon
Copy link

cyqsimon commented Dec 12, 2022

It's quite difficult to clearly explain what's wrong, so here's a MRE:

#![allow(dead_code, unused_variables)]
use std::borrow::Borrow;

fn main() {}

struct Foo {}
fn accepts_ref_foo(ref_foo: &Foo) {
    // ...
}

/// This is the MRE.
fn this_errors(foos: impl Borrow<Vec<Foo>>) {
    let vec_of_ref_foo = foos.borrow().iter().collect::<Vec<_>>();

    // 1. observe that RA fails to infer the type of `vec_of_ref_foo` (should be `Vec<&Foo>`)
    // 2. in the following for loop, observe that RA thinks `ref_foo` is `Foo` (should be `&Foo`)
    // 3. run `cargo check` and `cargo build`; verify that the compiler sees no problems here

    for ref_foo in vec_of_ref_foo {
        // this destructing statement is critical
        // without it, RA sees no issues
        let Foo { .. } = ref_foo;
        // RA thinks there's an error here where there is none
        accepts_ref_foo(ref_foo);
    }
}

/// Only `Borrow<Vec<Foo>>` is affected, not `Vec<Borrow<Foo>>`.
fn this_is_fine_0(foos: Vec<impl Borrow<Foo>>) {
    let vec_of_ref_foo = foos.iter().map(|foo| foo.borrow()).collect::<Vec<_>>();
    for ref_foo in vec_of_ref_foo {
        let Foo { .. } = ref_foo;
        accepts_ref_foo(ref_foo);
    }
}

rust-analyzer version: 0.3.1309-standalone

rustc version: rustc 1.65.0 (897e37553 2022-11-02)

@cyqsimon cyqsimon changed the title Type inference failure with std::borrow::Borrow leads to false positive errors Type inference failure with Borrow<Vec<Foo>> leads to false positive type mismatch errors Dec 12, 2022
@cyqsimon
Copy link
Author

VSCode error screenshot

@Veykril Veykril added A-ty type system / type inference / traits / method resolution C-bug Category: bug labels Dec 12, 2022
@lowr
Copy link
Contributor

lowr commented Dec 12, 2022

I think this is effectively a duplicate of #5514. We cannot resolve vec_of_ref_foo's type correctly as you pointed out because of that.

rust-analyzer doesn't show type mismatch errors that come from unresolved types (i.e. {unknown}), but when it sees that let Foo { .. } = ref_foo statement there, it coerces the unresolved type to Foo because that's the only information it has.

@cyqsimon
Copy link
Author

cyqsimon commented Dec 13, 2022

I think I'll leave this issue open for now, because it showcases a situation where this limitation leads to an actual false error rather than just an annoyance.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-ty type system / type inference / traits / method resolution C-bug Category: bug
Projects
None yet
Development

No branches or pull requests

3 participants