Skip to content

Commit

Permalink
Rename pat_constructor to Constructor::from_pat
Browse files Browse the repository at this point in the history
  • Loading branch information
Nadrieril committed Nov 27, 2020
1 parent ba3c419 commit 2de0475
Show file tree
Hide file tree
Showing 2 changed files with 63 additions and 63 deletions.
4 changes: 2 additions & 2 deletions compiler/rustc_mir_build/src/thir/pattern/_match.rs
Expand Up @@ -306,7 +306,7 @@
use self::Usefulness::*;
use self::WitnessPreference::*;

use super::deconstruct_pat::{pat_constructor, Constructor, Fields, MissingConstructors};
use super::deconstruct_pat::{Constructor, Fields, MissingConstructors};
use super::{Pat, PatKind};
use super::{PatternFoldable, PatternFolder};

Expand Down Expand Up @@ -438,7 +438,7 @@ impl<'p, 'tcx> PatStack<'p, 'tcx> {
}

fn head_ctor<'a>(&'a self, cx: &MatchCheckCtxt<'p, 'tcx>) -> &'a Constructor<'tcx> {
self.head_ctor.get_or_init(|| pat_constructor(cx, self.head()))
self.head_ctor.get_or_init(|| Constructor::from_pat(cx, self.head()))
}

fn iter(&self) -> impl Iterator<Item = &Pat<'tcx>> {
Expand Down
122 changes: 61 additions & 61 deletions compiler/rustc_mir_build/src/thir/pattern/deconstruct_pat.rs
Expand Up @@ -606,6 +606,67 @@ impl<'tcx> Constructor<'tcx> {
}
}

/// Determines the constructor that the given pattern can be specialized to.
pub(super) fn from_pat<'p>(cx: &MatchCheckCtxt<'p, 'tcx>, pat: &'p Pat<'tcx>) -> Self {
match pat.kind.as_ref() {
PatKind::AscribeUserType { .. } => bug!(), // Handled by `expand_pattern`
PatKind::Binding { .. } | PatKind::Wild => Wildcard,
PatKind::Leaf { .. } | PatKind::Deref { .. } => Single,
&PatKind::Variant { adt_def, variant_index, .. } => {
Variant(adt_def.variants[variant_index].def_id)
}
PatKind::Constant { value } => {
if let Some(int_range) = IntRange::from_const(cx.tcx, cx.param_env, value, pat.span)
{
IntRange(int_range)
} else {
match pat.ty.kind() {
ty::Float(_) => FloatRange(value, value, RangeEnd::Included),
// In `expand_pattern`, we convert string literals to `&CONST` patterns with
// `CONST` a pattern of type `str`. In truth this contains a constant of type
// `&str`.
ty::Str => Str(value),
// All constants that can be structurally matched have already been expanded
// into the corresponding `Pat`s by `const_to_pat`. Constants that remain are
// opaque.
_ => Opaque,
}
}
}
&PatKind::Range(PatRange { lo, hi, end }) => {
let ty = lo.ty;
if let Some(int_range) = IntRange::from_range(
cx.tcx,
lo.eval_bits(cx.tcx, cx.param_env, lo.ty),
hi.eval_bits(cx.tcx, cx.param_env, hi.ty),
ty,
&end,
pat.span,
) {
IntRange(int_range)
} else {
FloatRange(lo, hi, end)
}
}
PatKind::Array { prefix, slice, suffix } | PatKind::Slice { prefix, slice, suffix } => {
let array_len = match pat.ty.kind() {
ty::Array(_, length) => Some(length.eval_usize(cx.tcx, cx.param_env)),
ty::Slice(_) => None,
_ => span_bug!(pat.span, "bad ty {:?} for slice pattern", pat.ty),
};
let prefix = prefix.len() as u64;
let suffix = suffix.len() as u64;
let kind = if slice.is_some() {
VarLen(prefix, suffix)
} else {
FixedLen(prefix + suffix)
};
Slice(Slice::new(array_len, kind))
}
PatKind::Or { .. } => bug!("Or-pattern should have been expanded earlier on."),
}
}

/// Some constructors (namely `Wildcard`, `IntRange` and `Slice`) actually stand for a set of actual
/// constructors (like variants, integers or fixed-sized slices). When specializing for these
/// constructors, we want to be specialising for the actual underlying constructors.
Expand Down Expand Up @@ -756,67 +817,6 @@ impl<'tcx> Constructor<'tcx> {
}
}

/// Determines the constructor that the given pattern can be specialized to.
/// Returns `None` in case of a catch-all, which can't be specialized.
pub(super) fn pat_constructor<'p, 'tcx>(
cx: &MatchCheckCtxt<'p, 'tcx>,
pat: &'p Pat<'tcx>,
) -> Constructor<'tcx> {
match pat.kind.as_ref() {
PatKind::AscribeUserType { .. } => bug!(), // Handled by `expand_pattern`
PatKind::Binding { .. } | PatKind::Wild => Wildcard,
PatKind::Leaf { .. } | PatKind::Deref { .. } => Single,
&PatKind::Variant { adt_def, variant_index, .. } => {
Variant(adt_def.variants[variant_index].def_id)
}
PatKind::Constant { value } => {
if let Some(int_range) = IntRange::from_const(cx.tcx, cx.param_env, value, pat.span) {
IntRange(int_range)
} else {
match pat.ty.kind() {
ty::Float(_) => FloatRange(value, value, RangeEnd::Included),
// In `expand_pattern`, we convert string literals to `&CONST` patterns with
// `CONST` a pattern of type `str`. In truth this contains a constant of type
// `&str`.
ty::Str => Str(value),
// All constants that can be structurally matched have already been expanded
// into the corresponding `Pat`s by `const_to_pat`. Constants that remain are
// opaque.
_ => Opaque,
}
}
}
&PatKind::Range(PatRange { lo, hi, end }) => {
let ty = lo.ty;
if let Some(int_range) = IntRange::from_range(
cx.tcx,
lo.eval_bits(cx.tcx, cx.param_env, lo.ty),
hi.eval_bits(cx.tcx, cx.param_env, hi.ty),
ty,
&end,
pat.span,
) {
IntRange(int_range)
} else {
FloatRange(lo, hi, end)
}
}
PatKind::Array { prefix, slice, suffix } | PatKind::Slice { prefix, slice, suffix } => {
let array_len = match pat.ty.kind() {
ty::Array(_, length) => Some(length.eval_usize(cx.tcx, cx.param_env)),
ty::Slice(_) => None,
_ => span_bug!(pat.span, "bad ty {:?} for slice pattern", pat.ty),
};
let prefix = prefix.len() as u64;
let suffix = suffix.len() as u64;
let kind =
if slice.is_some() { VarLen(prefix, suffix) } else { FixedLen(prefix + suffix) };
Slice(Slice::new(array_len, kind))
}
PatKind::Or { .. } => bug!("Or-pattern should have been expanded earlier on."),
}
}

/// This determines the set of all possible constructors of a pattern matching
/// values of type `left_ty`. For vectors, this would normally be an infinite set
/// but is instead bounded by the maximum fixed length of slice patterns in
Expand Down

0 comments on commit 2de0475

Please sign in to comment.