Skip to content

Add MSRV to more lints specified in #6097 #6424

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Dec 11, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 23 additions & 3 deletions clippy_lints/src/checked_conversions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,12 @@ use rustc_errors::Applicability;
use rustc_hir::{BinOp, BinOpKind, Expr, ExprKind, QPath, TyKind};
use rustc_lint::{LateContext, LateLintPass, LintContext};
use rustc_middle::lint::in_external_macro;
use rustc_session::{declare_lint_pass, declare_tool_lint};
use rustc_semver::RustcVersion;
use rustc_session::{declare_tool_lint, impl_lint_pass};

use crate::utils::{snippet_with_applicability, span_lint_and_sugg, SpanlessEq};
use crate::utils::{meets_msrv, snippet_with_applicability, span_lint_and_sugg, SpanlessEq};

const CHECKED_CONVERSIONS_MSRV: RustcVersion = RustcVersion::new(1, 34, 0);

declare_clippy_lint! {
/// **What it does:** Checks for explicit bounds checking when casting.
Expand Down Expand Up @@ -39,10 +42,25 @@ declare_clippy_lint! {
"`try_from` could replace manual bounds checking when casting"
}

declare_lint_pass!(CheckedConversions => [CHECKED_CONVERSIONS]);
pub struct CheckedConversions {
msrv: Option<RustcVersion>,
}

impl CheckedConversions {
#[must_use]
pub fn new(msrv: Option<RustcVersion>) -> Self {
Self { msrv }
}
}

impl_lint_pass!(CheckedConversions => [CHECKED_CONVERSIONS]);

impl<'tcx> LateLintPass<'tcx> for CheckedConversions {
fn check_expr(&mut self, cx: &LateContext<'_>, item: &Expr<'_>) {
if !meets_msrv(self.msrv.as_ref(), &CHECKED_CONVERSIONS_MSRV) {
return;
}

let result = if_chain! {
if !in_external_macro(cx.sess(), item.span);
if let ExprKind::Binary(op, ref left, ref right) = &item.kind;
Expand Down Expand Up @@ -74,6 +92,8 @@ impl<'tcx> LateLintPass<'tcx> for CheckedConversions {
}
}
}

extract_msrv_attr!(LateContext);
}

/// Searches for a single check from unsigned to _ is done
Expand Down
15 changes: 8 additions & 7 deletions clippy_lints/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1003,6 +1003,14 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf:
store.register_late_pass(move || box matches::Matches::new(msrv));
store.register_early_pass(move || box manual_non_exhaustive::ManualNonExhaustive::new(msrv));
store.register_late_pass(move || box manual_strip::ManualStrip::new(msrv));
store.register_early_pass(move || box redundant_static_lifetimes::RedundantStaticLifetimes::new(msrv));
store.register_early_pass(move || box redundant_field_names::RedundantFieldNames::new(msrv));
store.register_late_pass(move || box checked_conversions::CheckedConversions::new(msrv));
store.register_late_pass(move || box mem_replace::MemReplace::new(msrv));
store.register_late_pass(move || box ranges::Ranges::new(msrv));
store.register_late_pass(move || box use_self::UseSelf::new(msrv));
store.register_late_pass(move || box missing_const_for_fn::MissingConstForFn::new(msrv));

store.register_late_pass(|| box size_of_in_element_count::SizeOfInElementCount);
store.register_late_pass(|| box map_clone::MapClone);
store.register_late_pass(|| box map_err_ignore::MapErrIgnore);
Expand All @@ -1013,7 +1021,6 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf:
store.register_late_pass(|| box main_recursion::MainRecursion::default());
store.register_late_pass(|| box lifetimes::Lifetimes);
store.register_late_pass(|| box entry::HashMapPass);
store.register_late_pass(|| box ranges::Ranges);
store.register_late_pass(|| box types::Casts);
let type_complexity_threshold = conf.type_complexity_threshold;
store.register_late_pass(move || box types::TypeComplexity::new(type_complexity_threshold));
Expand Down Expand Up @@ -1058,7 +1065,6 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf:
store.register_late_pass(|| box neg_multiply::NegMultiply);
store.register_late_pass(|| box mem_discriminant::MemDiscriminant);
store.register_late_pass(|| box mem_forget::MemForget);
store.register_late_pass(|| box mem_replace::MemReplace);
store.register_late_pass(|| box arithmetic::Arithmetic::default());
store.register_late_pass(|| box assign_ops::AssignOps);
store.register_late_pass(|| box let_if_seq::LetIfSeq);
Expand All @@ -1080,7 +1086,6 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf:
store.register_late_pass(move || box pass_by_ref_or_value);
store.register_late_pass(|| box ref_option_ref::RefOptionRef);
store.register_late_pass(|| box try_err::TryErr);
store.register_late_pass(|| box use_self::UseSelf);
store.register_late_pass(|| box bytecount::ByteCount);
store.register_late_pass(|| box infinite_iter::InfiniteIter);
store.register_late_pass(|| box inline_fn_without_body::InlineFnWithoutBody);
Expand All @@ -1106,10 +1111,8 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf:
store.register_late_pass(|| box unnecessary_wraps::UnnecessaryWraps);
store.register_late_pass(|| box types::RefToMut);
store.register_late_pass(|| box assertions_on_constants::AssertionsOnConstants);
store.register_late_pass(|| box missing_const_for_fn::MissingConstForFn);
store.register_late_pass(|| box transmuting_null::TransmutingNull);
store.register_late_pass(|| box path_buf_push_overwrite::PathBufPushOverwrite);
store.register_late_pass(|| box checked_conversions::CheckedConversions);
store.register_late_pass(|| box integer_division::IntegerDivision);
store.register_late_pass(|| box inherent_to_string::InherentToString);
let max_trait_bounds = conf.max_trait_bounds;
Expand Down Expand Up @@ -1138,7 +1141,6 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf:
store.register_early_pass(|| box redundant_else::RedundantElse);
store.register_late_pass(|| box create_dir::CreateDir);
store.register_early_pass(|| box needless_arbitrary_self_type::NeedlessArbitrarySelfType);
store.register_early_pass(|| box redundant_static_lifetimes::RedundantStaticLifetimes);
store.register_late_pass(|| box cargo_common_metadata::CargoCommonMetadata);
store.register_late_pass(|| box multiple_crate_versions::MultipleCrateVersions);
store.register_late_pass(|| box wildcard_dependencies::WildcardDependencies);
Expand Down Expand Up @@ -1178,7 +1180,6 @@ pub fn register_plugins(store: &mut rustc_lint::LintStore, sess: &Session, conf:
store.register_late_pass(|| box mut_mutex_lock::MutMutexLock);
store.register_late_pass(|| box match_on_vec_items::MatchOnVecItems);
store.register_late_pass(|| box manual_async_fn::ManualAsyncFn);
store.register_early_pass(|| box redundant_field_names::RedundantFieldNames);
store.register_late_pass(|| box vec_resize_to_zero::VecResizeToZero);
store.register_late_pass(|| box panic_in_result_fn::PanicInResultFn);
let single_char_binding_names_threshold = conf.single_char_binding_names_threshold;
Expand Down
27 changes: 22 additions & 5 deletions clippy_lints/src/mem_replace.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@
use crate::utils::{
in_macro, match_def_path, match_qpath, paths, snippet, snippet_with_applicability, span_lint_and_help,
in_macro, match_def_path, match_qpath, meets_msrv, paths, snippet, snippet_with_applicability, span_lint_and_help,
span_lint_and_sugg, span_lint_and_then,
};
use if_chain::if_chain;
use rustc_errors::Applicability;
use rustc_hir::{BorrowKind, Expr, ExprKind, Mutability, QPath};
use rustc_lint::{LateContext, LateLintPass};
use rustc_lint::{LateContext, LateLintPass, LintContext};
use rustc_middle::lint::in_external_macro;
use rustc_session::{declare_lint_pass, declare_tool_lint};
use rustc_semver::RustcVersion;
use rustc_session::{declare_tool_lint, impl_lint_pass};
use rustc_span::source_map::Span;
use rustc_span::symbol::sym;

Expand Down Expand Up @@ -94,7 +95,7 @@ declare_clippy_lint! {
"replacing a value of type `T` with `T::default()` instead of using `std::mem::take`"
}

declare_lint_pass!(MemReplace =>
impl_lint_pass!(MemReplace =>
[MEM_REPLACE_OPTION_WITH_NONE, MEM_REPLACE_WITH_UNINIT, MEM_REPLACE_WITH_DEFAULT]);

fn check_replace_option_with_none(cx: &LateContext<'_>, src: &Expr<'_>, dest: &Expr<'_>, expr_span: Span) {
Expand Down Expand Up @@ -224,6 +225,19 @@ fn check_replace_with_default(cx: &LateContext<'_>, src: &Expr<'_>, dest: &Expr<
}
}

const MEM_REPLACE_WITH_DEFAULT_MSRV: RustcVersion = RustcVersion::new(1, 40, 0);

pub struct MemReplace {
msrv: Option<RustcVersion>,
}

impl MemReplace {
#[must_use]
pub fn new(msrv: Option<RustcVersion>) -> Self {
Self { msrv }
}
}

impl<'tcx> LateLintPass<'tcx> for MemReplace {
fn check_expr(&mut self, cx: &LateContext<'tcx>, expr: &'tcx Expr<'_>) {
if_chain! {
Expand All @@ -236,8 +250,11 @@ impl<'tcx> LateLintPass<'tcx> for MemReplace {
then {
check_replace_option_with_none(cx, src, dest, expr.span);
check_replace_with_uninit(cx, src, dest, expr.span);
check_replace_with_default(cx, src, dest, expr.span);
if meets_msrv(self.msrv.as_ref(), &MEM_REPLACE_WITH_DEFAULT_MSRV) {
check_replace_with_default(cx, src, dest, expr.span);
}
}
}
}
extract_msrv_attr!(LateContext);
}
23 changes: 20 additions & 3 deletions clippy_lints/src/methods/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1487,7 +1487,7 @@ impl<'tcx> LateLintPass<'tcx> for Methods {
["expect", ..] => lint_expect(cx, expr, arg_lists[0]),
["unwrap_or", "map"] => option_map_unwrap_or::lint(cx, expr, arg_lists[1], arg_lists[0], method_spans[1]),
["unwrap_or_else", "map"] => {
if !lint_map_unwrap_or_else(cx, expr, arg_lists[1], arg_lists[0]) {
if !lint_map_unwrap_or_else(cx, expr, arg_lists[1], arg_lists[0], self.msrv.as_ref()) {
unnecessary_lazy_eval::lint(cx, expr, arg_lists[0], "unwrap_or");
}
},
Expand All @@ -1509,7 +1509,7 @@ impl<'tcx> LateLintPass<'tcx> for Methods {
["next", "iter"] => lint_iter_next(cx, expr, arg_lists[1]),
["map", "filter"] => lint_filter_map(cx, expr, arg_lists[1], arg_lists[0]),
["map", "filter_map"] => lint_filter_map_map(cx, expr, arg_lists[1], arg_lists[0]),
["next", "filter_map"] => lint_filter_map_next(cx, expr, arg_lists[1]),
["next", "filter_map"] => lint_filter_map_next(cx, expr, arg_lists[1], self.msrv.as_ref()),
["map", "find"] => lint_find_map(cx, expr, arg_lists[1], arg_lists[0]),
["flat_map", "filter"] => lint_filter_flat_map(cx, expr, arg_lists[1], arg_lists[0]),
["flat_map", "filter_map"] => lint_filter_map_flat_map(cx, expr, arg_lists[1], arg_lists[0]),
Expand Down Expand Up @@ -2733,14 +2733,20 @@ fn lint_map_flatten<'tcx>(cx: &LateContext<'tcx>, expr: &'tcx hir::Expr<'_>, map
}
}

const MAP_UNWRAP_OR_MSRV: RustcVersion = RustcVersion::new(1, 41, 0);

/// lint use of `map().unwrap_or_else()` for `Option`s and `Result`s
/// Return true if lint triggered
fn lint_map_unwrap_or_else<'tcx>(
cx: &LateContext<'tcx>,
expr: &'tcx hir::Expr<'_>,
map_args: &'tcx [hir::Expr<'_>],
unwrap_args: &'tcx [hir::Expr<'_>],
msrv: Option<&RustcVersion>,
) -> bool {
if !meets_msrv(msrv, &MAP_UNWRAP_OR_MSRV) {
return false;
}
// lint if the caller of `map()` is an `Option`
let is_option = is_type_diagnostic_item(cx, cx.typeck_results().expr_ty(&map_args[0]), sym::option_type);
let is_result = is_type_diagnostic_item(cx, cx.typeck_results().expr_ty(&map_args[0]), sym::result_type);
Expand Down Expand Up @@ -2923,9 +2929,20 @@ fn lint_filter_map<'tcx>(
}
}

const FILTER_MAP_NEXT_MSRV: RustcVersion = RustcVersion::new(1, 30, 0);

/// lint use of `filter_map().next()` for `Iterators`
fn lint_filter_map_next<'tcx>(cx: &LateContext<'tcx>, expr: &'tcx hir::Expr<'_>, filter_args: &'tcx [hir::Expr<'_>]) {
fn lint_filter_map_next<'tcx>(
cx: &LateContext<'tcx>,
expr: &'tcx hir::Expr<'_>,
filter_args: &'tcx [hir::Expr<'_>],
msrv: Option<&RustcVersion>,
) {
if match_trait_method(cx, expr, &paths::ITERATOR) {
if !meets_msrv(msrv, &FILTER_MAP_NEXT_MSRV) {
return;
}

let msg = "called `filter_map(..).next()` on an `Iterator`. This is more succinctly expressed by calling \
`.find_map(..)` instead.";
let filter_snippet = snippet(cx, filter_args[1].span, "..");
Expand Down
29 changes: 25 additions & 4 deletions clippy_lints/src/missing_const_for_fn.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,19 @@
use crate::utils::qualify_min_const_fn::is_min_const_fn;
use crate::utils::{fn_has_unsatisfiable_preds, has_drop, is_entrypoint_fn, span_lint, trait_ref_of_method};
use crate::utils::{
fn_has_unsatisfiable_preds, has_drop, is_entrypoint_fn, meets_msrv, span_lint, trait_ref_of_method,
};
use rustc_hir as hir;
use rustc_hir::intravisit::FnKind;
use rustc_hir::{Body, Constness, FnDecl, GenericParamKind, HirId};
use rustc_lint::{LateContext, LateLintPass};
use rustc_lint::{LateContext, LateLintPass, LintContext};
use rustc_middle::lint::in_external_macro;
use rustc_session::{declare_lint_pass, declare_tool_lint};
use rustc_semver::RustcVersion;
use rustc_session::{declare_tool_lint, impl_lint_pass};
use rustc_span::Span;
use rustc_typeck::hir_ty_to_ty;

const MISSING_CONST_FOR_FN_MSRV: RustcVersion = RustcVersion::new(1, 37, 0);

declare_clippy_lint! {
/// **What it does:**
///
Expand Down Expand Up @@ -69,7 +74,18 @@ declare_clippy_lint! {
"Lint functions definitions that could be made `const fn`"
}

declare_lint_pass!(MissingConstForFn => [MISSING_CONST_FOR_FN]);
impl_lint_pass!(MissingConstForFn => [MISSING_CONST_FOR_FN]);

pub struct MissingConstForFn {
msrv: Option<RustcVersion>,
}

impl MissingConstForFn {
#[must_use]
pub fn new(msrv: Option<RustcVersion>) -> Self {
Self { msrv }
}
}

impl<'tcx> LateLintPass<'tcx> for MissingConstForFn {
fn check_fn(
Expand All @@ -81,6 +97,10 @@ impl<'tcx> LateLintPass<'tcx> for MissingConstForFn {
span: Span,
hir_id: HirId,
) {
if !meets_msrv(self.msrv.as_ref(), &MISSING_CONST_FOR_FN_MSRV) {
return;
}

let def_id = cx.tcx.hir().local_def_id(hir_id);

if in_external_macro(cx.tcx.sess, span) || is_entrypoint_fn(cx, def_id.to_def_id()) {
Expand Down Expand Up @@ -126,6 +146,7 @@ impl<'tcx> LateLintPass<'tcx> for MissingConstForFn {
span_lint(cx, MISSING_CONST_FOR_FN, span, "this could be a `const fn`");
}
}
extract_msrv_attr!(LateContext);
}

/// Returns true if any of the method parameters is a type that implements `Drop`. The method
Expand Down
29 changes: 23 additions & 6 deletions clippy_lints/src/ranges.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,19 @@ use if_chain::if_chain;
use rustc_ast::ast::RangeLimits;
use rustc_errors::Applicability;
use rustc_hir::{BinOpKind, Expr, ExprKind, PathSegment, QPath};
use rustc_lint::{LateContext, LateLintPass};
use rustc_lint::{LateContext, LateLintPass, LintContext};
use rustc_middle::ty;
use rustc_session::{declare_lint_pass, declare_tool_lint};
use rustc_semver::RustcVersion;
use rustc_session::{declare_tool_lint, impl_lint_pass};
use rustc_span::source_map::{Span, Spanned};
use rustc_span::sym;
use rustc_span::symbol::Ident;
use std::cmp::Ordering;

use crate::utils::sugg::Sugg;
use crate::utils::{
get_parent_expr, is_integer_const, single_segment_path, snippet, snippet_opt, snippet_with_applicability,
span_lint, span_lint_and_sugg, span_lint_and_then,
get_parent_expr, is_integer_const, meets_msrv, single_segment_path, snippet, snippet_opt,
snippet_with_applicability, span_lint, span_lint_and_sugg, span_lint_and_then,
};
use crate::utils::{higher, SpanlessEq};

Expand Down Expand Up @@ -160,7 +161,20 @@ declare_clippy_lint! {
"manually reimplementing {`Range`, `RangeInclusive`}`::contains`"
}

declare_lint_pass!(Ranges => [
const MANUAL_RANGE_CONTAINS_MSRV: RustcVersion = RustcVersion::new(1, 35, 0);

pub struct Ranges {
msrv: Option<RustcVersion>,
}

impl Ranges {
#[must_use]
pub fn new(msrv: Option<RustcVersion>) -> Self {
Self { msrv }
}
}

impl_lint_pass!(Ranges => [
RANGE_ZIP_WITH_LEN,
RANGE_PLUS_ONE,
RANGE_MINUS_ONE,
Expand All @@ -175,7 +189,9 @@ impl<'tcx> LateLintPass<'tcx> for Ranges {
check_range_zip_with_len(cx, path, args, expr.span);
},
ExprKind::Binary(ref op, ref l, ref r) => {
check_possible_range_contains(cx, op.node, l, r, expr.span);
if meets_msrv(self.msrv.as_ref(), &MANUAL_RANGE_CONTAINS_MSRV) {
check_possible_range_contains(cx, op.node, l, r, expr.span);
}
},
_ => {},
}
Expand All @@ -184,6 +200,7 @@ impl<'tcx> LateLintPass<'tcx> for Ranges {
check_inclusive_range_minus_one(cx, expr);
check_reversed_empty_range(cx, expr);
}
extract_msrv_attr!(LateContext);
}

fn check_possible_range_contains(cx: &LateContext<'_>, op: BinOpKind, l: &Expr<'_>, r: &Expr<'_>, span: Span) {
Expand Down
Loading