Skip to content

Stacked Borrows: Retag (private) fields of ADTs? #125

Closed

Description

The following code currently gets rejected by Miri:

use std::cell::{RefCell, Ref};

fn break_it(rc: &RefCell<i32>, r: Ref<'_, i32>) {
    // `r` has a shared reference, it is passed in as argument and hence
    // a protector is added that marks this memory as read-only for the entire
    // duration of this function.
    drop(r);
    // *oops* here we can mutate that memory.
    *rc.borrow_mut() = 2;
}

fn main() {
    let rc = RefCell::new(0);
    break_it(&rc, rc.borrow())
}

A similar issue exists with RefMut, and vec_deque::Drain also has this problem.

In each of these cases, a protector gets added for a reference that is stored in a private field, and that reference gets invalidated while the protector is still active.

Another way to phrase is: Are types allowed to "lie" about the lifetime of references stored in private fields? Also see rust-lang/rust-memory-model#5.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Assignees

No one assigned

    Labels

    A-aliasing-modelTopic: Related to the aliasing model (e.g. Stacked/Tree Borrows)C-open-questionCategory: An open question that we should revisitS-pending-designStatus: Resolving this issue requires addressing some open design questions

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions