Skip to content

Crash on MIR projection through slice reference (autoderef) #22760

Description

@Wilfred

I've been trying to investigate a crash with slice references. I've successfully minimised a repro and written a unit test:

#[test]
fn index_assignment_through_reference() {
    check_borrowck(
        r#"
pub fn f(xs: &mut [i32]) {
    xs[0usize] = 1;
}
    "#,
    );
}
$ RUST_BACKTRACE=1 cargo t -p hir-ty index_assign
    Finished `test` profile [unoptimized + debuginfo] target(s) in 0.54s
     Running unittests src/lib.rs (target/debug/deps/hir_ty-1dfab1f1e1155558)

running 1 test
test mir::lower::tests::index_assignment_through_reference ... FAILED

failures:

---- mir::lower::tests::index_assignment_through_reference stdout ----

thread 'mir::lower::tests::index_assignment_through_reference' (66052050) panicked at crates/hir-ty/src/mir.rs:1335:82:
called `Option::unwrap()` on a `None` value
stack backtrace:
   0: __rustc::rust_begin_unwind
             at /rustc/59807616e1fa2540724bfbac14d7976d7e4a3860/library/std/src/panicking.rs:689:5
   1: core::panicking::panic_fmt
             at /rustc/59807616e1fa2540724bfbac14d7976d7e4a3860/library/core/src/panicking.rs:80:14
   2: core::panicking::panic
             at /rustc/59807616e1fa2540724bfbac14d7976d7e4a3860/library/core/src/panicking.rs:150:5
   3: core::option::unwrap_failed
             at /rustc/59807616e1fa2540724bfbac14d7976d7e4a3860/library/core/src/option.rs:2236:5
   4: core::option::Option<T>::unwrap
             at /Users/wilfred/.rustup/toolchains/stable-aarch64-apple-darwin/lib/rustlib/src/rust/library/core/src/option.rs:1016:21
   5: hir_ty::mir::PlaceTy::projection_ty_core
             at ./src/mir.rs:1335:82
   6: hir_ty::mir::PlaceTy::projection_ty
             at ./src/mir.rs:1289:14
   7: hir_ty::mir::borrowck::place_case
             at ./src/mir/borrowck.rs:441:17
   8: hir_ty::mir::borrowck::mutability_of_locals
             at ./src/mir/borrowck.rs:582:27

It's definitely a bug, and I think it's an issue with autoderef. I'm not sure what the correct fix is.

I could check for None instead of unwrapping here:

ProjectionElem::Index(_) | ProjectionElem::ConstantIndex { .. } => {
PlaceTy::from_ty(structurally_normalize(self.ty).builtin_index().unwrap())
}

but that feels wrong -- shouldn't MIR have autoderef logic already?

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions