diff --git a/clippy_lints/src/return_self_not_must_use.rs b/clippy_lints/src/return_self_not_must_use.rs
index 1118da6c8cb..2ff7f6bbb38 100644
--- a/clippy_lints/src/return_self_not_must_use.rs
+++ b/clippy_lints/src/return_self_not_must_use.rs
@@ -5,7 +5,7 @@ use rustc_hir::{Body, FnDecl, HirId, TraitItem, TraitItemKind};
 use rustc_lint::{LateContext, LateLintPass, LintContext};
 use rustc_middle::lint::in_external_macro;
 use rustc_session::{declare_lint_pass, declare_tool_lint};
-use rustc_span::Span;
+use rustc_span::{sym, Span};
 
 declare_clippy_lint! {
     /// ### What it does
@@ -86,6 +86,8 @@ impl<'tcx> LateLintPass<'tcx> for ReturnSelfNotMustUse {
             // We are only interested in methods, not in functions or associated functions.
             if matches!(kind, FnKind::Method(_, _, _));
             if let Some(fn_def) = cx.tcx.hir().opt_local_def_id(hir_id);
+            // We don't want to emit this lint if the `#[must_use]` attribute is already there.
+            if !cx.tcx.hir().attrs(hir_id).iter().any(|attr| attr.has_name(sym::must_use));
             if let Some(impl_def) = cx.tcx.impl_of_method(fn_def.to_def_id());
             // We don't want this method to be te implementation of a trait because the
             // `#[must_use]` should be put on the trait definition directly.
diff --git a/tests/ui/return_self_not_must_use.rs b/tests/ui/return_self_not_must_use.rs
index bdf3f3d7995..2fa389dec0a 100644
--- a/tests/ui/return_self_not_must_use.rs
+++ b/tests/ui/return_self_not_must_use.rs
@@ -5,12 +5,12 @@ pub struct Bar;
 
 pub trait Whatever {
     fn what(&self) -> Self;
-    // There should be no warning here!
+    // There should be no warning here! (returns a reference)
     fn what2(&self) -> &Self;
 }
 
 impl Bar {
-    // There should be no warning here!
+    // There should be no warning here! (note taking a self argument)
     pub fn not_new() -> Self {
         Self
     }
@@ -20,22 +20,27 @@ impl Bar {
     pub fn bar(self) -> Self {
         self
     }
-    // There should be no warning here!
+    // There should be no warning here! (private method)
     fn foo2(&self) -> Self {
         Self
     }
-    // There should be no warning here!
+    // There should be no warning here! (returns a reference)
     pub fn foo3(&self) -> &Self {
         self
     }
+    // There should be no warning here! (already a `must_use` attribute)
+    #[must_use]
+    pub fn foo4(&self) -> Self {
+        Self
+    }
 }
 
 impl Whatever for Bar {
-    // There should be no warning here!
+    // There should be no warning here! (comes from the trait)
     fn what(&self) -> Self {
         self.foo2()
     }
-    // There should be no warning here!
+    // There should be no warning here! (comes from the trait)
     fn what2(&self) -> &Self {
         self
     }