about summary refs log tree commit diff
path: root/tests
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2023-09-17 13:48:40 +0000
committerbors <bors@rust-lang.org>2023-09-17 13:48:40 +0000
commit251a475b724a81ffcfd0113820492a329feeef5c (patch)
tree6a8175048bfee8629701e218ba99786cae623cc5 /tests
parent7b5e0199dab373b1a379e4ea7161d1440509f3c7 (diff)
parent79247d95f7ec00019cc26db20a07d4f1c1f335aa (diff)
downloadrust-251a475b724a81ffcfd0113820492a329feeef5c.tar.gz
rust-251a475b724a81ffcfd0113820492a329feeef5c.zip
Auto merge of #11511 - Jarcho:split_borrow, r=llogiq
Split `needless_borrow` into two lints

Splits off the case where the borrow is used as a generic argument to a function. I think the two cases are different  enough to warrant a separate lint.

The tests for the new lint have been reordered to group related parts together. Two warning have been dropped, one looked like it was testing the generic argument form, but it ends up triggering the auto-deref variant. The second was just a redundant test that didn't do anything interesting.

An issue with cycle detection is also included. The old version was checking if a cycle was reachable from a block when it should have been checking if the block is part or a cycle.

As a side note, I'm liking the style of just jamming all the tests into separate scopes in main.

changelog: Split off `needless_borrows_for_generic_args` from `needless_borrow`
Diffstat (limited to 'tests')
-rw-r--r--tests/ui/needless_borrow.fixed290
-rw-r--r--tests/ui/needless_borrow.rs290
-rw-r--r--tests/ui/needless_borrow.stderr90
-rw-r--r--tests/ui/needless_borrows_for_generic_args.fixed287
-rw-r--r--tests/ui/needless_borrows_for_generic_args.rs287
-rw-r--r--tests/ui/needless_borrows_for_generic_args.stderr77
-rw-r--r--tests/ui/regex.rs3
-rw-r--r--tests/ui/regex.stderr48
-rw-r--r--tests/ui/unnecessary_to_owned.fixed2
-rw-r--r--tests/ui/unnecessary_to_owned.rs2
10 files changed, 682 insertions, 694 deletions
diff --git a/tests/ui/needless_borrow.fixed b/tests/ui/needless_borrow.fixed
index 0a52b25229d..c2c5f765abf 100644
--- a/tests/ui/needless_borrow.fixed
+++ b/tests/ui/needless_borrow.fixed
@@ -131,21 +131,6 @@ fn main() {
             0
         }
     }
-
-    let _ = std::process::Command::new("ls").args(["-a", "-l"]).status().unwrap();
-    let _ = std::path::Path::new(".").join(".");
-    deref_target_is_x(X);
-    multiple_constraints([[""]]);
-    multiple_constraints_normalizes_to_same(X, X);
-    let _ = Some("").unwrap_or("");
-    let _ = std::fs::write("x", "".to_string());
-
-    only_sized(&""); // Don't lint. `Sized` is only bound
-    let _ = std::any::Any::type_id(&""); // Don't lint. `Any` is only bound
-    let _ = Box::new(&""); // Don't lint. Type parameter appears in return type
-    ref_as_ref_path(&""); // Don't lint. Argument type is not a type parameter
-    refs_only(&()); // Don't lint. `&T` implements trait, but `T` doesn't
-    multiple_constraints_normalizes_to_different(&[[""]], &[""]); // Don't lint. Projected type appears in arguments
 }
 
 #[allow(clippy::needless_borrowed_reference)]
@@ -201,103 +186,6 @@ mod issue9160 {
     }
 }
 
-#[derive(Clone, Copy)]
-struct X;
-
-impl std::ops::Deref for X {
-    type Target = X;
-    fn deref(&self) -> &Self::Target {
-        self
-    }
-}
-
-fn deref_target_is_x<T>(_: T)
-where
-    T: std::ops::Deref<Target = X>,
-{
-}
-
-fn multiple_constraints<T, U, V, X, Y>(_: T)
-where
-    T: IntoIterator<Item = U> + IntoIterator<Item = X>,
-    U: IntoIterator<Item = V>,
-    V: AsRef<str>,
-    X: IntoIterator<Item = Y>,
-    Y: AsRef<std::ffi::OsStr>,
-{
-}
-
-fn multiple_constraints_normalizes_to_same<T, U, V>(_: T, _: V)
-where
-    T: std::ops::Deref<Target = U>,
-    U: std::ops::Deref<Target = V>,
-{
-}
-
-fn only_sized<T>(_: T) {}
-
-fn ref_as_ref_path<T: 'static>(_: &'static T)
-where
-    &'static T: AsRef<std::path::Path>,
-{
-}
-
-trait RefsOnly {
-    type Referent;
-}
-
-impl<T> RefsOnly for &T {
-    type Referent = T;
-}
-
-fn refs_only<T, U>(_: T)
-where
-    T: RefsOnly<Referent = U>,
-{
-}
-
-fn multiple_constraints_normalizes_to_different<T, U, V>(_: T, _: U)
-where
-    T: IntoIterator<Item = U>,
-    U: IntoIterator<Item = V>,
-    V: AsRef<str>,
-{
-}
-
-// https://github.com/rust-lang/rust-clippy/pull/9136#pullrequestreview-1037379321
-mod copyable_iterator {
-    #[derive(Clone, Copy)]
-    struct Iter;
-    impl Iterator for Iter {
-        type Item = ();
-        fn next(&mut self) -> Option<Self::Item> {
-            None
-        }
-    }
-    fn takes_iter(_: impl Iterator) {}
-    fn dont_warn(mut x: Iter) {
-        takes_iter(&mut x);
-    }
-    #[allow(unused_mut)]
-    fn warn(mut x: &mut Iter) {
-        takes_iter(x)
-    }
-}
-
-#[clippy::msrv = "1.52.0"]
-mod under_msrv {
-    fn foo() {
-        let _ = std::process::Command::new("ls").args(&["-a", "-l"]).status().unwrap();
-    }
-}
-
-#[clippy::msrv = "1.53.0"]
-mod meets_msrv {
-    fn foo() {
-        let _ = std::process::Command::new("ls").args(["-a", "-l"]).status().unwrap();
-    }
-}
-
 fn issue9383() {
     // Should not lint because unions need explicit deref when accessing field
     use std::mem::ManuallyDrop;
@@ -326,184 +214,6 @@ fn issue9383() {
     }
 }
 
-fn closure_test() {
-    let env = "env".to_owned();
-    let arg = "arg".to_owned();
-    let f = |arg| {
-        let loc = "loc".to_owned();
-        let _ = std::fs::write("x", &env); // Don't lint. In environment
-        let _ = std::fs::write("x", arg);
-        let _ = std::fs::write("x", loc);
-    };
-    let _ = std::fs::write("x", &env); // Don't lint. Borrowed by `f`
-    f(arg);
-}
-
-mod significant_drop {
-    #[derive(Debug)]
-    struct X;
-
-    #[derive(Debug)]
-    struct Y;
-
-    impl Drop for Y {
-        fn drop(&mut self) {}
-    }
-
-    fn foo(x: X, y: Y) {
-        debug(x);
-        debug(&y); // Don't lint. Has significant drop
-    }
-
-    fn debug(_: impl std::fmt::Debug) {}
-}
-
-mod used_exactly_once {
-    fn foo(x: String) {
-        use_x(x);
-    }
-    fn use_x(_: impl AsRef<str>) {}
-}
-
-mod used_more_than_once {
-    fn foo(x: String) {
-        use_x(&x);
-        use_x_again(&x);
-    }
-    fn use_x(_: impl AsRef<str>) {}
-    fn use_x_again(_: impl AsRef<str>) {}
-}
-
-// https://github.com/rust-lang/rust-clippy/issues/9111#issuecomment-1277114280
-mod issue_9111 {
-    struct A;
-
-    impl Extend<u8> for A {
-        fn extend<T: IntoIterator<Item = u8>>(&mut self, _: T) {
-            unimplemented!()
-        }
-    }
-
-    impl<'a> Extend<&'a u8> for A {
-        fn extend<T: IntoIterator<Item = &'a u8>>(&mut self, _: T) {
-            unimplemented!()
-        }
-    }
-
-    fn main() {
-        let mut a = A;
-        a.extend(&[]); // vs a.extend([]);
-    }
-}
-
-mod issue_9710 {
-    fn main() {
-        let string = String::new();
-        for _i in 0..10 {
-            f(&string);
-        }
-    }
-
-    fn f<T: AsRef<str>>(_: T) {}
-}
-
-mod issue_9739 {
-    fn foo<D: std::fmt::Display>(_it: impl IntoIterator<Item = D>) {}
-
-    fn main() {
-        foo(if std::env::var_os("HI").is_some() {
-            &[0]
-        } else {
-            &[] as &[u32]
-        });
-    }
-}
-
-mod issue_9739_method_variant {
-    struct S;
-
-    impl S {
-        fn foo<D: std::fmt::Display>(&self, _it: impl IntoIterator<Item = D>) {}
-    }
-
-    fn main() {
-        S.foo(if std::env::var_os("HI").is_some() {
-            &[0]
-        } else {
-            &[] as &[u32]
-        });
-    }
-}
-
-mod issue_9782 {
-    fn foo<T: AsRef<[u8]>>(t: T) {
-        println!("{}", std::mem::size_of::<T>());
-        let _t: &[u8] = t.as_ref();
-    }
-
-    fn main() {
-        let a: [u8; 100] = [0u8; 100];
-
-        // 100
-        foo::<[u8; 100]>(a);
-        foo(a);
-
-        // 16
-        foo::<&[u8]>(&a);
-        foo(a.as_slice());
-
-        // 8
-        foo::<&[u8; 100]>(&a);
-        foo(a);
-    }
-}
-
-mod issue_9782_type_relative_variant {
-    struct S;
-
-    impl S {
-        fn foo<T: AsRef<[u8]>>(t: T) {
-            println!("{}", std::mem::size_of::<T>());
-            let _t: &[u8] = t.as_ref();
-        }
-    }
-
-    fn main() {
-        let a: [u8; 100] = [0u8; 100];
-
-        S::foo::<&[u8; 100]>(&a);
-    }
-}
-
-mod issue_9782_method_variant {
-    struct S;
-
-    impl S {
-        fn foo<T: AsRef<[u8]>>(&self, t: T) {
-            println!("{}", std::mem::size_of::<T>());
-            let _t: &[u8] = t.as_ref();
-        }
-    }
-
-    fn main() {
-        let a: [u8; 100] = [0u8; 100];
-
-        S.foo::<&[u8; 100]>(&a);
-    }
-}
-
-mod issue_10535 {
-    static SOME_STATIC: String = String::new();
-
-    static UNIT: () = compute(&SOME_STATIC);
-
-    pub const fn compute<T>(_: T)
-    where
-        T: Copy,
-    {
-    }
-}
-
 mod issue_10253 {
     struct S;
     trait X {
diff --git a/tests/ui/needless_borrow.rs b/tests/ui/needless_borrow.rs
index 34a95d18463..0cd6e41b8a4 100644
--- a/tests/ui/needless_borrow.rs
+++ b/tests/ui/needless_borrow.rs
@@ -131,21 +131,6 @@ fn main() {
             0
         }
     }
-
-    let _ = std::process::Command::new("ls").args(&["-a", "-l"]).status().unwrap();
-    let _ = std::path::Path::new(".").join(&&".");
-    deref_target_is_x(&X);
-    multiple_constraints(&[[""]]);
-    multiple_constraints_normalizes_to_same(&X, X);
-    let _ = Some("").unwrap_or(&"");
-    let _ = std::fs::write("x", &"".to_string());
-
-    only_sized(&""); // Don't lint. `Sized` is only bound
-    let _ = std::any::Any::type_id(&""); // Don't lint. `Any` is only bound
-    let _ = Box::new(&""); // Don't lint. Type parameter appears in return type
-    ref_as_ref_path(&""); // Don't lint. Argument type is not a type parameter
-    refs_only(&()); // Don't lint. `&T` implements trait, but `T` doesn't
-    multiple_constraints_normalizes_to_different(&[[""]], &[""]); // Don't lint. Projected type appears in arguments
 }
 
 #[allow(clippy::needless_borrowed_reference)]
@@ -201,103 +186,6 @@ mod issue9160 {
     }
 }
 
-#[derive(Clone, Copy)]
-struct X;
-
-impl std::ops::Deref for X {
-    type Target = X;
-    fn deref(&self) -> &Self::Target {
-        self
-    }
-}
-
-fn deref_target_is_x<T>(_: T)
-where
-    T: std::ops::Deref<Target = X>,
-{
-}
-
-fn multiple_constraints<T, U, V, X, Y>(_: T)
-where
-    T: IntoIterator<Item = U> + IntoIterator<Item = X>,
-    U: IntoIterator<Item = V>,
-    V: AsRef<str>,
-    X: IntoIterator<Item = Y>,
-    Y: AsRef<std::ffi::OsStr>,
-{
-}
-
-fn multiple_constraints_normalizes_to_same<T, U, V>(_: T, _: V)
-where
-    T: std::ops::Deref<Target = U>,
-    U: std::ops::Deref<Target = V>,
-{
-}
-
-fn only_sized<T>(_: T) {}
-
-fn ref_as_ref_path<T: 'static>(_: &'static T)
-where
-    &'static T: AsRef<std::path::Path>,
-{
-}
-
-trait RefsOnly {
-    type Referent;
-}
-
-impl<T> RefsOnly for &T {
-    type Referent = T;
-}
-
-fn refs_only<T, U>(_: T)
-where
-    T: RefsOnly<Referent = U>,
-{
-}
-
-fn multiple_constraints_normalizes_to_different<T, U, V>(_: T, _: U)
-where
-    T: IntoIterator<Item = U>,
-    U: IntoIterator<Item = V>,
-    V: AsRef<str>,
-{
-}
-
-// https://github.com/rust-lang/rust-clippy/pull/9136#pullrequestreview-1037379321
-mod copyable_iterator {
-    #[derive(Clone, Copy)]
-    struct Iter;
-    impl Iterator for Iter {
-        type Item = ();
-        fn next(&mut self) -> Option<Self::Item> {
-            None
-        }
-    }
-    fn takes_iter(_: impl Iterator) {}
-    fn dont_warn(mut x: Iter) {
-        takes_iter(&mut x);
-    }
-    #[allow(unused_mut)]
-    fn warn(mut x: &mut Iter) {
-        takes_iter(&mut x)
-    }
-}
-
-#[clippy::msrv = "1.52.0"]
-mod under_msrv {
-    fn foo() {
-        let _ = std::process::Command::new("ls").args(&["-a", "-l"]).status().unwrap();
-    }
-}
-
-#[clippy::msrv = "1.53.0"]
-mod meets_msrv {
-    fn foo() {
-        let _ = std::process::Command::new("ls").args(&["-a", "-l"]).status().unwrap();
-    }
-}
-
 fn issue9383() {
     // Should not lint because unions need explicit deref when accessing field
     use std::mem::ManuallyDrop;
@@ -326,184 +214,6 @@ fn issue9383() {
     }
 }
 
-fn closure_test() {
-    let env = "env".to_owned();
-    let arg = "arg".to_owned();
-    let f = |arg| {
-        let loc = "loc".to_owned();
-        let _ = std::fs::write("x", &env); // Don't lint. In environment
-        let _ = std::fs::write("x", &arg);
-        let _ = std::fs::write("x", &loc);
-    };
-    let _ = std::fs::write("x", &env); // Don't lint. Borrowed by `f`
-    f(arg);
-}
-
-mod significant_drop {
-    #[derive(Debug)]
-    struct X;
-
-    #[derive(Debug)]
-    struct Y;
-
-    impl Drop for Y {
-        fn drop(&mut self) {}
-    }
-
-    fn foo(x: X, y: Y) {
-        debug(&x);
-        debug(&y); // Don't lint. Has significant drop
-    }
-
-    fn debug(_: impl std::fmt::Debug) {}
-}
-
-mod used_exactly_once {
-    fn foo(x: String) {
-        use_x(&x);
-    }
-    fn use_x(_: impl AsRef<str>) {}
-}
-
-mod used_more_than_once {
-    fn foo(x: String) {
-        use_x(&x);
-        use_x_again(&x);
-    }
-    fn use_x(_: impl AsRef<str>) {}
-    fn use_x_again(_: impl AsRef<str>) {}
-}
-
-// https://github.com/rust-lang/rust-clippy/issues/9111#issuecomment-1277114280
-mod issue_9111 {
-    struct A;
-
-    impl Extend<u8> for A {
-        fn extend<T: IntoIterator<Item = u8>>(&mut self, _: T) {
-            unimplemented!()
-        }
-    }
-
-    impl<'a> Extend<&'a u8> for A {
-        fn extend<T: IntoIterator<Item = &'a u8>>(&mut self, _: T) {
-            unimplemented!()
-        }
-    }
-
-    fn main() {
-        let mut a = A;
-        a.extend(&[]); // vs a.extend([]);
-    }
-}
-
-mod issue_9710 {
-    fn main() {
-        let string = String::new();
-        for _i in 0..10 {
-            f(&string);
-        }
-    }
-
-    fn f<T: AsRef<str>>(_: T) {}
-}
-
-mod issue_9739 {
-    fn foo<D: std::fmt::Display>(_it: impl IntoIterator<Item = D>) {}
-
-    fn main() {
-        foo(if std::env::var_os("HI").is_some() {
-            &[0]
-        } else {
-            &[] as &[u32]
-        });
-    }
-}
-
-mod issue_9739_method_variant {
-    struct S;
-
-    impl S {
-        fn foo<D: std::fmt::Display>(&self, _it: impl IntoIterator<Item = D>) {}
-    }
-
-    fn main() {
-        S.foo(if std::env::var_os("HI").is_some() {
-            &[0]
-        } else {
-            &[] as &[u32]
-        });
-    }
-}
-
-mod issue_9782 {
-    fn foo<T: AsRef<[u8]>>(t: T) {
-        println!("{}", std::mem::size_of::<T>());
-        let _t: &[u8] = t.as_ref();
-    }
-
-    fn main() {
-        let a: [u8; 100] = [0u8; 100];
-
-        // 100
-        foo::<[u8; 100]>(a);
-        foo(a);
-
-        // 16
-        foo::<&[u8]>(&a);
-        foo(a.as_slice());
-
-        // 8
-        foo::<&[u8; 100]>(&a);
-        foo(&a);
-    }
-}
-
-mod issue_9782_type_relative_variant {
-    struct S;
-
-    impl S {
-        fn foo<T: AsRef<[u8]>>(t: T) {
-            println!("{}", std::mem::size_of::<T>());
-            let _t: &[u8] = t.as_ref();
-        }
-    }
-
-    fn main() {
-        let a: [u8; 100] = [0u8; 100];
-
-        S::foo::<&[u8; 100]>(&a);
-    }
-}
-
-mod issue_9782_method_variant {
-    struct S;
-
-    impl S {
-        fn foo<T: AsRef<[u8]>>(&self, t: T) {
-            println!("{}", std::mem::size_of::<T>());
-            let _t: &[u8] = t.as_ref();
-        }
-    }
-
-    fn main() {
-        let a: [u8; 100] = [0u8; 100];
-
-        S.foo::<&[u8; 100]>(&a);
-    }
-}
-
-mod issue_10535 {
-    static SOME_STATIC: String = String::new();
-
-    static UNIT: () = compute(&SOME_STATIC);
-
-    pub const fn compute<T>(_: T)
-    where
-        T: Copy,
-    {
-    }
-}
-
 mod issue_10253 {
     struct S;
     trait X {
diff --git a/tests/ui/needless_borrow.stderr b/tests/ui/needless_borrow.stderr
index 8e27014d53c..e91b78b0a15 100644
--- a/tests/ui/needless_borrow.stderr
+++ b/tests/ui/needless_borrow.stderr
@@ -121,101 +121,17 @@ error: this expression creates a reference which is immediately dereferenced by
 LL |     (&&5).foo();
    |     ^^^^^ help: change this to: `(&5)`
 
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:135:51
-   |
-LL |     let _ = std::process::Command::new("ls").args(&["-a", "-l"]).status().unwrap();
-   |                                                   ^^^^^^^^^^^^^ help: change this to: `["-a", "-l"]`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:136:44
-   |
-LL |     let _ = std::path::Path::new(".").join(&&".");
-   |                                            ^^^^^ help: change this to: `"."`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:137:23
-   |
-LL |     deref_target_is_x(&X);
-   |                       ^^ help: change this to: `X`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:138:26
-   |
-LL |     multiple_constraints(&[[""]]);
-   |                          ^^^^^^^ help: change this to: `[[""]]`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:139:45
-   |
-LL |     multiple_constraints_normalizes_to_same(&X, X);
-   |                                             ^^ help: change this to: `X`
-
-error: this expression creates a reference which is immediately dereferenced by the compiler
-  --> $DIR/needless_borrow.rs:140:32
-   |
-LL |     let _ = Some("").unwrap_or(&"");
-   |                                ^^^ help: change this to: `""`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:141:33
-   |
-LL |     let _ = std::fs::write("x", &"".to_string());
-   |                                 ^^^^^^^^^^^^^^^ help: change this to: `"".to_string()`
-
 error: this expression borrows a value the compiler would automatically borrow
-  --> $DIR/needless_borrow.rs:190:13
+  --> $DIR/needless_borrow.rs:175:13
    |
 LL |             (&self.f)()
    |             ^^^^^^^^^ help: change this to: `(self.f)`
 
 error: this expression borrows a value the compiler would automatically borrow
-  --> $DIR/needless_borrow.rs:199:13
+  --> $DIR/needless_borrow.rs:184:13
    |
 LL |             (&mut self.f)()
    |             ^^^^^^^^^^^^^ help: change this to: `(self.f)`
 
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:283:20
-   |
-LL |         takes_iter(&mut x)
-   |                    ^^^^^^ help: change this to: `x`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:297:55
-   |
-LL |         let _ = std::process::Command::new("ls").args(&["-a", "-l"]).status().unwrap();
-   |                                                       ^^^^^^^^^^^^^ help: change this to: `["-a", "-l"]`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:335:37
-   |
-LL |         let _ = std::fs::write("x", &arg);
-   |                                     ^^^^ help: change this to: `arg`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:336:37
-   |
-LL |         let _ = std::fs::write("x", &loc);
-   |                                     ^^^^ help: change this to: `loc`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:354:15
-   |
-LL |         debug(&x);
-   |               ^^ help: change this to: `x`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:363:15
-   |
-LL |         use_x(&x);
-   |               ^^ help: change this to: `x`
-
-error: the borrowed expression implements the required traits
-  --> $DIR/needless_borrow.rs:457:13
-   |
-LL |         foo(&a);
-   |             ^^ help: change this to: `a`
-
-error: aborting due to 36 previous errors
+error: aborting due to 22 previous errors
 
diff --git a/tests/ui/needless_borrows_for_generic_args.fixed b/tests/ui/needless_borrows_for_generic_args.fixed
new file mode 100644
index 00000000000..2a335516f51
--- /dev/null
+++ b/tests/ui/needless_borrows_for_generic_args.fixed
@@ -0,0 +1,287 @@
+#![warn(clippy::needless_borrows_for_generic_args)]
+#![allow(
+    clippy::unnecessary_to_owned,
+    clippy::unnecessary_literal_unwrap,
+    clippy::needless_borrow
+)]
+
+use core::ops::Deref;
+use std::any::Any;
+use std::ffi::OsStr;
+use std::fmt::{Debug, Display};
+use std::path::Path;
+use std::process::Command;
+
+fn main() {
+    let _ = Command::new("ls").args(["-a", "-l"]).status().unwrap();
+    let _ = Path::new(".").join(".");
+    let _ = Any::type_id(&""); // Don't lint. `Any` is only bound
+    let _ = Box::new(&""); // Don't lint. Type parameter appears in return type
+    let _ = Some("").unwrap_or(&"");
+    let _ = std::fs::write("x", "".to_string());
+
+    {
+        #[derive(Clone, Copy)]
+        struct X;
+
+        impl Deref for X {
+            type Target = X;
+            fn deref(&self) -> &Self::Target {
+                self
+            }
+        }
+
+        fn deref_target_is_x<T: Deref<Target = X>>(_: T) {}
+
+        deref_target_is_x(X);
+    }
+    {
+        fn multiple_constraints<T, U, V, X, Y>(_: T)
+        where
+            T: IntoIterator<Item = U> + IntoIterator<Item = X>,
+            U: IntoIterator<Item = V>,
+            V: AsRef<str>,
+            X: IntoIterator<Item = Y>,
+            Y: AsRef<OsStr>,
+        {
+        }
+
+        multiple_constraints([[""]]);
+    }
+    {
+        #[derive(Clone, Copy)]
+        struct X;
+
+        impl Deref for X {
+            type Target = X;
+            fn deref(&self) -> &Self::Target {
+                self
+            }
+        }
+
+        fn multiple_constraints_normalizes_to_same<T, U, V>(_: T, _: V)
+        where
+            T: Deref<Target = U>,
+            U: Deref<Target = V>,
+        {
+        }
+
+        multiple_constraints_normalizes_to_same(X, X);
+    }
+    {
+        fn only_sized<T>(_: T) {}
+        only_sized(&""); // Don't lint. `Sized` is only bound
+    }
+    {
+        fn ref_as_ref_path<T: 'static>(_: &'static T)
+        where
+            &'static T: AsRef<Path>,
+        {
+        }
+
+        ref_as_ref_path(&""); // Don't lint. Argument type is not a type parameter
+    }
+    {
+        trait RefsOnly {
+            type Referent;
+        }
+
+        impl<T> RefsOnly for &T {
+            type Referent = T;
+        }
+
+        fn refs_only<T, U>(_: T)
+        where
+            T: RefsOnly<Referent = U>,
+        {
+        }
+
+        refs_only(&()); // Don't lint. `&T` implements trait, but `T` doesn't
+    }
+    {
+        fn multiple_constraints_normalizes_to_different<T, U, V>(_: T, _: U)
+        where
+            T: IntoIterator<Item = U>,
+            U: IntoIterator<Item = V>,
+            V: AsRef<str>,
+        {
+        }
+        multiple_constraints_normalizes_to_different(&[[""]], &[""]); // Don't lint. Projected type appears in arguments
+    }
+    // https://github.com/rust-lang/rust-clippy/pull/9136#pullrequestreview-1037379321
+    {
+        #[derive(Clone, Copy)]
+        struct Iter;
+        impl Iterator for Iter {
+            type Item = ();
+            fn next(&mut self) -> Option<Self::Item> {
+                None
+            }
+        }
+        fn takes_iter(_: impl Iterator) {}
+        fn dont_warn(mut x: Iter) {
+            takes_iter(&mut x);
+        }
+        #[allow(unused_mut)]
+        fn warn(mut x: &mut Iter) {
+            takes_iter(x)
+        }
+    }
+    #[clippy::msrv = "1.52.0"]
+    {
+        let _ = Command::new("ls").args(&["-a", "-l"]).status().unwrap();
+    };
+    #[clippy::msrv = "1.53.0"]
+    {
+        let _ = Command::new("ls").args(["-a", "-l"]).status().unwrap();
+    };
+    {
+        let env = "env".to_owned();
+        let arg = "arg".to_owned();
+        let f = |arg| {
+            let loc = "loc".to_owned();
+            let _ = std::fs::write("x", &env); // Don't lint. In environment
+            let _ = std::fs::write("x", arg);
+            let _ = std::fs::write("x", loc);
+        };
+        let _ = std::fs::write("x", &env); // Don't lint. Borrowed by `f`
+        f(arg);
+    }
+    {
+        #[derive(Debug)]
+        struct X;
+
+        impl Drop for X {
+            fn drop(&mut self) {}
+        }
+
+        fn f(_: impl Debug) {}
+
+        let x = X;
+        f(&x); // Don't lint. Has significant drop
+    }
+    {
+        fn f(_: impl AsRef<str>) {}
+
+        let x = String::new();
+        f(x);
+    }
+    {
+        fn f(_: impl AsRef<str>) {}
+        fn f2(_: impl AsRef<str>) {}
+
+        let x = String::new();
+        f(&x);
+        f2(&x);
+    }
+    // https://github.com/rust-lang/rust-clippy/issues/9111#issuecomment-1277114280
+    // issue 9111
+    {
+        struct A;
+
+        impl Extend<u8> for A {
+            fn extend<T: IntoIterator<Item = u8>>(&mut self, _: T) {
+                unimplemented!()
+            }
+        }
+
+        impl<'a> Extend<&'a u8> for A {
+            fn extend<T: IntoIterator<Item = &'a u8>>(&mut self, _: T) {
+                unimplemented!()
+            }
+        }
+
+        let mut a = A;
+        a.extend(&[]); // vs a.extend([]);
+    }
+    // issue 9710
+    {
+        fn f(_: impl AsRef<str>) {}
+
+        let x = String::new();
+        for _ in 0..10 {
+            f(&x);
+        }
+    }
+    // issue 9739
+    {
+        fn foo<D: Display>(_it: impl IntoIterator<Item = D>) {}
+        foo(if std::env::var_os("HI").is_some() {
+            &[0]
+        } else {
+            &[] as &[u32]
+        });
+    }
+    {
+        struct S;
+
+        impl S {
+            fn foo<D: Display>(&self, _it: impl IntoIterator<Item = D>) {}
+        }
+
+        S.foo(if std::env::var_os("HI").is_some() {
+            &[0]
+        } else {
+            &[] as &[u32]
+        });
+    }
+    // issue 9782
+    {
+        fn foo<T: AsRef<[u8]>>(t: T) {
+            println!("{}", std::mem::size_of::<T>());
+            let _t: &[u8] = t.as_ref();
+        }
+
+        let a: [u8; 100] = [0u8; 100];
+
+        // 100
+        foo::<[u8; 100]>(a);
+        foo(a);
+
+        // 16
+        foo::<&[u8]>(&a);
+        foo(a.as_slice());
+
+        // 8
+        foo::<&[u8; 100]>(&a);
+        foo(a);
+    }
+    {
+        struct S;
+
+        impl S {
+            fn foo<T: AsRef<[u8]>>(t: T) {
+                println!("{}", std::mem::size_of::<T>());
+                let _t: &[u8] = t.as_ref();
+            }
+        }
+
+        let a: [u8; 100] = [0u8; 100];
+        S::foo::<&[u8; 100]>(&a);
+    }
+    {
+        struct S;
+
+        impl S {
+            fn foo<T: AsRef<[u8]>>(&self, t: T) {
+                println!("{}", std::mem::size_of::<T>());
+                let _t: &[u8] = t.as_ref();
+            }
+        }
+
+        let a: [u8; 100] = [0u8; 100];
+        S.foo::<&[u8; 100]>(&a);
+    }
+    // issue 10535
+    {
+        static SOME_STATIC: String = String::new();
+
+        static UNIT: () = compute(&SOME_STATIC);
+
+        pub const fn compute<T>(_: T)
+        where
+            T: Copy,
+        {
+        }
+    }
+}
diff --git a/tests/ui/needless_borrows_for_generic_args.rs b/tests/ui/needless_borrows_for_generic_args.rs
new file mode 100644
index 00000000000..f0567f486ac
--- /dev/null
+++ b/tests/ui/needless_borrows_for_generic_args.rs
@@ -0,0 +1,287 @@
+#![warn(clippy::needless_borrows_for_generic_args)]
+#![allow(
+    clippy::unnecessary_to_owned,
+    clippy::unnecessary_literal_unwrap,
+    clippy::needless_borrow
+)]
+
+use core::ops::Deref;
+use std::any::Any;
+use std::ffi::OsStr;
+use std::fmt::{Debug, Display};
+use std::path::Path;
+use std::process::Command;
+
+fn main() {
+    let _ = Command::new("ls").args(&["-a", "-l"]).status().unwrap();
+    let _ = Path::new(".").join(&&".");
+    let _ = Any::type_id(&""); // Don't lint. `Any` is only bound
+    let _ = Box::new(&""); // Don't lint. Type parameter appears in return type
+    let _ = Some("").unwrap_or(&"");
+    let _ = std::fs::write("x", &"".to_string());
+
+    {
+        #[derive(Clone, Copy)]
+        struct X;
+
+        impl Deref for X {
+            type Target = X;
+            fn deref(&self) -> &Self::Target {
+                self
+            }
+        }
+
+        fn deref_target_is_x<T: Deref<Target = X>>(_: T) {}
+
+        deref_target_is_x(&X);
+    }
+    {
+        fn multiple_constraints<T, U, V, X, Y>(_: T)
+        where
+            T: IntoIterator<Item = U> + IntoIterator<Item = X>,
+            U: IntoIterator<Item = V>,
+            V: AsRef<str>,
+            X: IntoIterator<Item = Y>,
+            Y: AsRef<OsStr>,
+        {
+        }
+
+        multiple_constraints(&[[""]]);
+    }
+    {
+        #[derive(Clone, Copy)]
+        struct X;
+
+        impl Deref for X {
+            type Target = X;
+            fn deref(&self) -> &Self::Target {
+                self
+            }
+        }
+
+        fn multiple_constraints_normalizes_to_same<T, U, V>(_: T, _: V)
+        where
+            T: Deref<Target = U>,
+            U: Deref<Target = V>,
+        {
+        }
+
+        multiple_constraints_normalizes_to_same(&X, X);
+    }
+    {
+        fn only_sized<T>(_: T) {}
+        only_sized(&""); // Don't lint. `Sized` is only bound
+    }
+    {
+        fn ref_as_ref_path<T: 'static>(_: &'static T)
+        where
+            &'static T: AsRef<Path>,
+        {
+        }
+
+        ref_as_ref_path(&""); // Don't lint. Argument type is not a type parameter
+    }
+    {
+        trait RefsOnly {
+            type Referent;
+        }
+
+        impl<T> RefsOnly for &T {
+            type Referent = T;
+        }
+
+        fn refs_only<T, U>(_: T)
+        where
+            T: RefsOnly<Referent = U>,
+        {
+        }
+
+        refs_only(&()); // Don't lint. `&T` implements trait, but `T` doesn't
+    }
+    {
+        fn multiple_constraints_normalizes_to_different<T, U, V>(_: T, _: U)
+        where
+            T: IntoIterator<Item = U>,
+            U: IntoIterator<Item = V>,
+            V: AsRef<str>,
+        {
+        }
+        multiple_constraints_normalizes_to_different(&[[""]], &[""]); // Don't lint. Projected type appears in arguments
+    }
+    // https://github.com/rust-lang/rust-clippy/pull/9136#pullrequestreview-1037379321
+    {
+        #[derive(Clone, Copy)]
+        struct Iter;
+        impl Iterator for Iter {
+            type Item = ();
+            fn next(&mut self) -> Option<Self::Item> {
+                None
+            }
+        }
+        fn takes_iter(_: impl Iterator) {}
+        fn dont_warn(mut x: Iter) {
+            takes_iter(&mut x);
+        }
+        #[allow(unused_mut)]
+        fn warn(mut x: &mut Iter) {
+            takes_iter(&mut x)
+        }
+    }
+    #[clippy::msrv = "1.52.0"]
+    {
+        let _ = Command::new("ls").args(&["-a", "-l"]).status().unwrap();
+    };
+    #[clippy::msrv = "1.53.0"]
+    {
+        let _ = Command::new("ls").args(&["-a", "-l"]).status().unwrap();
+    };
+    {
+        let env = "env".to_owned();
+        let arg = "arg".to_owned();
+        let f = |arg| {
+            let loc = "loc".to_owned();
+            let _ = std::fs::write("x", &env); // Don't lint. In environment
+            let _ = std::fs::write("x", &arg);
+            let _ = std::fs::write("x", &loc);
+        };
+        let _ = std::fs::write("x", &env); // Don't lint. Borrowed by `f`
+        f(arg);
+    }
+    {
+        #[derive(Debug)]
+        struct X;
+
+        impl Drop for X {
+            fn drop(&mut self) {}
+        }
+
+        fn f(_: impl Debug) {}
+
+        let x = X;
+        f(&x); // Don't lint. Has significant drop
+    }
+    {
+        fn f(_: impl AsRef<str>) {}
+
+        let x = String::new();
+        f(&x);
+    }
+    {
+        fn f(_: impl AsRef<str>) {}
+        fn f2(_: impl AsRef<str>) {}
+
+        let x = String::new();
+        f(&x);
+        f2(&x);
+    }
+    // https://github.com/rust-lang/rust-clippy/issues/9111#issuecomment-1277114280
+    // issue 9111
+    {
+        struct A;
+
+        impl Extend<u8> for A {
+            fn extend<T: IntoIterator<Item = u8>>(&mut self, _: T) {
+                unimplemented!()
+            }
+        }
+
+        impl<'a> Extend<&'a u8> for A {
+            fn extend<T: IntoIterator<Item = &'a u8>>(&mut self, _: T) {
+                unimplemented!()
+            }
+        }
+
+        let mut a = A;
+        a.extend(&[]); // vs a.extend([]);
+    }
+    // issue 9710
+    {
+        fn f(_: impl AsRef<str>) {}
+
+        let x = String::new();
+        for _ in 0..10 {
+            f(&x);
+        }
+    }
+    // issue 9739
+    {
+        fn foo<D: Display>(_it: impl IntoIterator<Item = D>) {}
+        foo(if std::env::var_os("HI").is_some() {
+            &[0]
+        } else {
+            &[] as &[u32]
+        });
+    }
+    {
+        struct S;
+
+        impl S {
+            fn foo<D: Display>(&self, _it: impl IntoIterator<Item = D>) {}
+        }
+
+        S.foo(if std::env::var_os("HI").is_some() {
+            &[0]
+        } else {
+            &[] as &[u32]
+        });
+    }
+    // issue 9782
+    {
+        fn foo<T: AsRef<[u8]>>(t: T) {
+            println!("{}", std::mem::size_of::<T>());
+            let _t: &[u8] = t.as_ref();
+        }
+
+        let a: [u8; 100] = [0u8; 100];
+
+        // 100
+        foo::<[u8; 100]>(a);
+        foo(a);
+
+        // 16
+        foo::<&[u8]>(&a);
+        foo(a.as_slice());
+
+        // 8
+        foo::<&[u8; 100]>(&a);
+        foo(&a);
+    }
+    {
+        struct S;
+
+        impl S {
+            fn foo<T: AsRef<[u8]>>(t: T) {
+                println!("{}", std::mem::size_of::<T>());
+                let _t: &[u8] = t.as_ref();
+            }
+        }
+
+        let a: [u8; 100] = [0u8; 100];
+        S::foo::<&[u8; 100]>(&a);
+    }
+    {
+        struct S;
+
+        impl S {
+            fn foo<T: AsRef<[u8]>>(&self, t: T) {
+                println!("{}", std::mem::size_of::<T>());
+                let _t: &[u8] = t.as_ref();
+            }
+        }
+
+        let a: [u8; 100] = [0u8; 100];
+        S.foo::<&[u8; 100]>(&a);
+    }
+    // issue 10535
+    {
+        static SOME_STATIC: String = String::new();
+
+        static UNIT: () = compute(&SOME_STATIC);
+
+        pub const fn compute<T>(_: T)
+        where
+            T: Copy,
+        {
+        }
+    }
+}
diff --git a/tests/ui/needless_borrows_for_generic_args.stderr b/tests/ui/needless_borrows_for_generic_args.stderr
new file mode 100644
index 00000000000..e2cde2c59a6
--- /dev/null
+++ b/tests/ui/needless_borrows_for_generic_args.stderr
@@ -0,0 +1,77 @@
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:16:37
+   |
+LL |     let _ = Command::new("ls").args(&["-a", "-l"]).status().unwrap();
+   |                                     ^^^^^^^^^^^^^ help: change this to: `["-a", "-l"]`
+   |
+   = note: `-D clippy::needless-borrows-for-generic-args` implied by `-D warnings`
+   = help: to override `-D warnings` add `#[allow(clippy::needless_borrows_for_generic_args)]`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:17:33
+   |
+LL |     let _ = Path::new(".").join(&&".");
+   |                                 ^^^^^ help: change this to: `"."`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:21:33
+   |
+LL |     let _ = std::fs::write("x", &"".to_string());
+   |                                 ^^^^^^^^^^^^^^^ help: change this to: `"".to_string()`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:36:27
+   |
+LL |         deref_target_is_x(&X);
+   |                           ^^ help: change this to: `X`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:49:30
+   |
+LL |         multiple_constraints(&[[""]]);
+   |                              ^^^^^^^ help: change this to: `[[""]]`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:69:49
+   |
+LL |         multiple_constraints_normalizes_to_same(&X, X);
+   |                                                 ^^ help: change this to: `X`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:127:24
+   |
+LL |             takes_iter(&mut x)
+   |                        ^^^^^^ help: change this to: `x`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:136:41
+   |
+LL |         let _ = Command::new("ls").args(&["-a", "-l"]).status().unwrap();
+   |                                         ^^^^^^^^^^^^^ help: change this to: `["-a", "-l"]`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:144:41
+   |
+LL |             let _ = std::fs::write("x", &arg);
+   |                                         ^^^^ help: change this to: `arg`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:145:41
+   |
+LL |             let _ = std::fs::write("x", &loc);
+   |                                         ^^^^ help: change this to: `loc`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:167:11
+   |
+LL |         f(&x);
+   |           ^^ help: change this to: `x`
+
+error: the borrowed expression implements the required traits
+  --> $DIR/needless_borrows_for_generic_args.rs:247:13
+   |
+LL |         foo(&a);
+   |             ^^ help: change this to: `a`
+
+error: aborting due to 12 previous errors
+
diff --git a/tests/ui/regex.rs b/tests/ui/regex.rs
index 5259d9ce04b..094d9574ae9 100644
--- a/tests/ui/regex.rs
+++ b/tests/ui/regex.rs
@@ -2,7 +2,8 @@
     unused,
     clippy::needless_raw_strings,
     clippy::needless_raw_string_hashes,
-    clippy::needless_borrow
+    clippy::needless_borrow,
+    clippy::needless_borrows_for_generic_args
 )]
 #![warn(clippy::invalid_regex, clippy::trivial_regex)]
 
diff --git a/tests/ui/regex.stderr b/tests/ui/regex.stderr
index 91f90157e68..6d98d691d6f 100644
--- a/tests/ui/regex.stderr
+++ b/tests/ui/regex.stderr
@@ -1,5 +1,5 @@
 error: trivial regex
-  --> $DIR/regex.rs:18:45
+  --> $DIR/regex.rs:19:45
    |
 LL |     let pipe_in_wrong_position = Regex::new("|");
    |                                             ^^^
@@ -9,7 +9,7 @@ LL |     let pipe_in_wrong_position = Regex::new("|");
    = help: to override `-D warnings` add `#[allow(clippy::trivial_regex)]`
 
 error: trivial regex
-  --> $DIR/regex.rs:20:60
+  --> $DIR/regex.rs:21:60
    |
 LL |     let pipe_in_wrong_position_builder = RegexBuilder::new("|");
    |                                                            ^^^
@@ -17,7 +17,7 @@ LL |     let pipe_in_wrong_position_builder = RegexBuilder::new("|");
    = help: the regex is unlikely to be useful as it is
 
 error: regex syntax error: invalid character class range, the start must be <= the end
-  --> $DIR/regex.rs:22:42
+  --> $DIR/regex.rs:23:42
    |
 LL |     let wrong_char_ranice = Regex::new("[z-a]");
    |                                          ^^^
@@ -26,7 +26,7 @@ LL |     let wrong_char_ranice = Regex::new("[z-a]");
    = help: to override `-D warnings` add `#[allow(clippy::invalid_regex)]`
 
 error: regex syntax error: invalid character class range, the start must be <= the end
-  --> $DIR/regex.rs:25:37
+  --> $DIR/regex.rs:26:37
    |
 LL |     let some_unicode = Regex::new("[é-è]");
    |                                     ^^^
@@ -35,13 +35,13 @@ error: regex parse error:
            (
            ^
        error: unclosed group
-  --> $DIR/regex.rs:28:33
+  --> $DIR/regex.rs:29:33
    |
 LL |     let some_regex = Regex::new(OPENING_PAREN);
    |                                 ^^^^^^^^^^^^^
 
 error: trivial regex
-  --> $DIR/regex.rs:30:53
+  --> $DIR/regex.rs:31:53
    |
 LL |     let binary_pipe_in_wrong_position = BRegex::new("|");
    |                                                     ^^^
@@ -52,7 +52,7 @@ error: regex parse error:
            (
            ^
        error: unclosed group
-  --> $DIR/regex.rs:32:41
+  --> $DIR/regex.rs:33:41
    |
 LL |     let some_binary_regex = BRegex::new(OPENING_PAREN);
    |                                         ^^^^^^^^^^^^^
@@ -61,7 +61,7 @@ error: regex parse error:
            (
            ^
        error: unclosed group
-  --> $DIR/regex.rs:33:56
+  --> $DIR/regex.rs:34:56
    |
 LL |     let some_binary_regex_builder = BRegexBuilder::new(OPENING_PAREN);
    |                                                        ^^^^^^^^^^^^^
@@ -70,7 +70,7 @@ error: regex parse error:
            (
            ^
        error: unclosed group
-  --> $DIR/regex.rs:45:37
+  --> $DIR/regex.rs:46:37
    |
 LL |     let set_error = RegexSet::new(&[OPENING_PAREN, r"[a-z]+\.(com|org|net)"]);
    |                                     ^^^^^^^^^^^^^
@@ -79,7 +79,7 @@ error: regex parse error:
            (
            ^
        error: unclosed group
-  --> $DIR/regex.rs:46:39
+  --> $DIR/regex.rs:47:39
    |
 LL |     let bset_error = BRegexSet::new(&[OPENING_PAREN, r"[a-z]+\.(com|org|net)"]);
    |                                       ^^^^^^^^^^^^^
@@ -88,7 +88,7 @@ error: regex parse error:
            \b\c
              ^^
        error: unrecognized escape sequence
-  --> $DIR/regex.rs:53:42
+  --> $DIR/regex.rs:54:42
    |
 LL |     let escaped_string_span = Regex::new("\\b\\c");
    |                                          ^^^^^^^^
@@ -96,19 +96,19 @@ LL |     let escaped_string_span = Regex::new("\\b\\c");
    = help: consider using a raw string literal: `r".."`
 
 error: regex syntax error: duplicate flag
-  --> $DIR/regex.rs:55:34
+  --> $DIR/regex.rs:56:34
    |
 LL |     let aux_span = Regex::new("(?ixi)");
    |                                  ^ ^
 
 error: regex syntax error: pattern can match invalid UTF-8
-  --> $DIR/regex.rs:61:53
+  --> $DIR/regex.rs:62:53
    |
 LL |     let invalid_utf8_should_lint = Regex::new("(?-u).");
    |                                                     ^
 
 error: trivial regex
-  --> $DIR/regex.rs:66:33
+  --> $DIR/regex.rs:67:33
    |
 LL |     let trivial_eq = Regex::new("^foobar$");
    |                                 ^^^^^^^^^^
@@ -116,7 +116,7 @@ LL |     let trivial_eq = Regex::new("^foobar$");
    = help: consider using `==` on `str`s
 
 error: trivial regex
-  --> $DIR/regex.rs:69:48
+  --> $DIR/regex.rs:70:48
    |
 LL |     let trivial_eq_builder = RegexBuilder::new("^foobar$");
    |                                                ^^^^^^^^^^
@@ -124,7 +124,7 @@ LL |     let trivial_eq_builder = RegexBuilder::new("^foobar$");
    = help: consider using `==` on `str`s
 
 error: trivial regex
-  --> $DIR/regex.rs:72:42
+  --> $DIR/regex.rs:73:42
    |
 LL |     let trivial_starts_with = Regex::new("^foobar");
    |                                          ^^^^^^^^^
@@ -132,7 +132,7 @@ LL |     let trivial_starts_with = Regex::new("^foobar");
    = help: consider using `str::starts_with`
 
 error: trivial regex
-  --> $DIR/regex.rs:75:40
+  --> $DIR/regex.rs:76:40
    |
 LL |     let trivial_ends_with = Regex::new("foobar$");
    |                                        ^^^^^^^^^
@@ -140,7 +140,7 @@ LL |     let trivial_ends_with = Regex::new("foobar$");
    = help: consider using `str::ends_with`
 
 error: trivial regex
-  --> $DIR/regex.rs:78:39
+  --> $DIR/regex.rs:79:39
    |
 LL |     let trivial_contains = Regex::new("foobar");
    |                                       ^^^^^^^^
@@ -148,7 +148,7 @@ LL |     let trivial_contains = Regex::new("foobar");
    = help: consider using `str::contains`
 
 error: trivial regex
-  --> $DIR/regex.rs:81:39
+  --> $DIR/regex.rs:82:39
    |
 LL |     let trivial_contains = Regex::new(NOT_A_REAL_REGEX);
    |                                       ^^^^^^^^^^^^^^^^
@@ -156,7 +156,7 @@ LL |     let trivial_contains = Regex::new(NOT_A_REAL_REGEX);
    = help: consider using `str::contains`
 
 error: trivial regex
-  --> $DIR/regex.rs:84:40
+  --> $DIR/regex.rs:85:40
    |
 LL |     let trivial_backslash = Regex::new("a\\.b");
    |                                        ^^^^^^^
@@ -164,7 +164,7 @@ LL |     let trivial_backslash = Regex::new("a\\.b");
    = help: consider using `str::contains`
 
 error: trivial regex
-  --> $DIR/regex.rs:88:36
+  --> $DIR/regex.rs:89:36
    |
 LL |     let trivial_empty = Regex::new("");
    |                                    ^^
@@ -172,7 +172,7 @@ LL |     let trivial_empty = Regex::new("");
    = help: the regex is unlikely to be useful as it is
 
 error: trivial regex
-  --> $DIR/regex.rs:91:36
+  --> $DIR/regex.rs:92:36
    |
 LL |     let trivial_empty = Regex::new("^");
    |                                    ^^^
@@ -180,7 +180,7 @@ LL |     let trivial_empty = Regex::new("^");
    = help: the regex is unlikely to be useful as it is
 
 error: trivial regex
-  --> $DIR/regex.rs:94:36
+  --> $DIR/regex.rs:95:36
    |
 LL |     let trivial_empty = Regex::new("^$");
    |                                    ^^^^
@@ -188,7 +188,7 @@ LL |     let trivial_empty = Regex::new("^$");
    = help: consider using `str::is_empty`
 
 error: trivial regex
-  --> $DIR/regex.rs:97:44
+  --> $DIR/regex.rs:98:44
    |
 LL |     let binary_trivial_empty = BRegex::new("^$");
    |                                            ^^^^
diff --git a/tests/ui/unnecessary_to_owned.fixed b/tests/ui/unnecessary_to_owned.fixed
index 7b662ca92d2..67faabc53cb 100644
--- a/tests/ui/unnecessary_to_owned.fixed
+++ b/tests/ui/unnecessary_to_owned.fixed
@@ -1,4 +1,4 @@
-#![allow(clippy::needless_borrow, clippy::ptr_arg)]
+#![allow(clippy::needless_borrow, clippy::needless_borrows_for_generic_args, clippy::ptr_arg)]
 #![warn(clippy::unnecessary_to_owned, clippy::redundant_clone)]
 
 use std::borrow::Cow;
diff --git a/tests/ui/unnecessary_to_owned.rs b/tests/ui/unnecessary_to_owned.rs
index d79778a6a2e..99f9136427d 100644
--- a/tests/ui/unnecessary_to_owned.rs
+++ b/tests/ui/unnecessary_to_owned.rs
@@ -1,4 +1,4 @@
-#![allow(clippy::needless_borrow, clippy::ptr_arg)]
+#![allow(clippy::needless_borrow, clippy::needless_borrows_for_generic_args, clippy::ptr_arg)]
 #![warn(clippy::unnecessary_to_owned, clippy::redundant_clone)]
 
 use std::borrow::Cow;