Skip to content

Lint on calling to_owned on a reference #78187

Open
@Aaron1011

Description

@Aaron1011

The ToOwned trait has a blanket impl for T: Clone. Since references implement Clone, it's possible to call &SomeNonCloneType.to_owned() - this returns a new reference &SomeNonCloneType, not an owned SomeNonCloneType. This can result in a confusing error message:

struct Foo;

fn main() {
    let a = &Foo;
    let b: Foo = a.to_owned();
}
error[E0308]: mismatched types
 --> src/main.rs:5:18
  |
5 |     let b: Foo = a.to_owned();
  |            ---   ^^^^^^^^^^^^ expected struct `Foo`, found `&Foo`
  |            |
  |            expected due to this

Here, adding #[derive(Clone)] to Foo makes this code compile, but it's not at all obvious from looking at the error message.

We should lint on calling val.to_owned() or val.clone(), when val is a reference, and treated as the Self type (as opposed to being called on a reference to some non-reference type that implemented Clone). This is very likely a mistake, and in any case can be written more succinctly as *val

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-lintsArea: Lints (warnings about flaws in source code) such as unused_mut.C-bugCategory: This is a bug.T-compilerRelevant to the compiler team, which will review and decide on the PR/issue.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions