Skip to content

ignore uninhabited non-exhaustive variant fields - #65414

Merged
bors merged 1 commit into
rust-lang:masterfrom
davidtwco:issue-65157-non-exhaustive-always-useful
Oct 25, 2019
Merged

ignore uninhabited non-exhaustive variant fields#65414
bors merged 1 commit into
rust-lang:masterfrom
davidtwco:issue-65157-non-exhaustive-always-useful

Conversation

@davidtwco

@davidtwcodavidtwco commented Oct 14, 2019

Copy link
Copy Markdown
Member

Fixes#65157.

This PR modifies the uninhabitedness checking so that the fields of
a non-exhaustive variant (which is not local) are ignored if they are
uninhabited. This is an improvement over the previous behaviour which
considered all non-local non-exhaustive variants useful because
unreachable patterns are now detected.

r? @arielb1
cc @varkor

@rust-highfiverust-highfive added the S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. label Oct 14, 2019
@davidtwco

Copy link
Copy Markdown
MemberAuthor

I'm not sure if this is the best way to fix this, so I'm happy to take an alternate approach if anyone has a better solution.

@Nadrieril

Copy link
Copy Markdown
Member

Yeah, I'd think there must be a better solution.
What was the original reason that tuple variants with non-exhaustive fields should be treated differently ? I couldn't understand why you originally added that line of code

@Centril

Copy link
Copy Markdown
Contributor

What was the original reason that tuple variants with non-exhaustive fields should be treated differently ? I couldn't understand why you originally added that line of code

The idea is that with #![feature(exhaustive_patterns)], inhabitedness becomes structural rather than taking visibility into account (iirc). That is, for any type (sum or product), the inhabitedness of a type in crate A would leak to the external crate B which would be observable when matching on the type from A inside B. In #60529, the point was to make a #[non_exhaustive] be regarded as inhabited outside of the current crate no matter if it is an enum or a product type (see #60529 (comment)).

@Nadrieril

Copy link
Copy Markdown
Member

So this is about ignoring uninhabitedness when the variant is marked non_exhaustive and not local ? Then I think we should be able to find the code that checks whether a variant is inhabited and tweak that. I can't seem to find what part of the code does that however; I'll keep looking.

@Nadrieril

Copy link
Copy Markdown
Member

Okay I figured it out. I'll take this line as an example:

whileletPartiallyInhabitedVariants::Struct{ x, .. } = partially_inhabited_variant(){

That line would be detected as unreachable if the variant wasn't declared non_exhaustive. The reason for this behaviour is that we start with v = [PartiallyInhabitedVariants::Struct { x, .. }], then we specialize it by the PartiallyInhabitedVariants::Struct constructor. Then v = [_] where the wildcard has type !. So it is detected as unreachable.

We can't avoid expanding PartiallyInhabitedVariants::Struct into its fields altogether, otherwise we would incorrectly think the second branch is unreachable here: (Enum taken from #65157):

match Enum::Unit {
Enum::Unit => {}
Enum::Struct { x: true, .. } => {}
Enum::Struct { x: false, .. } => {}
}

So I'd say a good solution might be to specifically ignore the fields of PartiallyInhabitedVariants::Struct that are of an uninhabited type.

Does that make sense ?

PS: @davidtwco would you mind waiting for #65160 to get merged before merging this PR ? Otherwise I'd have to rebase the fix and it will be a pain.

@davidtwco

Copy link
Copy Markdown
MemberAuthor

Does that make sense ?

I haven’t read this yet, will do later.

PS: @davidtwco would you mind waiting for #65160 to get merged before merging this PR ? Otherwise I'd have to rebase the fix and it will be a pain.

No worries, I just wanted to put something up to get review.

@davidtwco
davidtwcoforce-pushed the issue-65157-non-exhaustive-always-useful branch from 11a0114 to dd5bd7bCompareOctober 18, 2019 20:34
@davidtwco

Copy link
Copy Markdown
MemberAuthor

Thanks @Nadrieril, I've updated the PR with your suggested approach.

@davidtwcodavidtwco changed the title uninhabited: non-exhaustive variants useful onceignore uninhabited non-exhaustive variant fieldsOct 18, 2019
@bors

This comment has been minimized.

@davidtwco
davidtwcoforce-pushed the issue-65157-non-exhaustive-always-useful branch from dd5bd7b to 1bf1236CompareOctober 20, 2019 15:18
@davidtwco

Copy link
Copy Markdown
MemberAuthor

r? @varkor

@rust-highfiverust-highfive assigned varkor and unassigned arielb1Oct 21, 2019
@varkorvarkor added S-blocked Status: Blocked on something else such as an RFC or other implementation work. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Oct 21, 2019
Comment threadsrc/librustc_mir/hair/pattern/_match.rs Outdated
This commit modifies the uninhabitedness checking so that the fields of
a non-exhaustive variant (which is not local) are ignored if they are
uninhabited. This is an improvement over the previous behaviour which
considered all non-local non-exhaustive variants useful because
unreachable patterns are now detected.
Signed-off-by: David Wood <david@davidtw.co>
@davidtwco
davidtwcoforce-pushed the issue-65157-non-exhaustive-always-useful branch from 1bf1236 to 7ffbd62CompareOctober 23, 2019 21:29
@davidtwco

Copy link
Copy Markdown
MemberAuthor

@varkor perhaps we should consider this unblocked and proceed with review and merging? - #65160 is already conflicted, this PR is quite small, and this PR is blocking RFC 2008’s stabilisation in #64639.

@CentrilCentril added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. and removed S-blocked Status: Blocked on something else such as an RFC or other implementation work. labels Oct 24, 2019
@Centril

Copy link
Copy Markdown
Contributor

Sounds reasonable; it does enhance the rationale for @Nadrieril to split their PR into parts. ;)

@varkor

Copy link
Copy Markdown
Contributor

@bors r+ rollup

@bors

bors commented Oct 24, 2019

Copy link
Copy Markdown
Collaborator

📌 Commit 7ffbd62 has been approved by varkor

@borsbors added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Oct 24, 2019
Centril added a commit to Centril/rust that referenced this pull request Oct 25, 2019
…e-always-useful, r=varkor
ignore uninhabited non-exhaustive variant fields
Fixesrust-lang#65157.
This PR modifies the uninhabitedness checking so that the fields of
a non-exhaustive variant (which is not local) are ignored if they are
uninhabited. This is an improvement over the previous behaviour which
considered all non-local non-exhaustive variants useful because
unreachable patterns are now detected.
r? @arielb1
cc @varkor
@CentrilCentril mentioned this pull request Oct 25, 2019
bors added a commit that referenced this pull request Oct 25, 2019
Rollup of 9 pull requests
Successful merges:
- #62959 (Add by-value iterator for arrays )
- #65390 (Add long error explanation for E0576)
- #65408 (reorder config.toml.example options and add one missing option)
- #65414 (ignore uninhabited non-exhaustive variant fields)
- #65666 (Deprecated proc_macro doesn't trigger warning on build library)
- #65742 (Pre-expansion gate most of the things)
- #65747 (Adjust the tracking issue for `untagged_unions`.)
- #65763 (Changed APIT with explicit generic args span to specific arg spans)
- #65775 (Fix more `ReEmpty` ICEs)
Failed merges:
- #65519 (trait-based structural match implementation)
r? @ghost
@bors
bors merged commit 7ffbd62 into rust-lang:masterOct 25, 2019
@CentrilCentril added the F-non_exhaustive `#![feature(non_exhaustive)]` label Oct 25, 2019
@davidtwco
davidtwco deleted the issue-65157-non-exhaustive-always-useful branch October 25, 2019 08:18
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

F-non_exhaustive`#![feature(non_exhaustive)]`S-waiting-on-borsStatus: Waiting on bors to run and complete tests. Bors will change the label on completion.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

#[non_exhaustive] variants are not detected to be redundant

7 participants

@davidtwco@Nadrieril@Centril@bors@varkor@arielb1@rust-highfive