about summary refs log tree commit diff
diff options
context:
space:
mode:
authorRalf Jung <post@ralfj.de>2025-05-19 09:02:56 +0000
committerGitHub <noreply@github.com>2025-05-19 09:02:56 +0000
commit44d3c93fc8836983c719419fb3398525a82a11b2 (patch)
tree5f35731b80389a097629dcafc605720ba45b1ae7
parentd5240ccd1cabcf8b7447246e1a0fc337785eb6fa (diff)
parent446fa22412e16142658da8664f6fe3981e4aaf3c (diff)
downloadrust-44d3c93fc8836983c719419fb3398525a82a11b2.tar.gz
rust-44d3c93fc8836983c719419fb3398525a82a11b2.zip
Merge pull request #4329 from RalfJung/no-casts
enable clippy::as_conversions to fully rule out as-casts
-rw-r--r--src/tools/miri/src/alloc_addresses/mod.rs2
-rw-r--r--src/tools/miri/src/alloc_addresses/reuse_pool.rs3
-rw-r--r--src/tools/miri/src/alloc_bytes.rs6
-rw-r--r--src/tools/miri/src/borrow_tracker/tree_borrows/unimap.rs20
-rw-r--r--src/tools/miri/src/concurrency/cpu_affinity.rs2
-rw-r--r--src/tools/miri/src/concurrency/vector_clock.rs5
-rw-r--r--src/tools/miri/src/helpers.rs23
-rw-r--r--src/tools/miri/src/intrinsics/simd.rs2
-rw-r--r--src/tools/miri/src/lib.rs11
-rw-r--r--src/tools/miri/src/shims/backtrace.rs8
-rw-r--r--src/tools/miri/src/shims/foreign_items.rs6
-rw-r--r--src/tools/miri/src/shims/native_lib.rs17
-rw-r--r--src/tools/miri/src/shims/unix/android/thread.rs4
-rw-r--r--src/tools/miri/src/shims/unix/freebsd/foreign_items.rs2
-rw-r--r--src/tools/miri/src/shims/unix/fs.rs4
-rw-r--r--src/tools/miri/src/shims/unix/linux/foreign_items.rs4
-rw-r--r--src/tools/miri/src/shims/unix/macos/foreign_items.rs2
-rw-r--r--src/tools/miri/src/shims/unix/thread.rs6
-rw-r--r--src/tools/miri/src/shims/windows/fs.rs2
-rw-r--r--src/tools/miri/src/shims/windows/handle.rs12
-rw-r--r--src/tools/miri/src/shims/x86/gfni.rs4
-rw-r--r--src/tools/miri/src/shims/x86/mod.rs2
-rw-r--r--src/tools/miri/src/shims/x86/sha.rs2
-rw-r--r--src/tools/miri/src/shims/x86/sse42.rs2
24 files changed, 83 insertions, 68 deletions
diff --git a/src/tools/miri/src/alloc_addresses/mod.rs b/src/tools/miri/src/alloc_addresses/mod.rs
index dd389d97cdc..21bd7fb54c6 100644
--- a/src/tools/miri/src/alloc_addresses/mod.rs
+++ b/src/tools/miri/src/alloc_addresses/mod.rs
@@ -168,7 +168,7 @@ trait EvalContextExtPriv<'tcx>: crate::MiriInterpCxExt<'tcx> {
                 AllocKind::Dead => unreachable!(),
             };
             // We don't have to expose this pointer yet, we do that in `prepare_for_native_call`.
