about summary refs log tree commit diff
path: root/src/tools/clippy/tests
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2021-08-13 05:30:37 +0000
committerbors <bors@rust-lang.org>2021-08-13 05:30:37 +0000
commit04c9901a0838d20e6ac0bcda94ea1a8c239bb0d7 (patch)
tree0edaa187be5d38e15b7a7337a613d6803685807c /src/tools/clippy/tests
parent13d6c5c90c84f59441a23ddfc0459b24c438589a (diff)
parentf92a0c8031339b1913e8ca89b1a9311c129c1091 (diff)
downloadrust-04c9901a0838d20e6ac0bcda94ea1a8c239bb0d7.tar.gz
rust-04c9901a0838d20e6ac0bcda94ea1a8c239bb0d7.zip
Auto merge of #87954 - flip1995:clippyup, r=Manishearth
Update Clippy

r? `@Manishearth`
Diffstat (limited to 'src/tools/clippy/tests')
-rw-r--r--src/tools/clippy/tests/ui-toml/functions_maxlines/test.rs16
-rw-r--r--src/tools/clippy/tests/ui-toml/functions_maxlines/test.stderr26
-rw-r--r--src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.rs10
-rw-r--r--src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.stderr28
-rw-r--r--src/tools/clippy/tests/ui/auxiliary/test_macro.rs (renamed from src/tools/clippy/tests/auxiliary/test_macro.rs)0
-rw-r--r--src/tools/clippy/tests/ui/extend_with_drain.fixed7
-rw-r--r--src/tools/clippy/tests/ui/extend_with_drain.rs7
-rw-r--r--src/tools/clippy/tests/ui/extend_with_drain.stderr8
-rw-r--r--src/tools/clippy/tests/ui/implicit_hasher.rs2
-rw-r--r--src/tools/clippy/tests/ui/map_flatten.fixed4
-rw-r--r--src/tools/clippy/tests/ui/map_flatten.rs4
-rw-r--r--src/tools/clippy/tests/ui/map_flatten.stderr20
-rw-r--r--src/tools/clippy/tests/ui/never_loop.stderr5
-rw-r--r--src/tools/clippy/tests/ui/no_effect.stderr8
-rw-r--r--src/tools/clippy/tests/ui/or_fun_call.fixed19
-rw-r--r--src/tools/clippy/tests/ui/or_fun_call.rs19
-rw-r--r--src/tools/clippy/tests/ui/or_fun_call.stderr58
-rw-r--r--src/tools/clippy/tests/ui/similar_names.rs3
-rw-r--r--src/tools/clippy/tests/ui/similar_names.stderr4
-rw-r--r--src/tools/clippy/tests/ui/swap.fixed57
-rw-r--r--src/tools/clippy/tests/ui/swap.rs61
-rw-r--r--src/tools/clippy/tests/ui/swap.stderr63
-rw-r--r--src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.rs2
-rw-r--r--src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.stderr20
-rw-r--r--src/tools/clippy/tests/ui/unwrap_or_else_default.fixed71
-rw-r--r--src/tools/clippy/tests/ui/unwrap_or_else_default.rs71
-rw-r--r--src/tools/clippy/tests/ui/unwrap_or_else_default.stderr22
-rw-r--r--src/tools/clippy/tests/ui/while_let_on_iterator.fixed32
-rw-r--r--src/tools/clippy/tests/ui/while_let_on_iterator.rs32
-rw-r--r--src/tools/clippy/tests/ui/while_let_on_iterator.stderr16
30 files changed, 608 insertions, 87 deletions
diff --git a/src/tools/clippy/tests/ui-toml/functions_maxlines/test.rs b/src/tools/clippy/tests/ui-toml/functions_maxlines/test.rs
index a47677a1f3a..33a3ef75136 100644
--- a/src/tools/clippy/tests/ui-toml/functions_maxlines/test.rs
+++ b/src/tools/clippy/tests/ui-toml/functions_maxlines/test.rs
@@ -1,3 +1,5 @@
+// edition:2018
+
 #![warn(clippy::too_many_lines)]
 
 // This function should be considered one line.
@@ -20,6 +22,20 @@ fn too_many_lines() {
     println!("This is bad.");
 }
 
+// This should only fail once (#7517).
+async fn async_too_many_lines() {
+    println!("This is bad.");
+    println!("This is bad.");
+}
+
+// This should fail only once, without failing on the closure.
+fn closure_too_many_lines() {
+    let _ = {
+        println!("This is bad.");
+        println!("This is bad.");
+    };
+}
+
 // This should be considered one line.
 #[rustfmt::skip]
 fn comment_starts_after_code() {
diff --git a/src/tools/clippy/tests/ui-toml/functions_maxlines/test.stderr b/src/tools/clippy/tests/ui-toml/functions_maxlines/test.stderr
index a27ce945ca5..7551cac9f50 100644
--- a/src/tools/clippy/tests/ui-toml/functions_maxlines/test.stderr
+++ b/src/tools/clippy/tests/ui-toml/functions_maxlines/test.stderr
@@ -1,5 +1,5 @@
 error: this function has too many lines (2/1)
-  --> $DIR/test.rs:18:1
+  --> $DIR/test.rs:20:1
    |
 LL | / fn too_many_lines() {
 LL | |     println!("This is bad.");
@@ -9,8 +9,28 @@ LL | | }
    |
    = note: `-D clippy::too-many-lines` implied by `-D warnings`
 
+error: this function has too many lines (4/1)
+  --> $DIR/test.rs:26:1
+   |
+LL | / async fn async_too_many_lines() {
+LL | |     println!("This is bad.");
+LL | |     println!("This is bad.");
+LL | | }
+   | |_^
+
+error: this function has too many lines (4/1)
+  --> $DIR/test.rs:32:1
+   |
+LL | / fn closure_too_many_lines() {
+LL | |     let _ = {
+LL | |         println!("This is bad.");
+LL | |         println!("This is bad.");
+LL | |     };
+LL | | }
+   | |_^
+
 error: this function has too many lines (2/1)
-  --> $DIR/test.rs:38:1
+  --> $DIR/test.rs:54:1
    |
 LL | / fn comment_before_code() {
 LL | |     let _ = "test";
@@ -19,5 +39,5 @@ LL | |     the code but this line should still count. */ let _ = 5;
 LL | | }
    | |_^
 
-error: aborting due to 2 previous errors
+error: aborting due to 4 previous errors
 
diff --git a/src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.rs b/src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.rs
index e9f042ddefc..5b4adc868df 100644
--- a/src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.rs
+++ b/src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.rs
@@ -32,13 +32,19 @@ macro_rules! type_pos {
     };
 }
 
+macro_rules! printlnfoo {
+    ($thing:expr) => {
+        println!("{}", $thing)
+    };
+}
+
 #[rustfmt::skip]
 fn main() {
     let _ = vec! {1, 2, 3};
     let _ = format!["ugh {} stop being such a good compiler", "hello"];
     let _ = quote!(let x = 1;);
     let _ = quote::quote!(match match match);
-    let _ = test!();
+    let _ = test!(); // trigger when macro def is inside our own crate
     let _ = vec![1,2,3];
 
     let _ = quote::quote! {true || false};
@@ -49,4 +55,6 @@ fn main() {
     let _: type_pos!(usize) = vec![];
 
     eprint!("test if user config overrides defaults");
+
+    printlnfoo!["test if printlnfoo is triggered by println"];
 }
diff --git a/src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.stderr b/src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.stderr
index 86063a08280..87e962b9228 100644
--- a/src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.stderr
+++ b/src/tools/clippy/tests/ui-toml/nonstandard_macro_braces/conf_nonstandard_macro_braces.stderr
@@ -1,48 +1,48 @@
 error: use of irregular braces for `vec!` macro
-  --> $DIR/conf_nonstandard_macro_braces.rs:37:13
+  --> $DIR/conf_nonstandard_macro_braces.rs:43:13
    |
 LL |     let _ = vec! {1, 2, 3};
    |             ^^^^^^^^^^^^^^
    |
    = note: `-D clippy::nonstandard-macro-braces` implied by `-D warnings`
 help: consider writing `vec![1, 2, 3]`
-  --> $DIR/conf_nonstandard_macro_braces.rs:37:13
+  --> $DIR/conf_nonstandard_macro_braces.rs:43:13
    |
 LL |     let _ = vec! {1, 2, 3};
    |             ^^^^^^^^^^^^^^
 
 error: use of irregular braces for `format!` macro
-  --> $DIR/conf_nonstandard_macro_braces.rs:38:13
+  --> $DIR/conf_nonstandard_macro_braces.rs:44:13
    |
 LL |     let _ = format!["ugh {} stop being such a good compiler", "hello"];
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 help: consider writing `format!("ugh () stop being such a good compiler", "hello")`
-  --> $DIR/conf_nonstandard_macro_braces.rs:38:13
+  --> $DIR/conf_nonstandard_macro_braces.rs:44:13
    |
 LL |     let _ = format!["ugh {} stop being such a good compiler", "hello"];
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
 
 error: use of irregular braces for `quote!` macro
-  --> $DIR/conf_nonstandard_macro_braces.rs:39:13
+  --> $DIR/conf_nonstandard_macro_braces.rs:45:13
    |
 LL |     let _ = quote!(let x = 1;);
    |             ^^^^^^^^^^^^^^^^^^
    |
 help: consider writing `quote! {let x = 1;}`
-  --> $DIR/conf_nonstandard_macro_braces.rs:39:13
+  --> $DIR/conf_nonstandard_macro_braces.rs:45:13
    |
 LL |     let _ = quote!(let x = 1;);
    |             ^^^^^^^^^^^^^^^^^^
 
 error: use of irregular braces for `quote::quote!` macro
-  --> $DIR/conf_nonstandard_macro_braces.rs:40:13
+  --> $DIR/conf_nonstandard_macro_braces.rs:46:13
    |
 LL |     let _ = quote::quote!(match match match);
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 help: consider writing `quote::quote! {match match match}`
-  --> $DIR/conf_nonstandard_macro_braces.rs:40:13
+  --> $DIR/conf_nonstandard_macro_braces.rs:46:13
    |
 LL |     let _ = quote::quote!(match match match);
    |             ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -53,7 +53,7 @@ error: use of irregular braces for `vec!` macro
 LL |         vec!{0, 0, 0}
    |         ^^^^^^^^^^^^^
 ...
-LL |     let _ = test!();
+LL |     let _ = test!(); // trigger when macro def is inside our own crate
    |             ------- in this macro invocation
    |
 help: consider writing `vec![0, 0, 0]`
@@ -62,30 +62,30 @@ help: consider writing `vec![0, 0, 0]`
 LL |         vec!{0, 0, 0}
    |         ^^^^^^^^^^^^^
 ...
-LL |     let _ = test!();
+LL |     let _ = test!(); // trigger when macro def is inside our own crate
    |             ------- in this macro invocation
    = note: this error originates in the macro `test` (in Nightly builds, run with -Z macro-backtrace for more info)
 
 error: use of irregular braces for `type_pos!` macro
-  --> $DIR/conf_nonstandard_macro_braces.rs:49:12
+  --> $DIR/conf_nonstandard_macro_braces.rs:55:12
    |
 LL |     let _: type_pos!(usize) = vec![];
    |            ^^^^^^^^^^^^^^^^
    |
 help: consider writing `type_pos![usize]`
-  --> $DIR/conf_nonstandard_macro_braces.rs:49:12
+  --> $DIR/conf_nonstandard_macro_braces.rs:55:12
    |
 LL |     let _: type_pos!(usize) = vec![];
    |            ^^^^^^^^^^^^^^^^
 
 error: use of irregular braces for `eprint!` macro
-  --> $DIR/conf_nonstandard_macro_braces.rs:51:5
+  --> $DIR/conf_nonstandard_macro_braces.rs:57:5
    |
 LL |     eprint!("test if user config overrides defaults");
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    |
 help: consider writing `eprint!["test if user config overrides defaults"];`
-  --> $DIR/conf_nonstandard_macro_braces.rs:51:5
+  --> $DIR/conf_nonstandard_macro_braces.rs:57:5
    |
 LL |     eprint!("test if user config overrides defaults");
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
diff --git a/src/tools/clippy/tests/auxiliary/test_macro.rs b/src/tools/clippy/tests/ui/auxiliary/test_macro.rs
index 624ca892add..624ca892add 100644
--- a/src/tools/clippy/tests/auxiliary/test_macro.rs
+++ b/src/tools/clippy/tests/ui/auxiliary/test_macro.rs
diff --git a/src/tools/clippy/tests/ui/extend_with_drain.fixed b/src/tools/clippy/tests/ui/extend_with_drain.fixed
index 00170e649e2..e863870e7d6 100644
--- a/src/tools/clippy/tests/ui/extend_with_drain.fixed
+++ b/src/tools/clippy/tests/ui/extend_with_drain.fixed
@@ -41,7 +41,12 @@ fn main() {
 
     let mut heap = BinaryHeap::from(vec![1, 3]);
     let mut heap2 = BinaryHeap::from(vec![]);
-    heap2.extend(heap.drain())
+    heap2.extend(heap.drain());
+
+    let mut x = vec![0, 1, 2, 3, 5];
+    let ref_x = &mut x;
+    let mut y = Vec::new();
+    y.append(ref_x);
 }
 
 fn return_vector() -> Vec<u8> {
diff --git a/src/tools/clippy/tests/ui/extend_with_drain.rs b/src/tools/clippy/tests/ui/extend_with_drain.rs
index d76458c3289..dcb36b5951c 100644
--- a/src/tools/clippy/tests/ui/extend_with_drain.rs
+++ b/src/tools/clippy/tests/ui/extend_with_drain.rs
@@ -41,7 +41,12 @@ fn main() {
 
     let mut heap = BinaryHeap::from(vec![1, 3]);
     let mut heap2 = BinaryHeap::from(vec![]);
-    heap2.extend(heap.drain())
+    heap2.extend(heap.drain());
+
+    let mut x = vec![0, 1, 2, 3, 5];
+    let ref_x = &mut x;
+    let mut y = Vec::new();
+    y.extend(ref_x.drain(..));
 }
 
 fn return_vector() -> Vec<u8> {
diff --git a/src/tools/clippy/tests/ui/extend_with_drain.stderr b/src/tools/clippy/tests/ui/extend_with_drain.stderr
index 57f344716a1..da14ddb25b3 100644
--- a/src/tools/clippy/tests/ui/extend_with_drain.stderr
+++ b/src/tools/clippy/tests/ui/extend_with_drain.stderr
@@ -18,5 +18,11 @@ error: use of `extend` instead of `append` for adding the full range of a second
 LL |     vec11.extend(return_vector().drain(..));
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `vec11.append(&mut return_vector())`
 
-error: aborting due to 3 previous errors
+error: use of `extend` instead of `append` for adding the full range of a second vector
+  --> $DIR/extend_with_drain.rs:49:5
+   |
+LL |     y.extend(ref_x.drain(..));
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `y.append(ref_x)`
+
+error: aborting due to 4 previous errors
 
diff --git a/src/tools/clippy/tests/ui/implicit_hasher.rs b/src/tools/clippy/tests/ui/implicit_hasher.rs
index fdcc9a33f55..97c26bc83ad 100644
--- a/src/tools/clippy/tests/ui/implicit_hasher.rs
+++ b/src/tools/clippy/tests/ui/implicit_hasher.rs
@@ -89,7 +89,7 @@ gen!(fn bar);
 // and should not cause an ICE
 // See #2707
 #[macro_use]
-#[path = "../auxiliary/test_macro.rs"]
+#[path = "auxiliary/test_macro.rs"]
 pub mod test_macro;
 __implicit_hasher_test_macro!(impl<K, V> for HashMap<K, V> where V: test_macro::A);
 
diff --git a/src/tools/clippy/tests/ui/map_flatten.fixed b/src/tools/clippy/tests/ui/map_flatten.fixed
index 773b5914439..18846c898da 100644
--- a/src/tools/clippy/tests/ui/map_flatten.fixed
+++ b/src/tools/clippy/tests/ui/map_flatten.fixed
@@ -5,6 +5,7 @@
 #![allow(clippy::missing_docs_in_private_items)]
 #![allow(clippy::map_identity)]
 #![allow(clippy::unnecessary_wraps)]
+#![feature(result_flattening)]
 
 fn main() {
     // mapping to Option on Iterator
@@ -23,4 +24,7 @@ fn main() {
 
     // mapping to Option on Option
     let _: Option<_> = (Some(Some(1))).and_then(|x| x);
+
+    // mapping to Result on Result
+    let _: Result<_, &str> = (Ok(Ok(1))).and_then(|x| x);
 }
diff --git a/src/tools/clippy/tests/ui/map_flatten.rs b/src/tools/clippy/tests/ui/map_flatten.rs
index 578bd877267..01db27876da 100644
--- a/src/tools/clippy/tests/ui/map_flatten.rs
+++ b/src/tools/clippy/tests/ui/map_flatten.rs
@@ -5,6 +5,7 @@
 #![allow(clippy::missing_docs_in_private_items)]
 #![allow(clippy::map_identity)]
 #![allow(clippy::unnecessary_wraps)]
+#![feature(result_flattening)]
 
 fn main() {
     // mapping to Option on Iterator
@@ -23,4 +24,7 @@ fn main() {
 
     // mapping to Option on Option
     let _: Option<_> = (Some(Some(1))).map(|x| x).flatten();
+
+    // mapping to Result on Result
+    let _: Result<_, &str> = (Ok(Ok(1))).map(|x| x).flatten();
 }
diff --git a/src/tools/clippy/tests/ui/map_flatten.stderr b/src/tools/clippy/tests/ui/map_flatten.stderr
index 756e6e818ad..38457c8ea4d 100644
--- a/src/tools/clippy/tests/ui/map_flatten.stderr
+++ b/src/tools/clippy/tests/ui/map_flatten.stderr
@@ -1,5 +1,5 @@
 error: called `map(..).flatten()` on an `Iterator`
-  --> $DIR/map_flatten.rs:16:46
+  --> $DIR/map_flatten.rs:17:46
    |
 LL |     let _: Vec<_> = vec![5_i8; 6].into_iter().map(option_id).flatten().collect();
    |                                              ^^^^^^^^^^^^^^^^^^^^^^^^^ help: try using `filter_map` instead: `.filter_map(option_id)`
@@ -7,34 +7,40 @@ LL |     let _: Vec<_> = vec![5_i8; 6].into_iter().map(option_id).flatten().coll
    = note: `-D clippy::map-flatten` implied by `-D warnings`
 
 error: called `map(..).flatten()` on an `Iterator`
-  --> $DIR/map_flatten.rs:17:46
+  --> $DIR/map_flatten.rs:18:46
    |
 LL |     let _: Vec<_> = vec![5_i8; 6].into_iter().map(option_id_ref).flatten().collect();
    |                                              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try using `filter_map` instead: `.filter_map(option_id_ref)`
 
 error: called `map(..).flatten()` on an `Iterator`
-  --> $DIR/map_flatten.rs:18:46
+  --> $DIR/map_flatten.rs:19:46
    |
 LL |     let _: Vec<_> = vec![5_i8; 6].into_iter().map(option_id_closure).flatten().collect();
    |                                              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try using `filter_map` instead: `.filter_map(option_id_closure)`
 
 error: called `map(..).flatten()` on an `Iterator`
-  --> $DIR/map_flatten.rs:19:46
+  --> $DIR/map_flatten.rs:20:46
    |
 LL |     let _: Vec<_> = vec![5_i8; 6].into_iter().map(|x| x.checked_add(1)).flatten().collect();
    |                                              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try using `filter_map` instead: `.filter_map(|x| x.checked_add(1))`
 
 error: called `map(..).flatten()` on an `Iterator`
-  --> $DIR/map_flatten.rs:22:46
+  --> $DIR/map_flatten.rs:23:46
    |
 LL |     let _: Vec<_> = vec![5_i8; 6].into_iter().map(|x| 0..x).flatten().collect();
    |                                              ^^^^^^^^^^^^^^^^^^^^^^^^ help: try using `flat_map` instead: `.flat_map(|x| 0..x)`
 
 error: called `map(..).flatten()` on an `Option`
-  --> $DIR/map_flatten.rs:25:39
+  --> $DIR/map_flatten.rs:26:39
    |
 LL |     let _: Option<_> = (Some(Some(1))).map(|x| x).flatten();
    |                                       ^^^^^^^^^^^^^^^^^^^^^ help: try using `and_then` instead: `.and_then(|x| x)`
 
-error: aborting due to 6 previous errors
+error: called `map(..).flatten()` on an `Result`
+  --> $DIR/map_flatten.rs:29:41
+   |
+LL |     let _: Result<_, &str> = (Ok(Ok(1))).map(|x| x).flatten();
+   |                                         ^^^^^^^^^^^^^^^^^^^^^ help: try using `and_then` instead: `.and_then(|x| x)`
+
+error: aborting due to 7 previous errors
 
diff --git a/src/tools/clippy/tests/ui/never_loop.stderr b/src/tools/clippy/tests/ui/never_loop.stderr
index c00b4c78cf2..f49b23924ef 100644
--- a/src/tools/clippy/tests/ui/never_loop.stderr
+++ b/src/tools/clippy/tests/ui/never_loop.stderr
@@ -75,6 +75,11 @@ LL | |             _ => return,
 LL | |         }
 LL | |     }
    | |_____^
+   |
+help: if you need the first element of the iterator, try writing
+   |
+LL |     if let Some(x) = (0..10).next() {
+   |     ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
 
 error: this loop never actually loops
   --> $DIR/never_loop.rs:157:5
diff --git a/src/tools/clippy/tests/ui/no_effect.stderr b/src/tools/clippy/tests/ui/no_effect.stderr
index 834b9056e31..6b24675ac2d 100644
--- a/src/tools/clippy/tests/ui/no_effect.stderr
+++ b/src/tools/clippy/tests/ui/no_effect.stderr
@@ -109,6 +109,12 @@ LL |     5..6;
    |     ^^^^^
 
 error: statement with no effect
+  --> $DIR/no_effect.rs:83:5
+   |
+LL |     5..=6;
+   |     ^^^^^^
+
+error: statement with no effect
   --> $DIR/no_effect.rs:84:5
    |
 LL |     [42, 55];
@@ -150,5 +156,5 @@ error: statement with no effect
 LL |     FooString { s: s };
    |     ^^^^^^^^^^^^^^^^^^^
 
-error: aborting due to 25 previous errors
+error: aborting due to 26 previous errors
 
diff --git a/src/tools/clippy/tests/ui/or_fun_call.fixed b/src/tools/clippy/tests/ui/or_fun_call.fixed
index 4390ff7dc30..c2f94d0e857 100644
--- a/src/tools/clippy/tests/ui/or_fun_call.fixed
+++ b/src/tools/clippy/tests/ui/or_fun_call.fixed
@@ -18,6 +18,19 @@ fn or_fun_call() {
         }
     }
 
+    struct FakeDefault;
+    impl FakeDefault {
+        fn default() -> Self {
+            FakeDefault
+        }
+    }
+
+    impl Default for FakeDefault {
+        fn default() -> Self {
+            FakeDefault
+        }
+    }
+
     enum Enum {
         A(i32),
     }
@@ -53,6 +66,12 @@ fn or_fun_call() {
     let with_default_type = Some(1);
     with_default_type.unwrap_or_default();
 
+    let self_default = None::<FakeDefault>;
+    self_default.unwrap_or_else(<FakeDefault>::default);
+
+    let real_default = None::<FakeDefault>;
+    real_default.unwrap_or_default();
+
     let with_vec = Some(vec![1]);
     with_vec.unwrap_or_default();
 
diff --git a/src/tools/clippy/tests/ui/or_fun_call.rs b/src/tools/clippy/tests/ui/or_fun_call.rs
index 75908c974cc..afaf92961b0 100644
--- a/src/tools/clippy/tests/ui/or_fun_call.rs
+++ b/src/tools/clippy/tests/ui/or_fun_call.rs
@@ -18,6 +18,19 @@ fn or_fun_call() {
         }
     }
 
+    struct FakeDefault;
+    impl FakeDefault {
+        fn default() -> Self {
+            FakeDefault
+        }
+    }
+
+    impl Default for FakeDefault {
+        fn default() -> Self {
+            FakeDefault
+        }
+    }
+
     enum Enum {
         A(i32),
     }
@@ -53,6 +66,12 @@ fn or_fun_call() {
     let with_default_type = Some(1);
     with_default_type.unwrap_or(u64::default());
 
+    let self_default = None::<FakeDefault>;
+    self_default.unwrap_or(<FakeDefault>::default());
+
+    let real_default = None::<FakeDefault>;
+    real_default.unwrap_or(<FakeDefault as Default>::default());
+
     let with_vec = Some(vec![1]);
     with_vec.unwrap_or(vec![]);
 
diff --git a/src/tools/clippy/tests/ui/or_fun_call.stderr b/src/tools/clippy/tests/ui/or_fun_call.stderr
index 9905029ce91..b2bcbd38c2d 100644
--- a/src/tools/clippy/tests/ui/or_fun_call.stderr
+++ b/src/tools/clippy/tests/ui/or_fun_call.stderr
@@ -1,5 +1,5 @@
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:33:19
+  --> $DIR/or_fun_call.rs:46:19
    |
 LL |     with_const_fn.unwrap_or(Duration::from_secs(5));
    |                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|| Duration::from_secs(5))`
@@ -7,130 +7,142 @@ LL |     with_const_fn.unwrap_or(Duration::from_secs(5));
    = note: `-D clippy::or-fun-call` implied by `-D warnings`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:36:22
+  --> $DIR/or_fun_call.rs:49:22
    |
 LL |     with_constructor.unwrap_or(make());
    |                      ^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(make)`
 
 error: use of `unwrap_or` followed by a call to `new`
-  --> $DIR/or_fun_call.rs:39:5
+  --> $DIR/or_fun_call.rs:52:5
    |
 LL |     with_new.unwrap_or(Vec::new());
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `with_new.unwrap_or_default()`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:42:21
+  --> $DIR/or_fun_call.rs:55:21
    |
 LL |     with_const_args.unwrap_or(Vec::with_capacity(12));
    |                     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|| Vec::with_capacity(12))`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:45:14
+  --> $DIR/or_fun_call.rs:58:14
    |
 LL |     with_err.unwrap_or(make());
    |              ^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|_| make())`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:48:19
+  --> $DIR/or_fun_call.rs:61:19
    |
 LL |     with_err_args.unwrap_or(Vec::with_capacity(12));
    |                   ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|_| Vec::with_capacity(12))`
 
 error: use of `unwrap_or` followed by a call to `default`
-  --> $DIR/or_fun_call.rs:51:5
+  --> $DIR/or_fun_call.rs:64:5
    |
 LL |     with_default_trait.unwrap_or(Default::default());
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `with_default_trait.unwrap_or_default()`
 
 error: use of `unwrap_or` followed by a call to `default`
-  --> $DIR/or_fun_call.rs:54:5
+  --> $DIR/or_fun_call.rs:67:5
    |
 LL |     with_default_type.unwrap_or(u64::default());
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `with_default_type.unwrap_or_default()`
 
+error: use of `unwrap_or` followed by a function call
+  --> $DIR/or_fun_call.rs:70:18
+   |
+LL |     self_default.unwrap_or(<FakeDefault>::default());
+   |                  ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(<FakeDefault>::default)`
+
+error: use of `unwrap_or` followed by a call to `default`
+  --> $DIR/or_fun_call.rs:73:5
+   |
+LL |     real_default.unwrap_or(<FakeDefault as Default>::default());
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `real_default.unwrap_or_default()`
+
 error: use of `unwrap_or` followed by a call to `new`
-  --> $DIR/or_fun_call.rs:57:5
+  --> $DIR/or_fun_call.rs:76:5
    |
 LL |     with_vec.unwrap_or(vec![]);
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `with_vec.unwrap_or_default()`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:60:21
+  --> $DIR/or_fun_call.rs:79:21
    |
 LL |     without_default.unwrap_or(Foo::new());
    |                     ^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(Foo::new)`
 
 error: use of `or_insert` followed by a function call
-  --> $DIR/or_fun_call.rs:63:19
+  --> $DIR/or_fun_call.rs:82:19
    |
 LL |     map.entry(42).or_insert(String::new());
    |                   ^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `or_insert_with(String::new)`
 
 error: use of `or_insert` followed by a function call
-  --> $DIR/or_fun_call.rs:66:23
+  --> $DIR/or_fun_call.rs:85:23
    |
 LL |     map_vec.entry(42).or_insert(vec![]);
    |                       ^^^^^^^^^^^^^^^^^ help: try this: `or_insert_with(Vec::new)`
 
 error: use of `or_insert` followed by a function call
-  --> $DIR/or_fun_call.rs:69:21
+  --> $DIR/or_fun_call.rs:88:21
    |
 LL |     btree.entry(42).or_insert(String::new());
    |                     ^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `or_insert_with(String::new)`
 
 error: use of `or_insert` followed by a function call
-  --> $DIR/or_fun_call.rs:72:25
+  --> $DIR/or_fun_call.rs:91:25
    |
 LL |     btree_vec.entry(42).or_insert(vec![]);
    |                         ^^^^^^^^^^^^^^^^^ help: try this: `or_insert_with(Vec::new)`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:75:21
+  --> $DIR/or_fun_call.rs:94:21
    |
 LL |     let _ = stringy.unwrap_or("".to_owned());
    |                     ^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|| "".to_owned())`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:83:21
+  --> $DIR/or_fun_call.rs:102:21
    |
 LL |     let _ = Some(1).unwrap_or(map[&1]);
    |                     ^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|| map[&1])`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:85:21
+  --> $DIR/or_fun_call.rs:104:21
    |
 LL |     let _ = Some(1).unwrap_or(map[&1]);
    |                     ^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|| map[&1])`
 
 error: use of `or` followed by a function call
-  --> $DIR/or_fun_call.rs:109:35
+  --> $DIR/or_fun_call.rs:128:35
    |
 LL |     let _ = Some("a".to_string()).or(Some("b".to_string()));
    |                                   ^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `or_else(|| Some("b".to_string()))`
 
 error: use of `or` followed by a function call
-  --> $DIR/or_fun_call.rs:113:10
+  --> $DIR/or_fun_call.rs:132:10
    |
 LL |         .or(Some(Bar(b, Duration::from_secs(2))));
    |          ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `or_else(|| Some(Bar(b, Duration::from_secs(2))))`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:141:14
+  --> $DIR/or_fun_call.rs:160:14
    |
 LL |         None.unwrap_or(s.as_mut_vec());
    |              ^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|| s.as_mut_vec())`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:146:14
+  --> $DIR/or_fun_call.rs:165:14
    |
 LL |         None.unwrap_or(unsafe { s.as_mut_vec() });
    |              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|| unsafe { s.as_mut_vec() })`
 
 error: use of `unwrap_or` followed by a function call
-  --> $DIR/or_fun_call.rs:148:14
+  --> $DIR/or_fun_call.rs:167:14
    |
 LL |         None.unwrap_or( unsafe { s.as_mut_vec() }    );
    |              ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try this: `unwrap_or_else(|| unsafe { s.as_mut_vec() })`
 
