提交 955e2b2d 编写于 作者: E Ellen

nits

上级 79be0802
//! Values computed by queries that use MIR. //! Values computed by queries that use MIR.
use crate::mir::{Body, Promoted}; use crate::mir::{Body, Promoted};
use crate::thir::abstract_const;
use crate::ty::{self, Ty, TyCtxt}; use crate::ty::{self, Ty, TyCtxt};
use rustc_data_structures::sync::Lrc; use rustc_data_structures::sync::Lrc;
use rustc_data_structures::vec_map::VecMap; use rustc_data_structures::vec_map::VecMap;
...@@ -432,16 +431,4 @@ pub fn mir_for_ctfe_opt_const_arg(self, def: ty::WithOptConstParam<DefId>) -> &' ...@@ -432,16 +431,4 @@ pub fn mir_for_ctfe_opt_const_arg(self, def: ty::WithOptConstParam<DefId>) -> &'
self.mir_for_ctfe(def.did) self.mir_for_ctfe(def.did)
} }
} }
#[inline]
pub fn thir_abstract_const_opt_const_arg(
self,
def: ty::WithOptConstParam<DefId>,
) -> Result<Option<&'tcx [abstract_const::Node<'tcx>]>, ErrorReported> {
if let Some((did, param_did)) = def.as_const_arg() {
self.thir_abstract_const_of_const_arg((did, param_did))
} else {
self.thir_abstract_const(def.did)
}
}
} }
//! A subset of a mir body used for const evaluatability checking. //! A subset of a mir body used for const evaluatability checking.
use crate::mir; use crate::mir;
use crate::ty::{self, Ty}; use crate::ty::{self, Ty, TyCtxt};
use rustc_errors::ErrorReported;
rustc_index::newtype_index! { rustc_index::newtype_index! {
/// An index into an `AbstractConst`. /// An index into an `AbstractConst`.
...@@ -22,13 +23,13 @@ pub enum Node<'tcx> { ...@@ -22,13 +23,13 @@ pub enum Node<'tcx> {
#[derive(Debug, Copy, Clone, PartialEq, Eq, HashStable, TyEncodable, TyDecodable)] #[derive(Debug, Copy, Clone, PartialEq, Eq, HashStable, TyEncodable, TyDecodable)]
pub enum NotConstEvaluatable { pub enum NotConstEvaluatable {
Error(rustc_errors::ErrorReported), Error(ErrorReported),
MentionsInfer, MentionsInfer,
MentionsParam, MentionsParam,
} }
impl From<rustc_errors::ErrorReported> for NotConstEvaluatable { impl From<ErrorReported> for NotConstEvaluatable {
fn from(e: rustc_errors::ErrorReported) -> NotConstEvaluatable { fn from(e: ErrorReported) -> NotConstEvaluatable {
NotConstEvaluatable::Error(e) NotConstEvaluatable::Error(e)
} }
} }
...@@ -36,3 +37,17 @@ fn from(e: rustc_errors::ErrorReported) -> NotConstEvaluatable { ...@@ -36,3 +37,17 @@ fn from(e: rustc_errors::ErrorReported) -> NotConstEvaluatable {
TrivialTypeFoldableAndLiftImpls! { TrivialTypeFoldableAndLiftImpls! {
NotConstEvaluatable, NotConstEvaluatable,
} }
impl<'tcx> TyCtxt<'tcx> {
#[inline]
pub fn thir_abstract_const_opt_const_arg(
self,
def: ty::WithOptConstParam<rustc_hir::def_id::DefId>,
) -> Result<Option<&'tcx [Node<'tcx>]>, ErrorReported> {
if let Some((did, param_did)) = def.as_const_arg() {
self.thir_abstract_const_of_const_arg((did, param_did))
} else {
self.thir_abstract_const(def.did)
}
}
}
use super::*; use super::{
Arm, Block, Expr, ExprKind, Guard, InlineAsmOperand, Pat, PatKind, Stmt, StmtKind, Thir,
};
use rustc_middle::ty::Const;
pub trait Visitor<'a, 'tcx: 'a>: Sized { pub trait Visitor<'a, 'tcx: 'a>: Sized {
fn thir(&self) -> &'a Thir<'tcx>; fn thir(&self) -> &'a Thir<'tcx>;
......
...@@ -8,7 +8,6 @@ ...@@ -8,7 +8,6 @@
//! In this case we try to build an abstract representation of this constant using //! In this case we try to build an abstract representation of this constant using
//! `thir_abstract_const` which can then be checked for structural equality with other //! `thir_abstract_const` which can then be checked for structural equality with other
//! generic constants mentioned in the `caller_bounds` of the current environment. //! generic constants mentioned in the `caller_bounds` of the current environment.
use rustc_data_structures::sync::Lrc;
use rustc_errors::ErrorReported; use rustc_errors::ErrorReported;
use rustc_hir::def::DefKind; use rustc_hir::def::DefKind;
use rustc_index::vec::IndexVec; use rustc_index::vec::IndexVec;
...@@ -227,8 +226,7 @@ pub fn root(self) -> Node<'tcx> { ...@@ -227,8 +226,7 @@ pub fn root(self) -> Node<'tcx> {
struct AbstractConstBuilder<'a, 'tcx> { struct AbstractConstBuilder<'a, 'tcx> {
tcx: TyCtxt<'tcx>, tcx: TyCtxt<'tcx>,
body_id: thir::ExprId, body_id: thir::ExprId,
/// `Lrc` is used to avoid borrowck difficulties in `recurse_build` body: &'a thir::Thir<'tcx>,
body: Lrc<&'a thir::Thir<'tcx>>,
/// The current WIP node tree. /// The current WIP node tree.
nodes: IndexVec<NodeId, Node<'tcx>>, nodes: IndexVec<NodeId, Node<'tcx>>,
} }
...@@ -253,8 +251,7 @@ fn new( ...@@ -253,8 +251,7 @@ fn new(
tcx: TyCtxt<'tcx>, tcx: TyCtxt<'tcx>,
(body, body_id): (&'a thir::Thir<'tcx>, thir::ExprId), (body, body_id): (&'a thir::Thir<'tcx>, thir::ExprId),
) -> Result<Option<AbstractConstBuilder<'a, 'tcx>>, ErrorReported> { ) -> Result<Option<AbstractConstBuilder<'a, 'tcx>>, ErrorReported> {
let builder = let builder = AbstractConstBuilder { tcx, body_id, body, nodes: IndexVec::new() };
AbstractConstBuilder { tcx, body_id, body: Lrc::new(body), nodes: IndexVec::new() };
struct IsThirPolymorphic<'a, 'tcx> { struct IsThirPolymorphic<'a, 'tcx> {
is_poly: bool, is_poly: bool,
...@@ -328,7 +325,7 @@ fn build(mut self) -> Result<&'tcx [Node<'tcx>], ErrorReported> { ...@@ -328,7 +325,7 @@ fn build(mut self) -> Result<&'tcx [Node<'tcx>], ErrorReported> {
fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported> { fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported> {
use thir::ExprKind; use thir::ExprKind;
let node = &self.body.clone().exprs[node]; let node = &self.body.exprs[node];
debug!("recurse_build: node={:?}", node); debug!("recurse_build: node={:?}", node);
Ok(match &node.kind { Ok(match &node.kind {
// I dont know if handling of these 3 is correct // I dont know if handling of these 3 is correct
...@@ -338,10 +335,9 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported> ...@@ -338,10 +335,9 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported>
// subtle: associated consts are literals this arm handles // subtle: associated consts are literals this arm handles
// `<T as Trait>::ASSOC` as well as `12` // `<T as Trait>::ASSOC` as well as `12`
&ExprKind::Literal { literal, .. } &ExprKind::Literal { literal, .. } => self.nodes.push(Node::Leaf(literal)),
| &ExprKind::StaticRef { literal, .. } => self.nodes.push(Node::Leaf(literal)),
// FIXME(generic_const_exprs) handle `from_hir_call` field // FIXME(generic_const_exprs): Handle `from_hir_call` field
ExprKind::Call { fun, args, .. } => { ExprKind::Call { fun, args, .. } => {
let fun = self.recurse_build(*fun)?; let fun = self.recurse_build(*fun)?;
...@@ -361,7 +357,7 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported> ...@@ -361,7 +357,7 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported>
let arg = self.recurse_build(arg)?; let arg = self.recurse_build(arg)?;
self.nodes.push(Node::UnaryOp(op, arg)) self.nodes.push(Node::UnaryOp(op, arg))
}, },
// this is necessary so that the following compiles: // This is necessary so that the following compiles:
// //
// ``` // ```
// fn foo<const N: usize>(a: [(); N + 1]) { // fn foo<const N: usize>(a: [(); N + 1]) {
...@@ -369,16 +365,16 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported> ...@@ -369,16 +365,16 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported>
// } // }
// ``` // ```
ExprKind::Block { body: thir::Block { stmts: box [], expr: Some(e), .. }} => self.recurse_build(*e)?, ExprKind::Block { body: thir::Block { stmts: box [], expr: Some(e), .. }} => self.recurse_build(*e)?,
// ExprKind::Use happens when a `hir::ExprKind::Cast` is a // `ExprKind::Use` happens when a `hir::ExprKind::Cast` is a
// "coercion cast" i.e. using a coercion or is a no-op. // "coercion cast" i.e. using a coercion or is a no-op.
// this is important so that `N as usize as usize` doesnt unify with `N as usize` // This is important so that `N as usize as usize` doesnt unify with `N as usize`. (untested)
&ExprKind::Use { source} &ExprKind::Use { source}
| &ExprKind::Cast { source } => { | &ExprKind::Cast { source } => {
let arg = self.recurse_build(source)?; let arg = self.recurse_build(source)?;
self.nodes.push(Node::Cast(arg, node.ty)) self.nodes.push(Node::Cast(arg, node.ty))
}, },
// FIXME(generic_const_exprs) we want to support these // FIXME(generic_const_exprs): We may want to support these.
ExprKind::AddressOf { .. } ExprKind::AddressOf { .. }
| ExprKind::Borrow { .. } | ExprKind::Borrow { .. }
| ExprKind::Deref { .. } | ExprKind::Deref { .. }
...@@ -390,21 +386,24 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported> ...@@ -390,21 +386,24 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported>
| ExprKind::Index { .. } | ExprKind::Index { .. }
| ExprKind::Field { .. } | ExprKind::Field { .. }
| ExprKind::ConstBlock { .. } | ExprKind::ConstBlock { .. }
| ExprKind::Adt(_) => return self.error( | ExprKind::Adt(_) => self.error(
Some(node.span), Some(node.span),
"unsupported operation in generic constant, this may be supported in the future", "unsupported operation in generic constant, this may be supported in the future",
).map(|never| never), )?,
ExprKind::Match { .. } ExprKind::Match { .. }
| ExprKind::VarRef { .. } // // we dont permit let stmts so `VarRef` and `UpvarRef` cant happen
| ExprKind::UpvarRef { .. } // we dont permit let stmts so... | ExprKind::VarRef { .. }
| ExprKind::UpvarRef { .. }
| ExprKind::Closure { .. } | ExprKind::Closure { .. }
| ExprKind::Let { .. } // let expressions imply control flow | ExprKind::Let { .. } // let expressions imply control flow
| ExprKind::Loop { .. } | ExprKind::Loop { .. }
| ExprKind::Assign { .. } | ExprKind::Assign { .. }
| ExprKind::StaticRef { .. }
| ExprKind::LogicalOp { .. } | ExprKind::LogicalOp { .. }
| ExprKind::Unary { .. } // // we handle valid unary/binary ops above
| ExprKind::Binary { .. } // we handle valid unary/binary ops above | ExprKind::Unary { .. }
| ExprKind::Binary { .. }
| ExprKind::Break { .. } | ExprKind::Break { .. }
| ExprKind::Continue { .. } | ExprKind::Continue { .. }
| ExprKind::If { .. } | ExprKind::If { .. }
...@@ -415,7 +414,7 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported> ...@@ -415,7 +414,7 @@ fn recurse_build(&mut self, node: thir::ExprId) -> Result<NodeId, ErrorReported>
| ExprKind::Box { .. } // allocations not allowed in constants | ExprKind::Box { .. } // allocations not allowed in constants
| ExprKind::AssignOp { .. } | ExprKind::AssignOp { .. }
| ExprKind::InlineAsm { .. } | ExprKind::InlineAsm { .. }
| ExprKind::Yield { .. } => return self.error(Some(node.span), "unsupported operation in generic constant").map(|never| never), | ExprKind::Yield { .. } => self.error(Some(node.span), "unsupported operation in generic constant")?,
}) })
} }
} }
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册