Skip to content

Commit

Permalink
Auto merge of rust-lang#11957 - J-ZhengLi:issue11535, r=Jarcho
Browse files Browse the repository at this point in the history
don't lint [`default_numeric_fallback`] on return and local assigned macro calls with type stated

fixes: rust-lang#11535

changelog: don't lint [`default_numeric_fallback`] on return and local assigned macro calls with type stated
  • Loading branch information
bors committed Dec 30, 2023
2 parents c6aeb28 + a9baf34 commit 0cc53f4
Show file tree
Hide file tree
Showing 7 changed files with 139 additions and 48 deletions.
41 changes: 35 additions & 6 deletions clippy_lints/src/default_numeric_fallback.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ use clippy_utils::{get_parent_node, numeric_literal};
use rustc_ast::ast::{LitFloatType, LitIntType, LitKind};
use rustc_errors::Applicability;
use rustc_hir::intravisit::{walk_expr, walk_stmt, Visitor};
use rustc_hir::{Body, Expr, ExprKind, HirId, ItemKind, Lit, Node, Stmt, StmtKind};
use rustc_hir::{Block, Body, Expr, ExprKind, FnRetTy, HirId, ItemKind, Lit, Node, Stmt, StmtKind};
use rustc_lint::{LateContext, LateLintPass, LintContext};
use rustc_middle::lint::in_external_macro;
use rustc_middle::ty::{self, FloatTy, IntTy, PolyFnSig, Ty};
Expand Down Expand Up @@ -122,13 +122,42 @@ impl<'a, 'tcx> NumericFallbackVisitor<'a, 'tcx> {
impl<'a, 'tcx> Visitor<'tcx> for NumericFallbackVisitor<'a, 'tcx> {
fn visit_expr(&mut self, expr: &'tcx Expr<'_>) {
match &expr.kind {
ExprKind::Block(
Block {
stmts, expr: Some(_), ..
},
_,
) => {
if let Some(parent) = self.cx.tcx.hir().find_parent(expr.hir_id)
&& let Some(fn_sig) = parent.fn_sig()
&& let FnRetTy::Return(_ty) = fn_sig.decl.output
{
// We cannot check the exact type since it's a `hir::Ty`` which does not implement `is_numeric`
self.ty_bounds.push(ExplicitTyBound(true));
for stmt in *stmts {
self.visit_stmt(stmt);
}
self.ty_bounds.pop();
// Ignore return expr since we know its type was inferred from return ty
return;
}
},

// Ignore return expr since we know its type was inferred from return ty
ExprKind::Ret(_) => return,

ExprKind::Call(func, args) => {
if let Some(fn_sig) = fn_sig_opt(self.cx, func.hir_id) {
for (expr, bound) in iter::zip(*args, fn_sig.skip_binder().inputs()) {
// Push found arg type, then visit arg.
self.ty_bounds.push((*bound).into());
self.visit_expr(expr);
self.ty_bounds.pop();
// If is from macro, try to use last bound type (typically pushed when visiting stmt),
// otherwise push found arg type, then visit arg,
if expr.span.from_expansion() {
self.visit_expr(expr);
} else {
self.ty_bounds.push((*bound).into());
self.visit_expr(expr);
self.ty_bounds.pop();
}
}
return;
}
Expand All @@ -137,7 +166,7 @@ impl<'a, 'tcx> Visitor<'tcx> for NumericFallbackVisitor<'a, 'tcx> {
ExprKind::MethodCall(_, receiver, args, _) => {
if let Some(def_id) = self.cx.typeck_results().type_dependent_def_id(expr.hir_id) {
let fn_sig = self.cx.tcx.fn_sig(def_id).instantiate_identity().skip_binder();
for (expr, bound) in iter::zip(std::iter::once(*receiver).chain(args.iter()), fn_sig.inputs()) {
for (expr, bound) in iter::zip(iter::once(*receiver).chain(args.iter()), fn_sig.inputs()) {
self.ty_bounds.push((*bound).into());
self.visit_expr(expr);
self.ty_bounds.pop();
Expand Down
4 changes: 1 addition & 3 deletions tests/ui/default_numeric_fallback_f64.fixed
Original file line number Diff line number Diff line change
Expand Up @@ -73,9 +73,7 @@ mod nested_local {

mod function_def {
fn ret_f64() -> f64 {
// Even though the output type is specified,
// this unsuffixed literal is linted to reduce heuristics and keep codebase simple.
1.0_f64
1.
}

fn test() {
Expand Down
2 changes: 0 additions & 2 deletions tests/ui/default_numeric_fallback_f64.rs
Original file line number Diff line number Diff line change
Expand Up @@ -73,8 +73,6 @@ mod nested_local {

mod function_def {
fn ret_f64() -> f64 {
// Even though the output type is specified,
// this unsuffixed literal is linted to reduce heuristics and keep codebase simple.
1.
}

Expand Down
26 changes: 10 additions & 16 deletions tests/ui/default_numeric_fallback_f64.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -86,66 +86,60 @@ LL | let y = 1.;
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:78:9
|
LL | 1.
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:84:27
--> $DIR/default_numeric_fallback_f64.rs:82:27
|
LL | let f = || -> _ { 1. };
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:88:29
--> $DIR/default_numeric_fallback_f64.rs:86:29
|
LL | let f = || -> f64 { 1. };
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:102:21
--> $DIR/default_numeric_fallback_f64.rs:100:21
|
LL | generic_arg(1.);
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:105:32
--> $DIR/default_numeric_fallback_f64.rs:103:32
|
LL | let x: _ = generic_arg(1.);
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:123:28
--> $DIR/default_numeric_fallback_f64.rs:121:28
|
LL | GenericStruct { x: 1. };
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:126:36
--> $DIR/default_numeric_fallback_f64.rs:124:36
|
LL | let _ = GenericStruct { x: 1. };
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:144:24
--> $DIR/default_numeric_fallback_f64.rs:142:24
|
LL | GenericEnum::X(1.);
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:164:23
--> $DIR/default_numeric_fallback_f64.rs:162:23
|
LL | s.generic_arg(1.);
| ^^ help: consider adding suffix: `1.0_f64`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_f64.rs:174:25
--> $DIR/default_numeric_fallback_f64.rs:172:25
|
LL | inline!(let x = 22.;);
| ^^^ help: consider adding suffix: `22.0_f64`
|
= note: this error originates in the macro `__inline_mac_fn_internal` (in Nightly builds, run with -Z macro-backtrace for more info)

error: aborting due to 24 previous errors
error: aborting due to 23 previous errors

36 changes: 33 additions & 3 deletions tests/ui/default_numeric_fallback_i32.fixed
Original file line number Diff line number Diff line change
Expand Up @@ -74,9 +74,7 @@ mod nested_local {

mod function_def {
fn ret_i32() -> i32 {
// Even though the output type is specified,
// this unsuffixed literal is linted to reduce heuristics and keep codebase simple.
1_i32
1
}

fn test() {
Expand Down Expand Up @@ -186,4 +184,36 @@ fn check_expect_suppression() {
let x = 21;
}

mod type_already_infered {
// Should NOT lint if bound to return type
fn ret_i32() -> i32 {
1
}

// Should NOT lint if bound to return type
fn ret_if_i32(b: bool) -> i32 {
if b { 100 } else { 0 }
}

// Should NOT lint if bound to return type
fn ret_i32_tuple() -> (i32, i32) {
(0, 1)
}

// Should NOT lint if bound to return type
fn ret_stmt(b: bool) -> (i32, i32) {
if b {
return (0, 1);
}
(0, 0)
}

#[allow(clippy::useless_vec)]
fn vec_macro() {
// Should NOT lint in `vec!` call if the type was already stated
let data_i32: Vec<i32> = vec![1, 2, 3];
let data_i32 = vec![1_i32, 2_i32, 3_i32];
}
}

fn main() {}
34 changes: 32 additions & 2 deletions tests/ui/default_numeric_fallback_i32.rs
Original file line number Diff line number Diff line change
Expand Up @@ -74,8 +74,6 @@ mod nested_local {

mod function_def {
fn ret_i32() -> i32 {
// Even though the output type is specified,
// this unsuffixed literal is linted to reduce heuristics and keep codebase simple.
1
}

Expand Down Expand Up @@ -186,4 +184,36 @@ fn check_expect_suppression() {
let x = 21;
}

mod type_already_infered {
// Should NOT lint if bound to return type
fn ret_i32() -> i32 {
1
}

// Should NOT lint if bound to return type
fn ret_if_i32(b: bool) -> i32 {
if b { 100 } else { 0 }
}

// Should NOT lint if bound to return type
fn ret_i32_tuple() -> (i32, i32) {
(0, 1)
}

// Should NOT lint if bound to return type
fn ret_stmt(b: bool) -> (i32, i32) {
if b {
return (0, 1);
}
(0, 0)
}

#[allow(clippy::useless_vec)]
fn vec_macro() {
// Should NOT lint in `vec!` call if the type was already stated
let data_i32: Vec<i32> = vec![1, 2, 3];
let data_i32 = vec![1, 2, 3];
}
}

fn main() {}
44 changes: 28 additions & 16 deletions tests/ui/default_numeric_fallback_i32.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -98,66 +98,78 @@ LL | let y = 1;
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:79:9
|
LL | 1
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:85:27
--> $DIR/default_numeric_fallback_i32.rs:83:27
|
LL | let f = || -> _ { 1 };
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:89:29
--> $DIR/default_numeric_fallback_i32.rs:87:29
|
LL | let f = || -> i32 { 1 };
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:103:21
--> $DIR/default_numeric_fallback_i32.rs:101:21
|
LL | generic_arg(1);
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:106:32
--> $DIR/default_numeric_fallback_i32.rs:104:32
|
LL | let x: _ = generic_arg(1);
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:124:28
--> $DIR/default_numeric_fallback_i32.rs:122:28
|
LL | GenericStruct { x: 1 };
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:127:36
--> $DIR/default_numeric_fallback_i32.rs:125:36
|
LL | let _ = GenericStruct { x: 1 };
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:145:24
--> $DIR/default_numeric_fallback_i32.rs:143:24
|
LL | GenericEnum::X(1);
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:165:23
--> $DIR/default_numeric_fallback_i32.rs:163:23
|
LL | s.generic_arg(1);
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:175:25
--> $DIR/default_numeric_fallback_i32.rs:173:25
|
LL | inline!(let x = 22;);
| ^^ help: consider adding suffix: `22_i32`
|
= note: this error originates in the macro `__inline_mac_fn_internal` (in Nightly builds, run with -Z macro-backtrace for more info)

error: aborting due to 26 previous errors
error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:215:29
|
LL | let data_i32 = vec![1, 2, 3];
| ^ help: consider adding suffix: `1_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:215:32
|
LL | let data_i32 = vec![1, 2, 3];
| ^ help: consider adding suffix: `2_i32`

error: default numeric fallback might occur
--> $DIR/default_numeric_fallback_i32.rs:215:35
|
LL | let data_i32 = vec![1, 2, 3];
| ^ help: consider adding suffix: `3_i32`

error: aborting due to 28 previous errors

0 comments on commit 0cc53f4

Please sign in to comment.