Skip to content
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

Disallow subtyping between T and U in T: Unsize<U>. #40319

Merged
merged 3 commits into from
Mar 12, 2017

Conversation

eddyb
Copy link
Member

@eddyb eddyb commented Mar 7, 2017

Because &mut T can be coerced to &mut U, T and U must be unified invariantly. Fixes #40288.
E.g. coercing &mut [&'a X; N] to &mut [&'b X] must require 'a be equal to 'b, otherwise you can convert between &'a X and &'b X (in either direction), potentially unsoundly lengthening lifetimes.

Subtyping here was introduced with Unsize in #24619 (landed in 1.1, original PR is #23785).

@rust-highfive
Copy link
Collaborator

r? @nrc

(rust_highfive has picked a reviewer for you, use r? to override)

@eddyb eddyb requested a review from nikomatsakis March 7, 2017 14:35
@eddyb eddyb added the S-waiting-on-crater Status: Waiting on a crater run to be completed. label Mar 7, 2017
@eddyb
Copy link
Member Author

eddyb commented Mar 7, 2017

(starting crater run now)

@nikomatsakis
Copy link
Contributor

r? @nikomatsakis

@rust-highfive rust-highfive assigned nikomatsakis and unassigned nrc Mar 7, 2017
@nikomatsakis
Copy link
Contributor

The code looks good to me, curious to hear the results of the crater run. I'll try to do a quick skim through the code to convince myself that these are all the relevant cases though.

@eddyb eddyb force-pushed the it's-"unsize"-not-"unsound" branch from 152f1c7 to 608d080 Compare March 8, 2017 12:44
let coercion = Coercion(self.cause.span);
let r_borrow = self.next_region_var(coercion);
(mt_a.ty, Some(AutoBorrow::Ref(r_borrow, mt_b.mutbl)))
// For `&T`, we don't reborrow, (which is only needed
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Don't you need this also on the raw ptr path? better to subtype source as one unit.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Subtype first, then resolve the variable, then reborrow from &mut and/or to raw pointers?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Aaaaah, that would also keep Rc working! I'll try to do it that way and add more testcases.

@eddyb eddyb force-pushed the it's-"unsize"-not-"unsound" branch from 608d080 to 721f5b8 Compare March 8, 2017 19:04
@eddyb
Copy link
Member Author

eddyb commented Mar 8, 2017

Crater report shows 6 3 root regressions:

EDIT: some were false positives, see #40319 (comment)

@Stebalien
Copy link
Contributor

similar/same crate as mime_multipart?

Different crates but the issue in both stems from the httparse bug (the original bug linked in the first post). Those are both legitimate UB (I can't tell with the other bugs).

@eddyb
Copy link
Member Author

eddyb commented Mar 8, 2017

@Stebalien I hadn't even realized that was the original report! Alright, I'm more confident now.
I've only looked in depth at crayon (AFAICT there's some lifetime parameter order confusion).

