rust: i2c: remove TryFrom<&Device> implementation for &I2cClient

A single fix for the Rust I2C abstractions, targeting 7.4.
 
 Removes an unsound TryFrom<&Device<Ctx>> conversion whose input and
 output reference lifetimes were not tied together, letting safe Rust
 upgrade a short-lived &Device borrow into an arbitrarily long-lived
 &I2cClient that could outlive the underlying device's removal
 (use-after-free, reported with a KASAN reproducer). The conversion
 had no users, so it's simply removed rather than lifetime-fixed.
 
 Signed-off-by: Nicolás Antinori <nico.antinori.7@gmail.com>
 Signed-off-by: Igor Korotin <igor.korotin@linux.dev>
 -----BEGIN PGP SIGNATURE-----
 
 iQIzBAABCgAdFiEEG0Kepq7dYk2deNuvoxQiWQ2T6tUFAmrY7ZwACgkQoxQiWQ2T
 6tWm8A//e1M0pmxKIX63Xqkh6BriHwz7YNQ4gIQPXc3GMxTJJvbqmB7uHSh52N8a
 frpH8i6YWyR84oA2nQeEAW3RI6jA+EWyGXNnTy9LWc6JvL7xqWPagyKJH4ELwchg
 C1zgx8EFlP99jj4bdSvC2Spg6TF9GgBvmJYzRMewlJ+4kyLte/MVpYNibe+vhu4w
 a/NxUO2yGHx66JtrjU4eLGM8rYS1R9PZNQSCABcYNPYfnW/oMK94xUmAXMaMYLN8
 UnLo7zSGWxQNxhrHdpxsI3XxtRdyZKAU6BzMnDXZuGX9PzABD1RxiZxpWRiEwU6u
 5cGjis4idiUrNlxS00muulMe1BPBCTw+C7rtzYP1JAB1ZnUFiy/jycqKEWh7G3HD
 jKuKfH667HwICUvVmq9npgGQIvJ6yZK4/TwXHms7rZVUC5WdzE5wcoifoduOfeEe
 2Jb0crgUWXPcABXW2R4KgIMwhWezyeuIeEABvj9lU39B1RuFVzTC+dg9C+LhjOZc
 J0lihLG4bNjvYMvHRZ7/M8ZQs+PXaDL/W9Uzkz7VxZmB9cT27QYutaRBKkLb05Ag
 fdGB1CHC6CPg8oCNdv9fbyVGaDJMPI55TIHFz2bddv+GnbdDKnYluwvJWi2ZeTtN
 MTIuXWiZ6TPpvMZgXmB5MYFJ3lP5OlG5iThwNZq3mVru6IU6Q84=
 =fBHR
 -----END PGP SIGNATURE-----
gpgsig -----BEGIN PGP SIGNATURE-----
 
 iHUEABYKAB0WIQScDfrjQa34uOld1VLaeAVmJtMtbgUCatuNdgAKCRDaeAVmJtMt
 bsnuAP9HLeI64YJQxEfITQyoFhm0/Ei3/1CSXmXB0y8dgOPe8gEA+B0CV1gXDzEC
 2TsauTYZziBKyyQ9UwCWXAT0LM7k/Q4=
 =xPdy
 -----END PGP SIGNATURE-----

Merge tag 'rust-i2c-for-7.4' into i2c/i2c

A single fix for the Rust I2C abstractions

* tag 'rust-i2c-for-7.4':
  rust: i2c: remove TryFrom<&Device> implementation for &I2cClient
This commit is contained in:
Andi Shyti 2026-10-23 18:36:39 +02:00
commit f0e53c16b1

View File

@ -5,7 +5,6 @@
// I2C Driver abstractions.
use crate::{
acpi,
container_of,
device,
device_id::{
RawDeviceId,
@ -517,26 +516,6 @@ fn as_ref(&self) -> &device::Device<Ctx> {
}
}
impl<Ctx: device::DeviceContext> TryFrom<&device::Device<Ctx>> for &I2cClient<Ctx> {
type Error = kernel::error::Error;
fn try_from(dev: &device::Device<Ctx>) -> Result<Self, Self::Error> {
// SAFETY: By the type invariant of `Device`, `dev.as_raw()` is a valid pointer to a
// `struct device`.
if unsafe { bindings::i2c_verify_client(dev.as_raw()).is_null() } {
return Err(EINVAL);
}
// SAFETY: We've just verified that the type of `dev` equals to
// `bindings::i2c_client_type`, hence `dev` must be embedded in a valid
// `struct i2c_client` as guaranteed by the corresponding C code.
let idev = unsafe { container_of!(dev.as_raw(), bindings::i2c_client, dev) };
// SAFETY: `idev` is a valid pointer to a `struct i2c_client`.
Ok(unsafe { &*idev.cast() })
}
}
// SAFETY: A `I2cClient` is always reference-counted and can be released from any thread.
unsafe impl Send for I2cClient {}