Skip to content

Missing lifetime specifier on Label #11

@t1mlange

Description

@t1mlange

Hi,

the following safe Rust code

// Requires root
fn main() -> anyhow::Result<()> {
    let label;
    {
        let ctx = fdisk::Context::new();
        ctx.assign_device("/dev/nvme2n1", true)?;
        label = ctx.get_label("")?;
        println!("Label: {:?}", label.get_name());
    }
    println!("Label: {:?}", label.get_name());

    Ok(())
}

leads to a use-after-free on the label. In this specific case, I then encounter a segfault while converting the CString to a Rust String.

After the last Context reference goes out of scope, the context also free's all subobjects, including the label. One way to fix the unsoundness is to restrict the label's lifetime to the context it has been derived from, allowing rustc to correctly reject the unsafe program from above, but is slightly more restrictive than the C implementation (would also reject unref'ing the context used to get the label even though another context reference is still in scope).

pub struct Label<'ctx> {
    pub(crate) ptr: *mut fdisk_sys::fdisk_label,
    marker: PhantomData<&'ctx Context>
}

Otherwise, you could also reference-count the context also in Rust, preventing an early free during runtime.

Kind Regards,
Tim

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions