summaryrefslogtreecommitdiffstats
path: root/src/tools/clippy/clippy_lints/src/casts/cast_nan_to_int.rs
blob: 322dc41b3a197dd4301a45c355f193f466d9be61 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
use super::CAST_NAN_TO_INT;

use clippy_utils::consts::{constant, Constant};
use clippy_utils::diagnostics::span_lint_and_note;
use rustc_hir::Expr;
use rustc_lint::LateContext;
use rustc_middle::ty::Ty;

pub(super) fn check(cx: &LateContext<'_>, expr: &Expr<'_>, cast_expr: &Expr<'_>, from_ty: Ty<'_>, to_ty: Ty<'_>) {
    if from_ty.is_floating_point() && to_ty.is_integral() && is_known_nan(cx, cast_expr) {
        span_lint_and_note(
            cx,
            CAST_NAN_TO_INT,
            expr.span,
            &format!("casting a known NaN to {to_ty}"),
            None,
            "this always evaluates to 0",
        );
    }
}

fn is_known_nan(cx: &LateContext<'_>, e: &Expr<'_>) -> bool {
    match constant(cx, cx.typeck_results(), e) {
        Some((Constant::F64(n), _)) => n.is_nan(),
        Some((Constant::F32(n), _)) => n.is_nan(),
        _ => false,
    }
}