//! THIR datatypes and definitions. See the [rustc dev guide] for more info.
//!
//! If you compare the THIR [`ExprKind`] to [`hir::ExprKind`], you will see it is
//! a good bit simpler. In fact, a number of the more straight-forward
//! MIR simplifications are already done in the lowering to THIR. For
//! example, method calls and overloaded operators are absent: they are
//! expected to be converted into [`ExprKind::Call`] instances.
//!
//! [rustc dev guide]: https://rustc-dev-guide.rust-lang.org/thir.html

use std::cmp::Ordering;
use std::fmt;
use std::ops::Index;
use std::sync::Arc;

use rustc_abi::{FieldIdx, Integer, Size, VariantIdx};
use rustc_ast::{AsmMacro, InlineAsmOptions, InlineAsmTemplatePiece, Mutability};
use rustc_data_structures::fx::FxIndexMap;
use rustc_data_structures::thin_vec::ThinVec;
use rustc_hir as hir;
use rustc_hir::attrs::AttributeKind;
use rustc_hir::def_id::DefId;
use rustc_hir::{BindingMode, ByRef, HirId, MatchSource, RangeEnd};
use rustc_index::{IndexVec, newtype_index};
use rustc_macros::{StableHash, TyDecodable, TyEncodable, TypeVisitable};
use rustc_span::def_id::LocalDefId;
use rustc_span::{ErrorGuaranteed, Span, Symbol};
use rustc_target::asm::InlineAsmRegOrRegClass;
use tracing::instrument;

use crate::middle::region;
use crate::mir::interpret::AllocId;
use crate::mir::{self, AssignOp, BinOp, BorrowKind, FakeReadCause, UnOp};
use crate::thir::visit::for_each_immediate_subpat;
use crate::ty::adjustment::PointerCoercion;
use crate::ty::layout::IntegerExt;
use crate::ty::{
    self, AdtDef, CanonicalUserType, CanonicalUserTypeAnnotation, FnSig, GenericArgsRef, Ty,
    TyCtxt, UpvarArgs,
};

pub mod visit;

macro_rules! thir_with_elements {
    (
        $($name:ident: $id:ty => $value:ty => $format:literal,)*
    ) => {
        $(
            newtype_index! {
                #[stable_hash]
                #[debug_format = $format]
                pub struct $id {}
            }
        )*

        // Note: Making `Thir` implement `Clone` is useful for external tools that need access to
        // THIR bodies even after the `Steal` query result has been stolen.
        // One such tool is https://github.com/rust-corpus/qrates/.
        /// A container for a THIR body.
        ///
        /// This can be indexed directly by any THIR index (e.g. [`ExprId`]).
        #[derive(Debug, StableHash, Clone)]
        pub struct Thir<'tcx> {
            pub body_type: BodyTy<'tcx>,
            pub attributes: FxIndexMap<ExprId, ThinVec<AttributeKind>>,
            $(
                pub $name: IndexVec<$id, $value>,
            )*
        }

        impl<'tcx> Thir<'tcx> {
            pub fn new(body_type: BodyTy<'tcx>) -> Thir<'tcx> {
                Thir {
                    body_type,
                    attributes: FxIndexMap::default(),
                    $(
                        $name: IndexVec::new(),
                    )*
                }
            }
        }

        $(
            impl<'tcx> Index<$id> for Thir<'tcx> {
                type Output = $value;
                fn index(&self, index: $id) -> &Self::Output {
                    &self.$name[index]
                }
            }
        )*
    }
}

thir_with_elements! {
    arms: ArmId => Arm<'tcx> => "a{}",
    blocks: BlockId => Block => "b{}",
    exprs: ExprId => Expr<'tcx> => "e{}",
    stmts: StmtId => Stmt<'tcx> => "s{}",
    params: ParamId => Param<'tcx> => "p{}",
}

#[derive(Debug, StableHash, Clone)]
pub enum BodyTy<'tcx> {
    Const(Ty<'tcx>),
    Fn(FnSig<'tcx>),
    GlobalAsm(Ty<'tcx>),
}

/// Description of a type-checked function parameter.
#[derive(Clone, Debug, StableHash)]
pub struct Param<'tcx> {
    /// The pattern that appears in the parameter list, or None for implicit parameters.
    pub pat: Option<Box<Pat<'tcx>>>,
    /// The possibly inferred type.
    pub ty: Ty<'tcx>,
    /// Span of the explicitly provided type, or None if inferred for closures.
    pub ty_span: Option<Span>,
    /// Whether this param is `self`, and how it is bound.
    pub self_kind: Option<hir::ImplicitSelfKind>,
    /// HirId for lints.
    pub hir_id: Option<HirId>,
}

#[derive(Clone, Debug, StableHash)]
pub struct Block {
    /// Whether the block itself has a label. Used by `label: {}`
    /// and `try` blocks.
    ///
    /// This does *not* include labels on loops, e.g. `'label: loop {}`.
    pub targeted_by_break: bool,
    pub region_scope: region::Scope,
    /// The span of the block, including the opening braces,
    /// the label, and the `unsafe` keyword, if present.
    pub span: Span,
    /// The statements in the blocK.
    pub stmts: Box<[StmtId]>,
    /// The trailing expression of the block, if any.
    pub expr: Option<ExprId>,
    pub safety_mode: BlockSafety,
}

type UserTy<'tcx> = Option<Box<CanonicalUserType<'tcx>>>;

#[derive(Clone, Debug, StableHash)]
pub struct AdtExpr<'tcx> {
    /// The ADT we're constructing.
    pub adt_def: AdtDef<'tcx>,
    /// The variant of the ADT.
    pub variant_index: VariantIdx,
    pub args: GenericArgsRef<'tcx>,

    /// Optional user-given args: for something like `let x =
    /// Bar::<T> { ... }`.
    pub user_ty: UserTy<'tcx>,

    pub fields: Box<[FieldExpr]>,
    /// The base, e.g. `Foo {x: 1, ..base}`.
    pub base: AdtExprBase<'tcx>,
}