Assuming only {mime_},multipart and valico have any dependents, we should be able to release fixed patch versions of them (if it's possible at all without changing the API), and that will be that.

@eddyb
Copy link
Member Author

eddyb commented Mar 8, 2017

So the crates that other crates depend on are:

  • @mikedilger's mime_multipart (needs fix and 0.3.6 and 0.4.1 released)
  • @abonander's multipart (needs fix and 0.9.1 released)

Everything else we can break without having a cascade of regressions.
I may attempt making PRs to some of the crates, but they're pretty tough to understand.

@abonander
Copy link
Contributor

I've already got this fixed in multipart 0.10.1 so it's trivial to backport.

@eddyb
Copy link
Member Author

eddyb commented Mar 8, 2017

@abonander (and everyone else) Ping me when you have the fix on a branch somewhere, or a patch in a gist, etc. if you want a confirmation that it indeed compiles with the changes in this PR.

@abonander
Copy link
Contributor

@eddyb branch 0.9 has the fix backported. I'll publish once you confirm.

@eddyb
Copy link
Member Author

eddyb commented Mar 8, 2017

@abonander It compiles 👍

@abonander
Copy link
Contributor

@eddyb Published.

@mikedilger
Copy link
Contributor

@eddyb Not sure I understand the bug very well, but I hope a simple sub-scope makes the borrow issue go away. Let me know if thats right or if I need some other fix. https://github.com/mikedilger/mime-multipart/tree/rust40288

@eddyb
Copy link
Member Author

eddyb commented Mar 8, 2017

@mikedilger Almost! I was getting confused by not knowing what is actually keeping the borrow alive.
Turns out your change is in the right direction, you just have to also move header_memory in that block.
That should work on both 0.4.0 (master) and 0.3.5 (b118d606feb62c15d0dbd4e3280597a02e004190).

@mikedilger
Copy link
Contributor

@eddyb Ok, I (evilly) force-pushed https://github.com/mikedilger/mime-multipart/tree/rust40288 and also created https://github.com/mikedilger/mime-multipart/tree/rust40288_03 for the 0.3 branch. Once they are confirmed to work I'll pull them in and publish new versions.

@eddyb
Copy link
Member Author

eddyb commented Mar 8, 2017

@mikedilger Those do indeed work, thank you!

@mikedilger
Copy link
Contributor

@eddyb Published.

// or `Rc<[&'static T; N]>` to `Rc<[&'a T]>`, etc.
let coercion = TypeVariableOrigin::MiscVariable(self.cause.span);
let super_source = self.next_ty_var(coercion);
match self.sub_types(false, &self.cause, source, super_source)? {
Copy link
Member Author

@eddyb eddyb Mar 9, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not needing use_lub felt wrong, and it is! Reordering these two match arms "fixes" the false positive, but both orders should work identically.
I'm preparing an improved version that should not have this problem.

@eddyb eddyb mentioned this pull request Mar 9, 2017
arielb1 pushed a commit to arielb1/rust that referenced this pull request Mar 11, 2017
…r=nikomatsakis

Disallow subtyping between T and U in T: Unsize<U>.

Because `&mut T` can be coerced to `&mut U`, `T` and `U` must be unified invariantly. Fixes rust-lang#40288.
E.g. coercing `&mut [&'a X; N]` to `&mut [&'b X]` must require `'a` be equal to `'b`, otherwise you can convert between `&'a X` and `&'b X` (in either direction), potentially unsoundly lengthening lifetimes.

Subtyping here was introduced with `Unsize` in rust-lang#24619 (landed in 1.1, original PR is rust-lang#23785).
bors added a commit that referenced this pull request Mar 11, 2017
Rollup of 13 pull requests

- Successful merges: #40146, #40299, #40315, #40319, #40344, #40345, #40367, #40372, #40373, #40385, #40400, #40404, #40431
- Failed merges:
arielb1 pushed a commit to arielb1/rust that referenced this pull request Mar 11, 2017
…r=nikomatsakis

Disallow subtyping between T and U in T: Unsize<U>.

Because `&mut T` can be coerced to `&mut U`, `T` and `U` must be unified invariantly. Fixes rust-lang#40288.
E.g. coercing `&mut [&'a X; N]` to `&mut [&'b X]` must require `'a` be equal to `'b`, otherwise you can convert between `&'a X` and `&'b X` (in either direction), potentially unsoundly lengthening lifetimes.

Subtyping here was introduced with `Unsize` in rust-lang#24619 (landed in 1.1, original PR is rust-lang#23785).
bors added a commit that referenced this pull request Mar 12, 2017
Rollup of 12 pull requests

- Successful merges: #40146, #40299, #40315, #40319, #40344, #40345, #40372, #40373, #40400, #40404, #40419, #40431
- Failed merges:
@bors bors merged commit cfb41ae into rust-lang:master Mar 12, 2017
@eddyb eddyb deleted the it's-"unsize"-not-"unsound" branch March 12, 2017 09:36
@brson brson added the relnotes Marks issues that should be documented in the release notes of the next release. label Apr 4, 2017
qnighy added a commit to qnighy/rust that referenced this pull request Jun 29, 2017
qnighy added a commit to qnighy/rust that referenced this pull request Jun 29, 2017
qnighy added a commit to qnighy/rust that referenced this pull request Jun 29, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
relnotes Marks issues that should be documented in the release notes of the next release.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

10 participants