Auto merge of #109732 - Urgau:uplift_drop_forget_ref_lints, r=davidtwco
Uplift `clippy::{drop,forget}_{ref,copy}` lints This PR aims at uplifting the `clippy::drop_ref`, `clippy::drop_copy`, `clippy::forget_ref` and `clippy::forget_copy` lints. Those lints are/were declared in the correctness category of clippy because they lint on useless and most probably is not what the developer wanted. ## `drop_ref` and `forget_ref` The `drop_ref` and `forget_ref` lint checks for calls to `std::mem::drop` or `std::mem::forget` with a reference instead of an owned value. ### Example ```rust let mut lock_guard = mutex.lock(); std::mem::drop(&lock_guard) // Should have been drop(lock_guard), mutex // still locked operation_that_requires_mutex_to_be_unlocked(); ``` ### Explanation Calling `drop` or `forget` on a reference will only drop the reference itself, which is a no-op. It will not call the `drop` or `forget` method on the underlying referenced value, which is likely what was intended. ## `drop_copy` and `forget_copy` The `drop_copy` and `forget_copy` lint checks for calls to `std::mem::forget` or `std::mem::drop` with a value that derives the Copy trait. ### Example ```rust let x: i32 = 42; // i32 implements Copy std::mem::forget(x) // A copy of x is passed to the function, leaving the // original unaffected ``` ### Explanation Calling `std::mem::forget` [does nothing for types that implement Copy](https://doc.rust-lang.org/std/mem/fn.drop.html) since the value will be copied and moved into the function on invocation. ----- Followed the instructions for uplift a clippy describe here: https://github.com/rust-lang/rust/pull/99696#pullrequestreview-1134072751 cc `@m-ou-se` (as T-libs-api leader because the uplifting was discussed in a recent meeting)
This commit is contained in:
commit
077fc26f0a
@ -562,15 +562,13 @@ pub(crate) mod printf {
|
||||
}
|
||||
|
||||
if let Type = state {
|
||||
drop(c);
|
||||
type_ = at.slice_between(next).unwrap();
|
||||
|
||||
// Don't use `move_to!` here, as we *can* be at the end of the input.
|
||||
at = next;
|
||||
}
|
||||
|
||||
drop(c);
|
||||
drop(next);
|
||||
let _ = c; // to avoid never used value
|
||||
|
||||
end = at;
|
||||
let position = InnerSpan::new(start.at, end.at);
|
||||
|
@ -828,7 +828,7 @@ where
|
||||
} else {
|
||||
match variables.probe(vid) {
|
||||
TypeVariableValue::Known { value: u } => {
|
||||
drop(variables);
|
||||
drop(inner);
|
||||
self.relate(u, u)
|
||||
}
|
||||
TypeVariableValue::Unknown { universe: _universe } => {
|
||||
|
@ -520,3 +520,19 @@ lint_opaque_hidden_inferred_bound = opaque type `{$ty}` does not satisfy its ass
|
||||
.specifically = this associated type bound is unsatisfied for `{$proj_ty}`
|
||||
|
||||
lint_opaque_hidden_inferred_bound_sugg = add this bound
|
||||
|
||||
lint_drop_ref = calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
.label = argument has type `{$arg_ty}`
|
||||
.note = use `let _ = ...` to ignore the expression or result
|
||||
|
||||
lint_drop_copy = calls to `std::mem::drop` with a value that implements `Copy` does nothing
|
||||
.label = argument has type `{$arg_ty}`
|
||||
.note = use `let _ = ...` to ignore the expression or result
|
||||
|
||||
lint_forget_ref = calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
.label = argument has type `{$arg_ty}`
|
||||
.note = use `let _ = ...` to ignore the expression or result
|
||||
|
||||
lint_forget_copy = calls to `std::mem::forget` with a value that implements `Copy` does nothing
|
||||
.label = argument has type `{$arg_ty}`
|
||||
.note = use `let _ = ...` to ignore the expression or result
|
||||
|
164
compiler/rustc_lint/src/drop_forget_useless.rs
Normal file
164
compiler/rustc_lint/src/drop_forget_useless.rs
Normal file
@ -0,0 +1,164 @@
|
||||
use rustc_hir::{Arm, Expr, ExprKind, Node};
|
||||
use rustc_span::sym;
|
||||
|
||||
use crate::{
|
||||
lints::{DropCopyDiag, DropRefDiag, ForgetCopyDiag, ForgetRefDiag},
|
||||
LateContext, LateLintPass, LintContext,
|
||||
};
|
||||
|
||||
declare_lint! {
|
||||
/// The `drop_ref` lint checks for calls to `std::mem::drop` with a reference
|
||||
/// instead of an owned value.
|
||||
///
|
||||
/// ### Example
|
||||
///
|
||||
/// ```rust
|
||||
/// # fn operation_that_requires_mutex_to_be_unlocked() {} // just to make it compile
|
||||
/// # let mutex = std::sync::Mutex::new(1); // just to make it compile
|
||||
/// let mut lock_guard = mutex.lock();
|
||||
/// std::mem::drop(&lock_guard); // Should have been drop(lock_guard), mutex
|
||||
/// // still locked
|
||||
/// operation_that_requires_mutex_to_be_unlocked();
|
||||
/// ```
|
||||
///
|
||||
/// {{produces}}
|
||||
///
|
||||
/// ### Explanation
|
||||
///
|
||||
/// Calling `drop` on a reference will only drop the
|
||||
/// reference itself, which is a no-op. It will not call the `drop` method (from
|
||||
/// the `Drop` trait implementation) on the underlying referenced value, which
|
||||
/// is likely what was intended.
|
||||
pub DROP_REF,
|
||||
Warn,
|
||||
"calls to `std::mem::drop` with a reference instead of an owned value"
|
||||
}
|
||||
|
||||
declare_lint! {
|
||||
/// The `forget_ref` lint checks for calls to `std::mem::forget` with a reference
|
||||
/// instead of an owned value.
|
||||
///
|
||||
/// ### Example
|
||||
///
|
||||
/// ```rust
|
||||
/// let x = Box::new(1);
|
||||
/// std::mem::forget(&x); // Should have been forget(x), x will still be dropped
|
||||
/// ```
|
||||
///
|
||||
/// {{produces}}
|
||||
///
|
||||
/// ### Explanation
|
||||
///
|
||||
/// Calling `forget` on a reference will only forget the
|
||||
/// reference itself, which is a no-op. It will not forget the underlying
|
||||
/// referenced value, which is likely what was intended.
|
||||
pub FORGET_REF,
|
||||
Warn,
|
||||
"calls to `std::mem::forget` with a reference instead of an owned value"
|
||||
}
|
||||
|
||||
declare_lint! {
|
||||
/// The `drop_copy` lint checks for calls to `std::mem::drop` with a value
|
||||
/// that derives the Copy trait.
|
||||
///
|
||||
/// ### Example
|
||||
///
|
||||
/// ```rust
|
||||
/// let x: i32 = 42; // i32 implements Copy
|
||||
/// std::mem::drop(x); // A copy of x is passed to the function, leaving the
|
||||
/// // original unaffected
|
||||
/// ```
|
||||
///
|
||||
/// {{produces}}
|
||||
///
|
||||
/// ### Explanation
|
||||
///
|
||||
/// Calling `std::mem::drop` [does nothing for types that
|
||||
/// implement Copy](https://doc.rust-lang.org/std/mem/fn.drop.html), since the
|
||||
/// value will be copied and moved into the function on invocation.
|
||||
pub DROP_COPY,
|
||||
Warn,
|
||||
"calls to `std::mem::drop` with a value that implements Copy"
|
||||
}
|
||||
|
||||
declare_lint! {
|
||||
/// The `forget_copy` lint checks for calls to `std::mem::forget` with a value
|
||||
/// that derives the Copy trait.
|
||||
///
|
||||
/// ### Example
|
||||
///
|
||||
/// ```rust
|
||||
/// let x: i32 = 42; // i32 implements Copy
|
||||
/// std::mem::forget(x); // A copy of x is passed to the function, leaving the
|
||||
/// // original unaffected
|
||||
/// ```
|
||||
///
|
||||
/// {{produces}}
|
||||
///
|
||||
/// ### Explanation
|
||||
///
|
||||
/// Calling `std::mem::forget` [does nothing for types that
|
||||
/// implement Copy](https://doc.rust-lang.org/std/mem/fn.drop.html) since the
|
||||
/// value will be copied and moved into the function on invocation.
|
||||
///
|
||||
/// An alternative, but also valid, explanation is that Copy types do not
|
||||
/// implement the Drop trait, which means they have no destructors. Without a
|
||||
/// destructor, there is nothing for `std::mem::forget` to ignore.
|
||||
pub FORGET_COPY,
|
||||
Warn,
|
||||
"calls to `std::mem::forget` with a value that implements Copy"
|
||||
}
|
||||
|
||||
declare_lint_pass!(DropForgetUseless => [DROP_REF, FORGET_REF, DROP_COPY, FORGET_COPY]);
|
||||
|
||||
impl<'tcx> LateLintPass<'tcx> for DropForgetUseless {
|
||||
fn check_expr(&mut self, cx: &LateContext<'tcx>, expr: &'tcx Expr<'tcx>) {
|
||||
if let ExprKind::Call(path, [arg]) = expr.kind
|
||||
&& let ExprKind::Path(ref qpath) = path.kind
|
||||
&& let Some(def_id) = cx.qpath_res(qpath, path.hir_id).opt_def_id()
|
||||
&& let Some(fn_name) = cx.tcx.get_diagnostic_name(def_id)
|
||||
{
|
||||
let arg_ty = cx.typeck_results().expr_ty(arg);
|
||||
let is_copy = arg_ty.is_copy_modulo_regions(cx.tcx, cx.param_env);
|
||||
let drop_is_single_call_in_arm = is_single_call_in_arm(cx, arg, expr);
|
||||
match fn_name {
|
||||
sym::mem_drop if arg_ty.is_ref() && !drop_is_single_call_in_arm => {
|
||||
cx.emit_spanned_lint(DROP_REF, expr.span, DropRefDiag { arg_ty, label: arg.span });
|
||||
},
|
||||
sym::mem_forget if arg_ty.is_ref() => {
|
||||
cx.emit_spanned_lint(FORGET_REF, expr.span, ForgetRefDiag { arg_ty, label: arg.span });
|
||||
},
|
||||
sym::mem_drop if is_copy && !drop_is_single_call_in_arm => {
|
||||
cx.emit_spanned_lint(DROP_COPY, expr.span, DropCopyDiag { arg_ty, label: arg.span });
|
||||
}
|
||||
sym::mem_forget if is_copy => {
|
||||
cx.emit_spanned_lint(FORGET_COPY, expr.span, ForgetCopyDiag { arg_ty, label: arg.span });
|
||||
}
|
||||
_ => return,
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Dropping returned value of a function, as in the following snippet is considered idiomatic, see
|
||||
// rust-lang/rust-clippy#9482 for examples.
|
||||
//
|
||||
// ```
|
||||
// match <var> {
|
||||
// <pat> => drop(fn_with_side_effect_and_returning_some_value()),
|
||||
// ..
|
||||
// }
|
||||
// ```
|
||||
fn is_single_call_in_arm<'tcx>(
|
||||
cx: &LateContext<'tcx>,
|
||||
arg: &'tcx Expr<'_>,
|
||||
drop_expr: &'tcx Expr<'_>,
|
||||
) -> bool {
|
||||
if matches!(arg.kind, ExprKind::Call(..) | ExprKind::MethodCall(..)) {
|
||||
let parent_node = cx.tcx.hir().find_parent(drop_expr.hir_id);
|
||||
if let Some(Node::Arm(Arm { body, .. })) = &parent_node {
|
||||
return body.hir_id == drop_expr.hir_id;
|
||||
}
|
||||
}
|
||||
false
|
||||
}
|
@ -52,6 +52,7 @@ mod array_into_iter;
|
||||
pub mod builtin;
|
||||
mod context;
|
||||
mod deref_into_dyn_supertrait;
|
||||
mod drop_forget_useless;
|
||||
mod early;
|
||||
mod enum_intrinsics_non_enums;
|
||||
mod errors;
|
||||
@ -96,6 +97,7 @@ use rustc_span::Span;
|
||||
use array_into_iter::ArrayIntoIter;
|
||||
use builtin::*;
|
||||
use deref_into_dyn_supertrait::*;
|
||||
use drop_forget_useless::*;
|
||||
use enum_intrinsics_non_enums::EnumIntrinsicsNonEnums;
|
||||
use for_loops_over_fallibles::*;
|
||||
use hidden_unicode_codepoints::*;
|
||||
@ -201,6 +203,7 @@ late_lint_methods!(
|
||||
[
|
||||
ForLoopsOverFallibles: ForLoopsOverFallibles,
|
||||
DerefIntoDynSupertrait: DerefIntoDynSupertrait,
|
||||
DropForgetUseless: DropForgetUseless,
|
||||
HardwiredLints: HardwiredLints,
|
||||
ImproperCTypesDeclarations: ImproperCTypesDeclarations,
|
||||
ImproperCTypesDefinitions: ImproperCTypesDefinitions,
|
||||
|
@ -662,6 +662,43 @@ pub struct ForLoopsOverFalliblesSuggestion<'a> {
|
||||
pub end_span: Span,
|
||||
}
|
||||
|
||||
// drop_ref.rs
|
||||
#[derive(LintDiagnostic)]
|
||||
#[diag(lint_drop_ref)]
|
||||
#[note]
|
||||
pub struct DropRefDiag<'a> {
|
||||
pub arg_ty: Ty<'a>,
|
||||
#[label]
|
||||
pub label: Span,
|
||||
}
|
||||
|
||||
#[derive(LintDiagnostic)]
|
||||
#[diag(lint_drop_copy)]
|
||||
#[note]
|
||||
pub struct DropCopyDiag<'a> {
|
||||
pub arg_ty: Ty<'a>,
|
||||
#[label]
|
||||
pub label: Span,
|
||||
}
|
||||
|
||||
#[derive(LintDiagnostic)]
|
||||
#[diag(lint_forget_ref)]
|
||||
#[note]
|
||||
pub struct ForgetRefDiag<'a> {
|
||||
pub arg_ty: Ty<'a>,
|
||||
#[label]
|
||||
pub label: Span,
|
||||
}
|
||||
|
||||
#[derive(LintDiagnostic)]
|
||||
#[diag(lint_forget_copy)]
|
||||
#[note]
|
||||
pub struct ForgetCopyDiag<'a> {
|
||||
pub arg_ty: Ty<'a>,
|
||||
#[label]
|
||||
pub label: Span,
|
||||
}
|
||||
|
||||
// hidden_unicode_codepoints.rs
|
||||
#[derive(LintDiagnostic)]
|
||||
#[diag(lint_hidden_unicode_codepoints)]
|
||||
|
@ -880,12 +880,11 @@ macro_rules! make_mir_visitor {
|
||||
) {
|
||||
let Constant {
|
||||
span,
|
||||
user_ty,
|
||||
user_ty: _, // no visit method for this
|
||||
literal,
|
||||
} = constant;
|
||||
|
||||
self.visit_span($(& $mutability)? *span);
|
||||
drop(user_ty); // no visit method for this
|
||||
match literal {
|
||||
ConstantKind::Ty(ct) => self.visit_ty_const($(&$mutability)? *ct, location),
|
||||
ConstantKind::Val(_, ty) => self.visit_ty($(& $mutability)? *ty, TyContext::Location(location)),
|
||||
|
@ -968,6 +968,7 @@ pub const fn replace<T>(dest: &mut T, src: T) -> T {
|
||||
/// Integers and other types implementing [`Copy`] are unaffected by `drop`.
|
||||
///
|
||||
/// ```
|
||||
/// # #![cfg_attr(not(bootstrap), allow(drop_copy))]
|
||||
/// #[derive(Copy, Clone)]
|
||||
/// struct Foo(u8);
|
||||
///
|
||||
|
@ -116,7 +116,7 @@ impl<T> Poll<T> {
|
||||
/// let fut = Pin::new(&mut fut);
|
||||
///
|
||||
/// let num = fut.poll(cx).ready()?;
|
||||
/// # drop(num);
|
||||
/// # let _ = num; // to silence unused warning
|
||||
/// // ... use num
|
||||
///
|
||||
/// Poll::Ready(())
|
||||
|
@ -22,7 +22,7 @@ use core::task::Poll;
|
||||
/// let fut = Pin::new(&mut fut);
|
||||
///
|
||||
/// let num = ready!(fut.poll(cx));
|
||||
/// # drop(num);
|
||||
/// # let _ = num;
|
||||
/// // ... use num
|
||||
///
|
||||
/// Poll::Ready(())
|
||||
@ -44,7 +44,7 @@ use core::task::Poll;
|
||||
/// Poll::Ready(t) => t,
|
||||
/// Poll::Pending => return Poll::Pending,
|
||||
/// };
|
||||
/// # drop(num);
|
||||
/// # let _ = num; // to silence unused warning
|
||||
/// # // ... use num
|
||||
/// #
|
||||
/// # Poll::Ready(())
|
||||
|
@ -541,7 +541,7 @@ pub fn begin_panic_handler(info: &PanicInfo<'_>) -> ! {
|
||||
// Lazily, the first time this gets called, run the actual string formatting.
|
||||
self.string.get_or_insert_with(|| {
|
||||
let mut s = String::new();
|
||||
drop(s.write_fmt(*inner));
|
||||
let _err = s.write_fmt(*inner);
|
||||
s
|
||||
})
|
||||
}
|
||||
|
@ -202,12 +202,18 @@ impl WaitQueue {
|
||||
pub fn notify_one<T>(
|
||||
mut guard: SpinMutexGuard<'_, WaitVariable<T>>,
|
||||
) -> Result<WaitGuard<'_, T>, SpinMutexGuard<'_, WaitVariable<T>>> {
|
||||
// SAFETY: lifetime of the pop() return value is limited to the map
|
||||
// closure (The closure return value is 'static). The underlying
|
||||
// stack frame won't be freed until after the WaitGuard created below
|
||||
// is dropped.
|
||||
unsafe {
|
||||
if let Some(entry) = guard.queue.inner.pop() {
|
||||
let tcs = guard.queue.inner.pop().map(|entry| -> Tcs {
|
||||
let mut entry_guard = entry.lock();
|
||||
let tcs = entry_guard.tcs;
|
||||
entry_guard.wake = true;
|
||||
drop(entry);
|
||||
entry_guard.tcs
|
||||
});
|
||||
|
||||
if let Some(tcs) = tcs {
|
||||
Ok(WaitGuard { mutex_guard: Some(guard), notified_tcs: NotifiedTcs::Single(tcs) })
|
||||
} else {
|
||||
Err(guard)
|
||||
@ -223,6 +229,9 @@ impl WaitQueue {
|
||||
pub fn notify_all<T>(
|
||||
mut guard: SpinMutexGuard<'_, WaitVariable<T>>,
|
||||
) -> Result<WaitGuard<'_, T>, SpinMutexGuard<'_, WaitVariable<T>>> {
|
||||
// SAFETY: lifetime of the pop() return values are limited to the
|
||||
// while loop body. The underlying stack frames won't be freed until
|
||||
// after the WaitGuard created below is dropped.
|
||||
unsafe {
|
||||
let mut count = 0;
|
||||
while let Some(entry) = guard.queue.inner.pop() {
|
||||
@ -230,6 +239,7 @@ impl WaitQueue {
|
||||
let mut entry_guard = entry.lock();
|
||||
entry_guard.wake = true;
|
||||
}
|
||||
|
||||
if let Some(count) = NonZeroUsize::new(count) {
|
||||
Ok(WaitGuard { mutex_guard: Some(guard), notified_tcs: NotifiedTcs::All { count } })
|
||||
} else {
|
||||
|
@ -1210,7 +1210,7 @@ impl File {
|
||||
// Redox doesn't appear to support `UTIME_OMIT`.
|
||||
// ESP-IDF and HorizonOS do not support `futimens` at all and the behavior for those OS is therefore
|
||||
// the same as for Redox.
|
||||
drop(times);
|
||||
let _ = times;
|
||||
Err(io::const_io_error!(
|
||||
io::ErrorKind::Unsupported,
|
||||
"setting file times not supported",
|
||||
|
@ -375,7 +375,9 @@ fn test_scoped_threads_nll() {
|
||||
// this is mostly a *compilation test* for this exact function:
|
||||
fn foo(x: &u8) {
|
||||
thread::scope(|s| {
|
||||
s.spawn(|| drop(x));
|
||||
s.spawn(|| match x {
|
||||
_ => (),
|
||||
});
|
||||
});
|
||||
}
|
||||
// let's also run it for good measure
|
||||
|
@ -132,12 +132,8 @@ pub(crate) static LINTS: &[&crate::LintInfo] = &[
|
||||
crate::doc::NEEDLESS_DOCTEST_MAIN_INFO,
|
||||
crate::doc::UNNECESSARY_SAFETY_DOC_INFO,
|
||||
crate::double_parens::DOUBLE_PARENS_INFO,
|
||||
crate::drop_forget_ref::DROP_COPY_INFO,
|
||||
crate::drop_forget_ref::DROP_NON_DROP_INFO,
|
||||
crate::drop_forget_ref::DROP_REF_INFO,
|
||||
crate::drop_forget_ref::FORGET_COPY_INFO,
|
||||
crate::drop_forget_ref::FORGET_NON_DROP_INFO,
|
||||
crate::drop_forget_ref::FORGET_REF_INFO,
|
||||
crate::drop_forget_ref::UNDROPPED_MANUALLY_DROPS_INFO,
|
||||
crate::duplicate_mod::DUPLICATE_MOD_INFO,
|
||||
crate::else_if_without_else::ELSE_IF_WITHOUT_ELSE_INFO,
|
||||
|
@ -7,102 +7,6 @@ use rustc_lint::{LateContext, LateLintPass};
|
||||
use rustc_session::{declare_lint_pass, declare_tool_lint};
|
||||
use rustc_span::sym;
|
||||
|
||||
declare_clippy_lint! {
|
||||
/// ### What it does
|
||||
/// Checks for calls to `std::mem::drop` with a reference
|
||||
/// instead of an owned value.
|
||||
///
|
||||
/// ### Why is this bad?
|
||||
/// Calling `drop` on a reference will only drop the
|
||||
/// reference itself, which is a no-op. It will not call the `drop` method (from
|
||||
/// the `Drop` trait implementation) on the underlying referenced value, which
|
||||
/// is likely what was intended.
|
||||
///
|
||||
/// ### Example
|
||||
/// ```ignore
|
||||
/// let mut lock_guard = mutex.lock();
|
||||
/// std::mem::drop(&lock_guard) // Should have been drop(lock_guard), mutex
|
||||
/// // still locked
|
||||
/// operation_that_requires_mutex_to_be_unlocked();
|
||||
/// ```
|
||||
#[clippy::version = "pre 1.29.0"]
|
||||
pub DROP_REF,
|
||||
correctness,
|
||||
"calls to `std::mem::drop` with a reference instead of an owned value"
|
||||
}
|
||||
|
||||
declare_clippy_lint! {
|
||||
/// ### What it does
|
||||
/// Checks for calls to `std::mem::forget` with a reference
|
||||
/// instead of an owned value.
|
||||
///
|
||||
/// ### Why is this bad?
|
||||
/// Calling `forget` on a reference will only forget the
|
||||
/// reference itself, which is a no-op. It will not forget the underlying
|
||||
/// referenced
|
||||
/// value, which is likely what was intended.
|
||||
///
|
||||
/// ### Example
|
||||
/// ```rust
|
||||
/// let x = Box::new(1);
|
||||
/// std::mem::forget(&x) // Should have been forget(x), x will still be dropped
|
||||
/// ```
|
||||
#[clippy::version = "pre 1.29.0"]
|
||||
pub FORGET_REF,
|
||||
correctness,
|
||||
"calls to `std::mem::forget` with a reference instead of an owned value"
|
||||
}
|
||||
|
||||
declare_clippy_lint! {
|
||||
/// ### What it does
|
||||
/// Checks for calls to `std::mem::drop` with a value
|
||||
/// that derives the Copy trait
|
||||
///
|
||||
/// ### Why is this bad?
|
||||
/// Calling `std::mem::drop` [does nothing for types that
|
||||
/// implement Copy](https://doc.rust-lang.org/std/mem/fn.drop.html), since the
|
||||
/// value will be copied and moved into the function on invocation.
|
||||
///
|
||||
/// ### Example
|
||||
/// ```rust
|
||||
/// let x: i32 = 42; // i32 implements Copy
|
||||
/// std::mem::drop(x) // A copy of x is passed to the function, leaving the
|
||||
/// // original unaffected
|
||||
/// ```
|
||||
#[clippy::version = "pre 1.29.0"]
|
||||
pub DROP_COPY,
|
||||
correctness,
|
||||
"calls to `std::mem::drop` with a value that implements Copy"
|
||||
}
|
||||
|
||||
declare_clippy_lint! {
|
||||
/// ### What it does
|
||||
/// Checks for calls to `std::mem::forget` with a value that
|
||||
/// derives the Copy trait
|
||||
///
|
||||
/// ### Why is this bad?
|
||||
/// Calling `std::mem::forget` [does nothing for types that
|
||||
/// implement Copy](https://doc.rust-lang.org/std/mem/fn.drop.html) since the
|
||||
/// value will be copied and moved into the function on invocation.
|
||||
///
|
||||
/// An alternative, but also valid, explanation is that Copy types do not
|
||||
/// implement
|
||||
/// the Drop trait, which means they have no destructors. Without a destructor,
|
||||
/// there
|
||||
/// is nothing for `std::mem::forget` to ignore.
|
||||
///
|
||||
/// ### Example
|
||||
/// ```rust
|
||||
/// let x: i32 = 42; // i32 implements Copy
|
||||
/// std::mem::forget(x) // A copy of x is passed to the function, leaving the
|
||||
/// // original unaffected
|
||||
/// ```
|
||||
#[clippy::version = "pre 1.29.0"]
|
||||
pub FORGET_COPY,
|
||||
correctness,
|
||||
"calls to `std::mem::forget` with a value that implements Copy"
|
||||
}
|
||||
|
||||
declare_clippy_lint! {
|
||||
/// ### What it does
|
||||
/// Checks for calls to `std::mem::drop` with a value that does not implement `Drop`.
|
||||
@ -172,24 +76,12 @@ declare_clippy_lint! {
|
||||
"use of safe `std::mem::drop` function to drop a std::mem::ManuallyDrop, which will not drop the inner value"
|
||||
}
|
||||
|
||||
const DROP_REF_SUMMARY: &str = "calls to `std::mem::drop` with a reference instead of an owned value. \
|
||||
Dropping a reference does nothing";
|
||||
const FORGET_REF_SUMMARY: &str = "calls to `std::mem::forget` with a reference instead of an owned value. \
|
||||
Forgetting a reference does nothing";
|
||||
const DROP_COPY_SUMMARY: &str = "calls to `std::mem::drop` with a value that implements `Copy`. \
|
||||
Dropping a copy leaves the original intact";
|
||||
const FORGET_COPY_SUMMARY: &str = "calls to `std::mem::forget` with a value that implements `Copy`. \
|
||||
Forgetting a copy leaves the original intact";
|
||||
const DROP_NON_DROP_SUMMARY: &str = "call to `std::mem::drop` with a value that does not implement `Drop`. \
|
||||
Dropping such a type only extends its contained lifetimes";
|
||||
const FORGET_NON_DROP_SUMMARY: &str = "call to `std::mem::forget` with a value that does not implement `Drop`. \
|
||||
Forgetting such a type is the same as dropping it";
|
||||
|
||||
declare_lint_pass!(DropForgetRef => [
|
||||
DROP_REF,
|
||||
FORGET_REF,
|
||||
DROP_COPY,
|
||||
FORGET_COPY,
|
||||
DROP_NON_DROP,
|
||||
FORGET_NON_DROP,
|
||||
UNDROPPED_MANUALLY_DROPS
|
||||
@ -206,10 +98,11 @@ impl<'tcx> LateLintPass<'tcx> for DropForgetRef {
|
||||
let is_copy = is_copy(cx, arg_ty);
|
||||
let drop_is_single_call_in_arm = is_single_call_in_arm(cx, arg, expr);
|
||||
let (lint, msg) = match fn_name {
|
||||
sym::mem_drop if arg_ty.is_ref() && !drop_is_single_call_in_arm => (DROP_REF, DROP_REF_SUMMARY),
|
||||
sym::mem_forget if arg_ty.is_ref() => (FORGET_REF, FORGET_REF_SUMMARY),
|
||||
sym::mem_drop if is_copy && !drop_is_single_call_in_arm => (DROP_COPY, DROP_COPY_SUMMARY),
|
||||
sym::mem_forget if is_copy => (FORGET_COPY, FORGET_COPY_SUMMARY),
|
||||
// early return for uplifted lints: drop_ref, drop_copy, forget_ref, forget_copy
|
||||
sym::mem_drop if arg_ty.is_ref() && !drop_is_single_call_in_arm => return,
|
||||
sym::mem_forget if arg_ty.is_ref() => return,
|
||||
sym::mem_drop if is_copy && !drop_is_single_call_in_arm => return,
|
||||
sym::mem_forget if is_copy => return,
|
||||
sym::mem_drop if is_type_lang_item(cx, arg_ty, LangItem::ManuallyDrop) => {
|
||||
span_lint_and_help(
|
||||
cx,
|
||||
|
@ -32,9 +32,13 @@ pub static RENAMED_LINTS: &[(&str, &str)] = &[
|
||||
("clippy::zero_width_space", "clippy::invisible_characters"),
|
||||
("clippy::clone_double_ref", "suspicious_double_ref_op"),
|
||||
("clippy::drop_bounds", "drop_bounds"),
|
||||
("clippy::drop_copy", "drop_copy"),
|
||||
("clippy::drop_ref", "drop_ref"),
|
||||
("clippy::for_loop_over_option", "for_loops_over_fallibles"),
|
||||
("clippy::for_loop_over_result", "for_loops_over_fallibles"),
|
||||
("clippy::for_loops_over_fallibles", "for_loops_over_fallibles"),
|
||||
("clippy::forget_copy", "forget_copy"),
|
||||
("clippy::forget_ref", "forget_ref"),
|
||||
("clippy::into_iter_on_array", "array_into_iter"),
|
||||
("clippy::invalid_atomic_ordering", "invalid_atomic_ordering"),
|
||||
("clippy::invalid_ref", "invalid_value"),
|
||||
|
@ -1,86 +0,0 @@
|
||||
#![warn(clippy::drop_copy, clippy::forget_copy)]
|
||||
#![allow(clippy::toplevel_ref_arg, clippy::drop_ref, clippy::forget_ref, unused_mut)]
|
||||
|
||||
use std::mem::{drop, forget};
|
||||
use std::vec::Vec;
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
struct SomeStruct;
|
||||
|
||||
struct AnotherStruct {
|
||||
x: u8,
|
||||
y: u8,
|
||||
z: Vec<u8>,
|
||||
}
|
||||
|
||||
impl Clone for AnotherStruct {
|
||||
fn clone(&self) -> AnotherStruct {
|
||||
AnotherStruct {
|
||||
x: self.x,
|
||||
y: self.y,
|
||||
z: self.z.clone(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let s1 = SomeStruct {};
|
||||
let s2 = s1;
|
||||
let s3 = &s1;
|
||||
let mut s4 = s1;
|
||||
let ref s5 = s1;
|
||||
|
||||
drop(s1);
|
||||
drop(s2);
|
||||
drop(s3);
|
||||
drop(s4);
|
||||
drop(s5);
|
||||
|
||||
forget(s1);
|
||||
forget(s2);
|
||||
forget(s3);
|
||||
forget(s4);
|
||||
forget(s5);
|
||||
|
||||
let a1 = AnotherStruct {
|
||||
x: 255,
|
||||
y: 0,
|
||||
z: vec![1, 2, 3],
|
||||
};
|
||||
let a2 = &a1;
|
||||
let mut a3 = a1.clone();
|
||||
let ref a4 = a1;
|
||||
let a5 = a1.clone();
|
||||
|
||||
drop(a2);
|
||||
drop(a3);
|
||||
drop(a4);
|
||||
drop(a5);
|
||||
|
||||
forget(a2);
|
||||
let a3 = &a1;
|
||||
forget(a3);
|
||||
forget(a4);
|
||||
let a5 = a1.clone();
|
||||
forget(a5);
|
||||
}
|
||||
|
||||
#[allow(unused)]
|
||||
#[allow(clippy::unit_cmp)]
|
||||
fn issue9482(x: u8) {
|
||||
fn println_and<T>(t: T) -> T {
|
||||
println!("foo");
|
||||
t
|
||||
}
|
||||
|
||||
match x {
|
||||
0 => drop(println_and(12)), // Don't lint (copy type), we only care about side-effects
|
||||
1 => drop(println_and(String::new())), // Don't lint (no copy type), we only care about side-effects
|
||||
2 => {
|
||||
drop(println_and(13)); // Lint, even if we only care about the side-effect, it's already in a block
|
||||
},
|
||||
3 if drop(println_and(14)) == () => (), // Lint, idiomatic use is only in body of `Arm`
|
||||
4 => drop(2), // Lint, not a fn/method call
|
||||
_ => (),
|
||||
}
|
||||
}
|
@ -1,112 +0,0 @@
|
||||
error: calls to `std::mem::drop` with a value that implements `Copy`. Dropping a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:33:5
|
||||
|
|
||||
LL | drop(s1);
|
||||
| ^^^^^^^^
|
||||
|
|
||||
note: argument has type `SomeStruct`
|
||||
--> $DIR/drop_forget_copy.rs:33:10
|
||||
|
|
||||
LL | drop(s1);
|
||||
| ^^
|
||||
= note: `-D clippy::drop-copy` implied by `-D warnings`
|
||||
|
||||
error: calls to `std::mem::drop` with a value that implements `Copy`. Dropping a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:34:5
|
||||
|
|
||||
LL | drop(s2);
|
||||
| ^^^^^^^^
|
||||
|
|
||||
note: argument has type `SomeStruct`
|
||||
--> $DIR/drop_forget_copy.rs:34:10
|
||||
|
|
||||
LL | drop(s2);
|
||||
| ^^
|
||||
|
||||
error: calls to `std::mem::drop` with a value that implements `Copy`. Dropping a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:36:5
|
||||
|
|
||||
LL | drop(s4);
|
||||
| ^^^^^^^^
|
||||
|
|
||||
note: argument has type `SomeStruct`
|
||||
--> $DIR/drop_forget_copy.rs:36:10
|
||||
|
|
||||
LL | drop(s4);
|
||||
| ^^
|
||||
|
||||
error: calls to `std::mem::forget` with a value that implements `Copy`. Forgetting a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:39:5
|
||||
|
|
||||
LL | forget(s1);
|
||||
| ^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `SomeStruct`
|
||||
--> $DIR/drop_forget_copy.rs:39:12
|
||||
|
|
||||
LL | forget(s1);
|
||||
| ^^
|
||||
= note: `-D clippy::forget-copy` implied by `-D warnings`
|
||||
|
||||
error: calls to `std::mem::forget` with a value that implements `Copy`. Forgetting a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:40:5
|
||||
|
|
||||
LL | forget(s2);
|
||||
| ^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `SomeStruct`
|
||||
--> $DIR/drop_forget_copy.rs:40:12
|
||||
|
|
||||
LL | forget(s2);
|
||||
| ^^
|
||||
|
||||
error: calls to `std::mem::forget` with a value that implements `Copy`. Forgetting a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:42:5
|
||||
|
|
||||
LL | forget(s4);
|
||||
| ^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `SomeStruct`
|
||||
--> $DIR/drop_forget_copy.rs:42:12
|
||||
|
|
||||
LL | forget(s4);
|
||||
| ^^
|
||||
|
||||
error: calls to `std::mem::drop` with a value that implements `Copy`. Dropping a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:80:13
|
||||
|
|
||||
LL | drop(println_and(13)); // Lint, even if we only care about the side-effect, it's already in a block
|
||||
| ^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `i32`
|
||||
--> $DIR/drop_forget_copy.rs:80:18
|
||||
|
|
||||
LL | drop(println_and(13)); // Lint, even if we only care about the side-effect, it's already in a block
|
||||
| ^^^^^^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a value that implements `Copy`. Dropping a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:82:14
|
||||
|
|
||||
LL | 3 if drop(println_and(14)) == () => (), // Lint, idiomatic use is only in body of `Arm`
|
||||
| ^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `i32`
|
||||
--> $DIR/drop_forget_copy.rs:82:19
|
||||
|
|
||||
LL | 3 if drop(println_and(14)) == () => (), // Lint, idiomatic use is only in body of `Arm`
|
||||
| ^^^^^^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a value that implements `Copy`. Dropping a copy leaves the original intact
|
||||
--> $DIR/drop_forget_copy.rs:83:14
|
||||
|
|
||||
LL | 4 => drop(2), // Lint, not a fn/method call
|
||||
| ^^^^^^^
|
||||
|
|
||||
note: argument has type `i32`
|
||||
--> $DIR/drop_forget_copy.rs:83:19
|
||||
|
|
||||
LL | 4 => drop(2), // Lint, not a fn/method call
|
||||
| ^
|
||||
|
||||
error: aborting due to 9 previous errors
|
||||
|
@ -1,147 +0,0 @@
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:11:5
|
||||
|
|
||||
LL | drop(&SomeStruct);
|
||||
| ^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/drop_ref.rs:11:10
|
||||
|
|
||||
LL | drop(&SomeStruct);
|
||||
| ^^^^^^^^^^^
|
||||
= note: `-D clippy::drop-ref` implied by `-D warnings`
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:14:5
|
||||
|
|
||||
LL | drop(&owned1);
|
||||
| ^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/drop_ref.rs:14:10
|
||||
|
|
||||
LL | drop(&owned1);
|
||||
| ^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:15:5
|
||||
|
|
||||
LL | drop(&&owned1);
|
||||
| ^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&&SomeStruct`
|
||||
--> $DIR/drop_ref.rs:15:10
|
||||
|
|
||||
LL | drop(&&owned1);
|
||||
| ^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:16:5
|
||||
|
|
||||
LL | drop(&mut owned1);
|
||||
| ^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&mut SomeStruct`
|
||||
--> $DIR/drop_ref.rs:16:10
|
||||
|
|
||||
LL | drop(&mut owned1);
|
||||
| ^^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:20:5
|
||||
|
|
||||
LL | drop(reference1);
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/drop_ref.rs:20:10
|
||||
|
|
||||
LL | drop(reference1);
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:23:5
|
||||
|
|
||||
LL | drop(reference2);
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&mut SomeStruct`
|
||||
--> $DIR/drop_ref.rs:23:10
|
||||
|
|
||||
LL | drop(reference2);
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:26:5
|
||||
|
|
||||
LL | drop(reference3);
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/drop_ref.rs:26:10
|
||||
|
|
||||
LL | drop(reference3);
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:31:5
|
||||
|
|
||||
LL | drop(&val);
|
||||
| ^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&T`
|
||||
--> $DIR/drop_ref.rs:31:10
|
||||
|
|
||||
LL | drop(&val);
|
||||
| ^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:39:5
|
||||
|
|
||||
LL | std::mem::drop(&SomeStruct);
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/drop_ref.rs:39:20
|
||||
|
|
||||
LL | std::mem::drop(&SomeStruct);
|
||||
| ^^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:91:13
|
||||
|
|
||||
LL | drop(println_and(&13)); // Lint, even if we only care about the side-effect, it's already in a block
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&i32`
|
||||
--> $DIR/drop_ref.rs:91:18
|
||||
|
|
||||
LL | drop(println_and(&13)); // Lint, even if we only care about the side-effect, it's already in a block
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:93:14
|
||||
|
|
||||
LL | 3 if drop(println_and(&14)) == () => (), // Lint, idiomatic use is only in body of `Arm`
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&i32`
|
||||
--> $DIR/drop_ref.rs:93:19
|
||||
|
|
||||
LL | 3 if drop(println_and(&14)) == () => (), // Lint, idiomatic use is only in body of `Arm`
|
||||
| ^^^^^^^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::drop` with a reference instead of an owned value. Dropping a reference does nothing
|
||||
--> $DIR/drop_ref.rs:94:14
|
||||
|
|
||||
LL | 4 => drop(&2), // Lint, not a fn/method call
|
||||
| ^^^^^^^^
|
||||
|
|
||||
note: argument has type `&i32`
|
||||
--> $DIR/drop_ref.rs:94:19
|
||||
|
|
||||
LL | 4 => drop(&2), // Lint, not a fn/method call
|
||||
| ^^
|
||||
|
||||
error: aborting due to 12 previous errors
|
||||
|
@ -1,50 +0,0 @@
|
||||
#![warn(clippy::forget_ref)]
|
||||
#![allow(clippy::toplevel_ref_arg)]
|
||||
#![allow(clippy::unnecessary_wraps, clippy::forget_non_drop)]
|
||||
#![allow(clippy::borrow_deref_ref)]
|
||||
|
||||
use std::mem::forget;
|
||||
|
||||
struct SomeStruct;
|
||||
|
||||
fn main() {
|
||||
forget(&SomeStruct);
|
||||
|
||||
let mut owned = SomeStruct;
|
||||
forget(&owned);
|
||||
forget(&&owned);
|
||||
forget(&mut owned);
|
||||
forget(owned); //OK
|
||||
|
||||
let reference1 = &SomeStruct;
|
||||
forget(&*reference1);
|
||||
|
||||
let reference2 = &mut SomeStruct;
|
||||
forget(reference2);
|
||||
|
||||
let ref reference3 = SomeStruct;
|
||||
forget(reference3);
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
fn test_generic_fn_forget<T>(val: T) {
|
||||
forget(&val);
|
||||
forget(val); //OK
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
fn test_similarly_named_function() {
|
||||
fn forget<T>(_val: T) {}
|
||||
forget(&SomeStruct); //OK; call to unrelated function which happens to have the same name
|
||||
std::mem::forget(&SomeStruct);
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct Error;
|
||||
fn produce_half_owl_error() -> Result<(), Error> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn produce_half_owl_ok() -> Result<bool, ()> {
|
||||
Ok(true)
|
||||
}
|
@ -1,111 +0,0 @@
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:11:5
|
||||
|
|
||||
LL | forget(&SomeStruct);
|
||||
| ^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/forget_ref.rs:11:12
|
||||
|
|
||||
LL | forget(&SomeStruct);
|
||||
| ^^^^^^^^^^^
|
||||
= note: `-D clippy::forget-ref` implied by `-D warnings`
|
||||
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:14:5
|
||||
|
|
||||
LL | forget(&owned);
|
||||
| ^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/forget_ref.rs:14:12
|
||||
|
|
||||
LL | forget(&owned);
|
||||
| ^^^^^^
|
||||
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:15:5
|
||||
|
|
||||
LL | forget(&&owned);
|
||||
| ^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&&SomeStruct`
|
||||
--> $DIR/forget_ref.rs:15:12
|
||||
|
|
||||
LL | forget(&&owned);
|
||||
| ^^^^^^^
|
||||
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:16:5
|
||||
|
|
||||
LL | forget(&mut owned);
|
||||
| ^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&mut SomeStruct`
|
||||
--> $DIR/forget_ref.rs:16:12
|
||||
|
|
||||
LL | forget(&mut owned);
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:20:5
|
||||
|
|
||||
LL | forget(&*reference1);
|
||||
| ^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/forget_ref.rs:20:12
|
||||
|
|
||||
LL | forget(&*reference1);
|
||||
| ^^^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:23:5
|
||||
|
|
||||
LL | forget(reference2);
|
||||
| ^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&mut SomeStruct`
|
||||
--> $DIR/forget_ref.rs:23:12
|
||||
|
|
||||
LL | forget(reference2);
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:26:5
|
||||
|
|
||||
LL | forget(reference3);
|
||||
| ^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/forget_ref.rs:26:12
|
||||
|
|
||||
LL | forget(reference3);
|
||||
| ^^^^^^^^^^
|
||||
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:31:5
|
||||
|
|
||||
LL | forget(&val);
|
||||
| ^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&T`
|
||||
--> $DIR/forget_ref.rs:31:12
|
||||
|
|
||||
LL | forget(&val);
|
||||
| ^^^^
|
||||
|
||||
error: calls to `std::mem::forget` with a reference instead of an owned value. Forgetting a reference does nothing
|
||||
--> $DIR/forget_ref.rs:39:5
|
||||
|
|
||||
LL | std::mem::forget(&SomeStruct);
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
note: argument has type `&SomeStruct`
|
||||
--> $DIR/forget_ref.rs:39:22
|
||||
|
|
||||
LL | std::mem::forget(&SomeStruct);
|
||||
| ^^^^^^^^^^^
|
||||
|
||||
error: aborting due to 9 previous errors
|
||||
|
@ -5,7 +5,7 @@ use std::mem as memstuff;
|
||||
use std::mem::forget as forgetSomething;
|
||||
|
||||
#[warn(clippy::mem_forget)]
|
||||
#[allow(clippy::forget_copy)]
|
||||
#[allow(forget_copy)]
|
||||
fn main() {
|
||||
let five: i32 = 5;
|
||||
forgetSomething(five);
|
||||
|
@ -2,7 +2,7 @@
|
||||
#![allow(unused)]
|
||||
#![allow(deref_nullptr)]
|
||||
#![allow(clippy::unnecessary_operation)]
|
||||
#![allow(clippy::drop_copy)]
|
||||
#![allow(drop_copy)]
|
||||
#![warn(clippy::multiple_unsafe_ops_per_block)]
|
||||
|
||||
extern crate proc_macros;
|
||||
|
@ -29,7 +29,11 @@
|
||||
#![allow(clippy::invisible_characters)]
|
||||
#![allow(suspicious_double_ref_op)]
|
||||
#![allow(drop_bounds)]
|
||||
#![allow(drop_copy)]
|
||||
#![allow(drop_ref)]
|
||||
#![allow(for_loops_over_fallibles)]
|
||||
#![allow(forget_copy)]
|
||||
#![allow(forget_ref)]
|
||||
#![allow(array_into_iter)]
|
||||
#![allow(invalid_atomic_ordering)]
|
||||
#![allow(invalid_value)]
|
||||
@ -71,9 +75,13 @@
|
||||
#![warn(clippy::invisible_characters)]
|
||||
#![warn(suspicious_double_ref_op)]
|
||||
#![warn(drop_bounds)]
|
||||
#![warn(drop_copy)]
|
||||
#![warn(drop_ref)]
|
||||
#![warn(for_loops_over_fallibles)]
|
||||
#![warn(for_loops_over_fallibles)]
|
||||
#![warn(for_loops_over_fallibles)]
|
||||
#![warn(forget_copy)]
|
||||
#![warn(forget_ref)]
|
||||
#![warn(array_into_iter)]
|
||||
#![warn(invalid_atomic_ordering)]
|
||||
#![warn(invalid_value)]
|
||||
|
@ -29,7 +29,11 @@
|
||||
#![allow(clippy::invisible_characters)]
|
||||
#![allow(suspicious_double_ref_op)]
|
||||
#![allow(drop_bounds)]
|
||||
#![allow(drop_copy)]
|
||||
#![allow(drop_ref)]
|
||||
#![allow(for_loops_over_fallibles)]
|
||||
#![allow(forget_copy)]
|
||||
#![allow(forget_ref)]
|
||||
#![allow(array_into_iter)]
|
||||
#![allow(invalid_atomic_ordering)]
|
||||
#![allow(invalid_value)]
|
||||
@ -71,9 +75,13 @@
|
||||
#![warn(clippy::zero_width_space)]
|
||||
#![warn(clippy::clone_double_ref)]
|
||||
#![warn(clippy::drop_bounds)]
|
||||
#![warn(clippy::drop_copy)]
|
||||
#![warn(clippy::drop_ref)]
|
||||
#![warn(clippy::for_loop_over_option)]
|
||||
#![warn(clippy::for_loop_over_result)]
|
||||
#![warn(clippy::for_loops_over_fallibles)]
|
||||
#![warn(clippy::forget_copy)]
|
||||
#![warn(clippy::forget_ref)]
|
||||
#![warn(clippy::into_iter_on_array)]
|
||||
#![warn(clippy::invalid_atomic_ordering)]
|
||||
#![warn(clippy::invalid_ref)]
|
||||
|
@ -1,5 +1,5 @@
|
||||
error: lint `clippy::almost_complete_letter_range` has been renamed to `clippy::almost_complete_range`
|
||||
--> $DIR/rename.rs:44:9
|
||||
--> $DIR/rename.rs:48:9
|
||||
|
|
||||
LL | #![warn(clippy::almost_complete_letter_range)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::almost_complete_range`
|
||||
@ -7,256 +7,280 @@ LL | #![warn(clippy::almost_complete_letter_range)]
|
||||
= note: `-D renamed-and-removed-lints` implied by `-D warnings`
|
||||
|
||||
error: lint `clippy::blacklisted_name` has been renamed to `clippy::disallowed_names`
|
||||
--> $DIR/rename.rs:45:9
|
||||
--> $DIR/rename.rs:49:9
|
||||
|
|
||||
LL | #![warn(clippy::blacklisted_name)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::disallowed_names`
|
||||
|
||||
error: lint `clippy::block_in_if_condition_expr` has been renamed to `clippy::blocks_in_if_conditions`
|
||||
--> $DIR/rename.rs:46:9
|
||||
--> $DIR/rename.rs:50:9
|
||||
|
|
||||
LL | #![warn(clippy::block_in_if_condition_expr)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::blocks_in_if_conditions`
|
||||
|
||||
error: lint `clippy::block_in_if_condition_stmt` has been renamed to `clippy::blocks_in_if_conditions`
|
||||
--> $DIR/rename.rs:47:9
|
||||
--> $DIR/rename.rs:51:9
|
||||
|
|
||||
LL | #![warn(clippy::block_in_if_condition_stmt)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::blocks_in_if_conditions`
|
||||
|
||||
error: lint `clippy::box_vec` has been renamed to `clippy::box_collection`
|
||||
--> $DIR/rename.rs:48:9
|
||||
--> $DIR/rename.rs:52:9
|
||||
|
|
||||
LL | #![warn(clippy::box_vec)]
|
||||
| ^^^^^^^^^^^^^^^ help: use the new name: `clippy::box_collection`
|
||||
|
||||
error: lint `clippy::const_static_lifetime` has been renamed to `clippy::redundant_static_lifetimes`
|
||||
--> $DIR/rename.rs:49:9
|
||||
--> $DIR/rename.rs:53:9
|
||||
|
|
||||
LL | #![warn(clippy::const_static_lifetime)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::redundant_static_lifetimes`
|
||||
|
||||
error: lint `clippy::cyclomatic_complexity` has been renamed to `clippy::cognitive_complexity`
|
||||
--> $DIR/rename.rs:50:9
|
||||
--> $DIR/rename.rs:54:9
|
||||
|
|
||||
LL | #![warn(clippy::cyclomatic_complexity)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::cognitive_complexity`
|
||||
|
||||
error: lint `clippy::derive_hash_xor_eq` has been renamed to `clippy::derived_hash_with_manual_eq`
|
||||
--> $DIR/rename.rs:51:9
|
||||
--> $DIR/rename.rs:55:9
|
||||
|
|
||||
LL | #![warn(clippy::derive_hash_xor_eq)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::derived_hash_with_manual_eq`
|
||||
|
||||
error: lint `clippy::disallowed_method` has been renamed to `clippy::disallowed_methods`
|
||||
--> $DIR/rename.rs:52:9
|
||||
--> $DIR/rename.rs:56:9
|
||||
|
|
||||
LL | #![warn(clippy::disallowed_method)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::disallowed_methods`
|
||||
|
||||
error: lint `clippy::disallowed_type` has been renamed to `clippy::disallowed_types`
|
||||
--> $DIR/rename.rs:53:9
|
||||
--> $DIR/rename.rs:57:9
|
||||
|
|
||||
LL | #![warn(clippy::disallowed_type)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::disallowed_types`
|
||||
|
||||
error: lint `clippy::eval_order_dependence` has been renamed to `clippy::mixed_read_write_in_expression`
|
||||
--> $DIR/rename.rs:54:9
|
||||
--> $DIR/rename.rs:58:9
|
||||
|
|
||||
LL | #![warn(clippy::eval_order_dependence)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::mixed_read_write_in_expression`
|
||||
|
||||
error: lint `clippy::identity_conversion` has been renamed to `clippy::useless_conversion`
|
||||
--> $DIR/rename.rs:55:9
|
||||
--> $DIR/rename.rs:59:9
|
||||
|
|
||||
LL | #![warn(clippy::identity_conversion)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::useless_conversion`
|
||||
|
||||
error: lint `clippy::if_let_some_result` has been renamed to `clippy::match_result_ok`
|
||||
--> $DIR/rename.rs:56:9
|
||||
--> $DIR/rename.rs:60:9
|
||||
|
|
||||
LL | #![warn(clippy::if_let_some_result)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::match_result_ok`
|
||||
|
||||
error: lint `clippy::logic_bug` has been renamed to `clippy::overly_complex_bool_expr`
|
||||
--> $DIR/rename.rs:57:9
|
||||
--> $DIR/rename.rs:61:9
|
||||
|
|
||||
LL | #![warn(clippy::logic_bug)]
|
||||
| ^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::overly_complex_bool_expr`
|
||||
|
||||
error: lint `clippy::new_without_default_derive` has been renamed to `clippy::new_without_default`
|
||||
--> $DIR/rename.rs:58:9
|
||||
--> $DIR/rename.rs:62:9
|
||||
|
|
||||
LL | #![warn(clippy::new_without_default_derive)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::new_without_default`
|
||||
|
||||
error: lint `clippy::option_and_then_some` has been renamed to `clippy::bind_instead_of_map`
|
||||
--> $DIR/rename.rs:59:9
|
||||
--> $DIR/rename.rs:63:9
|
||||
|
|
||||
LL | #![warn(clippy::option_and_then_some)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::bind_instead_of_map`
|
||||
|
||||
error: lint `clippy::option_expect_used` has been renamed to `clippy::expect_used`
|
||||
--> $DIR/rename.rs:60:9
|
||||
--> $DIR/rename.rs:64:9
|
||||
|
|
||||
LL | #![warn(clippy::option_expect_used)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::expect_used`
|
||||
|
||||
error: lint `clippy::option_map_unwrap_or` has been renamed to `clippy::map_unwrap_or`
|
||||
--> $DIR/rename.rs:61:9
|
||||
--> $DIR/rename.rs:65:9
|
||||
|
|
||||
LL | #![warn(clippy::option_map_unwrap_or)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::map_unwrap_or`
|
||||
|
||||
error: lint `clippy::option_map_unwrap_or_else` has been renamed to `clippy::map_unwrap_or`
|
||||
--> $DIR/rename.rs:62:9
|
||||
--> $DIR/rename.rs:66:9
|
||||
|
|
||||
LL | #![warn(clippy::option_map_unwrap_or_else)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::map_unwrap_or`
|
||||
|
||||
error: lint `clippy::option_unwrap_used` has been renamed to `clippy::unwrap_used`
|
||||
--> $DIR/rename.rs:63:9
|
||||
--> $DIR/rename.rs:67:9
|
||||
|
|
||||
LL | #![warn(clippy::option_unwrap_used)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::unwrap_used`
|
||||
|
||||
error: lint `clippy::ref_in_deref` has been renamed to `clippy::needless_borrow`
|
||||
--> $DIR/rename.rs:64:9
|
||||
--> $DIR/rename.rs:68:9
|
||||
|
|
||||
LL | #![warn(clippy::ref_in_deref)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::needless_borrow`
|
||||
|
||||
error: lint `clippy::result_expect_used` has been renamed to `clippy::expect_used`
|
||||
--> $DIR/rename.rs:65:9
|
||||
--> $DIR/rename.rs:69:9
|
||||
|
|
||||
LL | #![warn(clippy::result_expect_used)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::expect_used`
|
||||
|
||||
error: lint `clippy::result_map_unwrap_or_else` has been renamed to `clippy::map_unwrap_or`
|
||||
--> $DIR/rename.rs:66:9
|
||||
--> $DIR/rename.rs:70:9
|
||||
|
|
||||
LL | #![warn(clippy::result_map_unwrap_or_else)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::map_unwrap_or`
|
||||
|
||||
error: lint `clippy::result_unwrap_used` has been renamed to `clippy::unwrap_used`
|
||||
--> $DIR/rename.rs:67:9
|
||||
--> $DIR/rename.rs:71:9
|
||||
|
|
||||
LL | #![warn(clippy::result_unwrap_used)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::unwrap_used`
|
||||
|
||||
error: lint `clippy::single_char_push_str` has been renamed to `clippy::single_char_add_str`
|
||||
--> $DIR/rename.rs:68:9
|
||||
--> $DIR/rename.rs:72:9
|
||||
|
|
||||
LL | #![warn(clippy::single_char_push_str)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::single_char_add_str`
|
||||
|
||||
error: lint `clippy::stutter` has been renamed to `clippy::module_name_repetitions`
|
||||
--> $DIR/rename.rs:69:9
|
||||
--> $DIR/rename.rs:73:9
|
||||
|
|
||||
LL | #![warn(clippy::stutter)]
|
||||
| ^^^^^^^^^^^^^^^ help: use the new name: `clippy::module_name_repetitions`
|
||||
|
||||
error: lint `clippy::to_string_in_display` has been renamed to `clippy::recursive_format_impl`
|
||||
--> $DIR/rename.rs:70:9
|
||||
--> $DIR/rename.rs:74:9
|
||||
|
|
||||
LL | #![warn(clippy::to_string_in_display)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::recursive_format_impl`
|
||||
|
||||
error: lint `clippy::zero_width_space` has been renamed to `clippy::invisible_characters`
|
||||
--> $DIR/rename.rs:71:9
|
||||
--> $DIR/rename.rs:75:9
|
||||
|
|
||||
LL | #![warn(clippy::zero_width_space)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `clippy::invisible_characters`
|
||||
|
||||
error: lint `clippy::clone_double_ref` has been renamed to `suspicious_double_ref_op`
|
||||
--> $DIR/rename.rs:72:9
|
||||
--> $DIR/rename.rs:76:9
|
||||
|
|
||||
LL | #![warn(clippy::clone_double_ref)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `suspicious_double_ref_op`
|
||||
|
||||
error: lint `clippy::drop_bounds` has been renamed to `drop_bounds`
|
||||
--> $DIR/rename.rs:73:9
|
||||
--> $DIR/rename.rs:77:9
|
||||
|
|
||||
LL | #![warn(clippy::drop_bounds)]
|
||||
| ^^^^^^^^^^^^^^^^^^^ help: use the new name: `drop_bounds`
|
||||
|
||||
error: lint `clippy::drop_copy` has been renamed to `drop_copy`
|
||||
--> $DIR/rename.rs:78:9
|
||||
|
|
||||
LL | #![warn(clippy::drop_copy)]
|
||||
| ^^^^^^^^^^^^^^^^^ help: use the new name: `drop_copy`
|
||||
|
||||
error: lint `clippy::drop_ref` has been renamed to `drop_ref`
|
||||
--> $DIR/rename.rs:79:9
|
||||
|
|
||||
LL | #![warn(clippy::drop_ref)]
|
||||
| ^^^^^^^^^^^^^^^^ help: use the new name: `drop_ref`
|
||||
|
||||
error: lint `clippy::for_loop_over_option` has been renamed to `for_loops_over_fallibles`
|
||||
--> $DIR/rename.rs:74:9
|
||||
--> $DIR/rename.rs:80:9
|
||||
|
|
||||
LL | #![warn(clippy::for_loop_over_option)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `for_loops_over_fallibles`
|
||||
|
||||
error: lint `clippy::for_loop_over_result` has been renamed to `for_loops_over_fallibles`
|
||||
--> $DIR/rename.rs:75:9
|
||||
--> $DIR/rename.rs:81:9
|
||||
|
|
||||
LL | #![warn(clippy::for_loop_over_result)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `for_loops_over_fallibles`
|
||||
|
||||
error: lint `clippy::for_loops_over_fallibles` has been renamed to `for_loops_over_fallibles`
|
||||
--> $DIR/rename.rs:76:9
|
||||
--> $DIR/rename.rs:82:9
|
||||
|
|
||||
LL | #![warn(clippy::for_loops_over_fallibles)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `for_loops_over_fallibles`
|
||||
|
||||
error: lint `clippy::forget_copy` has been renamed to `forget_copy`
|
||||
--> $DIR/rename.rs:83:9
|
||||
|
|
||||
LL | #![warn(clippy::forget_copy)]
|
||||
| ^^^^^^^^^^^^^^^^^^^ help: use the new name: `forget_copy`
|
||||
|
||||
error: lint `clippy::forget_ref` has been renamed to `forget_ref`
|
||||
--> $DIR/rename.rs:84:9
|
||||
|
|
||||
LL | #![warn(clippy::forget_ref)]
|
||||
| ^^^^^^^^^^^^^^^^^^ help: use the new name: `forget_ref`
|
||||
|
||||
error: lint `clippy::into_iter_on_array` has been renamed to `array_into_iter`
|
||||
--> $DIR/rename.rs:77:9
|
||||
--> $DIR/rename.rs:85:9
|
||||
|
|
||||
LL | #![warn(clippy::into_iter_on_array)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `array_into_iter`
|
||||
|
||||
error: lint `clippy::invalid_atomic_ordering` has been renamed to `invalid_atomic_ordering`
|
||||
--> $DIR/rename.rs:78:9
|
||||
--> $DIR/rename.rs:86:9
|
||||
|
|
||||
LL | #![warn(clippy::invalid_atomic_ordering)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `invalid_atomic_ordering`
|
||||
|
||||
error: lint `clippy::invalid_ref` has been renamed to `invalid_value`
|
||||
--> $DIR/rename.rs:79:9
|
||||
--> $DIR/rename.rs:87:9
|
||||
|
|
||||
LL | #![warn(clippy::invalid_ref)]
|
||||
| ^^^^^^^^^^^^^^^^^^^ help: use the new name: `invalid_value`
|
||||
|
||||
error: lint `clippy::let_underscore_drop` has been renamed to `let_underscore_drop`
|
||||
--> $DIR/rename.rs:80:9
|
||||
--> $DIR/rename.rs:88:9
|
||||
|
|
||||
LL | #![warn(clippy::let_underscore_drop)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `let_underscore_drop`
|
||||
|
||||
error: lint `clippy::mem_discriminant_non_enum` has been renamed to `enum_intrinsics_non_enums`
|
||||
--> $DIR/rename.rs:81:9
|
||||
--> $DIR/rename.rs:89:9
|
||||
|
|
||||
LL | #![warn(clippy::mem_discriminant_non_enum)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `enum_intrinsics_non_enums`
|
||||
|
||||
error: lint `clippy::panic_params` has been renamed to `non_fmt_panics`
|
||||
--> $DIR/rename.rs:82:9
|
||||
--> $DIR/rename.rs:90:9
|
||||
|
|
||||
LL | #![warn(clippy::panic_params)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^ help: use the new name: `non_fmt_panics`
|
||||
|
||||
error: lint `clippy::positional_named_format_parameters` has been renamed to `named_arguments_used_positionally`
|
||||
--> $DIR/rename.rs:83:9
|
||||
--> $DIR/rename.rs:91:9
|
||||
|
|
||||
LL | #![warn(clippy::positional_named_format_parameters)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `named_arguments_used_positionally`
|
||||
|
||||
error: lint `clippy::temporary_cstring_as_ptr` has been renamed to `temporary_cstring_as_ptr`
|
||||
--> $DIR/rename.rs:84:9
|
||||
--> $DIR/rename.rs:92:9
|
||||
|
|
||||
LL | #![warn(clippy::temporary_cstring_as_ptr)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `temporary_cstring_as_ptr`
|
||||
|
||||
error: lint `clippy::unknown_clippy_lints` has been renamed to `unknown_lints`
|
||||
--> $DIR/rename.rs:85:9
|
||||
--> $DIR/rename.rs:93:9
|
||||
|
|
||||
LL | #![warn(clippy::unknown_clippy_lints)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `unknown_lints`
|
||||
|
||||
error: lint `clippy::unused_label` has been renamed to `unused_labels`
|
||||
--> $DIR/rename.rs:86:9
|
||||
--> $DIR/rename.rs:94:9
|
||||
|
|
||||
LL | #![warn(clippy::unused_label)]
|
||||
| ^^^^^^^^^^^^^^^^^^^^ help: use the new name: `unused_labels`
|
||||
|
||||
error: aborting due to 43 previous errors
|
||||
error: aborting due to 47 previous errors
|
||||
|
||||
|
@ -10,7 +10,7 @@
|
||||
#[warn(clippy::unnecessary_cast)]
|
||||
#[warn(clippy::useless_transmute)]
|
||||
// Shouldn't suggest rustc lint name(`dead_code`)
|
||||
#[warn(clippy::drop_copy)]
|
||||
#[warn(clippy::eq_op)]
|
||||
// Shouldn't suggest removed/deprecated clippy lint name(`unused_collect`)
|
||||
#[warn(clippy::unused_self)]
|
||||
// Shouldn't suggest renamed clippy lint name(`const_static_lifetime`)
|
||||
|
@ -34,7 +34,7 @@ error: unknown lint: `clippy::dead_cod`
|
||||
--> $DIR/unknown_clippy_lints.rs:13:8
|
||||
|
|
||||
LL | #[warn(clippy::dead_cod)]
|
||||
| ^^^^^^^^^^^^^^^^ help: did you mean: `clippy::drop_copy`
|
||||
| ^^^^^^^^^^^^^^^^ help: did you mean: `clippy::eq_op`
|
||||
|
||||
error: unknown lint: `clippy::unused_colle`
|
||||
--> $DIR/unknown_clippy_lints.rs:15:8
|
||||
|
@ -1,3 +1,5 @@
|
||||
#![allow(drop_ref)]
|
||||
|
||||
fn main() {
|
||||
let target = &mut 42;
|
||||
let target2 = target as *mut _;
|
||||
|
@ -1,5 +1,7 @@
|
||||
//@error-in-other-file: memory is uninitialized at [0x4..0x10]
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
use std::alloc::{alloc, dealloc, Layout};
|
||||
use std::slice::from_raw_parts;
|
||||
|
||||
|
@ -2,6 +2,8 @@
|
||||
//@normalize-stderr-test: "a[0-9]+" -> "ALLOC"
|
||||
#![feature(strict_provenance)]
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
// Test printing allocations that contain single-byte provenance.
|
||||
|
||||
use std::alloc::{alloc, dealloc, Layout};
|
||||
|
@ -1,5 +1,8 @@
|
||||
//@compile-flags: -Zmiri-retag-fields
|
||||
// Checks that the test does not run forever (which relies on a fast path).
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
fn main() {
|
||||
let array = [(); usize::MAX];
|
||||
drop(array); // Pass the array to a function, retagging its fields
|
||||
|
@ -3,6 +3,7 @@
|
||||
|
||||
#![feature(inherent_associated_types)]
|
||||
#![allow(incomplete_features)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
use std::convert::identity;
|
||||
|
||||
|
@ -4,7 +4,7 @@
|
||||
async fn lotsa_lifetimes<'a, 'b, 'c>(a: &'a u32, b: &'b u32, c: &'c u32) -> (&'a u32, &'b u32)
|
||||
where 'b: 'a
|
||||
{
|
||||
drop((a, c));
|
||||
let _ = (a, c);
|
||||
(b, b)
|
||||
}
|
||||
|
||||
|
@ -1,6 +1,7 @@
|
||||
// Check that closure captures for slice patterns are inferred correctly
|
||||
|
||||
#![allow(unused_variables)]
|
||||
#![allow(drop_ref)]
|
||||
|
||||
// run-pass
|
||||
|
||||
|
@ -1,6 +1,7 @@
|
||||
// run-pass
|
||||
#![allow(unused_mut)]
|
||||
#![allow(unused_variables)]
|
||||
#![allow(drop_copy)]
|
||||
// pretty-expanded FIXME #23616
|
||||
|
||||
struct A { a: isize, b: Box<isize> }
|
||||
|
@ -1,6 +1,8 @@
|
||||
// run-pass
|
||||
// pretty-expanded FIXME #23616
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
struct A { a: isize, b: Box<isize> }
|
||||
|
||||
fn field_copy_after_field_borrow() {
|
||||
|
@ -1,6 +1,7 @@
|
||||
// run-pass
|
||||
|
||||
#![warn(rust_2021_incompatible_closure_captures)]
|
||||
#![allow(drop_ref, drop_copy)]
|
||||
|
||||
fn main() {
|
||||
if let a = "" {
|
||||
|
@ -1,5 +1,5 @@
|
||||
warning: irrefutable `if let` pattern
|
||||
--> $DIR/issue-78720.rs:6:8
|
||||
--> $DIR/issue-78720.rs:7:8
|
||||
|
|
||||
LL | if let a = "" {
|
||||
| ^^^^^^^^^^
|
||||
|
@ -3,6 +3,7 @@
|
||||
|
||||
#![allow(unused)]
|
||||
#![allow(dead_code)]
|
||||
#![allow(drop_ref)]
|
||||
|
||||
struct Int(i32);
|
||||
struct B<'a>(&'a i32);
|
||||
|
@ -1,6 +1,8 @@
|
||||
// edition:2021
|
||||
// check-pass
|
||||
|
||||
#![feature(rustc_attrs)]
|
||||
#![allow(drop_ref)]
|
||||
|
||||
fn main() {
|
||||
let mut x = 1;
|
||||
|
@ -1,5 +1,7 @@
|
||||
// check-pass
|
||||
|
||||
#![allow(forget_copy)]
|
||||
|
||||
use std::mem::forget;
|
||||
|
||||
const _: () = forget(0i32);
|
||||
|
@ -1,4 +1,7 @@
|
||||
// check-pass
|
||||
|
||||
#![allow(forget_copy)]
|
||||
|
||||
const _: () = core::mem::forget(Box::<u32>::default);
|
||||
const _: () = core::mem::forget(|| Box::<u32>::default());
|
||||
|
||||
|
@ -1,6 +1,8 @@
|
||||
// run-pass
|
||||
// pretty-expanded FIXME #23616
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
fn main() {
|
||||
use ::std::mem;
|
||||
mem::drop(2_usize);
|
||||
|
@ -1,6 +1,8 @@
|
||||
// run-pass
|
||||
// needs-unwind
|
||||
|
||||
#![allow(drop_ref, drop_copy)]
|
||||
|
||||
static mut CHECK: usize = 0;
|
||||
|
||||
struct DropChecker(usize);
|
||||
|
@ -1,4 +1,7 @@
|
||||
// run-rustfix
|
||||
|
||||
#![allow(drop_ref)]
|
||||
|
||||
struct Foo {
|
||||
x: isize
|
||||
}
|
||||
|
@ -1,4 +1,7 @@
|
||||
// run-rustfix
|
||||
|
||||
#![allow(drop_ref)]
|
||||
|
||||
struct Foo {
|
||||
x: isize
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
error[E0040]: explicit use of destructor method
|
||||
--> $DIR/explicit-call-to-supertrait-dtor.rs:19:14
|
||||
--> $DIR/explicit-call-to-supertrait-dtor.rs:22:14
|
||||
|
|
||||
LL | self.drop();
|
||||
| -----^^^^--
|
||||
|
@ -13,5 +13,4 @@ fn non_unsafe_pin_new_unchecked<T>(pointer: &mut T) -> Pin<&mut T> {
|
||||
fn main() {
|
||||
let mut self_referential = PhantomPinned;
|
||||
let _: Pin<&mut PhantomPinned> = non_unsafe_pin_new_unchecked(&mut self_referential);
|
||||
core::mem::forget(self_referential); // move and disable drop glue!
|
||||
}
|
||||
|
@ -4,6 +4,7 @@
|
||||
//[nomiropt]compile-flags: -Z mir-opt-level=0
|
||||
|
||||
#![feature(generators, generator_trait)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
use std::ops::Generator;
|
||||
use std::pin::Pin;
|
||||
|
@ -1,5 +1,5 @@
|
||||
error: generator cannot be sent between threads safely
|
||||
--> $DIR/issue-57017.rs:31:25
|
||||
--> $DIR/issue-57017.rs:32:25
|
||||
|
|
||||
LL | assert_send(g);
|
||||
| ^ generator is not `Send`
|
||||
@ -15,7 +15,7 @@ LL | | );
|
||||
|
|
||||
= help: the trait `Sync` is not implemented for `copy::unsync::Client`
|
||||
note: generator is not `Send` as this value is used across a yield
|
||||
--> $DIR/issue-57017.rs:29:28
|
||||
--> $DIR/issue-57017.rs:30:28
|
||||
|
|
||||
LL | let g = move || match drop(&$name::unsync::Client::default()) {
|
||||
| --------------------------------- has type `©::unsync::Client` which is not `Send`
|
||||
@ -33,14 +33,14 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
note: required by a bound in `assert_send`
|
||||
--> $DIR/issue-57017.rs:51:19
|
||||
--> $DIR/issue-57017.rs:52:19
|
||||
|
|
||||
LL | fn assert_send<T: Send>(_thing: T) {}
|
||||
| ^^^^ required by this bound in `assert_send`
|
||||
= note: this error originates in the macro `type_combinations` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: generator cannot be sent between threads safely
|
||||
--> $DIR/issue-57017.rs:43:25
|
||||
--> $DIR/issue-57017.rs:44:25
|
||||
|
|
||||
LL | assert_send(g);
|
||||
| ^ generator is not `Send`
|
||||
@ -54,9 +54,9 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
|
|
||||
= help: within `[generator@$DIR/issue-57017.rs:40:21: 40:28]`, the trait `Send` is not implemented for `copy::unsend::Client`
|
||||
= help: within `[generator@$DIR/issue-57017.rs:41:21: 41:28]`, the trait `Send` is not implemented for `copy::unsend::Client`
|
||||
note: generator is not `Send` as this value is used across a yield
|
||||
--> $DIR/issue-57017.rs:41:28
|
||||
--> $DIR/issue-57017.rs:42:28
|
||||
|
|
||||
LL | let g = move || match drop($name::unsend::Client::default()) {
|
||||
| -------------------------------- has type `copy::unsend::Client` which is not `Send`
|
||||
@ -74,14 +74,14 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
note: required by a bound in `assert_send`
|
||||
--> $DIR/issue-57017.rs:51:19
|
||||
--> $DIR/issue-57017.rs:52:19
|
||||
|
|
||||
LL | fn assert_send<T: Send>(_thing: T) {}
|
||||
| ^^^^ required by this bound in `assert_send`
|
||||
= note: this error originates in the macro `type_combinations` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: generator cannot be sent between threads safely
|
||||
--> $DIR/issue-57017.rs:31:25
|
||||
--> $DIR/issue-57017.rs:32:25
|
||||
|
|
||||
LL | assert_send(g);
|
||||
| ^ generator is not `Send`
|
||||
@ -97,7 +97,7 @@ LL | | );
|
||||
|
|
||||
= help: the trait `Sync` is not implemented for `derived_drop::unsync::Client`
|
||||
note: generator is not `Send` as this value is used across a yield
|
||||
--> $DIR/issue-57017.rs:29:28
|
||||
--> $DIR/issue-57017.rs:30:28
|
||||
|
|
||||
LL | let g = move || match drop(&$name::unsync::Client::default()) {
|
||||
| --------------------------------- has type `&derived_drop::unsync::Client` which is not `Send`
|
||||
@ -115,14 +115,14 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
note: required by a bound in `assert_send`
|
||||
--> $DIR/issue-57017.rs:51:19
|
||||
--> $DIR/issue-57017.rs:52:19
|
||||
|
|
||||
LL | fn assert_send<T: Send>(_thing: T) {}
|
||||
| ^^^^ required by this bound in `assert_send`
|
||||
= note: this error originates in the macro `type_combinations` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: generator cannot be sent between threads safely
|
||||
--> $DIR/issue-57017.rs:43:25
|
||||
--> $DIR/issue-57017.rs:44:25
|
||||
|
|
||||
LL | assert_send(g);
|
||||
| ^ generator is not `Send`
|
||||
@ -136,9 +136,9 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
|
|
||||
= help: within `[generator@$DIR/issue-57017.rs:40:21: 40:28]`, the trait `Send` is not implemented for `derived_drop::unsend::Client`
|
||||
= help: within `[generator@$DIR/issue-57017.rs:41:21: 41:28]`, the trait `Send` is not implemented for `derived_drop::unsend::Client`
|
||||
note: generator is not `Send` as this value is used across a yield
|
||||
--> $DIR/issue-57017.rs:41:28
|
||||
--> $DIR/issue-57017.rs:42:28
|
||||
|
|
||||
LL | let g = move || match drop($name::unsend::Client::default()) {
|
||||
| -------------------------------- has type `derived_drop::unsend::Client` which is not `Send`
|
||||
@ -156,14 +156,14 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
note: required by a bound in `assert_send`
|
||||
--> $DIR/issue-57017.rs:51:19
|
||||
--> $DIR/issue-57017.rs:52:19
|
||||
|
|
||||
LL | fn assert_send<T: Send>(_thing: T) {}
|
||||
| ^^^^ required by this bound in `assert_send`
|
||||
= note: this error originates in the macro `type_combinations` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: generator cannot be sent between threads safely
|
||||
--> $DIR/issue-57017.rs:31:25
|
||||
--> $DIR/issue-57017.rs:32:25
|
||||
|
|
||||
LL | assert_send(g);
|
||||
| ^ generator is not `Send`
|
||||
@ -179,7 +179,7 @@ LL | | );
|
||||
|
|
||||
= help: the trait `Sync` is not implemented for `significant_drop::unsync::Client`
|
||||
note: generator is not `Send` as this value is used across a yield
|
||||
--> $DIR/issue-57017.rs:29:28
|
||||
--> $DIR/issue-57017.rs:30:28
|
||||
|
|
||||
LL | let g = move || match drop(&$name::unsync::Client::default()) {
|
||||
| --------------------------------- has type `&significant_drop::unsync::Client` which is not `Send`
|
||||
@ -197,14 +197,14 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
note: required by a bound in `assert_send`
|
||||
--> $DIR/issue-57017.rs:51:19
|
||||
--> $DIR/issue-57017.rs:52:19
|
||||
|
|
||||
LL | fn assert_send<T: Send>(_thing: T) {}
|
||||
| ^^^^ required by this bound in `assert_send`
|
||||
= note: this error originates in the macro `type_combinations` (in Nightly builds, run with -Z macro-backtrace for more info)
|
||||
|
||||
error: generator cannot be sent between threads safely
|
||||
--> $DIR/issue-57017.rs:43:25
|
||||
--> $DIR/issue-57017.rs:44:25
|
||||
|
|
||||
LL | assert_send(g);
|
||||
| ^ generator is not `Send`
|
||||
@ -218,9 +218,9 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
|
|
||||
= help: within `[generator@$DIR/issue-57017.rs:40:21: 40:28]`, the trait `Send` is not implemented for `significant_drop::unsend::Client`
|
||||
= help: within `[generator@$DIR/issue-57017.rs:41:21: 41:28]`, the trait `Send` is not implemented for `significant_drop::unsend::Client`
|
||||
note: generator is not `Send` as this value is used across a yield
|
||||
--> $DIR/issue-57017.rs:41:28
|
||||
--> $DIR/issue-57017.rs:42:28
|
||||
|
|
||||
LL | let g = move || match drop($name::unsend::Client::default()) {
|
||||
| -------------------------------- has type `significant_drop::unsend::Client` which is not `Send`
|
||||
@ -238,7 +238,7 @@ LL | | }
|
||||
LL | | );
|
||||
| |_____- in this macro invocation
|
||||
note: required by a bound in `assert_send`
|
||||
--> $DIR/issue-57017.rs:51:19
|
||||
--> $DIR/issue-57017.rs:52:19
|
||||
|
|
||||
LL | fn assert_send<T: Send>(_thing: T) {}
|
||||
| ^^^^ required by this bound in `assert_send`
|
||||
|
@ -5,6 +5,7 @@
|
||||
// [drop_tracking_mir] build-pass
|
||||
|
||||
#![feature(generators, negative_impls)]
|
||||
#![allow(drop_ref, drop_copy)]
|
||||
|
||||
macro_rules! type_combinations {
|
||||
(
|
||||
|
@ -3,6 +3,7 @@
|
||||
// run-pass
|
||||
|
||||
#![feature(generators, generator_trait)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
use std::marker::{PhantomPinned, Unpin};
|
||||
|
||||
|
@ -1,4 +1,5 @@
|
||||
#![feature(generators)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
// run-pass
|
||||
|
||||
|
@ -1,6 +1,7 @@
|
||||
// check-pass
|
||||
|
||||
#![feature(decl_macro)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
macro mac() {
|
||||
mod m {
|
||||
|
@ -1,4 +1,7 @@
|
||||
// run-rustfix
|
||||
|
||||
#![allow(drop_ref)]
|
||||
|
||||
struct Foo;
|
||||
|
||||
impl Drop for Foo {
|
||||
|
@ -1,4 +1,7 @@
|
||||
// run-rustfix
|
||||
|
||||
#![allow(drop_ref)]
|
||||
|
||||
struct Foo;
|
||||
|
||||
impl Drop for Foo {
|
||||
|
@ -1,5 +1,5 @@
|
||||
error[E0040]: explicit use of destructor method
|
||||
--> $DIR/illegal-ufcs-drop.rs:9:5
|
||||
--> $DIR/illegal-ufcs-drop.rs:12:5
|
||||
|
|
||||
LL | Drop::drop(&mut Foo)
|
||||
| ^^^^^^^^^^
|
||||
|
79
tests/ui/lint/drop_copy.rs
Normal file
79
tests/ui/lint/drop_copy.rs
Normal file
@ -0,0 +1,79 @@
|
||||
// check-pass
|
||||
|
||||
#![warn(drop_copy)]
|
||||
|
||||
use std::mem::drop;
|
||||
use std::vec::Vec;
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
struct SomeStruct;
|
||||
|
||||
struct AnotherStruct {
|
||||
x: u8,
|
||||
y: u8,
|
||||
z: Vec<u8>,
|
||||
}
|
||||
|
||||
impl Clone for AnotherStruct {
|
||||
fn clone(&self) -> AnotherStruct {
|
||||
AnotherStruct {
|
||||
x: self.x,
|
||||
y: self.y,
|
||||
z: self.z.clone(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let s1 = SomeStruct {};
|
||||
let s2 = s1;
|
||||
let s3 = &s1;
|
||||
let mut s4 = s1;
|
||||
let ref s5 = s1;
|
||||
|
||||
drop(s1); //~ WARN calls to `std::mem::drop`
|
||||
drop(s2); //~ WARN calls to `std::mem::drop`
|
||||
drop(s3); //~ WARN calls to `std::mem::drop`
|
||||
drop(s4); //~ WARN calls to `std::mem::drop`
|
||||
drop(s5); //~ WARN calls to `std::mem::drop`
|
||||
|
||||
let a1 = AnotherStruct {
|
||||
x: 255,
|
||||
y: 0,
|
||||
z: vec![1, 2, 3],
|
||||
};
|
||||
let a2 = &a1;
|
||||
let mut a3 = a1.clone();
|
||||
let ref a4 = a1;
|
||||
let a5 = a1.clone();
|
||||
|
||||
drop(a2); //~ WARN calls to `std::mem::drop`
|
||||
drop(a3);
|
||||
drop(a4); //~ WARN calls to `std::mem::drop`
|
||||
drop(a5);
|
||||
}
|
||||
|
||||
#[allow(unused)]
|
||||
#[allow(clippy::unit_cmp)]
|
||||
fn issue9482(x: u8) {
|
||||
fn println_and<T>(t: T) -> T {
|
||||
println!("foo");
|
||||
t
|
||||
}
|
||||
|
||||
match x {
|
||||
// Don't lint (copy type), we only care about side-effects
|
||||
0 => drop(println_and(12)),
|
||||
// Don't lint (no copy type), we only care about side-effects
|
||||
1 => drop(println_and(String::new())),
|
||||
2 => {
|
||||
// Lint, even if we only care about the side-effect, it's already in a block
|
||||
drop(println_and(13)); //~ WARN calls to `std::mem::drop`
|
||||
},
|
||||
// Lint, idiomatic use is only in body of `Arm`
|
||||
3 if drop(println_and(14)) == () => (), //~ WARN calls to `std::mem::drop`
|
||||
// Lint, not a fn/method call
|
||||
4 => drop(2),//~ WARN calls to `std::mem::drop`
|
||||
_ => (),
|
||||
}
|
||||
}
|
108
tests/ui/lint/drop_copy.stderr
Normal file
108
tests/ui/lint/drop_copy.stderr
Normal file
@ -0,0 +1,108 @@
|
||||
warning: calls to `std::mem::drop` with a value that implements `Copy` does nothing
|
||||
--> $DIR/drop_copy.rs:34:5
|
||||
|
|
||||
LL | drop(s1);
|
||||
| ^^^^^--^
|
||||
| |
|
||||
| argument has type `SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
note: the lint level is defined here
|
||||
--> $DIR/drop_copy.rs:3:9
|
||||
|
|
||||
LL | #![warn(drop_copy)]
|
||||
| ^^^^^^^^^
|
||||
|
||||
warning: calls to `std::mem::drop` with a value that implements `Copy` does nothing
|
||||
--> $DIR/drop_copy.rs:35:5
|
||||
|
|
||||
LL | drop(s2);
|
||||
| ^^^^^--^
|
||||
| |
|
||||
| argument has type `SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_copy.rs:36:5
|
||||
|
|
||||
LL | drop(s3);
|
||||
| ^^^^^--^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
= note: `#[warn(drop_ref)]` on by default
|
||||
|
||||
warning: calls to `std::mem::drop` with a value that implements `Copy` does nothing
|
||||
--> $DIR/drop_copy.rs:37:5
|
||||
|
|
||||
LL | drop(s4);
|
||||
| ^^^^^--^
|
||||
| |
|
||||
| argument has type `SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_copy.rs:38:5
|
||||
|
|
||||
LL | drop(s5);
|
||||
| ^^^^^--^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_copy.rs:50:5
|
||||
|
|
||||
LL | drop(a2);
|
||||
| ^^^^^--^
|
||||
| |
|
||||
| argument has type `&AnotherStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_copy.rs:52:5
|
||||
|
|
||||
LL | drop(a4);
|
||||
| ^^^^^--^
|
||||
| |
|
||||
| argument has type `&AnotherStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a value that implements `Copy` does nothing
|
||||
--> $DIR/drop_copy.rs:71:13
|
||||
|
|
||||
LL | drop(println_and(13));
|
||||
| ^^^^^---------------^
|
||||
| |
|
||||
| argument has type `i32`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a value that implements `Copy` does nothing
|
||||
--> $DIR/drop_copy.rs:74:14
|
||||
|
|
||||
LL | 3 if drop(println_and(14)) == () => (),
|
||||
| ^^^^^---------------^
|
||||
| |
|
||||
| argument has type `i32`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a value that implements `Copy` does nothing
|
||||
--> $DIR/drop_copy.rs:76:14
|
||||
|
|
||||
LL | 4 => drop(2),
|
||||
| ^^^^^-^
|
||||
| |
|
||||
| argument has type `i32`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: 10 warnings emitted
|
||||
|
@ -1,42 +1,39 @@
|
||||
#![warn(clippy::drop_ref)]
|
||||
#![allow(clippy::toplevel_ref_arg)]
|
||||
#![allow(clippy::map_err_ignore)]
|
||||
#![allow(clippy::unnecessary_wraps, clippy::drop_non_drop)]
|
||||
// check-pass
|
||||
|
||||
use std::mem::drop;
|
||||
#![warn(drop_ref)]
|
||||
|
||||
struct SomeStruct;
|
||||
|
||||
fn main() {
|
||||
drop(&SomeStruct);
|
||||
drop(&SomeStruct); //~ WARN calls to `std::mem::drop`
|
||||
|
||||
let mut owned1 = SomeStruct;
|
||||
drop(&owned1);
|
||||
drop(&&owned1);
|
||||
drop(&mut owned1);
|
||||
drop(owned1); //OK
|
||||
drop(&owned1); //~ WARN calls to `std::mem::drop`
|
||||
drop(&&owned1); //~ WARN calls to `std::mem::drop`
|
||||
drop(&mut owned1); //~ WARN calls to `std::mem::drop`
|
||||
drop(owned1);
|
||||
|
||||
let reference1 = &SomeStruct;
|
||||
drop(reference1);
|
||||
drop(reference1); //~ WARN calls to `std::mem::drop`
|
||||
|
||||
let reference2 = &mut SomeStruct;
|
||||
drop(reference2);
|
||||
drop(reference2); //~ WARN calls to `std::mem::drop`
|
||||
|
||||
let ref reference3 = SomeStruct;
|
||||
drop(reference3);
|
||||
drop(reference3); //~ WARN calls to `std::mem::drop`
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
fn test_generic_fn_drop<T>(val: T) {
|
||||
drop(&val);
|
||||
drop(val); //OK
|
||||
drop(&val); //~ WARN calls to `std::mem::drop`
|
||||
drop(val);
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
fn test_similarly_named_function() {
|
||||
fn drop<T>(_val: T) {}
|
||||
drop(&SomeStruct); //OK; call to unrelated function which happens to have the same name
|
||||
std::mem::drop(&SomeStruct);
|
||||
std::mem::drop(&SomeStruct); //~ WARN calls to `std::mem::drop`
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
@ -77,21 +74,26 @@ fn test_owl_result_2() -> Result<u8, ()> {
|
||||
#[allow(clippy::unit_cmp)]
|
||||
fn issue10122(x: u8) {
|
||||
// This is a function which returns a reference and has a side-effect, which means
|
||||
// that calling drop() on the function is considered an idiomatic way of achieving the side-effect
|
||||
// in a match arm.
|
||||
// that calling drop() on the function is considered an idiomatic way of achieving
|
||||
// the side-effect in a match arm.
|
||||
fn println_and<T>(t: &T) -> &T {
|
||||
println!("foo");
|
||||
t
|
||||
}
|
||||
|
||||
match x {
|
||||
0 => drop(println_and(&12)), // Don't lint (copy type), we only care about side-effects
|
||||
1 => drop(println_and(&String::new())), // Don't lint (no copy type), we only care about side-effects
|
||||
// Don't lint (copy type), we only care about side-effects
|
||||
0 => drop(println_and(&12)),
|
||||
// Don't lint (no copy type), we only care about side-effects
|
||||
1 => drop(println_and(&String::new())),
|
||||
2 => {
|
||||
drop(println_and(&13)); // Lint, even if we only care about the side-effect, it's already in a block
|
||||
// Lint, even if we only care about the side-effect, it's already in a block
|
||||
drop(println_and(&13)); //~ WARN calls to `std::mem::drop`
|
||||
},
|
||||
3 if drop(println_and(&14)) == () => (), // Lint, idiomatic use is only in body of `Arm`
|
||||
4 => drop(&2), // Lint, not a fn/method call
|
||||
// Lint, idiomatic use is only in body of `Arm`
|
||||
3 if drop(println_and(&14)) == () => (), //~ WARN calls to `std::mem::drop`
|
||||
// Lint, not a fn/method call
|
||||
4 => drop(&2), //~ WARN calls to `std::mem::drop`
|
||||
_ => (),
|
||||
}
|
||||
}
|
127
tests/ui/lint/drop_ref.stderr
Normal file
127
tests/ui/lint/drop_ref.stderr
Normal file
@ -0,0 +1,127 @@
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:8:5
|
||||
|
|
||||
LL | drop(&SomeStruct);
|
||||
| ^^^^^-----------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
note: the lint level is defined here
|
||||
--> $DIR/drop_ref.rs:3:9
|
||||
|
|
||||
LL | #![warn(drop_ref)]
|
||||
| ^^^^^^^^
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:11:5
|
||||
|
|
||||
LL | drop(&owned1);
|
||||
| ^^^^^-------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:12:5
|
||||
|
|
||||
LL | drop(&&owned1);
|
||||
| ^^^^^--------^
|
||||
| |
|
||||
| argument has type `&&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:13:5
|
||||
|
|
||||
LL | drop(&mut owned1);
|
||||
| ^^^^^-----------^
|
||||
| |
|
||||
| argument has type `&mut SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:17:5
|
||||
|
|
||||
LL | drop(reference1);
|
||||
| ^^^^^----------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:20:5
|
||||
|
|
||||
LL | drop(reference2);
|
||||
| ^^^^^----------^
|
||||
| |
|
||||
| argument has type `&mut SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:23:5
|
||||
|
|
||||
LL | drop(reference3);
|
||||
| ^^^^^----------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:28:5
|
||||
|
|
||||
LL | drop(&val);
|
||||
| ^^^^^----^
|
||||
| |
|
||||
| argument has type `&T`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:36:5
|
||||
|
|
||||
LL | std::mem::drop(&SomeStruct);
|
||||
| ^^^^^^^^^^^^^^^-----------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:91:13
|
||||
|
|
||||
LL | drop(println_and(&13));
|
||||
| ^^^^^----------------^
|
||||
| |
|
||||
| argument has type `&i32`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:94:14
|
||||
|
|
||||
LL | 3 if drop(println_and(&14)) == () => (),
|
||||
| ^^^^^----------------^
|
||||
| |
|
||||
| argument has type `&i32`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::drop` with a reference instead of an owned value does nothing
|
||||
--> $DIR/drop_ref.rs:96:14
|
||||
|
|
||||
LL | 4 => drop(&2),
|
||||
| ^^^^^--^
|
||||
| |
|
||||
| argument has type `&i32`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: 12 warnings emitted
|
||||
|
56
tests/ui/lint/forget_copy.rs
Normal file
56
tests/ui/lint/forget_copy.rs
Normal file
@ -0,0 +1,56 @@
|
||||
// check-pass
|
||||
|
||||
#![warn(forget_copy)]
|
||||
|
||||
use std::mem::forget;
|
||||
use std::vec::Vec;
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
struct SomeStruct;
|
||||
|
||||
struct AnotherStruct {
|
||||
x: u8,
|
||||
y: u8,
|
||||
z: Vec<u8>,
|
||||
}
|
||||
|
||||
impl Clone for AnotherStruct {
|
||||
fn clone(&self) -> AnotherStruct {
|
||||
AnotherStruct {
|
||||
x: self.x,
|
||||
y: self.y,
|
||||
z: self.z.clone(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let s1 = SomeStruct {};
|
||||
let s2 = s1;
|
||||
let s3 = &s1;
|
||||
let mut s4 = s1;
|
||||
let ref s5 = s1;
|
||||
|
||||
forget(s1); //~ WARN calls to `std::mem::forget`
|
||||
forget(s2); //~ WARN calls to `std::mem::forget`
|
||||
forget(s3); //~ WARN calls to `std::mem::forget`
|
||||
forget(s4); //~ WARN calls to `std::mem::forget`
|
||||
forget(s5); //~ WARN calls to `std::mem::forget`
|
||||
|
||||
let a1 = AnotherStruct {
|
||||
x: 255,
|
||||
y: 0,
|
||||
z: vec![1, 2, 3],
|
||||
};
|
||||
let a2 = &a1;
|
||||
let mut a3 = a1.clone();
|
||||
let ref a4 = a1;
|
||||
let a5 = a1.clone();
|
||||
|
||||
forget(a2); //~ WARN calls to `std::mem::forget`
|
||||
let a3 = &a1;
|
||||
forget(a3); //~ WARN calls to `std::mem::forget`
|
||||
forget(a4); //~ WARN calls to `std::mem::forget`
|
||||
let a5 = a1.clone();
|
||||
forget(a5);
|
||||
}
|
88
tests/ui/lint/forget_copy.stderr
Normal file
88
tests/ui/lint/forget_copy.stderr
Normal file
@ -0,0 +1,88 @@
|
||||
warning: calls to `std::mem::forget` with a value that implements `Copy` does nothing
|
||||
--> $DIR/forget_copy.rs:34:5
|
||||
|
|
||||
LL | forget(s1);
|
||||
| ^^^^^^^--^
|
||||
| |
|
||||
| argument has type `SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
note: the lint level is defined here
|
||||
--> $DIR/forget_copy.rs:3:9
|
||||
|
|
||||
LL | #![warn(forget_copy)]
|
||||
| ^^^^^^^^^^^
|
||||
|
||||
warning: calls to `std::mem::forget` with a value that implements `Copy` does nothing
|
||||
--> $DIR/forget_copy.rs:35:5
|
||||
|
|
||||
LL | forget(s2);
|
||||
| ^^^^^^^--^
|
||||
| |
|
||||
| argument has type `SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_copy.rs:36:5
|
||||
|
|
||||
LL | forget(s3);
|
||||
| ^^^^^^^--^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
= note: `#[warn(forget_ref)]` on by default
|
||||
|
||||
warning: calls to `std::mem::forget` with a value that implements `Copy` does nothing
|
||||
--> $DIR/forget_copy.rs:37:5
|
||||
|
|
||||
LL | forget(s4);
|
||||
| ^^^^^^^--^
|
||||
| |
|
||||
| argument has type `SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_copy.rs:38:5
|
||||
|
|
||||
LL | forget(s5);
|
||||
| ^^^^^^^--^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_copy.rs:50:5
|
||||
|
|
||||
LL | forget(a2);
|
||||
| ^^^^^^^--^
|
||||
| |
|
||||
| argument has type `&AnotherStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_copy.rs:52:5
|
||||
|
|
||||
LL | forget(a3);
|
||||
| ^^^^^^^--^
|
||||
| |
|
||||
| argument has type `&AnotherStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_copy.rs:53:5
|
||||
|
|
||||
LL | forget(a4);
|
||||
| ^^^^^^^--^
|
||||
| |
|
||||
| argument has type `&AnotherStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: 8 warnings emitted
|
||||
|
39
tests/ui/lint/forget_ref.rs
Normal file
39
tests/ui/lint/forget_ref.rs
Normal file
@ -0,0 +1,39 @@
|
||||
// check-pass
|
||||
|
||||
#![warn(forget_ref)]
|
||||
|
||||
use std::mem::forget;
|
||||
|
||||
struct SomeStruct;
|
||||
|
||||
fn main() {
|
||||
forget(&SomeStruct); //~ WARN calls to `std::mem::forget`
|
||||
|
||||
let mut owned = SomeStruct;
|
||||
forget(&owned); //~ WARN calls to `std::mem::forget`
|
||||
forget(&&owned); //~ WARN calls to `std::mem::forget`
|
||||
forget(&mut owned); //~ WARN calls to `std::mem::forget`
|
||||
forget(owned);
|
||||
|
||||
let reference1 = &SomeStruct;
|
||||
forget(&*reference1); //~ WARN calls to `std::mem::forget`
|
||||
|
||||
let reference2 = &mut SomeStruct;
|
||||
forget(reference2); //~ WARN calls to `std::mem::forget`
|
||||
|
||||
let ref reference3 = SomeStruct;
|
||||
forget(reference3); //~ WARN calls to `std::mem::forget`
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
fn test_generic_fn_forget<T>(val: T) {
|
||||
forget(&val); //~ WARN calls to `std::mem::forget`
|
||||
forget(val);
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
fn test_similarly_named_function() {
|
||||
fn forget<T>(_val: T) {}
|
||||
forget(&SomeStruct); //OK; call to unrelated function which happens to have the same name
|
||||
std::mem::forget(&SomeStruct); //~ WARN calls to `std::mem::forget`
|
||||
}
|
97
tests/ui/lint/forget_ref.stderr
Normal file
97
tests/ui/lint/forget_ref.stderr
Normal file
@ -0,0 +1,97 @@
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:10:5
|
||||
|
|
||||
LL | forget(&SomeStruct);
|
||||
| ^^^^^^^-----------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
note: the lint level is defined here
|
||||
--> $DIR/forget_ref.rs:3:9
|
||||
|
|
||||
LL | #![warn(forget_ref)]
|
||||
| ^^^^^^^^^^
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:13:5
|
||||
|
|
||||
LL | forget(&owned);
|
||||
| ^^^^^^^------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:14:5
|
||||
|
|
||||
LL | forget(&&owned);
|
||||
| ^^^^^^^-------^
|
||||
| |
|
||||
| argument has type `&&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:15:5
|
||||
|
|
||||
LL | forget(&mut owned);
|
||||
| ^^^^^^^----------^
|
||||
| |
|
||||
| argument has type `&mut SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:19:5
|
||||
|
|
||||
LL | forget(&*reference1);
|
||||
| ^^^^^^^------------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:22:5
|
||||
|
|
||||
LL | forget(reference2);
|
||||
| ^^^^^^^----------^
|
||||
| |
|
||||
| argument has type `&mut SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:25:5
|
||||
|
|
||||
LL | forget(reference3);
|
||||
| ^^^^^^^----------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:30:5
|
||||
|
|
||||
LL | forget(&val);
|
||||
| ^^^^^^^----^
|
||||
| |
|
||||
| argument has type `&T`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: calls to `std::mem::forget` with a reference instead of an owned value does nothing
|
||||
--> $DIR/forget_ref.rs:38:5
|
||||
|
|
||||
LL | std::mem::forget(&SomeStruct);
|
||||
| ^^^^^^^^^^^^^^^^^-----------^
|
||||
| |
|
||||
| argument has type `&SomeStruct`
|
||||
|
|
||||
= note: use `let _ = ...` to ignore the expression or result
|
||||
|
||||
warning: 9 warnings emitted
|
||||
|
@ -1,7 +1,7 @@
|
||||
#![warn(unused)]
|
||||
#![deny(unused_variables)]
|
||||
#![deny(unused_assignments)]
|
||||
#![allow(dead_code, non_camel_case_types, trivial_numeric_casts)]
|
||||
#![allow(dead_code, non_camel_case_types, trivial_numeric_casts, drop_copy)]
|
||||
|
||||
use std::ops::AddAssign;
|
||||
|
||||
|
@ -4,6 +4,7 @@
|
||||
#![allow(unused_assignments)]
|
||||
#![allow(unused_variables)]
|
||||
#![allow(stable_features)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
// Test parsing binary operators after macro invocations.
|
||||
|
||||
|
@ -3,6 +3,7 @@
|
||||
// check-pass
|
||||
|
||||
#![feature(never_type)]
|
||||
#![allow(drop_copy)]
|
||||
#![warn(unused)]
|
||||
|
||||
fn main() {
|
||||
|
@ -1,5 +1,5 @@
|
||||
warning: unreachable statement
|
||||
--> $DIR/never-assign-dead-code.rs:10:5
|
||||
--> $DIR/never-assign-dead-code.rs:11:5
|
||||
|
|
||||
LL | let x: ! = panic!("aah");
|
||||
| ------------- any code following this expression is unreachable
|
||||
@ -7,14 +7,14 @@ LL | drop(x);
|
||||
| ^^^^^^^^ unreachable statement
|
||||
|
|
||||
note: the lint level is defined here
|
||||
--> $DIR/never-assign-dead-code.rs:6:9
|
||||
--> $DIR/never-assign-dead-code.rs:7:9
|
||||
|
|
||||
LL | #![warn(unused)]
|
||||
| ^^^^^^
|
||||
= note: `#[warn(unreachable_code)]` implied by `#[warn(unused)]`
|
||||
|
||||
warning: unreachable call
|
||||
--> $DIR/never-assign-dead-code.rs:10:5
|
||||
--> $DIR/never-assign-dead-code.rs:11:5
|
||||
|
|
||||
LL | drop(x);
|
||||
| ^^^^ - any code following this expression is unreachable
|
||||
@ -22,7 +22,7 @@ LL | drop(x);
|
||||
| unreachable call
|
||||
|
||||
warning: unused variable: `x`
|
||||
--> $DIR/never-assign-dead-code.rs:9:9
|
||||
--> $DIR/never-assign-dead-code.rs:10:9
|
||||
|
|
||||
LL | let x: ! = panic!("aah");
|
||||
| ^ help: if this is intentional, prefix it with an underscore: `_x`
|
||||
|
@ -5,6 +5,8 @@
|
||||
// check-pass
|
||||
// compile-flags:-Zno-leak-check
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
fn make_it() -> for<'a, 'b> fn(&'a u32, &'b u32) -> &'a u32 {
|
||||
panic!()
|
||||
}
|
||||
|
@ -3,6 +3,8 @@
|
||||
//
|
||||
// check-pass
|
||||
|
||||
#![allow(drop_ref)]
|
||||
|
||||
trait MyTrait<'a> {
|
||||
type Output;
|
||||
}
|
||||
|
@ -3,6 +3,8 @@
|
||||
// check-pass
|
||||
|
||||
#![allow(irrefutable_let_patterns)]
|
||||
#![allow(drop_copy)]
|
||||
#![allow(drop_ref)]
|
||||
|
||||
fn main() {
|
||||
// A regression test for a mistake we made at one point:
|
||||
|
@ -2,6 +2,9 @@
|
||||
|
||||
// Test `@` patterns combined with `box` patterns.
|
||||
|
||||
#![allow(drop_ref)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
#![feature(box_patterns)]
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
|
@ -2,6 +2,8 @@
|
||||
|
||||
// Test `Copy` bindings in the rhs of `@` patterns.
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
struct C;
|
||||
|
||||
|
@ -1,5 +1,7 @@
|
||||
// check-pass
|
||||
|
||||
#![allow(drop_ref)]
|
||||
|
||||
fn main() {}
|
||||
|
||||
struct U;
|
||||
|
@ -1,5 +1,7 @@
|
||||
// check-pass
|
||||
|
||||
#![allow(drop_ref)]
|
||||
|
||||
fn main() {
|
||||
struct U;
|
||||
fn accept_fn_once(_: impl FnOnce()) {}
|
||||
|
@ -3,6 +3,8 @@
|
||||
// build-pass
|
||||
// ignore-pass
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
async fn wait() {}
|
||||
|
||||
pub async fn test(arg: [u8; 8192]) {
|
||||
|
@ -1,4 +1,4 @@
|
||||
print-type-size type: `[async fn body@$DIR/async.rs:8:36: 11:2]`: 16386 bytes, alignment: 1 bytes
|
||||
print-type-size type: `[async fn body@$DIR/async.rs:10:36: 13:2]`: 16386 bytes, alignment: 1 bytes
|
||||
print-type-size discriminant: 1 bytes
|
||||
print-type-size variant `Unresumed`: 8192 bytes
|
||||
print-type-size upvar `.arg`: 8192 bytes
|
||||
@ -16,14 +16,14 @@ print-type-size type: `std::mem::MaybeUninit<[u8; 8192]>`: 8192 bytes, alignment
|
||||
print-type-size variant `MaybeUninit`: 8192 bytes
|
||||
print-type-size field `.uninit`: 0 bytes
|
||||
print-type-size field `.value`: 8192 bytes
|
||||
print-type-size type: `[async fn body@$DIR/async.rs:6:17: 6:19]`: 1 bytes, alignment: 1 bytes
|
||||
print-type-size type: `[async fn body@$DIR/async.rs:8:17: 8:19]`: 1 bytes, alignment: 1 bytes
|
||||
print-type-size discriminant: 1 bytes
|
||||
print-type-size variant `Unresumed`: 0 bytes
|
||||
print-type-size variant `Returned`: 0 bytes
|
||||
print-type-size variant `Panicked`: 0 bytes
|
||||
print-type-size type: `std::mem::ManuallyDrop<[async fn body@$DIR/async.rs:6:17: 6:19]>`: 1 bytes, alignment: 1 bytes
|
||||
print-type-size type: `std::mem::ManuallyDrop<[async fn body@$DIR/async.rs:8:17: 8:19]>`: 1 bytes, alignment: 1 bytes
|
||||
print-type-size field `.value`: 1 bytes
|
||||
print-type-size type: `std::mem::MaybeUninit<[async fn body@$DIR/async.rs:6:17: 6:19]>`: 1 bytes, alignment: 1 bytes
|
||||
print-type-size type: `std::mem::MaybeUninit<[async fn body@$DIR/async.rs:8:17: 8:19]>`: 1 bytes, alignment: 1 bytes
|
||||
print-type-size variant `MaybeUninit`: 1 bytes
|
||||
print-type-size field `.uninit`: 0 bytes
|
||||
print-type-size field `.value`: 1 bytes
|
||||
|
@ -6,6 +6,7 @@
|
||||
|
||||
// Avoid emitting panic handlers, like the rest of these tests...
|
||||
#![feature(generators)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
pub fn foo() {
|
||||
let a = || {
|
||||
|
@ -1,4 +1,4 @@
|
||||
print-type-size type: `[generator@$DIR/generator_discr_placement.rs:11:13: 11:15]`: 8 bytes, alignment: 4 bytes
|
||||
print-type-size type: `[generator@$DIR/generator_discr_placement.rs:12:13: 12:15]`: 8 bytes, alignment: 4 bytes
|
||||
print-type-size discriminant: 1 bytes
|
||||
print-type-size variant `Unresumed`: 0 bytes
|
||||
print-type-size variant `Suspend0`: 7 bytes
|
||||
|
@ -55,11 +55,11 @@ where
|
||||
}
|
||||
|
||||
pub fn x<T: Copy>(a: Array<T>) {
|
||||
// drop just avoids a must_use warning
|
||||
drop((0..1).filter(|_| true));
|
||||
// _ just avoids a must_use warning
|
||||
let _ = (0..1).filter(|_| true);
|
||||
let y = a.index_axis();
|
||||
a.axis_iter().for_each(|_| {
|
||||
drop(y);
|
||||
let _ = y;
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -3,6 +3,8 @@
|
||||
|
||||
// check-pass
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
use std::marker::PhantomData;
|
||||
|
||||
fn apply<T, F: FnOnce(T)>(_: T, _: F) {}
|
||||
|
@ -3,6 +3,8 @@
|
||||
|
||||
// check-pass
|
||||
|
||||
#![allow(drop_ref)]
|
||||
|
||||
// aux-build:monovariants.rs
|
||||
extern crate monovariants;
|
||||
|
||||
|
@ -4,6 +4,8 @@
|
||||
// Tests ensuring that `dbg!(expr)` has the expected run-time behavior.
|
||||
// as well as some compile time properties we expect.
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
struct Unit;
|
||||
|
||||
|
@ -1,28 +1,28 @@
|
||||
[$DIR/dbg-macro-expected-behavior.rs:20] Unit = Unit
|
||||
[$DIR/dbg-macro-expected-behavior.rs:21] a = Unit
|
||||
[$DIR/dbg-macro-expected-behavior.rs:27] Point { x: 42, y: 24 } = Point {
|
||||
[$DIR/dbg-macro-expected-behavior.rs:22] Unit = Unit
|
||||
[$DIR/dbg-macro-expected-behavior.rs:23] a = Unit
|
||||
[$DIR/dbg-macro-expected-behavior.rs:29] Point { x: 42, y: 24 } = Point {
|
||||
x: 42,
|
||||
y: 24,
|
||||
}
|
||||
[$DIR/dbg-macro-expected-behavior.rs:28] b = Point {
|
||||
[$DIR/dbg-macro-expected-behavior.rs:30] b = Point {
|
||||
x: 42,
|
||||
y: 24,
|
||||
}
|
||||
[$DIR/dbg-macro-expected-behavior.rs:36]
|
||||
[$DIR/dbg-macro-expected-behavior.rs:40] &a = NoCopy(
|
||||
[$DIR/dbg-macro-expected-behavior.rs:38]
|
||||
[$DIR/dbg-macro-expected-behavior.rs:42] &a = NoCopy(
|
||||
1337,
|
||||
)
|
||||
[$DIR/dbg-macro-expected-behavior.rs:40] dbg!(& a) = NoCopy(
|
||||
[$DIR/dbg-macro-expected-behavior.rs:42] dbg!(& a) = NoCopy(
|
||||
1337,
|
||||
)
|
||||
[$DIR/dbg-macro-expected-behavior.rs:45] f(&42) = 42
|
||||
[$DIR/dbg-macro-expected-behavior.rs:47] f(&42) = 42
|
||||
before
|
||||
[$DIR/dbg-macro-expected-behavior.rs:50] { foo += 1; eprintln!("before"); 7331 } = 7331
|
||||
[$DIR/dbg-macro-expected-behavior.rs:58] ("Yeah",) = (
|
||||
[$DIR/dbg-macro-expected-behavior.rs:52] { foo += 1; eprintln!("before"); 7331 } = 7331
|
||||
[$DIR/dbg-macro-expected-behavior.rs:60] ("Yeah",) = (
|
||||
"Yeah",
|
||||
)
|
||||
[$DIR/dbg-macro-expected-behavior.rs:61] 1 = 1
|
||||
[$DIR/dbg-macro-expected-behavior.rs:61] 2 = 2
|
||||
[$DIR/dbg-macro-expected-behavior.rs:65] 1u8 = 1
|
||||
[$DIR/dbg-macro-expected-behavior.rs:65] 2u32 = 2
|
||||
[$DIR/dbg-macro-expected-behavior.rs:65] "Yeah" = "Yeah"
|
||||
[$DIR/dbg-macro-expected-behavior.rs:63] 1 = 1
|
||||
[$DIR/dbg-macro-expected-behavior.rs:63] 2 = 2
|
||||
[$DIR/dbg-macro-expected-behavior.rs:67] 1u8 = 1
|
||||
[$DIR/dbg-macro-expected-behavior.rs:67] 2u32 = 2
|
||||
[$DIR/dbg-macro-expected-behavior.rs:67] "Yeah" = "Yeah"
|
||||
|
@ -5,6 +5,7 @@
|
||||
// compile-flags:--extern remove_extern_crate
|
||||
|
||||
#![warn(rust_2018_idioms)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
//~ WARNING unused extern crate
|
||||
// Shouldn't suggest changing to `use`, as `another_name`
|
||||
|
@ -5,6 +5,7 @@
|
||||
// compile-flags:--extern remove_extern_crate
|
||||
|
||||
#![warn(rust_2018_idioms)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
extern crate core; //~ WARNING unused extern crate
|
||||
// Shouldn't suggest changing to `use`, as `another_name`
|
||||
|
@ -1,5 +1,5 @@
|
||||
warning: unused extern crate
|
||||
--> $DIR/remove-extern-crate.rs:9:1
|
||||
--> $DIR/remove-extern-crate.rs:10:1
|
||||
|
|
||||
LL | extern crate core;
|
||||
| ^^^^^^^^^^^^^^^^^^ help: remove it
|
||||
@ -12,7 +12,7 @@ LL | #![warn(rust_2018_idioms)]
|
||||
= note: `#[warn(unused_extern_crates)]` implied by `#[warn(rust_2018_idioms)]`
|
||||
|
||||
warning: `extern crate` is not idiomatic in the new edition
|
||||
--> $DIR/remove-extern-crate.rs:33:5
|
||||
--> $DIR/remove-extern-crate.rs:34:5
|
||||
|
|
||||
LL | extern crate core;
|
||||
| ^^^^^^^^^^^^^^^^^^
|
||||
@ -23,7 +23,7 @@ LL | use core;
|
||||
| ~~~
|
||||
|
||||
warning: `extern crate` is not idiomatic in the new edition
|
||||
--> $DIR/remove-extern-crate.rs:43:5
|
||||
--> $DIR/remove-extern-crate.rs:44:5
|
||||
|
|
||||
LL | pub extern crate core;
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
@ -12,6 +12,8 @@
|
||||
//
|
||||
// In regular builds, the bad cast was UB, like "Invalid LLVMRustVisibility value!"
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
pub mod before {
|
||||
#[no_mangle]
|
||||
pub static GLOBAL1: [u8; 1] = [1];
|
||||
|
@ -1,5 +1,8 @@
|
||||
// run-pass
|
||||
|
||||
#![allow(dead_code)]
|
||||
#![allow(drop_copy)]
|
||||
|
||||
// "guessing" in trait selection can affect `copy_or_move`. Check that this
|
||||
// is correctly handled. I am not sure what is the "correct" behaviour,
|
||||
// but we should at least not ICE.
|
||||
|
@ -6,6 +6,8 @@
|
||||
|
||||
// check-pass
|
||||
|
||||
#![allow(drop_copy)]
|
||||
|
||||
trait A {
|
||||
type B;
|
||||
}
|
||||
|
@ -1,5 +1,5 @@
|
||||
error[E0277]: `impl Future<Output = ()>` cannot be sent between threads safely
|
||||
--> $DIR/auto-with-drop_tracking_mir.rs:24:13
|
||||
--> $DIR/auto-with-drop_tracking_mir.rs:25:13
|
||||
|
|
||||
LL | is_send(foo());
|
||||
| ------- ^^^^^ `impl Future<Output = ()>` cannot be sent between threads safely
|
||||
@ -8,7 +8,7 @@ LL | is_send(foo());
|
||||
|
|
||||
= help: the trait `Send` is not implemented for `impl Future<Output = ()>`
|
||||
note: required by a bound in `is_send`
|
||||
--> $DIR/auto-with-drop_tracking_mir.rs:23:24
|
||||
--> $DIR/auto-with-drop_tracking_mir.rs:24:24
|
||||
|
|
||||
LL | fn is_send(_: impl Send) {}
|
||||
| ^^^^ required by this bound in `is_send`
|
||||
|
@ -14,6 +14,7 @@ async fn foo() {
|
||||
#[cfg(fail)]
|
||||
let x = &NotSync;
|
||||
bar().await;
|
||||
#[allow(drop_ref)]
|
||||
drop(x);
|
||||
}
|
||||
|
||||
|
@ -18,5 +18,5 @@ fn main() {
|
||||
let w = Wrapper(x);
|
||||
needs_foo(w);
|
||||
x = 1;
|
||||
drop(x);
|
||||
let _ = x;
|
||||
}
|
||||
|
@ -1,6 +1,8 @@
|
||||
// check-pass
|
||||
// Check tautalogically false `Copy` bounds
|
||||
|
||||
#![feature(trivial_bounds)]
|
||||
#![allow(drop_ref, drop_copy)]
|
||||
|
||||
fn copy_string(t: String) -> String where String: Copy { //~ WARNING trivial_bounds
|
||||
is_copy(&t);
|
||||
|
@ -1,5 +1,5 @@
|
||||
warning: trait bound String: Copy does not depend on any type or lifetime parameters
|
||||
--> $DIR/trivial-bounds-inconsistent-copy.rs:5:51
|
||||
--> $DIR/trivial-bounds-inconsistent-copy.rs:7:51
|
||||
|
|
||||
LL | fn copy_string(t: String) -> String where String: Copy {
|
||||
| ^^^^
|
||||
@ -7,19 +7,19 @@ LL | fn copy_string(t: String) -> String where String: Copy {
|
||||
= note: `#[warn(trivial_bounds)]` on by default
|
||||
|
||||
warning: trait bound String: Copy does not depend on any type or lifetime parameters
|
||||
--> $DIR/trivial-bounds-inconsistent-copy.rs:12:56
|
||||
--> $DIR/trivial-bounds-inconsistent-copy.rs:14:56
|
||||
|
|
||||
LL | fn copy_out_string(t: &String) -> String where String: Copy {
|
||||
| ^^^^
|
||||
|
||||
warning: trait bound String: Copy does not depend on any type or lifetime parameters
|
||||
--> $DIR/trivial-bounds-inconsistent-copy.rs:16:55
|
||||
--> $DIR/trivial-bounds-inconsistent-copy.rs:18:55
|
||||
|
|
||||
LL | fn copy_string_with_param<T>(x: String) where String: Copy {
|
||||
| ^^^^
|
||||
|
||||
warning: trait bound for<'b> &'b mut i32: Copy does not depend on any type or lifetime parameters
|
||||
--> $DIR/trivial-bounds-inconsistent-copy.rs:22:76
|
||||
--> $DIR/trivial-bounds-inconsistent-copy.rs:24:76
|
||||
|
|
||||
LL | fn copy_mut<'a>(t: &&'a mut i32) -> &'a mut i32 where for<'b> &'b mut i32: Copy {
|
||||
| ^^^^
|
||||
|
Loading…
x
Reference in New Issue
Block a user