Skip to content

normalize in MIR borrowck doesn't normalize, breaking soundness fix #146

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
lcnr opened this issue Jan 21, 2025 · 1 comment
Closed

normalize in MIR borrowck doesn't normalize, breaking soundness fix #146

lcnr opened this issue Jan 21, 2025 · 1 comment

Comments

@lcnr
Copy link
Contributor

lcnr commented Jan 21, 2025

affected test

  • tests/ui/nll/check-normalized-sig-for-wf.rs

This test passes again:

// <https://github.com/rust-lang/rust/issues/114936>
fn whoops(
    s: String,
    f: impl for<'s> FnOnce(&'s str) -> (&'static str, [&'static &'s (); 0]),
) -> &'static str
{
    f(&s).0
    //~^ ERROR `s` does not live long enough
}

// <https://github.com/rust-lang/rust/issues/118876>
fn extend<T>(input: &T) -> &'static T {
    struct Bounded<'a, 'b: 'static, T>(&'a T, [&'b (); 0]);
    let n: Box<dyn FnOnce(&T) -> Bounded<'static, '_, T>> = Box::new(|x| Bounded(x, []));
    n(input).0
    //~^ ERROR borrowed data escapes outside of function
}

// <https://github.com/rust-lang/rust/issues/118876>
fn extend_mut<'a, T>(input: &'a mut T) -> &'static mut T {
    struct Bounded<'a, 'b: 'static, T>(&'a mut T, [&'b (); 0]);
    let mut n: Box<dyn FnMut(&mut T) -> Bounded<'static, '_, T>> = Box::new(|x| Bounded(x, []));
    n(input).0
    //~^ ERROR borrowed data escapes outside of function
}

fn main() {}

https://github.com/rust-lang/rust/blob/ebbe63891f1fae21734cb97f2f863b08b1d44bf8/compiler/rustc_borrowck/src/type_check/mod.rs#L1097-L1111

@lcnr lcnr moved this to in progress in -Znext-solver=globally Jan 29, 2025
bors added a commit to rust-lang-ci/rust that referenced this issue Feb 12, 2025
…t-solver, r=lcnr

Properly deeply normalize in the next solver

Turn deep normalization into a `TypeOp`. In the old solver, just dispatch to the `Normalize` type op, but in the new solver call `deeply_normalize`. I chose to separate it into a different type op b/c some normalization is a no-op in the new solver, so this distinguishes just the normalization we need for correctness.

Then use `DeeplyNormalize` in the callsites we used to be using a `CustomTypeOp` (for normalizing known type outlives obligations), and also use it to normalize function args and impl headers in the new solver.

Finally, use it to normalize signatures for WF checks in the new solver as well. This addresses rust-lang/trait-system-refactor-initiative#146.
@lcnr
Copy link
Contributor Author

lcnr commented Feb 12, 2025

fixed by rust-lang/rust#136074

@lcnr lcnr closed this as completed Feb 12, 2025
@lcnr lcnr moved this from in progress to done in -Znext-solver=globally Feb 12, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
Development

No branches or pull requests

2 participants