Uh oh!
There was an error while loading. Please reload this page.
permit negative impls for non-auto traits - #68004
Conversation
rust-highfive
commented
Jan 8, 2020
Some changes occurred in diagnostic error codes |
rust-highfive
commented
Jan 8, 2020
r? @varkor (rust_highfive has picked a reviewer for you, use r? to override) |
This comment has been minimized.
This comment has been minimized.
Aaron1011
commented
Jan 8, 2020
@nikomatsakis: How does this relate to reservation impls? |
This comment has been minimized.
This comment has been minimized.
nikomatsakis
commented
Jan 8, 2020
A negative impl is a semver commitment never to implement the given trait for the given type. It should eventually mean that you can rely on the impl not existing for the purposes of negative reasoning in coherence, though this PR doesn't implement that. What this PR does is simply require that no negative and positive impls (for the same trait) can overlap. This means that you can rely on an impl not existing for the purpose of proving soundness, and in particular for proving A reservation impl is...something harder to express. It is considered a kind of "ambiguous" impl -- it doesn't exist yet, but it might exist in the future. This prevents people from assuming negatively that it would never exist. But it doesn't prevent you from writing overlapping impls. |
e3a0b47 to
e16b360Compare
This comment has been minimized.
This comment has been minimized.
e16b360 to
c6875fdComparenikomatsakis
commented
Jan 8, 2020
@comex do you think you could provide me with "clean, minimized versions" of your exploits? The code in this playground is rather complex .. I'd prefer to have three or four simple tests I can add for regression tests. They don't have to be fully weaponized necessarily, either -- something like what @withoutboats did would be perfect. (In particular, I believe we need a negative |
c6875fd to
e2a82faComparewithoutboats
commented
Jan 8, 2020
@nikomatsakis I can provide minimal examples for both DerefMut and Clone. Here they are: DerefMut for shared reference: https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=7d0c6cef76960efecd8e9afd3a851443 Clone for mutable reference: https://play.rust-lang.org/?version=stable&mode=debug&edition=2018&gist=55430b595a04fa05c52fb6abe024d5e8 (You'll notice these work almost exactly the same way.) For CoerceUnsized I don't have a sample ready, but I think fixing CoerceUnsized should be tracked separately, possibly even opening a separate issue from #66544 |
nikomatsakis
commented
Jan 8, 2020
withoutboats
commented
Jan 8, 2020
Yea I think it'd be better to track the coerceunsized problem as "we added an unchecked invariant to implementing coerceunsized but didnt mark the trait unsafe," just separate from this coherence hole issue. |
This comment has been minimized.
This comment has been minimized.
e2a82fa to
83d1c33Compare
This comment has been minimized.
This comment has been minimized.
fa21734 to
a10769aComparenikomatsakis
commented
Jan 8, 2020
I've removed the WIP, I think this PR is roughly ready to land, though I think it merits an FCP and a more detailed write-up of (a) the semantics of what is happening I can try to get to that in a bit. |
a10769a to
4663d8fCompare
varkor
left a comment
There was a problem hiding this comment.
The implementation looks good. The diagnostics around negative trait bounds in general could be improved, but that can be left as a follow up.
Uh oh!
There was an error while loading. Please reload this page.
varkor
commented
Jan 8, 2020
It might also be worth putting negative impls for non-auto traits behind a separate feature flag to |
nikomatsakis
commented
Jan 8, 2020
Ah yeah, I meant to add "new feature flag" to the checklist |
Lokathor
commented
Jan 8, 2020
The "stable" version number should be 1.41 or whenever this actually gets to stable. This might sound silly to say but sometimes version strings like this have gone unnoticed so I thought i'd just throw in a reminder. |
Do we want to do a crater run for this? On one hand, I would be shocked if anyone ever wrote this kind of bizarre impl in real code. On the other hand, if someone did write such an impl, it would be good to know that there exists code in the wild that will be permanently broken by this. |
1515754 to
011215bComparenikomatsakis
commented
Mar 26, 2020
@bors r=varkor |
bors
commented
Mar 26, 2020
📌 Commit 0d07026 has been approved by |
bors
commented
Mar 26, 2020
⌛ Testing commit 0d07026 with merge 8599f89a0f86493bfe6d12bc1a1f0a09d86818eb... |
Centril
commented
Mar 26, 2020
@bors retry |
Rollup of 5 pull requests Successful merges: - rust-lang#68004 (permit negative impls for non-auto traits) - rust-lang#70385 (Miri nits: comment and var name improvement) - rust-lang#70411 (Fix for rust-lang#62691: use the largest niche across all fields) - rust-lang#70417 (parser: recover on `...` as a pattern, suggesting `..`) - rust-lang#70424 (simplify match stmt) Failed merges: r? @ghost
bors
commented
Mar 26, 2020
| #![feature(optin_builtin_traits)] | ||
| struct TestType; | ||
| trait TestTrait { | ||
| fn dummy(&self) { } | ||
| } | ||
| impl !TestTrait for TestType {} | ||
| //~^ ERROR invalid negative impl | ||
| fn main() {} |
There was a problem hiding this comment.
Shouldn't a test for this without the feature flag remain?
This is a prototype impl that extends
impl !Traitbeyond auto traits. It is not integrated with coherence or anything else, and hence only serves to prevent downstream impls (but not to allow downstream crates to rely on the absence of such impls for coherence purposes).Fixes#66544
TODO:
Clonein order to fully fixPinis unsound due to rogue Deref/DerefMut implementations #66544CoerceUnsizedunsafe? -- that problem is now split out intoPinis unsound due to transitive effects ofCoerceUnsized#68015