-            return interp_ok(base_ptr.addr().try_into().unwrap());
+            return interp_ok(base_ptr.addr().to_u64());
         }
         // We are not in native lib mode, so we control the addresses ourselves.
         if let Some((reuse_addr, clock)) = global_state.reuse.take_addr(
diff --git a/src/tools/miri/src/alloc_addresses/reuse_pool.rs b/src/tools/miri/src/alloc_addresses/reuse_pool.rs
index 29d4f2bb7b0..ab6aaed5e3e 100644
--- a/src/tools/miri/src/alloc_addresses/reuse_pool.rs
+++ b/src/tools/miri/src/alloc_addresses/reuse_pool.rs
@@ -4,6 +4,7 @@ use rand::Rng;
 use rustc_abi::{Align, Size};
 
 use crate::concurrency::VClock;
+use crate::helpers::ToUsize as _;
 use crate::{MemoryKind, MiriConfig, ThreadId};
 
 const MAX_POOL_SIZE: usize = 64;
@@ -46,7 +47,7 @@ impl ReusePool {
     }
 
     fn subpool(&mut self, align: Align) -> &mut Vec<(u64, Size, ThreadId, VClock)> {
-        let pool_idx: usize = align.bytes().trailing_zeros().try_into().unwrap();
+        let pool_idx: usize = align.bytes().trailing_zeros().to_usize();
         if self.pool.len() <= pool_idx {
             self.pool.resize(pool_idx + 1, Vec::new());
         }
diff --git a/src/tools/miri/src/alloc_bytes.rs b/src/tools/miri/src/alloc_bytes.rs
index 69ede279aa9..6788494c01c 100644
--- a/src/tools/miri/src/alloc_bytes.rs
+++ b/src/tools/miri/src/alloc_bytes.rs
@@ -5,6 +5,8 @@ use std::{alloc, slice};
 use rustc_abi::{Align, Size};
 use rustc_middle::mir::interpret::AllocBytes;
 
+use crate::helpers::ToU64 as _;
+
 /// Allocation bytes that explicitly handle the layout of the data they're storing.
 /// This is necessary to interface with native code that accesses the program store in Miri.
 #[derive(Debug)]
@@ -21,7 +23,7 @@ pub struct MiriAllocBytes {
 impl Clone for MiriAllocBytes {
     fn clone(&self) -> Self {
         let bytes: Cow<'_, [u8]> = Cow::Borrowed(self);
-        let align = Align::from_bytes(self.layout.align().try_into().unwrap()).unwrap();
+        let align = Align::from_bytes(self.layout.align().to_u64()).unwrap();
         MiriAllocBytes::from_bytes(bytes, align)
     }
 }
@@ -90,7 +92,7 @@ impl AllocBytes for MiriAllocBytes {
         let align = align.bytes();
         // SAFETY: `alloc_fn` will only be used with `size != 0`.
         let alloc_fn = |layout| unsafe { alloc::alloc(layout) };
-        let alloc_bytes = MiriAllocBytes::alloc_with(size.try_into().unwrap(), align, alloc_fn)
+        let alloc_bytes = MiriAllocBytes::alloc_with(size.to_u64(), align, alloc_fn)
             .unwrap_or_else(|()| {
                 panic!("Miri ran out of memory: cannot create allocation of {size} bytes")
             });
diff --git a/src/tools/miri/src/borrow_tracker/tree_borrows/unimap.rs b/src/tools/miri/src/borrow_tracker/tree_borrows/unimap.rs
index 7874721c0ac..dcd5a6cb023 100644
--- a/src/tools/miri/src/borrow_tracker/tree_borrows/unimap.rs
+++ b/src/tools/miri/src/borrow_tracker/tree_borrows/unimap.rs
@@ -17,6 +17,8 @@ use std::mem;
 
 use rustc_data_structures::fx::FxHashMap;
 
+use crate::helpers::ToUsize;
+
 /// Intermediate key between a UniKeyMap and a UniValMap.
 #[derive(Debug, Clone, Copy, PartialEq, Eq)]
 pub struct UniIndex {
@@ -158,7 +160,7 @@ where
 impl<V> UniValMap<V> {
     /// Whether this index has an associated value.
     pub fn contains_idx(&self, idx: UniIndex) -> bool {
-        self.data.get(idx.idx as usize).and_then(Option::as_ref).is_some()
+        self.data.get(idx.idx.to_usize()).and_then(Option::as_ref).is_some()
     }
 
     /// Reserve enough space to insert the value at the right index.
@@ -174,29 +176,29 @@ impl<V> UniValMap<V> {
 
     /// Assign a value to the index. Permanently overwrites any previous value.
     pub fn insert(&mut self, idx: UniIndex, val: V) {
-        self.extend_to_length(idx.idx as usize + 1);
-        self.data[idx.idx as usize] = Some(val)
+        self.extend_to_length(idx.idx.to_usize() + 1);
+        self.data[idx.idx.to_usize()] = Some(val)
     }
 
     /// Get the value at this index, if it exists.
     pub fn get(&self, idx: UniIndex) -> Option<&V> {
-        self.data.get(idx.idx as usize).and_then(Option::as_ref)
+        self.data.get(idx.idx.to_usize()).and_then(Option::as_ref)
     }
 
     /// Get the value at this index mutably, if it exists.
     pub fn get_mut(&mut self, idx: UniIndex) -> Option<&mut V> {
-        self.data.get_mut(idx.idx as usize).and_then(Option::as_mut)
+        self.data.get_mut(idx.idx.to_usize()).and_then(Option::as_mut)
     }
 
     /// Delete any value associated with this index.
     /// Returns None if the value was not present, otherwise
     /// returns the previously stored value.
     pub fn remove(&mut self, idx: UniIndex) -> Option<V> {
-        if idx.idx as usize >= self.data.len() {
+        if idx.idx.to_usize() >= self.data.len() {
             return None;
         }
         let mut res = None;
-        mem::swap(&mut res, &mut self.data[idx.idx as usize]);
+        mem::swap(&mut res, &mut self.data[idx.idx.to_usize()]);
         res
     }
 }
@@ -209,8 +211,8 @@ pub struct UniEntry<'a, V> {
 impl<'a, V> UniValMap<V> {
     /// Get a wrapper around a mutable access to the value corresponding to `idx`.
     pub fn entry(&'a mut self, idx: UniIndex) -> UniEntry<'a, V> {
-        self.extend_to_length(idx.idx as usize + 1);
-        UniEntry { inner: &mut self.data[idx.idx as usize] }
+        self.extend_to_length(idx.idx.to_usize() + 1);
+        UniEntry { inner: &mut self.data[idx.idx.to_usize()] }
     }
 }
 
diff --git a/src/tools/miri/src/concurrency/cpu_affinity.rs b/src/tools/miri/src/concurrency/cpu_affinity.rs
index b47b614cf5f..9583de5a483 100644
--- a/src/tools/miri/src/concurrency/cpu_affinity.rs
+++ b/src/tools/miri/src/concurrency/cpu_affinity.rs
@@ -25,7 +25,7 @@ impl CpuAffinityMask {
         let mut this = Self([0; Self::CPU_MASK_BYTES]);
 
         // the default affinity mask includes only the available CPUs
-        for i in 0..cpu_count as usize {
+        for i in 0..cpu_count.to_usize() {
             this.set(cx, i);
         }
 
diff --git a/src/tools/miri/src/concurrency/vector_clock.rs b/src/tools/miri/src/concurrency/vector_clock.rs
index 78858fcedae..494e7922d2b 100644
--- a/src/tools/miri/src/concurrency/vector_clock.rs
+++ b/src/tools/miri/src/concurrency/vector_clock.rs
@@ -7,6 +7,7 @@ use rustc_span::{DUMMY_SP, Span, SpanData};
 use smallvec::SmallVec;
 
 use super::data_race::NaReadType;
+use crate::helpers::ToUsize;
 
 /// A vector clock index, this is associated with a thread id
 /// but in some cases one vector index may be shared with
@@ -157,7 +158,7 @@ impl VClock {
 
     #[inline]
     pub(super) fn index_mut(&mut self, index: VectorIdx) -> &mut VTimestamp {
-        self.0.as_mut_slice().get_mut(index.to_u32() as usize).unwrap()
+        self.0.as_mut_slice().get_mut(index.to_u32().to_usize()).unwrap()
     }
 
     /// Get a mutable slice to the internal vector with minimum `min_len`
@@ -420,7 +421,7 @@ impl Index<VectorIdx> for VClock {
 
     #[inline]
     fn index(&self, index: VectorIdx) -> &VTimestamp {
-        self.as_slice().get(index.to_u32() as usize).unwrap_or(&VTimestamp::ZERO)
+        self.as_slice().get(index.to_u32().to_usize()).unwrap_or(&VTimestamp::ZERO)
     }
 }
 
diff --git a/src/tools/miri/src/helpers.rs b/src/tools/miri/src/helpers.rs
index 8e7c9edfcc0..ff2ec1b3e60 100644
--- a/src/tools/miri/src/helpers.rs
+++ b/src/tools/miri/src/helpers.rs
@@ -1412,3 +1412,26 @@ pub(crate) fn windows_check_buffer_size((success, len): (bool, u64)) -> u32 {
         u32::try_from(len).unwrap()
     }
 }
+
+/// We don't support 16-bit systems, so let's have ergonomic conversion from `u32` to `usize`.
+pub trait ToUsize {
+    fn to_usize(self) -> usize;
+}
+
+impl ToUsize for u32 {
+    fn to_usize(self) -> usize {
+        self.try_into().unwrap()
+    }
+}
+
+/// Similarly, a maximum address size of `u64` is assumed widely here, so let's have ergonomic
+/// converion from `usize` to `u64`.
+pub trait ToU64 {
+    fn to_u64(self) -> u64;
+}
+
+impl ToU64 for usize {
+    fn to_u64(self) -> u64 {
+        self.try_into().unwrap()
+    }
+}
diff --git a/src/tools/miri/src/intrinsics/simd.rs b/src/tools/miri/src/intrinsics/simd.rs
index c9250ba1b81..b17fd4fb7f9 100644
--- a/src/tools/miri/src/intrinsics/simd.rs
+++ b/src/tools/miri/src/intrinsics/simd.rs
@@ -634,7 +634,7 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
                 let index_len = index.len();
 
                 assert_eq!(left_len, right_len);
-                assert_eq!(index_len as u64, dest_len);
+                assert_eq!(u64::try_from(index_len).unwrap(), dest_len);
 
                 for i in 0..dest_len {
                     let src_index: u64 =
diff --git a/src/tools/miri/src/lib.rs b/src/tools/miri/src/lib.rs
index 0b7a067058b..9b3ec977c5d 100644
--- a/src/tools/miri/src/lib.rs
+++ b/src/tools/miri/src/lib.rs
@@ -41,14 +41,7 @@
     rustc::potential_query_instability,
     rustc::untranslatable_diagnostic,
 )]
-#![warn(
-    rust_2018_idioms,
-    unqualified_local_imports,
-    clippy::cast_possible_wrap, // unsigned -> signed
-    clippy::cast_sign_loss, // signed -> unsigned
-    clippy::cast_lossless,
-    clippy::cast_possible_truncation,
-)]
+#![warn(rust_2018_idioms, unqualified_local_imports, clippy::as_conversions)]
 // Needed for rustdoc from bootstrap (with `-Znormalize-docs`).
 #![recursion_limit = "256"]
 
@@ -140,7 +133,7 @@ pub use crate::eval::{
     AlignmentCheck, BacktraceStyle, IsolatedOp, MiriConfig, MiriEntryFnType, RejectOpWith,
     ValidationMode, create_ecx, eval_entry,
 };
-pub use crate::helpers::{AccessKind, EvalContextExt as _};
+pub use crate::helpers::{AccessKind, EvalContextExt as _, ToU64 as _, ToUsize as _};
 pub use crate::intrinsics::EvalContextExt as _;
 pub use crate::machine::{
     AllocExtra, DynMachineCallback, FrameExtra, MachineCallback, MemoryKind, MiriInterpCx,
diff --git a/src/tools/miri/src/shims/backtrace.rs b/src/tools/miri/src/shims/backtrace.rs
index 7e667e70a17..9f3bc06771f 100644
--- a/src/tools/miri/src/shims/backtrace.rs
+++ b/src/tools/miri/src/shims/backtrace.rs
@@ -25,7 +25,7 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
 
         let frame_count = this.active_thread_stack().len();
 
-        this.write_scalar(Scalar::from_target_usize(frame_count.try_into().unwrap(), this), dest)
+        this.write_scalar(Scalar::from_target_usize(frame_count.to_u64(), this), dest)
     }
 
     fn handle_miri_get_backtrace(
@@ -70,7 +70,7 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
             }
             1 =>
                 for (i, ptr) in ptrs.into_iter().enumerate() {
-                    let offset = ptr_layout.size.checked_mul(i.try_into().unwrap(), this).unwrap();
+                    let offset = ptr_layout.size.checked_mul(i.to_u64(), this).unwrap();
 
                     let op_place = buf_place.offset(offset, ptr_layout, this)?;
 
@@ -158,11 +158,11 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
             }
             1 => {
                 this.write_scalar(
-                    Scalar::from_target_usize(name.len().try_into().unwrap(), this),
+                    Scalar::from_target_usize(name.len().to_u64(), this),
                     &this.project_field(dest, 0)?,
                 )?;
                 this.write_scalar(
-                    Scalar::from_target_usize(filename.len().try_into().unwrap(), this),
+                    Scalar::from_target_usize(filename.len().to_u64(), this),
                     &this.project_field(dest, 1)?,
                 )?;
             }
diff --git a/src/tools/miri/src/shims/foreign_items.rs b/src/tools/miri/src/shims/foreign_items.rs
index 52c16a0c2e2..a81f459e5e1 100644
--- a/src/tools/miri/src/shims/foreign_items.rs
+++ b/src/tools/miri/src/shims/foreign_items.rs
@@ -639,7 +639,7 @@ trait EvalContextExtPriv<'tcx>: crate::MiriInterpCxExt<'tcx> {
                 let val = this.read_scalar(val)?.to_i32()?;
                 let num = this.read_target_usize(num)?;
                 // The docs say val is "interpreted as unsigned char".
-                #[expect(clippy::cast_sign_loss, clippy::cast_possible_truncation)]
+                #[expect(clippy::as_conversions)]
                 let val = val as u8;
 
                 // C requires that this must always be a valid pointer (C18 §7.1.4).
@@ -665,7 +665,7 @@ trait EvalContextExtPriv<'tcx>: crate::MiriInterpCxExt<'tcx> {
                 let val = this.read_scalar(val)?.to_i32()?;
                 let num = this.read_target_usize(num)?;
                 // The docs say val is "interpreted as unsigned char".
-                #[expect(clippy::cast_sign_loss, clippy::cast_possible_truncation)]
+                #[expect(clippy::as_conversions)]
                 let val = val as u8;
 
                 // C requires that this must always be a valid pointer (C18 §7.1.4).
@@ -676,7 +676,7 @@ trait EvalContextExtPriv<'tcx>: crate::MiriInterpCxExt<'tcx> {
                     .iter()
                     .position(|&c| c == val);
                 if let Some(idx) = idx {
-                    let new_ptr = ptr.wrapping_offset(Size::from_bytes(idx as u64), this);
+                    let new_ptr = ptr.wrapping_offset(Size::from_bytes(idx), this);
                     this.write_pointer(new_ptr, dest)?;
                 } else {
                     this.write_null(dest)?;
diff --git a/src/tools/miri/src/shims/native_lib.rs b/src/tools/miri/src/shims/native_lib.rs
index 837e1b31cac..1f44ed30b9a 100644
--- a/src/tools/miri/src/shims/native_lib.rs
+++ b/src/tools/miri/src/shims/native_lib.rs
@@ -94,14 +94,10 @@ trait EvalContextExtPriv<'tcx>: crate::MiriInterpCxExt<'tcx> {
         // Try getting the function from the shared library.
         // On windows `_lib_path` will be unused, hence the name starting with `_`.
         let (lib, _lib_path) = this.machine.native_lib.as_ref().unwrap();
-        let func: libloading::Symbol<'_, unsafe extern "C" fn()> = unsafe {
-            match lib.get(link_name.as_str().as_bytes()) {
-                Ok(x) => x,
-                Err(_) => {
-                    return None;
-                }
-            }
-        };
+        let func: libloading::Symbol<'_, unsafe extern "C" fn()> =
+            unsafe { lib.get(link_name.as_str().as_bytes()).ok()? };
+        #[expect(clippy::as_conversions)] // fn-ptr to raw-ptr cast needs `as`.
+        let fn_ptr = *func.deref() as *mut std::ffi::c_void;
 
         // FIXME: this is a hack!
         // The `libloading` crate will automatically load system libraries like `libc`.
@@ -116,7 +112,7 @@ trait EvalContextExtPriv<'tcx>: crate::MiriInterpCxExt<'tcx> {
         // using the `libc` crate where this interface is public.
         let mut info = std::mem::MaybeUninit::<libc::Dl_info>::uninit();
         unsafe {
-            if libc::dladdr(*func.deref() as *const _, info.as_mut_ptr()) != 0 {
+            if libc::dladdr(fn_ptr, info.as_mut_ptr()) != 0 {
                 let info = info.assume_init();
                 #[cfg(target_os = "cygwin")]
                 let fname_ptr = info.dli_fname.as_ptr();
@@ -129,8 +125,9 @@ trait EvalContextExtPriv<'tcx>: crate::MiriInterpCxExt<'tcx> {
                 }
             }
         }
+
         // Return a pointer to the function.
-        Some(CodePtr(*func.deref() as *mut _))
+        Some(CodePtr(fn_ptr))
     }
 }
 
diff --git a/src/tools/miri/src/shims/unix/android/thread.rs b/src/tools/miri/src/shims/unix/android/thread.rs
index 30ec0aefcbf..aa3a05ead85 100644
--- a/src/tools/miri/src/shims/unix/android/thread.rs
+++ b/src/tools/miri/src/shims/unix/android/thread.rs
@@ -7,7 +7,7 @@ use crate::helpers::check_min_vararg_count;
 use crate::shims::unix::thread::{EvalContextExt as _, ThreadNameResult};
 use crate::*;
 
-const TASK_COMM_LEN: usize = 16;
+const TASK_COMM_LEN: u64 = 16;
 
 pub fn prctl<'tcx>(
     ecx: &mut MiriInterpCx<'tcx>,
@@ -38,7 +38,7 @@ pub fn prctl<'tcx>(
             let [name] = check_min_vararg_count("prctl(PR_GET_NAME, ...)", varargs)?;
             let name = ecx.read_scalar(name)?;
             let thread = ecx.pthread_self()?;
-            let len = Scalar::from_target_usize(TASK_COMM_LEN as u64, ecx);
+            let len = Scalar::from_target_usize(TASK_COMM_LEN, ecx);
             ecx.check_ptr_access(
                 name.to_pointer(ecx)?,
                 Size::from_bytes(TASK_COMM_LEN),
diff --git a/src/tools/miri/src/shims/unix/freebsd/foreign_items.rs b/src/tools/miri/src/shims/unix/freebsd/foreign_items.rs
index 21a386b2927..c0872daee8d 100644
--- a/src/tools/miri/src/shims/unix/freebsd/foreign_items.rs
+++ b/src/tools/miri/src/shims/unix/freebsd/foreign_items.rs
@@ -24,7 +24,7 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
             // Threading
             "pthread_setname_np" => {
                 let [thread, name] = this.check_shim(abi, Conv::C, link_name, args)?;
-                let max_len = usize::MAX; // FreeBSD does not seem to have a limit.
+                let max_len = u64::MAX; // FreeBSD does not seem to have a limit.
                 let res = match this.pthread_setname_np(
                     this.read_scalar(thread)?,
                     this.read_scalar(name)?,
diff --git a/src/tools/miri/src/shims/unix/fs.rs b/src/tools/miri/src/shims/unix/fs.rs
index 1f6acff0787..fa8f84e3867 100644
--- a/src/tools/miri/src/shims/unix/fs.rs
+++ b/src/tools/miri/src/shims/unix/fs.rs
@@ -121,13 +121,13 @@ impl UnixFileDescription for FileHandle {
                 use std::os::windows::io::AsRawHandle;
 
                 use windows_sys::Win32::Foundation::{
-                    ERROR_IO_PENDING, ERROR_LOCK_VIOLATION, FALSE, HANDLE, TRUE,
+                    ERROR_IO_PENDING, ERROR_LOCK_VIOLATION, FALSE, TRUE,
                 };
                 use windows_sys::Win32::Storage::FileSystem::{
                     LOCKFILE_EXCLUSIVE_LOCK, LOCKFILE_FAIL_IMMEDIATELY, LockFileEx, UnlockFile,
                 };
 
-                let fh = self.file.as_raw_handle() as HANDLE;
+                let fh = self.file.as_raw_handle();
 
                 use FlockOp::*;
                 let (ret, lock_nb) = match op {
diff --git a/src/tools/miri/src/shims/unix/linux/foreign_items.rs b/src/tools/miri/src/shims/unix/linux/foreign_items.rs
index f5da7b0170b..51c2434d68a 100644
--- a/src/tools/miri/src/shims/unix/linux/foreign_items.rs
+++ b/src/tools/miri/src/shims/unix/linux/foreign_items.rs
@@ -14,7 +14,7 @@ use crate::*;
 // The documentation of glibc complains that the kernel never exposes
 // TASK_COMM_LEN through the headers, so it's assumed to always be 16 bytes
 // long including a null terminator.
-const TASK_COMM_LEN: usize = 16;
+const TASK_COMM_LEN: u64 = 16;
 
 pub fn is_dyn_sym(name: &str) -> bool {
     matches!(name, "statx")
@@ -96,7 +96,7 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
                 // In case of glibc, the length of the output buffer must
                 // be not shorter than TASK_COMM_LEN.
                 let len = this.read_scalar(len)?;
-                let res = if len.to_target_usize(this)? >= TASK_COMM_LEN as u64 {
+                let res = if len.to_target_usize(this)? >= TASK_COMM_LEN {
                     match this.pthread_getname_np(
                         this.read_scalar(thread)?,
                         this.read_scalar(name)?,
diff --git a/src/tools/miri/src/shims/unix/macos/foreign_items.rs b/src/tools/miri/src/shims/unix/macos/foreign_items.rs
index 5046e965082..0281bb9f71d 100644
--- a/src/tools/miri/src/shims/unix/macos/foreign_items.rs
+++ b/src/tools/miri/src/shims/unix/macos/foreign_items.rs
@@ -186,7 +186,7 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
                 let res = match this.pthread_setname_np(
                     thread,
                     this.read_scalar(name)?,
-                    this.eval_libc("MAXTHREADNAMESIZE").to_target_usize(this)?.try_into().unwrap(),
+                    this.eval_libc("MAXTHREADNAMESIZE").to_target_usize(this)?,
                     /* truncate */ false,
                 )? {
                     ThreadNameResult::Ok => Scalar::from_u32(0),
diff --git a/src/tools/miri/src/shims/unix/thread.rs b/src/tools/miri/src/shims/unix/thread.rs
index 3d990a1a042..4b6615b3ea8 100644
--- a/src/tools/miri/src/shims/unix/thread.rs
+++ b/src/tools/miri/src/shims/unix/thread.rs
@@ -86,7 +86,7 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
         &mut self,
         thread: Scalar,
         name: Scalar,
-        name_max_len: usize,
+        name_max_len: u64,
         truncate: bool,
     ) -> InterpResult<'tcx, ThreadNameResult> {
         let this = self.eval_context_mut();
@@ -99,9 +99,9 @@ pub trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
         let mut name = this.read_c_str(name)?.to_owned();
 
         // Comparing with `>=` to account for null terminator.
-        if name.len() >= name_max_len {
+        if name.len().to_u64() >= name_max_len {
             if truncate {
-                name.truncate(name_max_len.saturating_sub(1));
+                name.truncate(name_max_len.saturating_sub(1).try_into().unwrap());
             } else {
                 return interp_ok(ThreadNameResult::NameTooLong);
             }
diff --git a/src/tools/miri/src/shims/windows/fs.rs b/src/tools/miri/src/shims/windows/fs.rs
index 7561bf45219..0ac82d55b10 100644
--- a/src/tools/miri/src/shims/windows/fs.rs
+++ b/src/tools/miri/src/shims/windows/fs.rs
@@ -401,7 +401,7 @@ fn extract_windows_epoch<'tcx>(
         Some(time) => {
             let duration = ecx.system_time_since_windows_epoch(&time)?;
             let duration_ticks = ecx.windows_ticks_for(duration)?;
-            #[allow(clippy::cast_possible_truncation)]
+            #[expect(clippy::as_conversions)]
             interp_ok(Some((duration_ticks as u32, (duration_ticks >> 32) as u32)))
         }
         None => interp_ok(None),
diff --git a/src/tools/miri/src/shims/windows/handle.rs b/src/tools/miri/src/shims/windows/handle.rs
index eec6c62bebc..09dac9c1378 100644
--- a/src/tools/miri/src/shims/windows/handle.rs
+++ b/src/tools/miri/src/shims/windows/handle.rs
@@ -70,8 +70,7 @@ impl Handle {
             Self::Null => 0,
             Self::Pseudo(pseudo_handle) => pseudo_handle.value(),
             Self::Thread(thread) => thread.to_u32(),
-            #[expect(clippy::cast_sign_loss)]
-            Self::File(fd) => fd as u32,
+            Self::File(fd) => fd.cast_unsigned(),
             // INVALID_HANDLE_VALUE is -1. This fact is explicitly declared or implied in several
             // pages of Windows documentation.
             // 1: https://learn.microsoft.com/en-us/dotnet/api/microsoft.win32.safehandles.safefilehandle?view=net-9.0
@@ -124,11 +123,10 @@ impl Handle {
             Self::NULL_DISCRIMINANT if data == 0 => Some(Self::Null),
             Self::PSEUDO_DISCRIMINANT => Some(Self::Pseudo(PseudoHandle::from_value(data)?)),
             Self::THREAD_DISCRIMINANT => Some(Self::Thread(ThreadId::new_unchecked(data))),
-            #[expect(clippy::cast_possible_wrap)]
             Self::FILE_DISCRIMINANT => {
                 // This cast preserves all bits.
                 assert_eq!(size_of_val(&data), size_of::<FdNum>());
-                Some(Self::File(data as FdNum))
+                Some(Self::File(data.cast_signed()))
             }
             Self::INVALID_DISCRIMINANT => Some(Self::Invalid),
             _ => None,
@@ -156,8 +154,7 @@ impl Handle {
     pub fn to_scalar(self, cx: &impl HasDataLayout) -> Scalar {
         // 64-bit handles are sign extended 32-bit handles
         // see https://docs.microsoft.com/en-us/windows/win32/winprog64/interprocess-communication
-        #[expect(clippy::cast_possible_wrap)] // we want it to wrap
-        let signed_handle = self.to_packed() as i32;
+        let signed_handle = self.to_packed().cast_signed();
         Scalar::from_target_isize(signed_handle.into(), cx)
     }
 
@@ -171,9 +168,8 @@ impl Handle {
     ) -> InterpResult<'tcx, Result<Self, HandleError>> {
         let sign_extended_handle = handle.to_target_isize(cx)?;
 
-        #[expect(clippy::cast_sign_loss)] // we want to lose the sign
         let handle = if let Ok(signed_handle) = i32::try_from(sign_extended_handle) {
-            signed_handle as u32
+            signed_handle.cast_unsigned()
         } else {
             // if a handle doesn't fit in an i32, it isn't valid.
             return interp_ok(Err(HandleError::InvalidHandle));
diff --git a/src/tools/miri/src/shims/x86/gfni.rs b/src/tools/miri/src/shims/x86/gfni.rs
index 4774ec9f9d8..a91c74283fd 100644
--- a/src/tools/miri/src/shims/x86/gfni.rs
+++ b/src/tools/miri/src/shims/x86/gfni.rs
@@ -133,12 +133,12 @@ fn affine_transform<'tcx>(
 // This is a evaluated at compile time. Trait based conversion is not available.
 /// See <https://www.corsix.org/content/galois-field-instructions-2021-cpus> for the
 /// definition of `gf_inv` which was used for the creation of this table.
-#[expect(clippy::cast_possible_truncation)]
 static TABLE: [u8; 256] = {
     let mut array = [0; 256];
 
     let mut i = 1;
     while i < 256 {
+        #[expect(clippy::as_conversions)] // no `try_from` in const...
         let mut x = i as u8;
         let mut y = gf2p8_mul(x, x);
         x = y;
@@ -160,7 +160,7 @@ static TABLE: [u8; 256] = {
 /// polynomial representation with the reduction polynomial x^8 + x^4 + x^3 + x + 1.
 /// See <https://www.corsix.org/content/galois-field-instructions-2021-cpus> for details.
 // This is a const function. Trait based conversion is not available.
-#[expect(clippy::cast_possible_truncation)]
+#[expect(clippy::as_conversions)]
 const fn gf2p8_mul(left: u8, right: u8) -> u8 {
     // This implementation is based on the `gf2p8mul_byte` definition found inside the Intel intrinsics guide.
     // See https://www.intel.com/content/www/us/en/docs/intrinsics-guide/index.html#text=gf2p8mul
diff --git a/src/tools/miri/src/shims/x86/mod.rs b/src/tools/miri/src/shims/x86/mod.rs
index e57217dc6f2..ac59cc2dfeb 100644
--- a/src/tools/miri/src/shims/x86/mod.rs
+++ b/src/tools/miri/src/shims/x86/mod.rs
@@ -1110,7 +1110,7 @@ fn pmulhrsw<'tcx>(
 
         // The result of this operation can overflow a signed 16-bit integer.
         // When `left` and `right` are -0x8000, the result is 0x8000.
-        #[expect(clippy::cast_possible_truncation)]
+        #[expect(clippy::as_conversions)]
         let res = res as i16;
 
         ecx.write_scalar(Scalar::from_i16(res), &dest)?;
diff --git a/src/tools/miri/src/shims/x86/sha.rs b/src/tools/miri/src/shims/x86/sha.rs
index 6d2c151243c..23c83553f3b 100644
--- a/src/tools/miri/src/shims/x86/sha.rs
+++ b/src/tools/miri/src/shims/x86/sha.rs
@@ -43,7 +43,7 @@ pub(super) trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
             // We reverse the order because x86 is little endian but the copied implementation uses
             // big endian.
             for (i, part) in val.into_iter().rev().enumerate() {
-                let projected = &ecx.project_index(dest, i.try_into().unwrap())?;
+                let projected = &ecx.project_index(dest, i.to_u64())?;
                 ecx.write_scalar(Scalar::from_u32(part), projected)?;
             }
             interp_ok(())
diff --git a/src/tools/miri/src/shims/x86/sse42.rs b/src/tools/miri/src/shims/x86/sse42.rs
index 02336a722f7..66bff328626 100644
--- a/src/tools/miri/src/shims/x86/sse42.rs
+++ b/src/tools/miri/src/shims/x86/sse42.rs
@@ -440,7 +440,7 @@ pub(super) trait EvalContextExt<'tcx>: crate::MiriInterpCxExt<'tcx> {
                 let crc = if bit_size == 64 {
                     // The 64-bit version will only consider the lower 32 bits,
                     // while the upper 32 bits get discarded.
-                    #[expect(clippy::cast_possible_truncation)]
+                    #[expect(clippy::as_conversions)]
                     u128::from((left.to_u64()? as u32).reverse_bits())
                 } else {
                     u128::from(left.to_u32()?.reverse_bits())