#[derive(Clone, Debug, StableHash)]
pub enum AdtExprBase<'tcx> {
    /// A struct expression where all the fields are explicitly enumerated: `Foo { a, b }`.
    None,
    /// A struct expression with a "base", an expression of the same type as the outer struct that
    /// will be used to populate any fields not explicitly mentioned: `Foo { ..base }`
    Base(FruInfo<'tcx>),
    /// A struct expression with a `..` tail but no "base" expression. The values from the struct
    /// fields' default values will be used to populate any fields not explicitly mentioned:
    /// `Foo { .. }`.
    DefaultFields(Box<[Ty<'tcx>]>),
}

#[derive(Clone, Debug, StableHash)]
pub struct ClosureExpr<'tcx> {
    pub closure_id: LocalDefId,
    pub args: UpvarArgs<'tcx>,
    pub upvars: Box<[ExprId]>,
    pub movability: Option<hir::Movability>,
    pub fake_reads: Vec<(ExprId, FakeReadCause, HirId)>,
}

#[derive(Clone, Debug, StableHash)]
pub struct InlineAsmExpr<'tcx> {
    pub asm_macro: AsmMacro,
    pub template: &'tcx [InlineAsmTemplatePiece],
    pub operands: Box<[InlineAsmOperand<'tcx>]>,
    pub options: InlineAsmOptions,
    pub line_spans: &'tcx [Span],
}

#[derive(Copy, Clone, Debug, StableHash)]
pub enum BlockSafety {
    Safe,
    /// A compiler-generated unsafe block
    BuiltinUnsafe,
    /// An `unsafe` block. The `HirId` is the ID of the block.
    ExplicitUnsafe(HirId),
}

#[derive(Clone, Debug, StableHash)]
pub struct Stmt<'tcx> {
    pub kind: StmtKind<'tcx>,
}

#[derive(Clone, Debug, StableHash)]
pub enum StmtKind<'tcx> {
    /// An expression with a trailing semicolon.
    Expr {
        /// The scope for this statement; may be used as lifetime of temporaries.
        scope: region::Scope,

        /// The expression being evaluated in this statement.
        expr: ExprId,
    },

    /// A `let` binding.
    Let {
        /// The scope for variables bound in this `let`; it covers this and
        /// all the remaining statements in the block.
        remainder_scope: region::Scope,

        /// The scope for the initialization itself; might be used as
        /// lifetime of temporaries.
        init_scope: region::Scope,

        /// `let <PAT> = ...`
        ///
        /// If a type annotation is included, it is added as an ascription pattern.
        pattern: Box<Pat<'tcx>>,

        /// `let pat: ty = <INIT>`
        initializer: Option<ExprId>,

        /// `let pat: ty = <INIT> else { <ELSE> }`
        else_block: Option<BlockId>,

        /// The [`HirId`] for this `let` statement.
        hir_id: HirId,

        /// Span of the `let <PAT> = <INIT>` part.
        span: Span,
    },
}

#[derive(Clone, Debug, Copy, PartialEq, Eq, Hash, StableHash, TyEncodable, TyDecodable)]
pub struct LocalVarId(pub HirId);

/// A THIR expression.
#[derive(Clone, Debug, StableHash)]
pub struct Expr<'tcx> {
    /// kind of expression
    pub kind: ExprKind<'tcx>,

    /// The type of this expression
    pub ty: Ty<'tcx>,

    /// The id of the HIR expression whose [temporary scope] should be used for this expression.
    ///
    /// [temporary scope]: https://doc.rust-lang.org/reference/destructors.html#temporary-scopes
    pub temp_scope_id: hir::ItemLocalId,

    /// span of the expression in the source
    pub span: Span,
}

