mirror of
https://github.com/rust-lang/rust.git
synced 2026-05-08 01:28:18 +03:00
fix: for_kv_map wrongly unmangled macros
This commit is contained in:
@@ -1,16 +1,22 @@
|
||||
use super::FOR_KV_MAP;
|
||||
use clippy_utils::diagnostics::span_lint_and_then;
|
||||
use clippy_utils::res::MaybeDef;
|
||||
use clippy_utils::source::snippet;
|
||||
use clippy_utils::source::{snippet_with_applicability, walk_span_to_context};
|
||||
use clippy_utils::{pat_is_wild, sugg};
|
||||
use rustc_errors::Applicability;
|
||||
use rustc_hir::{BorrowKind, Expr, ExprKind, Mutability, Pat, PatKind};
|
||||
use rustc_lint::LateContext;
|
||||
use rustc_middle::ty;
|
||||
use rustc_span::sym;
|
||||
use rustc_span::{Span, sym};
|
||||
|
||||
/// Checks for the `FOR_KV_MAP` lint.
|
||||
pub(super) fn check<'tcx>(cx: &LateContext<'tcx>, pat: &'tcx Pat<'_>, arg: &'tcx Expr<'_>, body: &'tcx Expr<'_>) {
|
||||
pub(super) fn check<'tcx>(
|
||||
cx: &LateContext<'tcx>,
|
||||
pat: &'tcx Pat<'_>,
|
||||
arg: &'tcx Expr<'_>,
|
||||
body: &'tcx Expr<'_>,
|
||||
span: Span,
|
||||
) {
|
||||
let pat_span = pat.span;
|
||||
|
||||
if let PatKind::Tuple(pat, _) = pat.kind
|
||||
@@ -34,21 +40,25 @@ pub(super) fn check<'tcx>(cx: &LateContext<'tcx>, pat: &'tcx Pat<'_>, arg: &'tcx
|
||||
_ => arg,
|
||||
};
|
||||
|
||||
if matches!(ty.opt_diag_name(cx), Some(sym::HashMap | sym::BTreeMap)) {
|
||||
if matches!(ty.opt_diag_name(cx), Some(sym::HashMap | sym::BTreeMap))
|
||||
&& let Some(arg_span) = walk_span_to_context(arg_span, span.ctxt())
|
||||
{
|
||||
span_lint_and_then(
|
||||
cx,
|
||||
FOR_KV_MAP,
|
||||
arg_span,
|
||||
format!("you seem to want to iterate on a map's {kind}s"),
|
||||
|diag| {
|
||||
let map = sugg::Sugg::hir(cx, arg, "map");
|
||||
let mut applicability = Applicability::MachineApplicable;
|
||||
let map = sugg::Sugg::hir_with_context(cx, arg, span.ctxt(), "map", &mut applicability);
|
||||
let pat = snippet_with_applicability(cx, new_pat_span, kind, &mut applicability);
|
||||
diag.multipart_suggestion(
|
||||
"use the corresponding method",
|
||||
vec![
|
||||
(pat_span, snippet(cx, new_pat_span, kind).into_owned()),
|
||||
(pat_span, pat.to_string()),
|
||||
(arg_span, format!("{}.{kind}s{mutbl}()", map.maybe_paren())),
|
||||
],
|
||||
Applicability::MachineApplicable,
|
||||
applicability,
|
||||
);
|
||||
},
|
||||
);
|
||||
|
||||
@@ -943,7 +943,7 @@ fn check_for_loop<'tcx>(
|
||||
explicit_counter_loop::check(cx, pat, arg, body, expr, label);
|
||||
}
|
||||
self.check_for_loop_arg(cx, pat, arg);
|
||||
for_kv_map::check(cx, pat, arg, body);
|
||||
for_kv_map::check(cx, pat, arg, body, span);
|
||||
mut_range_bound::check(cx, arg, body);
|
||||
single_element_loop::check(cx, pat, arg, body, expr);
|
||||
same_item_push::check(cx, pat, arg, body, expr, self.msrv);
|
||||
|
||||
@@ -69,3 +69,20 @@ fn main() {
|
||||
let _v = v;
|
||||
}
|
||||
}
|
||||
|
||||
fn wrongly_unmangled_macros() {
|
||||
use std::collections::HashMap;
|
||||
|
||||
macro_rules! test_map {
|
||||
($val:expr) => {
|
||||
&*$val
|
||||
};
|
||||
}
|
||||
|
||||
let m: HashMap<u64, u64> = HashMap::new();
|
||||
let wrapped = Rc::new(m);
|
||||
for v in test_map!(wrapped).values() {
|
||||
//~^ for_kv_map
|
||||
let _v = v;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -69,3 +69,20 @@ fn main() {
|
||||
let _v = v;
|
||||
}
|
||||
}
|
||||
|
||||
fn wrongly_unmangled_macros() {
|
||||
use std::collections::HashMap;
|
||||
|
||||
macro_rules! test_map {
|
||||
($val:expr) => {
|
||||
&*$val
|
||||
};
|
||||
}
|
||||
|
||||
let m: HashMap<u64, u64> = HashMap::new();
|
||||
let wrapped = Rc::new(m);
|
||||
for (_, v) in test_map!(wrapped) {
|
||||
//~^ for_kv_map
|
||||
let _v = v;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -72,5 +72,17 @@ LL - 'label: for (k, _value) in rm {
|
||||
LL + 'label: for k in rm.keys() {
|
||||
|
|
||||
|
||||
error: aborting due to 6 previous errors
|
||||
error: you seem to want to iterate on a map's values
|
||||
--> tests/ui/for_kv_map.rs:84:19
|
||||
|
|
||||
LL | for (_, v) in test_map!(wrapped) {
|
||||
| ^^^^^^^^^^^^^^^^^^
|
||||
|
|
||||
help: use the corresponding method
|
||||
|
|
||||
LL - for (_, v) in test_map!(wrapped) {
|
||||
LL + for v in test_map!(wrapped).values() {
|
||||
|
|
||||
|
||||
error: aborting due to 7 previous errors
|
||||
|
||||
|
||||
Reference in New Issue
Block a user