1 // Copyright 2014-2018 The Rust Project Developers. See the COPYRIGHT
2 // file at the top-level directory of this distribution.
4 // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
5 // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
6 // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
7 // option. This file may not be copied, modified, or distributed
8 // except according to those terms.
10 use crate::utils::{get_pat_name, match_var, snippet};
11 use rustc::hir::intravisit::{walk_expr, NestedVisitorMap, Visitor};
13 use rustc::lint::LateContext;
15 use syntax::ast::Name;
16 use syntax::source_map::Span;
19 cx: &LateContext<'_, '_>,
20 opt_body_id: Option<BodyId>,
22 replacements: &'static [(&'static str, &'static str)],
23 ) -> Option<Vec<(Span, Cow<'static, str>)>> {
24 if let Some(body) = opt_body_id.map(|id| cx.tcx.hir().body(id)) {
25 get_binding_name(&body.arguments[idx]).map_or_else(
27 |name| extract_clone_suggestions(cx, name, replacements, body),
34 fn extract_clone_suggestions<'a, 'tcx: 'a>(
35 cx: &LateContext<'a, 'tcx>,
37 replace: &'static [(&'static str, &'static str)],
39 ) -> Option<Vec<(Span, Cow<'static, str>)>> {
40 let mut visitor = PtrCloneVisitor {
47 visitor.visit_body(body);
55 struct PtrCloneVisitor<'a, 'tcx: 'a> {
56 cx: &'a LateContext<'a, 'tcx>,
58 replace: &'static [(&'static str, &'static str)],
59 spans: Vec<(Span, Cow<'static, str>)>,
63 impl<'a, 'tcx: 'a> Visitor<'tcx> for PtrCloneVisitor<'a, 'tcx> {
64 fn visit_expr(&mut self, expr: &'tcx Expr) {
68 if let ExprKind::MethodCall(ref seg, _, ref args) = expr.node {
69 if args.len() == 1 && match_var(&args[0], self.name) {
70 if seg.ident.name == "capacity" {
74 for &(fn_name, suffix) in self.replace {
75 if seg.ident.name == fn_name {
77 .push((expr.span, snippet(self.cx, args[0].span, "_") + suffix));
84 walk_expr(self, expr);
87 fn nested_visit_map<'this>(&'this mut self) -> NestedVisitorMap<'this, 'tcx> {
88 NestedVisitorMap::None
92 fn get_binding_name(arg: &Arg) -> Option<Name> {
93 get_pat_name(&arg.pat)