#[derive(Clone, Debug, StableHash)]
pub enum ExprKind<'tcx> {
    /// `Scope`s are used to explicitly mark destruction scopes,
    /// and to track the `HirId` of the expressions within the scope.
    Scope {
        region_scope: region::Scope,
        hir_id: HirId,
        value: ExprId,
    },
    /// An `if` expression.
    If {
        if_then_scope: region::Scope,
        cond: ExprId,
        /// `then` is always `ExprKind::Block`.
        then: ExprId,
        /// If present, the `else_opt` expr is always `ExprKind::Block` (for
        /// `else`) or `ExprKind::If` (for `else if`).
        else_opt: Option<ExprId>,
    },
    /// A function call. Method calls and overloaded operators are converted to plain function calls.
    Call {
        /// The type of the function. This is often a [`FnDef`] or a [`FnPtr`].
        ///
        /// [`FnDef`]: ty::TyKind::FnDef
        /// [`FnPtr`]: ty::TyKind::FnPtr
        ty: Ty<'tcx>,
        /// The function itself.
        fun: ExprId,
        /// The arguments passed to the function.
        ///
        /// Note: in some cases (like calling a closure), the function call `f(...args)` gets
        /// rewritten as a call to a function trait method (e.g. `FnOnce::call_once(f, (...args))`).
        args: Box<[ExprId]>,
        /// Whether this is from an overloaded operator rather than a
        /// function call from HIR. `true` for overloaded function call.
        from_hir_call: bool,
        /// The span of the function, without the dot and receiver
        /// (e.g. `foo(a, b)` in `x.foo(a, b)`).
        fn_span: Span,
    },
    /// A use expression `x.use`.
    ByUse {
        /// The expression on which use is applied.
        expr: ExprId,
        /// The span of use, without the dot and receiver
        /// (e.g. `use` in `x.use`).
        span: Span,
    },
    /// A *non-overloaded* dereference.
    Deref {
        arg: ExprId,
    },
    /// A *non-overloaded* binary operation.
    Binary {
        op: BinOp,
        lhs: ExprId,
        rhs: ExprId,
    },
    /// A logical operation. This is distinct from `BinaryOp` because
    /// the operands need to be lazily evaluated.
    LogicalOp {
        op: LogicalOp,
        lhs: ExprId,
        rhs: ExprId,
    },
    /// A *non-overloaded* unary operation. Note that here the deref (`*`)
    /// operator is represented by `ExprKind::Deref`.
    Unary {
        op: UnOp,
        arg: ExprId,
    },
    /// A cast: `<source> as <type>`. The type we cast to is the type of
    /// the parent expression.
    Cast {
        source: ExprId,
    },
    /// Forces its contents to be treated as a value expression, not a place
    /// expression. This is inserted in some places where an operation would
    /// otherwise be erased completely (e.g. some no-op casts), but we still
    /// need to ensure that its operand is treated as a value and not a place.
    Use {
        source: ExprId,
    },
    /// A coercion from `!` to any type.
    NeverToAny {
        source: ExprId,
    },
    /// A pointer coercion. More information can be found in [`PointerCoercion`].
    /// Pointer casts that cannot be done by coercions are represented by [`ExprKind::Cast`].
    PointerCoercion {
        cast: PointerCoercion,
        source: ExprId,
        /// Whether this coercion is written with an `as` cast in the source code.
        is_from_as_cast: bool,
    },
    /// A `loop` expression.
    Loop {
        body: ExprId,
    },
    /// A `#[loop_match] loop { state = 'blk: { match state { ... } } }` expression.
    LoopMatch {
        /// The state variable that is updated.
        /// The `match_data.scrutinee` is the same variable, but with a different span.
        state: ExprId,
        region_scope: region::Scope,
        match_data: Box<LoopMatchMatchData>,
    },
    /// Special expression representing the `let` part of an `if let` or similar construct
    /// (including `if let` guards in match arms, and let-chains formed by `&&`).
    ///
    /// This isn't considered a real expression in surface Rust syntax, so it can
    /// only appear in specific situations, such as within the condition of an `if`.
    ///
    /// (Not to be confused with [`StmtKind::Let`], which is a normal `let` statement.)
    Let {
        expr: ExprId,
        pat: Box<Pat<'tcx>>,
    },
    /// A `match` expression.
    Match {
        scrutinee: ExprId,
        arms: Box<[ArmId]>,
        match_source: MatchSource,
    },
    /// A block.
    Block {
        block: BlockId,
    },
    /// An assignment: `lhs = rhs`.
    Assign {
        lhs: ExprId,
        rhs: ExprId,
    },
    /// A *non-overloaded* operation assignment, e.g. `lhs += rhs`.
    AssignOp {
        op: AssignOp,
        lhs: ExprId,
        rhs: ExprId,
    },
    /// Access to a field of a struct, a tuple, an union, or an enum.
    Field {
        lhs: ExprId,
        /// Variant containing the field.
        variant_index: VariantIdx,
        /// This can be a named (`.foo`) or unnamed (`.0`) field.
        name: FieldIdx,
    },
    /// A *non-overloaded* indexing operation.
    Index {
        lhs: ExprId,
        index: ExprId,
    },
    /// A local variable.
    VarRef {
        id: LocalVarId,
    },
    /// Used to represent upvars mentioned in a closure/coroutine
    UpvarRef {
        /// DefId of the closure/coroutine
        closure_def_id: DefId,

        /// HirId of the root variable
        var_hir_id: LocalVarId,
    },
    /// A borrow, e.g. `&arg`.
    Borrow {
        borrow_kind: BorrowKind,
        arg: ExprId,
    },
    /// A `&raw [const|mut] $place_expr` raw borrow resulting in type `*[const|mut] T`.
    RawBorrow {
        mutability: hir::Mutability,
        arg: ExprId,
    },
    /// A `break` expression.
    Break {
        label: region::Scope,
        value: Option<ExprId>,
    },
    /// A `continue` expression.
    Continue {
        label: region::Scope,
    },
    /// A `#[const_continue] break` expression.
    ConstContinue {
        label: region::Scope,
        value: ExprId,
    },
    /// A `return` expression.
    Return {
        value: Option<ExprId>,
    },
    /// A `become` expression.
    Become {
        value: ExprId,
    },
    /// An inline `const` block, e.g. `const {}`.
    ConstBlock {
        did: DefId,
        args: GenericArgsRef<'tcx>,
    },
    /// An array literal constructed from one repeated element, e.g. `[1; 5]`.
    Repeat {
        value: ExprId,
        count: ty::Const<'tcx>,
    },
    /// An array, e.g. `[a, b, c, d]`.
    Array {
        fields: Box<[ExprId]>,
    },
    /// A tuple, e.g. `(a, b, c, d)`.
    Tuple {
        fields: Box<[ExprId]>,
    },
    /// An ADT constructor, e.g. `Foo {x: 1, y: 2}`.
    Adt(Box<AdtExpr<'tcx>>),
    /// A type ascription on a place.
    PlaceTypeAscription {
        source: ExprId,
        /// Type that the user gave to this expression
        user_ty: UserTy<'tcx>,
        user_ty_span: Span,
    },
    /// A type ascription on a value, e.g. `type_ascribe!(42, i32)` or `42 as i32`.
    ValueTypeAscription {
        source: ExprId,
        /// Type that the user gave to this expression
        user_ty: UserTy<'tcx>,
        user_ty_span: Span,
    },
    /// An unsafe binder cast on a place, e.g. `unwrap_binder!(*ptr)`.
    PlaceUnwrapUnsafeBinder {
        source: ExprId,
    },
    /// An unsafe binder cast on a value, e.g. `unwrap_binder!(rvalue())`,
    /// which makes a temporary.
    ValueUnwrapUnsafeBinder {
        source: ExprId,
    },
    /// Construct an unsafe binder, e.g. `wrap_binder(&ref)`.
    WrapUnsafeBinder {
        source: ExprId,
    },
    /// A closure definition.
    Closure(Box<ClosureExpr<'tcx>>),
    /// A literal.
    Literal {
        lit: hir::Lit,
        neg: bool,
    },
    /// For literals that don't correspond to anything in the HIR
    NonHirLiteral {
        lit: ty::ScalarInt,
        user_ty: UserTy<'tcx>,
    },
    /// A literal of a ZST type.
    ZstLiteral {
        user_ty: UserTy<'tcx>,
    },
    /// Associated constants and named constants
    NamedConst {
        def_id: DefId,
        args: GenericArgsRef<'tcx>,
        user_ty: UserTy<'tcx>,
    },
    ConstParam {
        param: ty::ParamConst,
        def_id: DefId,
    },
    // FIXME improve docs for `StaticRef` by distinguishing it from `NamedConst`
    /// A literal containing the address of a `static`.
    ///
    /// This is only distinguished from `Literal` so that we can register some
    /// info for diagnostics.
    StaticRef {
        alloc_id: AllocId,
        ty: Ty<'tcx>,
        def_id: DefId,
    },
    /// Inline assembly, i.e. `asm!()`.
    InlineAsm(Box<InlineAsmExpr<'tcx>>),
    /// An expression taking a reference to a thread local.
    ThreadLocalRef(DefId),
    /// A `yield` expression.
    Yield {
        value: ExprId,
    },
    /// Use of an ADT that implements the Reborrow (for Mut) or CoerceShared traits (for Not). This
    /// expression is produced by the [`Adjust::GenericReborrow`] in places where normally the ADT
    /// would be moved or assigned over. Instead, this produces an [`Rvalue::Reborrow`] which
    /// produces a bitwise copy of the source ADT and disables the source for the copy's lifetime.
    ///
    /// [`Adjust::GenericReborrow`]: crate::ty::adjustment::Adjust::GenericReborrow
    /// [`Rvalue::Reborrow`]: mir::Rvalue::Reborrow
    Reborrow {
        source: ExprId,
        mutability: Mutability,
        target: Ty<'tcx>,
    },
}

/// Represents the association of a field identifier and an expression.
///
/// This is used in struct constructors.
#[derive(Clone, Debug, StableHash)]
pub struct FieldExpr {
    pub name: FieldIdx,
    pub expr: ExprId,
}

#[derive(Clone, Debug, StableHash)]
pub struct FruInfo<'tcx> {
    pub base: ExprId,
    pub field_types: Box<[Ty<'tcx>]>,
}

/// A `match` arm.
#[derive(Clone, Debug, StableHash)]
pub struct Arm<'tcx> {
    pub pattern: Box<Pat<'tcx>>,
    pub guard: Option<ExprId>,
    pub body: ExprId,
    pub hir_id: HirId,
    pub scope: region::Scope,
    pub span: Span,
}

/// The `match` part of a `#[loop_match]`
#[derive(Clone, Debug, StableHash)]
pub struct LoopMatchMatchData {
    pub scrutinee: ExprId,
    pub arms: Box<[ArmId]>,
    pub span: Span,
}

#[derive(Copy, Clone, Debug, StableHash)]
pub enum LogicalOp {
    /// The `&&` operator.
    And,
    /// The `||` operator.
    Or,
}

#[derive(Clone, Debug, StableHash)]
pub enum InlineAsmOperand<'tcx> {
    In {
        reg: InlineAsmRegOrRegClass,
        expr: ExprId,
    },
    Out {
        reg: InlineAsmRegOrRegClass,
        late: bool,
        expr: Option<ExprId>,
    },
    InOut {
        reg: InlineAsmRegOrRegClass,
        late: bool,
        expr: ExprId,
    },
    SplitInOut {
        reg: InlineAsmRegOrRegClass,
        late: bool,
        in_expr: ExprId,
        out_expr: Option<ExprId>,
    },
    Const {
        value: mir::Const<'tcx>,
        span: Span,
    },
    SymFn {
        value: ExprId,
    },
    SymStatic {
        def_id: DefId,
    },
    Label {
        block: BlockId,
    },
}

#[derive(Clone, Debug, StableHash, TypeVisitable)]
pub struct FieldPat<'tcx> {
    pub field: FieldIdx,
    pub pattern: Pat<'tcx>,
}

/// Additional per-node data that is not present on most THIR pattern nodes.
#[derive(Clone, Debug, Default, StableHash, TypeVisitable)]
pub struct PatExtra<'tcx> {
    /// If present, this node represents a named constant that was lowered to
    /// a pattern using `const_to_pat`.
    ///
    /// This is used by some diagnostics for non-exhaustive matches, to map
    /// the pattern node back to the `DefId` of its original constant.
    pub expanded_const: Option<DefId>,

    /// User-written types that must be preserved into MIR so that they can be
    /// checked.
    pub ascriptions: Vec<Ascription<'tcx>>,
}

#[derive(Clone, Debug, StableHash, TypeVisitable)]
pub struct Pat<'tcx> {
    pub ty: Ty<'tcx>,
    pub span: Span,
    pub extra: Option<Box<PatExtra<'tcx>>>,
    pub kind: PatKind<'tcx>,
}

impl<'tcx> Pat<'tcx> {
    pub fn simple_ident(&self) -> Option<Symbol> {
        match self.kind {
            PatKind::Binding {
                name, mode: BindingMode(ByRef::No, _), subpattern: None, ..
            } => Some(name),
            _ => None,
        }
    }

