about summary refs log tree commit diff
path: root/compiler/rustc_pattern_analysis
diff options
context:
space:
mode:
authorNadrieril <nadrieril+git@gmail.com>2023-12-22 23:47:44 +0100
committerNadrieril <nadrieril+git@gmail.com>2023-12-23 00:08:38 +0100
commit5fccaee59c290b85612d4adb120b3e745d3f16dd (patch)
tree70825ead158d7c22abeed9bde643e2f6fec65353 /compiler/rustc_pattern_analysis
parentf6af7478ba66fc016b5baabd689883b88316bfc2 (diff)
downloadrust-5fccaee59c290b85612d4adb120b3e745d3f16dd.tar.gz
rust-5fccaee59c290b85612d4adb120b3e745d3f16dd.zip
Clarify the situation with dummy patterns and `PatData`
Use an explicit `Option` instead of requiring a `Default` bound
Diffstat (limited to 'compiler/rustc_pattern_analysis')
-rw-r--r--compiler/rustc_pattern_analysis/src/lib.rs5
-rw-r--r--compiler/rustc_pattern_analysis/src/lints.rs4
-rw-r--r--compiler/rustc_pattern_analysis/src/pat.rs18
-rw-r--r--compiler/rustc_pattern_analysis/src/rustc.rs6
-rw-r--r--compiler/rustc_pattern_analysis/src/usefulness.rs3
5 files changed, 19 insertions, 17 deletions
diff --git a/compiler/rustc_pattern_analysis/src/lib.rs b/compiler/rustc_pattern_analysis/src/lib.rs
index 9f758dd8263..a1c9b157666 100644
--- a/compiler/rustc_pattern_analysis/src/lib.rs
+++ b/compiler/rustc_pattern_analysis/src/lib.rs
@@ -58,9 +58,8 @@ pub trait TypeCx: Sized + fmt::Debug {
     type StrLit: Clone + PartialEq + fmt::Debug;
     /// Extra data to store in a match arm.
     type ArmData: Copy + Clone + fmt::Debug;
-    /// Extra data to store in a pattern. `Default` needed when we create fictitious wildcard
-    /// patterns during analysis.
-    type PatData: Clone + Default;
+    /// Extra data to store in a pattern.
+    type PatData: Clone;
 
     /// FIXME(Nadrieril): `Cx` should only give us revealed types.
     fn reveal_opaque_ty(&self, ty: Self::Ty) -> Self::Ty;
diff --git a/compiler/rustc_pattern_analysis/src/lints.rs b/compiler/rustc_pattern_analysis/src/lints.rs
index 450a5cb0a10..2be6e8e3db3 100644
--- a/compiler/rustc_pattern_analysis/src/lints.rs
+++ b/compiler/rustc_pattern_analysis/src/lints.rs
@@ -203,7 +203,7 @@ pub(crate) fn lint_nonexhaustive_missing_variants<'a, 'p, 'tcx>(
                 };
 
                 use rustc_errors::DecorateLint;
-                let mut err = rcx.tcx.sess.struct_span_warn(*arm.pat.data(), "");
+                let mut err = rcx.tcx.sess.struct_span_warn(*arm.pat.data().unwrap(), "");
                 err.set_primary_message(decorator.msg());
                 decorator.decorate_lint(&mut err);
                 err.emit();
@@ -253,8 +253,8 @@ pub(crate) fn lint_overlapping_range_endpoints<'a, 'p, 'tcx>(
                 let mut suffixes: SmallVec<[_; 1]> = Default::default();
                 // Iterate on patterns that contained `overlap`.
                 for pat in column.iter() {
-                    let this_span = *pat.data();
                     let Constructor::IntRange(this_range) = pat.ctor() else { continue };
+                    let this_span = *pat.data().unwrap();
                     if this_range.is_singleton() {
                         // Don't lint when one of the ranges is a singleton.
                         continue;
diff --git a/compiler/rustc_pattern_analysis/src/pat.rs b/compiler/rustc_pattern_analysis/src/pat.rs
index 90772003a0a..9efd3e864da 100644
--- a/compiler/rustc_pattern_analysis/src/pat.rs
+++ b/compiler/rustc_pattern_analysis/src/pat.rs
@@ -26,14 +26,16 @@ pub struct DeconstructedPat<'p, Cx: TypeCx> {
     ctor: Constructor<Cx>,
     fields: &'p [DeconstructedPat<'p, Cx>],
     ty: Cx::Ty,
-    data: Cx::PatData,
+    /// Extra data to store in a pattern. `None` if the pattern is a wildcard that does not
+    /// correspond to a user-supplied pattern.
+    data: Option<Cx::PatData>,
     /// Whether removing this arm would change the behavior of the match expression.
     useful: Cell<bool>,
 }
 
 impl<'p, Cx: TypeCx> DeconstructedPat<'p, Cx> {
-    pub fn wildcard(ty: Cx::Ty, data: Cx::PatData) -> Self {
-        Self::new(Wildcard, &[], ty, data)
+    pub fn wildcard(ty: Cx::Ty) -> Self {
+        DeconstructedPat { ctor: Wildcard, fields: &[], ty, data: None, useful: Cell::new(false) }
     }
 
     pub fn new(
@@ -42,7 +44,7 @@ impl<'p, Cx: TypeCx> DeconstructedPat<'p, Cx> {
         ty: Cx::Ty,
         data: Cx::PatData,
     ) -> Self {
-        DeconstructedPat { ctor, fields, ty, data, useful: Cell::new(false) }
+        DeconstructedPat { ctor, fields, ty, data: Some(data), useful: Cell::new(false) }
     }
 
     pub(crate) fn is_or_pat(&self) -> bool {
@@ -63,8 +65,10 @@ impl<'p, Cx: TypeCx> DeconstructedPat<'p, Cx> {
     pub fn ty(&self) -> Cx::Ty {
         self.ty
     }
-    pub fn data(&self) -> &Cx::PatData {
-        &self.data
+    /// Returns the extra data stored in a pattern. Returns `None` if the pattern is a wildcard that
+    /// does not correspond to a user-supplied pattern.
+    pub fn data(&self) -> Option<&Cx::PatData> {
+        self.data.as_ref()
     }
 
     pub fn iter_fields<'a>(
@@ -83,7 +87,7 @@ impl<'p, Cx: TypeCx> DeconstructedPat<'p, Cx> {
         let wildcard_sub_tys = || {
             let tys = pcx.ctor_sub_tys(other_ctor);
             tys.iter()
-                .map(|ty| DeconstructedPat::wildcard(*ty, Cx::PatData::default()))
+                .map(|ty| DeconstructedPat::wildcard(*ty))
                 .map(|pat| pcx.mcx.wildcard_arena.alloc(pat) as &_)
                 .collect()
         };
diff --git a/compiler/rustc_pattern_analysis/src/rustc.rs b/compiler/rustc_pattern_analysis/src/rustc.rs
index d2cfb9a8b06..adaa2ecbe4f 100644
--- a/compiler/rustc_pattern_analysis/src/rustc.rs
+++ b/compiler/rustc_pattern_analysis/src/rustc.rs
@@ -416,7 +416,7 @@ impl<'p, 'tcx> RustcMatchCheckCtxt<'p, 'tcx> {
                     ty::Tuple(fs) => {
                         ctor = Struct;
                         let mut wilds: SmallVec<[_; 2]> =
-                            fs.iter().map(|ty| DeconstructedPat::wildcard(ty, pat.span)).collect();
+                            fs.iter().map(|ty| DeconstructedPat::wildcard(ty)).collect();
                         for pat in subpatterns {
                             wilds[pat.field.index()] = self.lower_pat(&pat.pattern);
                         }
@@ -439,7 +439,7 @@ impl<'p, 'tcx> RustcMatchCheckCtxt<'p, 'tcx> {
                         let pat = if let Some(pat) = pattern {
                             self.lower_pat(&pat.pattern)
                         } else {
-                            DeconstructedPat::wildcard(args.type_at(0), pat.span)
+                            DeconstructedPat::wildcard(args.type_at(0))
                         };
                         ctor = Struct;
                         fields = singleton(pat);
@@ -464,7 +464,7 @@ impl<'p, 'tcx> RustcMatchCheckCtxt<'p, 'tcx> {
                                 ty
                             });
                         let mut wilds: SmallVec<[_; 2]> =
-                            tys.map(|ty| DeconstructedPat::wildcard(ty, pat.span)).collect();
+                            tys.map(|ty| DeconstructedPat::wildcard(ty)).collect();
                         for pat in subpatterns {
                             if let Some(i) = field_id_to_id[pat.field.index()] {
                                 wilds[i] = self.lower_pat(&pat.pattern);
diff --git a/compiler/rustc_pattern_analysis/src/usefulness.rs b/compiler/rustc_pattern_analysis/src/usefulness.rs
index b1190d84c8e..a7cd944c0f1 100644
--- a/compiler/rustc_pattern_analysis/src/usefulness.rs
+++ b/compiler/rustc_pattern_analysis/src/usefulness.rs
@@ -840,8 +840,7 @@ impl<'a, 'p, Cx: TypeCx> Matrix<'a, 'p, Cx> {
         scrut_ty: Cx::Ty,
         scrut_validity: ValidityConstraint,
     ) -> Self {
-        let wild_pattern =
-            wildcard_arena.alloc(DeconstructedPat::wildcard(scrut_ty, Default::default()));
+        let wild_pattern = wildcard_arena.alloc(DeconstructedPat::wildcard(scrut_ty));
         let wildcard_row = PatStack::from_pattern(wild_pattern);
         let mut matrix = Matrix {
             rows: Vec::with_capacity(arms.len()),