-error: aborting due to 22 previous errors
+error: aborting due to 24 previous errors
 
diff --git a/src/tools/clippy/tests/ui/similar_names.rs b/src/tools/clippy/tests/ui/similar_names.rs
index 2b1bc1f4859..daa07341457 100644
--- a/src/tools/clippy/tests/ui/similar_names.rs
+++ b/src/tools/clippy/tests/ui/similar_names.rs
@@ -76,6 +76,9 @@ fn main() {
     // names often used in win32 code (for example WindowProc)
     let wparam: i32;
     let lparam: i32;
+
+    let iter: i32;
+    let item: i32;
 }
 
 fn foo() {
diff --git a/src/tools/clippy/tests/ui/similar_names.stderr b/src/tools/clippy/tests/ui/similar_names.stderr
index b24accd962a..f621595abae 100644
--- a/src/tools/clippy/tests/ui/similar_names.stderr
+++ b/src/tools/clippy/tests/ui/similar_names.stderr
@@ -72,13 +72,13 @@ LL |     let parser: i32;
    |         ^^^^^^
 
 error: binding's name is too similar to existing binding
-  --> $DIR/similar_names.rs:85:16
+  --> $DIR/similar_names.rs:88:16
    |
 LL |         bpple: sprang,
    |                ^^^^^^
    |
 note: existing binding defined here
-  --> $DIR/similar_names.rs:84:16
+  --> $DIR/similar_names.rs:87:16
    |
 LL |         apple: spring,
    |                ^^^^^^
diff --git a/src/tools/clippy/tests/ui/swap.fixed b/src/tools/clippy/tests/ui/swap.fixed
index 0f8f839a0d5..ef518359ec5 100644
--- a/src/tools/clippy/tests/ui/swap.fixed
+++ b/src/tools/clippy/tests/ui/swap.fixed
@@ -6,6 +6,7 @@
     clippy::no_effect,
     clippy::redundant_clone,
     redundant_semicolons,
+    dead_code,
     unused_assignments
 )]
 
@@ -20,9 +21,7 @@ struct Bar {
 fn field() {
     let mut bar = Bar { a: 1, b: 2 };
 
-    let temp = bar.a;
-    bar.a = bar.b;
-    bar.b = temp;
+    std::mem::swap(&mut bar.a, &mut bar.b);
 
     let mut baz = vec![bar.clone(), bar.clone()];
     let temp = baz[0].a;
@@ -51,6 +50,7 @@ fn unswappable_slice() {
     foo[1][0] = temp;
 
     // swap(foo[0][1], foo[1][0]) would fail
+    // this could use split_at_mut and mem::swap, but that is not much simpler.
 }
 
 fn vec() {
@@ -60,13 +60,54 @@ fn vec() {
     foo.swap(0, 1);
 }
 
+fn xor_swap_locals() {
+    // This is an xor-based swap of local variables.
+    let mut a = 0;
+    let mut b = 1;
+    std::mem::swap(&mut a, &mut b)
+}
+
+fn xor_field_swap() {
+    // This is an xor-based swap of fields in a struct.
+    let mut bar = Bar { a: 0, b: 1 };
+    std::mem::swap(&mut bar.a, &mut bar.b)
+}
+
+fn xor_slice_swap() {
+    // This is an xor-based swap of a slice
+    let foo = &mut [1, 2];
+    foo.swap(0, 1)
+}
+
+fn xor_no_swap() {
+    // This is a sequence of xor-assignment statements that doesn't result in a swap.
+    let mut a = 0;
+    let mut b = 1;
+    let mut c = 2;
+    a ^= b;
+    b ^= c;
+    a ^= c;
+    c ^= a;
+}
+
+fn xor_unswappable_slice() {
+    let foo = &mut [vec![1, 2], vec![3, 4]];
+    foo[0][1] ^= foo[1][0];
+    foo[1][0] ^= foo[0][0];
+    foo[0][1] ^= foo[1][0];
+
+    // swap(foo[0][1], foo[1][0]) would fail
+    // this could use split_at_mut and mem::swap, but that is not much simpler.
+}
+
+fn distinct_slice() {
+    let foo = &mut [vec![1, 2], vec![3, 4]];
+    let bar = &mut [vec![1, 2], vec![3, 4]];
+    std::mem::swap(&mut foo[0][1], &mut bar[1][0]);
+}
+
 #[rustfmt::skip]
 fn main() {
-    field();
-    array();
-    slice();
-    unswappable_slice();
-    vec();
 
     let mut a = 42;
     let mut b = 1337;
diff --git a/src/tools/clippy/tests/ui/swap.rs b/src/tools/clippy/tests/ui/swap.rs
index 5763d9e82d4..8518659ccf3 100644
--- a/src/tools/clippy/tests/ui/swap.rs
+++ b/src/tools/clippy/tests/ui/swap.rs
@@ -6,6 +6,7 @@
     clippy::no_effect,
     clippy::redundant_clone,
     redundant_semicolons,
+    dead_code,
     unused_assignments
 )]
 
@@ -55,6 +56,7 @@ fn unswappable_slice() {
     foo[1][0] = temp;
 
     // swap(foo[0][1], foo[1][0]) would fail
+    // this could use split_at_mut and mem::swap, but that is not much simpler.
 }
 
 fn vec() {
@@ -66,13 +68,62 @@ fn vec() {
     foo.swap(0, 1);
 }
 
+fn xor_swap_locals() {
+    // This is an xor-based swap of local variables.
+    let mut a = 0;
+    let mut b = 1;
+    a ^= b;
+    b ^= a;
+    a ^= b;
+}
+
+fn xor_field_swap() {
+    // This is an xor-based swap of fields in a struct.
+    let mut bar = Bar { a: 0, b: 1 };
+    bar.a ^= bar.b;
+    bar.b ^= bar.a;
+    bar.a ^= bar.b;
+}
+
+fn xor_slice_swap() {
+    // This is an xor-based swap of a slice
+    let foo = &mut [1, 2];
+    foo[0] ^= foo[1];
+    foo[1] ^= foo[0];
+    foo[0] ^= foo[1];
+}
+
+fn xor_no_swap() {
+    // This is a sequence of xor-assignment statements that doesn't result in a swap.
+    let mut a = 0;
+    let mut b = 1;
+    let mut c = 2;
+    a ^= b;
+    b ^= c;
+    a ^= c;
+    c ^= a;
+}
+
+fn xor_unswappable_slice() {
+    let foo = &mut [vec![1, 2], vec![3, 4]];
+    foo[0][1] ^= foo[1][0];
+    foo[1][0] ^= foo[0][0];
+    foo[0][1] ^= foo[1][0];
+
+    // swap(foo[0][1], foo[1][0]) would fail
+    // this could use split_at_mut and mem::swap, but that is not much simpler.
+}
+
+fn distinct_slice() {
+    let foo = &mut [vec![1, 2], vec![3, 4]];
+    let bar = &mut [vec![1, 2], vec![3, 4]];
+    let temp = foo[0][1];
+    foo[0][1] = bar[1][0];
+    bar[1][0] = temp;
+}
+
 #[rustfmt::skip]
 fn main() {
-    field();
-    array();
-    slice();
-    unswappable_slice();
-    vec();
 
     let mut a = 42;
     let mut b = 1337;
diff --git a/src/tools/clippy/tests/ui/swap.stderr b/src/tools/clippy/tests/ui/swap.stderr
index f49bcfedf3a..614d16ced40 100644
--- a/src/tools/clippy/tests/ui/swap.stderr
+++ b/src/tools/clippy/tests/ui/swap.stderr
@@ -1,15 +1,24 @@
+error: this looks like you are swapping `bar.a` and `bar.b` manually
+  --> $DIR/swap.rs:24:5
+   |
+LL | /     let temp = bar.a;
+LL | |     bar.a = bar.b;
+LL | |     bar.b = temp;
+   | |________________^ help: try: `std::mem::swap(&mut bar.a, &mut bar.b)`
+   |
+   = note: `-D clippy::manual-swap` implied by `-D warnings`
+   = note: or maybe you should use `std::mem::replace`?
+
 error: this looks like you are swapping elements of `foo` manually
-  --> $DIR/swap.rs:35:5
+  --> $DIR/swap.rs:36:5
    |
 LL | /     let temp = foo[0];
 LL | |     foo[0] = foo[1];
 LL | |     foo[1] = temp;
    | |_________________^ help: try: `foo.swap(0, 1)`
-   |
-   = note: `-D clippy::manual-swap` implied by `-D warnings`
 
 error: this looks like you are swapping elements of `foo` manually
-  --> $DIR/swap.rs:44:5
+  --> $DIR/swap.rs:45:5
    |
 LL | /     let temp = foo[0];
 LL | |     foo[0] = foo[1];
@@ -17,7 +26,7 @@ LL | |     foo[1] = temp;
    | |_________________^ help: try: `foo.swap(0, 1)`
 
 error: this looks like you are swapping elements of `foo` manually
-  --> $DIR/swap.rs:62:5
+  --> $DIR/swap.rs:64:5
    |
 LL | /     let temp = foo[0];
 LL | |     foo[0] = foo[1];
@@ -25,7 +34,41 @@ LL | |     foo[1] = temp;
    | |_________________^ help: try: `foo.swap(0, 1)`
 
 error: this looks like you are swapping `a` and `b` manually
-  --> $DIR/swap.rs:83:7
+  --> $DIR/swap.rs:75:5
+   |
+LL | /     a ^= b;
+LL | |     b ^= a;
+LL | |     a ^= b;
+   | |___________^ help: try: `std::mem::swap(&mut a, &mut b)`
+
+error: this looks like you are swapping `bar.a` and `bar.b` manually
+  --> $DIR/swap.rs:83:5
+   |
+LL | /     bar.a ^= bar.b;
+LL | |     bar.b ^= bar.a;
+LL | |     bar.a ^= bar.b;
+   | |___________________^ help: try: `std::mem::swap(&mut bar.a, &mut bar.b)`
+
+error: this looks like you are swapping elements of `foo` manually
+  --> $DIR/swap.rs:91:5
+   |
+LL | /     foo[0] ^= foo[1];
+LL | |     foo[1] ^= foo[0];
+LL | |     foo[0] ^= foo[1];
+   | |_____________________^ help: try: `foo.swap(0, 1)`
+
+error: this looks like you are swapping `foo[0][1]` and `bar[1][0]` manually
+  --> $DIR/swap.rs:120:5
+   |
+LL | /     let temp = foo[0][1];
+LL | |     foo[0][1] = bar[1][0];
+LL | |     bar[1][0] = temp;
+   | |____________________^ help: try: `std::mem::swap(&mut foo[0][1], &mut bar[1][0])`
+   |
+   = note: or maybe you should use `std::mem::replace`?
+
+error: this looks like you are swapping `a` and `b` manually
+  --> $DIR/swap.rs:134:7
    |
 LL |       ; let t = a;
    |  _______^
@@ -36,7 +79,7 @@ LL | |     b = t;
    = note: or maybe you should use `std::mem::replace`?
 
 error: this looks like you are swapping `c.0` and `a` manually
-  --> $DIR/swap.rs:92:7
+  --> $DIR/swap.rs:143:7
    |
 LL |       ; let t = c.0;
    |  _______^
@@ -47,7 +90,7 @@ LL | |     a = t;
    = note: or maybe you should use `std::mem::replace`?
 
 error: this looks like you are trying to swap `a` and `b`
-  --> $DIR/swap.rs:80:5
+  --> $DIR/swap.rs:131:5
    |
 LL | /     a = b;
 LL | |     b = a;
@@ -57,7 +100,7 @@ LL | |     b = a;
    = note: or maybe you should use `std::mem::replace`?
 
 error: this looks like you are trying to swap `c.0` and `a`
-  --> $DIR/swap.rs:89:5
+  --> $DIR/swap.rs:140:5
    |
 LL | /     c.0 = a;
 LL | |     a = c.0;
@@ -65,5 +108,5 @@ LL | |     a = c.0;
    |
    = note: or maybe you should use `std::mem::replace`?
 
-error: aborting due to 7 previous errors
+error: aborting due to 12 previous errors
 
diff --git a/src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.rs b/src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.rs
index e7e0a31febc..1a0123803a3 100644
--- a/src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.rs
+++ b/src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.rs
@@ -58,6 +58,8 @@ impl Foo {
     fn bad(&self, x: &u32, y: &Foo, z: &Baz) {}
 
     fn bad2(x: &u32, y: &Foo, z: &Baz) {}
+
+    fn bad_issue7518(self, other: &Self) {}
 }
 
 impl AsRef<u32> for Foo {
diff --git a/src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.stderr b/src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.stderr
index 2b0005bbff1..9c4c49ceac4 100644
--- a/src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.stderr
+++ b/src/tools/clippy/tests/ui/trivially_copy_pass_by_ref.stderr
@@ -65,40 +65,46 @@ LL |     fn bad2(x: &u32, y: &Foo, z: &Baz) {}
    |                                  ^^^^ help: consider passing by value instead: `Baz`
 
 error: this argument (N byte) is passed by reference, but would be more efficient if passed by value (limit: N byte)
-  --> $DIR/trivially_copy_pass_by_ref.rs:72:16
+  --> $DIR/trivially_copy_pass_by_ref.rs:62:35
+   |
+LL |     fn bad_issue7518(self, other: &Self) {}
+   |                                   ^^^^^ help: consider passing by value instead: `Self`
+
+error: this argument (N byte) is passed by reference, but would be more efficient if passed by value (limit: N byte)
+  --> $DIR/trivially_copy_pass_by_ref.rs:74:16
    |
 LL |     fn bad2(x: &u32, y: &Foo, z: &Baz) {}
    |                ^^^^ help: consider passing by value instead: `u32`
 
 error: this argument (N byte) is passed by reference, but would be more efficient if passed by value (limit: N byte)
-  --> $DIR/trivially_copy_pass_by_ref.rs:72:25
+  --> $DIR/trivially_copy_pass_by_ref.rs:74:25
    |
 LL |     fn bad2(x: &u32, y: &Foo, z: &Baz) {}
    |                         ^^^^ help: consider passing by value instead: `Foo`
 
 error: this argument (N byte) is passed by reference, but would be more efficient if passed by value (limit: N byte)
-  --> $DIR/trivially_copy_pass_by_ref.rs:72:34
+  --> $DIR/trivially_copy_pass_by_ref.rs:74:34
    |
 LL |     fn bad2(x: &u32, y: &Foo, z: &Baz) {}
    |                                  ^^^^ help: consider passing by value instead: `Baz`
 
 error: this argument (N byte) is passed by reference, but would be more efficient if passed by value (limit: N byte)
-  --> $DIR/trivially_copy_pass_by_ref.rs:76:34
+  --> $DIR/trivially_copy_pass_by_ref.rs:78:34
    |
 LL |     fn trait_method(&self, _foo: &Foo);
    |                                  ^^^^ help: consider passing by value instead: `Foo`
 
 error: this argument (N byte) is passed by reference, but would be more efficient if passed by value (limit: N byte)
-  --> $DIR/trivially_copy_pass_by_ref.rs:108:21
+  --> $DIR/trivially_copy_pass_by_ref.rs:110:21
    |
 LL |     fn foo_never(x: &i32) {
    |                     ^^^^ help: consider passing by value instead: `i32`
 
 error: this argument (N byte) is passed by reference, but would be more efficient if passed by value (limit: N byte)
-  --> $DIR/trivially_copy_pass_by_ref.rs:113:15
+  --> $DIR/trivially_copy_pass_by_ref.rs:115:15
    |
 LL |     fn foo(x: &i32) {
    |               ^^^^ help: consider passing by value instead: `i32`
 
-error: aborting due to 16 previous errors
+error: aborting due to 17 previous errors
 
diff --git a/src/tools/clippy/tests/ui/unwrap_or_else_default.fixed b/src/tools/clippy/tests/ui/unwrap_or_else_default.fixed
new file mode 100644
index 00000000000..7ac3f426c97
--- /dev/null
+++ b/src/tools/clippy/tests/ui/unwrap_or_else_default.fixed
@@ -0,0 +1,71 @@
+// run-rustfix
+
+#![warn(clippy::unwrap_or_else_default)]
+#![allow(dead_code)]
+#![allow(clippy::unnecessary_wraps)]
+
+/// Checks implementation of the `UNWRAP_OR_ELSE_DEFAULT` lint.
+fn unwrap_or_else_default() {
+    struct Foo;
+
+    impl Foo {
+        fn new() -> Foo {
+            Foo
+        }
+
+        // fake default, we should not trigger on this
+        fn default() -> Foo {
+            Foo
+        }
+    }
+
+    struct HasDefaultAndDuplicate;
+
+    impl HasDefaultAndDuplicate {
+        fn default() -> Self {
+            HasDefaultAndDuplicate
+        }
+    }
+
+    impl Default for HasDefaultAndDuplicate {
+        fn default() -> Self {
+            HasDefaultAndDuplicate
+        }
+    }
+
+    enum Enum {
+        A(),
+    }
+
+    fn make<T, V>(_: V) -> T {
+        unimplemented!();
+    }
+
+    let with_enum = Some(Enum::A());
+    with_enum.unwrap_or_else(Enum::A);
+
+    let with_new = Some(vec![1]);
+    with_new.unwrap_or_else(Vec::new);
+
+    let with_err: Result<_, ()> = Ok(vec![1]);
+    with_err.unwrap_or_else(make);
+
+    // should not be changed
+    let with_fake_default = None::<Foo>;
+    with_fake_default.unwrap_or_else(Foo::default);
+
+    // should not be changed
+    let with_fake_default2 = None::<HasDefaultAndDuplicate>;
+    with_fake_default2.unwrap_or_else(<HasDefaultAndDuplicate>::default);
+
+    let with_real_default = None::<HasDefaultAndDuplicate>;
+    with_real_default.unwrap_or_default();
+
+    let with_default_trait = Some(1);
+    with_default_trait.unwrap_or_default();
+
+    let with_default_type = Some(1);
+    with_default_type.unwrap_or_default();
+}
+
+fn main() {}
diff --git a/src/tools/clippy/tests/ui/unwrap_or_else_default.rs b/src/tools/clippy/tests/ui/unwrap_or_else_default.rs
new file mode 100644
index 00000000000..82b727a039e
--- /dev/null
+++ b/src/tools/clippy/tests/ui/unwrap_or_else_default.rs
@@ -0,0 +1,71 @@
+// run-rustfix
+
+#![warn(clippy::unwrap_or_else_default)]
+#![allow(dead_code)]
+#![allow(clippy::unnecessary_wraps)]
+
+/// Checks implementation of the `UNWRAP_OR_ELSE_DEFAULT` lint.
+fn unwrap_or_else_default() {
+    struct Foo;
+
+    impl Foo {
+        fn new() -> Foo {
+            Foo
+        }
+
+        // fake default, we should not trigger on this
+        fn default() -> Foo {
+            Foo
+        }
+    }
+
+    struct HasDefaultAndDuplicate;
+
+    impl HasDefaultAndDuplicate {
+        fn default() -> Self {
+            HasDefaultAndDuplicate
+        }
+    }
+
+    impl Default for HasDefaultAndDuplicate {
+        fn default() -> Self {
+            HasDefaultAndDuplicate
+        }
+    }
+
+    enum Enum {
+        A(),
+    }
+
+    fn make<T, V>(_: V) -> T {
+        unimplemented!();
+    }
+
+    let with_enum = Some(Enum::A());
+    with_enum.unwrap_or_else(Enum::A);
+
+    let with_new = Some(vec![1]);
+    with_new.unwrap_or_else(Vec::new);
+
+    let with_err: Result<_, ()> = Ok(vec![1]);
+    with_err.unwrap_or_else(make);
+
+    // should not be changed
+    let with_fake_default = None::<Foo>;
+    with_fake_default.unwrap_or_else(Foo::default);
+
+    // should not be changed
+    let with_fake_default2 = None::<HasDefaultAndDuplicate>;
+    with_fake_default2.unwrap_or_else(<HasDefaultAndDuplicate>::default);
+
+    let with_real_default = None::<HasDefaultAndDuplicate>;
+    with_real_default.unwrap_or_else(<HasDefaultAndDuplicate as Default>::default);
+
+    let with_default_trait = Some(1);
+    with_default_trait.unwrap_or_else(Default::default);
+
+    let with_default_type = Some(1);
+    with_default_type.unwrap_or_else(u64::default);
+}
+
+fn main() {}
diff --git a/src/tools/clippy/tests/ui/unwrap_or_else_default.stderr b/src/tools/clippy/tests/ui/unwrap_or_else_default.stderr
new file mode 100644
index 00000000000..feb215b09f6
--- /dev/null
+++ b/src/tools/clippy/tests/ui/unwrap_or_else_default.stderr
@@ -0,0 +1,22 @@
+error: use of `.unwrap_or_else(..)` to construct default value
+  --> $DIR/unwrap_or_else_default.rs:62:5
+   |
+LL |     with_real_default.unwrap_or_else(<HasDefaultAndDuplicate as Default>::default);
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `with_real_default.unwrap_or_default()`
+   |
+   = note: `-D clippy::unwrap-or-else-default` implied by `-D warnings`
+
+error: use of `.unwrap_or_else(..)` to construct default value
+  --> $DIR/unwrap_or_else_default.rs:65:5
+   |
+LL |     with_default_trait.unwrap_or_else(Default::default);
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `with_default_trait.unwrap_or_default()`
+
+error: use of `.unwrap_or_else(..)` to construct default value
+  --> $DIR/unwrap_or_else_default.rs:68:5
+   |
+LL |     with_default_type.unwrap_or_else(u64::default);
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `with_default_type.unwrap_or_default()`
+
+error: aborting due to 3 previous errors
+
diff --git a/src/tools/clippy/tests/ui/while_let_on_iterator.fixed b/src/tools/clippy/tests/ui/while_let_on_iterator.fixed
index 52e80ceee83..cdcdd808c94 100644
--- a/src/tools/clippy/tests/ui/while_let_on_iterator.fixed
+++ b/src/tools/clippy/tests/ui/while_let_on_iterator.fixed
@@ -334,6 +334,38 @@ fn issue7249() {
     x();
 }
 
+fn issue7510() {
+    let mut it = 0..10;
+    let it = &mut it;
+    // Needs to reborrow `it` as the binding isn't mutable
+    for x in &mut *it {
+        if x % 2 == 0 {
+            break;
+        }
+    }
+    println!("{}", it.next().unwrap());
+
+    struct S<T>(T);
+    let mut it = 0..10;
+    let it = S(&mut it);
+    // Needs to reborrow `it.0` as the binding isn't mutable
+    for x in &mut *it.0 {
+        if x % 2 == 0 {
+            break;
+        }
+    }
+    println!("{}", it.0.next().unwrap());
+}
+
+fn exact_match_with_single_field() {
+    struct S<T>(T);
+    let mut s = S(0..10);
+    // Don't lint. `s.0` is used inside the loop.
+    while let Some(_) = s.0.next() {
+        let _ = &mut s.0;
+    }
+}
+
 fn main() {
     let mut it = 0..20;
     for _ in it {
diff --git a/src/tools/clippy/tests/ui/while_let_on_iterator.rs b/src/tools/clippy/tests/ui/while_let_on_iterator.rs
index 5078a3c9028..72f34257d1f 100644
--- a/src/tools/clippy/tests/ui/while_let_on_iterator.rs
+++ b/src/tools/clippy/tests/ui/while_let_on_iterator.rs
@@ -334,6 +334,38 @@ fn issue7249() {
     x();
 }
 
+fn issue7510() {
+    let mut it = 0..10;
+    let it = &mut it;
+    // Needs to reborrow `it` as the binding isn't mutable
+    while let Some(x) = it.next() {
+        if x % 2 == 0 {
+            break;
+        }
+    }
+    println!("{}", it.next().unwrap());
+
+    struct S<T>(T);
+    let mut it = 0..10;
+    let it = S(&mut it);
+    // Needs to reborrow `it.0` as the binding isn't mutable
+    while let Some(x) = it.0.next() {
+        if x % 2 == 0 {
+            break;
+        }
+    }
+    println!("{}", it.0.next().unwrap());
+}
+
+fn exact_match_with_single_field() {
+    struct S<T>(T);
+    let mut s = S(0..10);
+    // Don't lint. `s.0` is used inside the loop.
+    while let Some(_) = s.0.next() {
+        let _ = &mut s.0;
+    }
+}
+
 fn main() {
     let mut it = 0..20;
     while let Some(..) = it.next() {
diff --git a/src/tools/clippy/tests/ui/while_let_on_iterator.stderr b/src/tools/clippy/tests/ui/while_let_on_iterator.stderr
index cb0afeae15e..ff9b08996da 100644
--- a/src/tools/clippy/tests/ui/while_let_on_iterator.stderr
+++ b/src/tools/clippy/tests/ui/while_let_on_iterator.stderr
@@ -111,10 +111,22 @@ LL |         while let Some(x) = it.next() {
    |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `for x in &mut it`
 
 error: this loop could be written as a `for` loop
-  --> $DIR/while_let_on_iterator.rs:339:5
+  --> $DIR/while_let_on_iterator.rs:341:5
+   |
+LL |     while let Some(x) = it.next() {
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `for x in &mut *it`
+
+error: this loop could be written as a `for` loop
+  --> $DIR/while_let_on_iterator.rs:352:5
+   |
+LL |     while let Some(x) = it.0.next() {
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `for x in &mut *it.0`
+
+error: this loop could be written as a `for` loop
+  --> $DIR/while_let_on_iterator.rs:371:5
    |
 LL |     while let Some(..) = it.next() {
    |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: try: `for _ in it`
 
-error: aborting due to 19 previous errors
+error: aborting due to 21 previous errors