rust-embedded / rust-i2cdev

Rust library for interfacing with i2c devices under Linux
Apache License 2.0
205 stars 53 forks source link

Fix unsound lifetime on LinuxI2CMessage #78

Closed kevinmehall closed 1 year ago

kevinmehall commented 1 year ago

The following code currently compiles, but passes a dangling pointer to the kernel, which will write to deallocated memory.

extern crate i2cdev;

use i2cdev::core::*;
use i2cdev::linux::{LinuxI2CBus, LinuxI2CMessage};

const SLAVE_ADDR: u16 = 0x57;

fn main() {
    let mut dev = LinuxI2CBus::new("/dev/i2c-1").unwrap();

    let mut v = vec![0, 0, 0];

    let mut msgs = [
        LinuxI2CMessage::write(&[0x01]).with_address(SLAVE_ADDR),
        LinuxI2CMessage::read(&mut v).with_address(SLAVE_ADDR),
    ];

    drop(v);
    // Now pointer in in the message is pointing to the deallocated Vec

    dev.transfer(&mut msgs).unwrap();
}

The lifetime parameter on the type alias doesn't do anything (arguably a rustc bug that this is not an error). The internal i2c_msg type without a lifetime parameter of its own does not actually enforce that the borrowed buffer is still valid at the time it is passed to the ioctl.

kevinmehall commented 1 year ago

Updated

kevinmehall commented 1 year ago

Actually regex requires Rust 1.60.0. Updated the MSRV for that.

bors[bot] commented 1 year ago

Build succeeded!

The publicly hosted instance of bors-ng is deprecated and will go away soon.

If you want to self-host your own instance, instructions are here. For more help, visit the forum.

If you want to switch to GitHub's built-in merge queue, visit their help page.