    /// Call `f` on every "binding" in a pattern, e.g., on `a` in
    /// `match foo() { Some(a) => (), None => () }`
    pub fn each_binding(&self, mut f: impl FnMut(Symbol, ByRef, Ty<'tcx>, Span)) {
        self.walk_always(|p| {
            if let PatKind::Binding { name, mode, ty, .. } = p.kind {
                f(name, mode.0, ty, p.span);
            }
        });
    }

    /// Walk the pattern in left-to-right order.
    ///
    /// If `it(pat)` returns `false`, the children are not visited.
    pub fn walk(&self, mut it: impl FnMut(&Pat<'tcx>) -> bool) {
        self.walk_(&mut it)
    }

    fn walk_(&self, it: &mut impl FnMut(&Pat<'tcx>) -> bool) {
        if !it(self) {
            return;
        }

        for_each_immediate_subpat(self, |p| p.walk_(it));
    }

    /// Whether the pattern has a `PatKind::Error` nested within.
    pub fn pat_error_reported(&self) -> Result<(), ErrorGuaranteed> {
        let mut error = None;
        self.walk(|pat| {
            if let PatKind::Error(e) = pat.kind
                && error.is_none()
            {
                error = Some(e);
            }
            error.is_none()
        });
        match error {
            None => Ok(()),
            Some(e) => Err(e),
        }
    }

    /// Walk the pattern in left-to-right order.
    ///
    /// If you always want to recurse, prefer this method over `walk`.
    pub fn walk_always(&self, mut it: impl FnMut(&Pat<'tcx>)) {
        self.walk(|p| {
            it(p);
            true
        })
    }
}

#[derive(Clone, Debug, StableHash, TypeVisitable)]
pub struct Ascription<'tcx> {
    pub annotation: CanonicalUserTypeAnnotation<'tcx>,
    /// Variance to use when relating the `user_ty` to the **type of the value being
    /// matched**. Typically, this is `Variance::Covariant`, since the value being matched must
    /// have a type that is some subtype of the ascribed type.
    ///
    /// Note that this variance does not apply for any bindings within subpatterns. The type
    /// assigned to those bindings must be exactly equal to the `user_ty` given here.
    ///
    /// The only place where this field is not `Covariant` is when matching constants, where
    /// we currently use `Contravariant` -- this is because the constant type just needs to
    /// be "comparable" to the type of the input value. So, for example:
    ///
    /// ```text
    /// match x { "foo" => .. }
    /// ```
    ///
    /// requires that `&'static str <: T_x`, where `T_x` is the type of `x`. Really, we should
    /// probably be checking for a `PartialEq` impl instead, but this preserves the behavior
    /// of the old type-check for now. See #57280 for details.
    pub variance: ty::Variance,
}

#[derive(Clone, Debug, StableHash, TypeVisitable)]
pub enum PatKind<'tcx> {
    /// A missing pattern, e.g. for an anonymous param in a bare fn like `fn f(u32)`.
    Missing,

    /// A wildcard pattern: `_`.
    Wild,

    /// `x`, `ref x`, `x @ P`, etc.
    Binding {
        name: Symbol,
        #[type_visitable(ignore)]
        mode: BindingMode,
        #[type_visitable(ignore)]
        var: LocalVarId,
        ty: Ty<'tcx>,
        subpattern: Option<Box<Pat<'tcx>>>,

        /// Is this the leftmost occurrence of the binding, i.e., is `var` the
        /// `HirId` of this pattern?
        ///
        /// (The same binding can occur multiple times in different branches of
        /// an or-pattern, but only one of them will be primary.)
        is_primary: bool,
        /// Is this binding a shorthand struct pattern, i.e. `Foo { a }`?
        is_shorthand: bool,
    },

    /// `Foo(...)` or `Foo{...}` or `Foo`, where `Foo` is a variant name from an ADT with
    /// multiple variants.
    Variant {
        adt_def: AdtDef<'tcx>,
        args: GenericArgsRef<'tcx>,
        variant_index: VariantIdx,
        subpatterns: Vec<FieldPat<'tcx>>,
    },

    /// `(...)`, `Foo(...)`, `Foo{...}`, or `Foo`, where `Foo` is a variant name from an ADT with
    /// a single variant.
    Leaf {
        subpatterns: Vec<FieldPat<'tcx>>,
    },

    /// Explicit or implicit `&P` or `&mut P`, for some subpattern `P`.
    ///
    /// Implicit `&`/`&mut` patterns can be inserted by match-ergonomics.
    ///
    /// With `feature(pin_ergonomics)`, this can also be `&pin const P` or
    /// `&pin mut P`, as indicated by the `pin` field.
    Deref {
        #[type_visitable(ignore)]
        pin: hir::Pinnedness,
        subpattern: Box<Pat<'tcx>>,
    },

    /// Explicit or implicit `deref!(..)` pattern, under `feature(deref_patterns)`.
    /// Represents a call to `Deref` or `DerefMut`, or a deref-move of `Box`.
    ///
    /// `box P` patterns also lower to this, under `feature(box_patterns)`.
    DerefPattern {
        subpattern: Box<Pat<'tcx>>,
        /// Whether the pattern scrutinee needs to be borrowed in order to call `Deref::deref` or
        /// `DerefMut::deref_mut`, and if so, which. This is `DerefPatBorrowMode::Box` for deref patterns on
        /// boxes; they are lowered using a built-in deref rather than a method call, thus they
        /// don't borrow the scrutinee.
        #[type_visitable(ignore)]
        borrow: DerefPatBorrowMode,
    },

    /// One of the following:
    /// * `&str`, which will be handled as a string pattern and thus
    ///   exhaustiveness checking will detect if you use the same string twice in different
    ///   patterns.
    /// * integer, bool, char or float, which will be handled by
    ///   exhaustiveness to cover exactly its own value, similar to `&str`, but these values are
    ///   much simpler.
    /// * raw pointers derived from integers, other raw pointers will have already resulted in an
    ///   error.
    Constant {
        value: ty::Value<'tcx>,
    },

    Range(Arc<PatRange<'tcx>>),

    /// Matches against a slice, checking the length and extracting elements.
    /// irrefutable when there is a slice pattern and both `prefix` and `suffix` are empty.
    /// e.g., `&[ref xs @ ..]`.
    Slice {
        prefix: Box<[Pat<'tcx>]>,
        slice: Option<Box<Pat<'tcx>>>,
        suffix: Box<[Pat<'tcx>]>,
    },

    /// Fixed match against an array; irrefutable.
    Array {
        prefix: Box<[Pat<'tcx>]>,
        slice: Option<Box<Pat<'tcx>>>,
        suffix: Box<[Pat<'tcx>]>,
    },

    /// An or-pattern, e.g. `p | q`.
    /// Invariant: `pats.len() >= 2`.
    Or {
        pats: Box<[Pat<'tcx>]>,
    },

    /// A guard pattern, e.g. `x if guard(x)`
    Guard {
        subpattern: Box<Pat<'tcx>>,
        #[type_visitable(ignore)]
        condition: ExprId,
    },

    /// A never pattern `!`.
    Never,

    /// An error has been encountered during lowering. We probably shouldn't report more lints
    /// related to this pattern.
    Error(ErrorGuaranteed),
}

#[derive(Copy, Clone, Debug, StableHash)]
pub enum DerefPatBorrowMode {
    Borrow(Mutability),
    Box,
}

/// A range pattern.
/// The boundaries must be of the same type and that type must be numeric.
#[derive(Clone, Debug, PartialEq, StableHash, TypeVisitable)]
pub struct PatRange<'tcx> {
    /// Must not be `PosInfinity`.
    pub lo: PatRangeBoundary<'tcx>,
    /// Must not be `NegInfinity`.
    pub hi: PatRangeBoundary<'tcx>,
    #[type_visitable(ignore)]
    pub end: RangeEnd,
    pub ty: Ty<'tcx>,
}

impl<'tcx> PatRange<'tcx> {
    /// Whether this range covers the full extent of possible values (best-effort, we ignore floats).
    #[inline]
    pub fn is_full_range(&self, tcx: TyCtxt<'tcx>) -> Option<bool> {
        let (min, max, size, bias) = match *self.ty.kind() {
            ty::Char => (0, std::char::MAX as u128, Size::from_bits(32), 0),
            ty::Int(ity) => {
                let size = Integer::from_int_ty(&tcx, ity).size();
                let max = size.truncate(u128::MAX);
                let bias = 1u128 << (size.bits() - 1);
                (0, max, size, bias)
            }
            ty::Uint(uty) => {
                let size = Integer::from_uint_ty(&tcx, uty).size();
                let max = size.unsigned_int_max();
                (0, max, size, 0)
            }
            _ => return None,
        };

        // We want to compare ranges numerically, but the order of the bitwise representation of
        // signed integers does not match their numeric order. Thus, to correct the ordering, we
        // need to shift the range of signed integers to correct the comparison. This is achieved by
        // XORing with a bias (see pattern/deconstruct_pat.rs for another pertinent example of this
        // pattern).
        //
        // Also, for performance, it's important to only do the second `try_to_bits` if necessary.
        let lo_is_min = match self.lo {
            PatRangeBoundary::NegInfinity => true,
            PatRangeBoundary::Finite(value) => {
                let lo = value.to_leaf().to_bits(size) ^ bias;
                lo <= min
            }
            PatRangeBoundary::PosInfinity => false,
        };
        if lo_is_min {
            let hi_is_max = match self.hi {
                PatRangeBoundary::NegInfinity => false,
                PatRangeBoundary::Finite(value) => {
                    let hi = value.to_leaf().to_bits(size) ^ bias;
                    hi > max || hi == max && self.end == RangeEnd::Included
                }
                PatRangeBoundary::PosInfinity => true,
            };
            if hi_is_max {
                return Some(true);
            }
        }
        Some(false)
    }

    #[inline]
    pub fn contains(&self, value: ty::Value<'tcx>, tcx: TyCtxt<'tcx>) -> Option<bool> {
        use Ordering::*;
        debug_assert_eq!(value.ty, self.ty);
        let ty = self.ty;
        let value = PatRangeBoundary::Finite(value.valtree);
        // For performance, it's important to only do the second comparison if necessary.
        Some(
            match self.lo.compare_with(value, ty, tcx)? {
                Less | Equal => true,
                Greater => false,
            } && match value.compare_with(self.hi, ty, tcx)? {
                Less => true,
                Equal => self.end == RangeEnd::Included,
                Greater => false,
            },
        )
    }

    #[inline]
    pub fn overlaps(&self, other: &Self, tcx: TyCtxt<'tcx>) -> Option<bool> {
        use Ordering::*;
        debug_assert_eq!(self.ty, other.ty);
        // For performance, it's important to only do the second comparison if necessary.
        Some(
            match other.lo.compare_with(self.hi, self.ty, tcx)? {
                Less => true,
                Equal => self.end == RangeEnd::Included,
                Greater => false,
            } && match self.lo.compare_with(other.hi, self.ty, tcx)? {
                Less => true,
                Equal => other.end == RangeEnd::Included,
                Greater => false,
            },
        )
    }
}

impl<'tcx> fmt::Display for PatRange<'tcx> {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        if let &PatRangeBoundary::Finite(valtree) = &self.lo {
            let value = ty::Value { ty: self.ty, valtree };
            write!(f, "{value}")?;
        }
        if let &PatRangeBoundary::Finite(valtree) = &self.hi {
            write!(f, "{}", self.end)?;
            let value = ty::Value { ty: self.ty, valtree };
            write!(f, "{value}")?;
        } else {
            // `0..` is parsed as an inclusive range, we must display it correctly.
            write!(f, "..")?;
        }
        Ok(())
    }
}

/// A (possibly open) boundary of a range pattern.
/// If present, the const must be of a numeric type.
#[derive(Copy, Clone, Debug, PartialEq, StableHash, TypeVisitable)]
pub enum PatRangeBoundary<'tcx> {
    /// The type of this valtree is stored in the surrounding `PatRange`.
    Finite(ty::ValTree<'tcx>),
    NegInfinity,
    PosInfinity,
}

impl<'tcx> PatRangeBoundary<'tcx> {
    #[inline]
    pub fn is_finite(self) -> bool {
        matches!(self, Self::Finite(..))
    }
    #[inline]
    pub fn as_finite(self) -> Option<ty::ValTree<'tcx>> {
        match self {
            Self::Finite(value) => Some(value),
            Self::NegInfinity | Self::PosInfinity => None,
        }
    }
    pub fn to_bits(self, ty: Ty<'tcx>, tcx: TyCtxt<'tcx>) -> u128 {
        match self {
            Self::Finite(value) => value.to_leaf().to_bits_unchecked(),
            Self::NegInfinity => {
                // Unwrap is ok because the type is known to be numeric.
                ty.numeric_min_and_max_as_bits(tcx).unwrap().0
            }
            Self::PosInfinity => {
                // Unwrap is ok because the type is known to be numeric.
                ty.numeric_min_and_max_as_bits(tcx).unwrap().1
            }
        }
    }

    #[instrument(skip(tcx), level = "debug", ret)]
    pub fn compare_with(self, other: Self, ty: Ty<'tcx>, tcx: TyCtxt<'tcx>) -> Option<Ordering> {
        use PatRangeBoundary::*;
        match (self, other) {
            // When comparing with infinities, we must remember that `0u8..` and `0u8..=255`
            // describe the same range. These two shortcuts are ok, but for the rest we must check
            // bit values.
            (PosInfinity, PosInfinity) => return Some(Ordering::Equal),
            (NegInfinity, NegInfinity) => return Some(Ordering::Equal),

            // This code is hot when compiling matches with many ranges. So we
            // special-case extraction of evaluated scalars for speed, for types where
            // we can do scalar comparisons. E.g. `unicode-normalization` has
            // many ranges such as '\u{037A}'..='\u{037F}', and chars can be compared
            // in this way.
            (Finite(a), Finite(b)) if matches!(ty.kind(), ty::Int(_) | ty::Uint(_) | ty::Char) => {
                if let (Some(a), Some(b)) = (a.try_to_leaf(), b.try_to_leaf()) {
                    let sz = ty.primitive_size(tcx);
                    let cmp = match ty.kind() {
                        ty::Uint(_) | ty::Char => a.to_uint(sz).cmp(&b.to_uint(sz)),
                        ty::Int(_) => a.to_int(sz).cmp(&b.to_int(sz)),
                        _ => unreachable!(),
                    };
                    return Some(cmp);
                }
            }
            _ => {}
        }

        let a = self.to_bits(ty, tcx);
        let b = other.to_bits(ty, tcx);

        match ty.kind() {
            ty::Float(ty::FloatTy::F16) => {
                use rustc_apfloat::Float;
                let a = rustc_apfloat::ieee::Half::from_bits(a);
                let b = rustc_apfloat::ieee::Half::from_bits(b);
                a.partial_cmp(&b)
            }
            ty::Float(ty::FloatTy::F32) => {
                use rustc_apfloat::Float;
                let a = rustc_apfloat::ieee::Single::from_bits(a);
                let b = rustc_apfloat::ieee::Single::from_bits(b);
                a.partial_cmp(&b)
            }
            ty::Float(ty::FloatTy::F64) => {
                use rustc_apfloat::Float;
                let a = rustc_apfloat::ieee::Double::from_bits(a);
                let b = rustc_apfloat::ieee::Double::from_bits(b);
                a.partial_cmp(&b)
            }
            ty::Float(ty::FloatTy::F128) => {
                use rustc_apfloat::Float;
                let a = rustc_apfloat::ieee::Quad::from_bits(a);
                let b = rustc_apfloat::ieee::Quad::from_bits(b);
                a.partial_cmp(&b)
            }
            ty::Int(ity) => {
                let size = rustc_abi::Integer::from_int_ty(&tcx, *ity).size();
                let a = size.sign_extend(a) as i128;
                let b = size.sign_extend(b) as i128;
                Some(a.cmp(&b))
            }
            ty::Uint(_) | ty::Char => Some(a.cmp(&b)),
            _ => bug!(),
        }
    }
}

// Some nodes are used a lot. Make sure they don't unintentionally get bigger.
#[cfg(target_pointer_width = "64")]
mod size_asserts {
    use rustc_data_structures::static_assert_size;

    use super::*;
    // tidy-alphabetical-start
    static_assert_size!(Block, 48);
    static_assert_size!(Expr<'_>, 64);
    static_assert_size!(ExprKind<'_>, 40);
    static_assert_size!(Pat<'_>, 72);
    static_assert_size!(PatKind<'_>, 48);
    static_assert_size!(Stmt<'_>, 48);
    static_assert_size!(StmtKind<'_>, 48);
    // tidy-alphabetical-end
}
