rust-lang / rust-lang/rust-clippy

`cast_possible_truncation`: `x.min(C) as T` is only recognized when `C` is a literal

Open
#17,722 1 comment 1 reaction 0 assignees View on GitHub

Nobody has claimed this yet.

C-bug I-false-positive L-pedantic
Dominant language
Rust
Stars
13.5k
Forks
2.2k
Avg merge
2d 10h
Merged PRs (30d)
32

Description

Summary

cast_possible_truncation knows that x.min(C) bounds the value, but only when C is a literal. With the same bound written as u32::MAX as u64, u32::MAX.into() or u64::from(u32::MAX) it still fires. The last form is what cast_lossless suggests for u32::MAX as u64, so following the suggestion of one lint keeps this one firing.

Related: #9613.

Lint Name

cast_possible_truncation

Reproducer

I tried this code:

#![warn(clippy::cast_possible_truncation)]

pub fn literal(x: u64) -> u32 {
    x.min(0xFFFF_FFFF) as u32
}

pub fn cast(x: u64) -> u32 {
    x.min(u32::MAX as u64) as u32
}

pub fn into(x: u64) -> u32 {
    x.min(u32::MAX.into()) as u32
}

pub fn from(x: u64) -> u32 {
    x.min(u64::from(u32::MAX)) as u32
}

I saw this happen:

warning: casting `u64` to `u32` may truncate the value
 --> lib.rs:8:5
  |
8 |     x.min(u32::MAX as u64) as u32
  |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  |
  = help: if this is intentional allow the lint with `#[allow(clippy::cast_possible_truncation)]` ...
  = help: for further information visit https://rust-lang.github.io/rust-clippy/rust-1.98.0/index.html#cast_possible_truncation
note: the lint level is defined here
 --> lib.rs:1:9
  |
1 | #![warn(clippy::cast_possible_truncation)]
  |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
help: ... or use `try_from` and handle the error accordingly
  |
8 -     x.min(u32::MAX as u64) as u32
8 +     u32::try_from(x.min(u32::MAX as u64))
  |

warning: casting `u64` to `u32` may truncate the value
  --> lib.rs:12:5
   |
12 |     x.min(u32::MAX.into()) as u32
   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
   |
   = help: if this is intentional allow the lint with `#[allow(clippy::cast_possible_truncation)]` ...
   = help: for further information visit https://rust-lang.github.io/rust-clippy/rust-1.98.0/index.html#cast_possible_truncation
help: ... or use `try_from` and handle the error accordingly
   |
12 -     x.min(u32::MAX.into()) as u32
12 +     u32::try_from(x.min(u32::MAX.into()))
   |

warning: casting `u64` to `u32` may truncate the value
  --> lib.rs:16:5
   |
16 |     x.min(u64::from(u32::MAX)) as u32
   |     ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
   |
   = help: if this is intentional allow the lint with `#[allow(clippy::cast_possible_truncation)]` ...
   = help: for further information visit https://rust-lang.github.io/rust-clippy/rust-1.98.0/index.html#cast_possible_truncation
help: ... or use `try_from` and handle the error accordingly
   |
16 -     x.min(u64::from(u32::MAX)) as u32
16 +     u32::try_from(x.min(u64::from(u32::MAX)))
   |

I expected to see this happen: No warning in any of the four functions, as in literal: the value is bounded by u32::MAX before the cast.

Version
rustc 1.98.0 (88d9e12ae 2026-08-18)
binary: rustc
commit-hash: 88d9e12ae178fab0fb5cc050a94da85685d449ea
commit-date: 2026-08-18
host: x86_64-pc-windows-msvc
release: 1.98.0
LLVM version: 22.1.8

Contributor guide

Open the contributing guide

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Use the cast_possible_truncation lint as the entry point and reproduce the four functions shown in the issue. Trace how bounds from u32::MAX as u64, .into(), and u64::from are recognized, then verify that all four forms avoid the warning while the existing literal case remains unchanged.

Written by the indexing model from the issue text.

Assessment

Tech stack
rust
Domain
tooling
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Active
Clarity
Mostly clear
Newbie friendliness
68/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.