Auto merge of #28138 - nrc:hir, r=nikomatsakis
r? @nikomatsakis Trying to land this first stab, which basically just duplicates the AST. Will file issues for the various things I've got in mind to improve.
This commit is contained in:
commit
cd138dc447
19
mk/crates.mk
19
mk/crates.mk
@ -56,7 +56,7 @@ TARGET_CRATES := libc std flate arena term \
|
||||
alloc_system
|
||||
RUSTC_CRATES := rustc rustc_typeck rustc_borrowck rustc_resolve rustc_driver \
|
||||
rustc_trans rustc_back rustc_llvm rustc_privacy rustc_lint \
|
||||
rustc_data_structures rustc_platform_intrinsics
|
||||
rustc_data_structures rustc_front rustc_platform_intrinsics
|
||||
HOST_CRATES := syntax $(RUSTC_CRATES) rustdoc fmt_macros
|
||||
TOOLS := compiletest rustdoc rustc rustbook error-index-generator
|
||||
|
||||
@ -71,23 +71,24 @@ DEPS_graphviz := std
|
||||
DEPS_syntax := std term serialize log fmt_macros arena libc rustc_bitflags
|
||||
DEPS_rustc_driver := arena flate getopts graphviz libc rustc rustc_back rustc_borrowck \
|
||||
rustc_typeck rustc_resolve log syntax serialize rustc_llvm \
|
||||
rustc_trans rustc_privacy rustc_lint
|
||||
rustc_trans rustc_privacy rustc_lint rustc_front
|
||||
|
||||
DEPS_rustc_trans := arena flate getopts graphviz libc rustc rustc_back \
|
||||
log syntax serialize rustc_llvm rustc_platform_intrinsics
|
||||
DEPS_rustc_typeck := rustc syntax rustc_platform_intrinsics
|
||||
DEPS_rustc_borrowck := rustc log graphviz syntax
|
||||
DEPS_rustc_resolve := rustc log syntax
|
||||
DEPS_rustc_privacy := rustc log syntax
|
||||
log syntax serialize rustc_llvm rustc_front rustc_platform_intrinsics
|
||||
DEPS_rustc_typeck := rustc syntax rustc_front rustc_platform_intrinsics
|
||||
DEPS_rustc_borrowck := rustc rustc_front log graphviz syntax
|
||||
DEPS_rustc_resolve := rustc rustc_front log syntax
|
||||
DEPS_rustc_privacy := rustc rustc_front log syntax
|
||||
DEPS_rustc_lint := rustc log syntax
|
||||
DEPS_rustc := syntax flate arena serialize getopts rbml \
|
||||
log graphviz rustc_llvm rustc_back rustc_data_structures
|
||||
DEPS_rustc_llvm := native:rustllvm libc std rustc_bitflags
|
||||
DEPS_rustc_platform_intrinsics := rustc rustc_llvm
|
||||
DEPS_rustc_back := std syntax rustc_llvm flate log libc
|
||||
DEPS_rustc_back := std syntax rustc_llvm rustc_front flate log libc
|
||||
DEPS_rustc_front := std syntax log serialize
|
||||
DEPS_rustc_data_structures := std log serialize
|
||||
DEPS_rustdoc := rustc rustc_driver native:hoedown serialize getopts \
|
||||
test rustc_lint
|
||||
test rustc_lint rustc_front
|
||||
DEPS_rustc_bitflags := core
|
||||
DEPS_flate := std native:miniz
|
||||
DEPS_arena := std
|
||||
|
@ -268,7 +268,7 @@ fn run_pretty_test(config: &Config, props: &TestProps, testfile: &Path) {
|
||||
// FIXME (#9639): This needs to handle non-utf8 paths
|
||||
let mut args = vec!("-".to_owned(),
|
||||
"-Zunstable-options".to_owned(),
|
||||
"--pretty".to_owned(),
|
||||
"--unpretty".to_owned(),
|
||||
pretty_type,
|
||||
format!("--target={}", config.target),
|
||||
"-L".to_owned(),
|
||||
|
@ -23,12 +23,13 @@
|
||||
|
||||
pub use self::Code::*;
|
||||
|
||||
use ast_map::{self, Node};
|
||||
use front::map::{self, Node};
|
||||
use syntax::abi;
|
||||
use syntax::ast::{Block, FnDecl, NodeId};
|
||||
use syntax::ast;
|
||||
use rustc_front::hir::{Block, FnDecl};
|
||||
use syntax::ast::{NodeId, Ident};
|
||||
use rustc_front::hir as ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit::FnKind;
|
||||
use rustc_front::visit::FnKind;
|
||||
|
||||
/// An FnLikeNode is a Node that is like a fn, in that it has a decl
|
||||
/// and a body (as well as a NodeId, a span, etc).
|
||||
@ -40,7 +41,7 @@ use syntax::visit::FnKind;
|
||||
///
|
||||
/// To construct one, use the `Code::from_node` function.
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct FnLikeNode<'a> { node: ast_map::Node<'a> }
|
||||
pub struct FnLikeNode<'a> { node: map::Node<'a> }
|
||||
|
||||
/// MaybeFnLike wraps a method that indicates if an object
|
||||
/// corresponds to some FnLikeNode.
|
||||
@ -86,7 +87,7 @@ pub enum Code<'a> {
|
||||
}
|
||||
|
||||
impl<'a> Code<'a> {
|
||||
pub fn id(&self) -> ast::NodeId {
|
||||
pub fn id(&self) -> NodeId {
|
||||
match *self {
|
||||
FnLikeCode(node) => node.id(),
|
||||
BlockCode(block) => block.id,
|
||||
@ -95,7 +96,7 @@ impl<'a> Code<'a> {
|
||||
|
||||
/// Attempts to construct a Code from presumed FnLike or Block node input.
|
||||
pub fn from_node(node: Node) -> Option<Code> {
|
||||
if let ast_map::NodeBlock(block) = node {
|
||||
if let map::NodeBlock(block) = node {
|
||||
Some(BlockCode(block))
|
||||
} else {
|
||||
FnLikeNode::from_node(node).map(|fn_like| FnLikeCode(fn_like))
|
||||
@ -106,7 +107,7 @@ impl<'a> Code<'a> {
|
||||
/// These are all the components one can extract from a fn item for
|
||||
/// use when implementing FnLikeNode operations.
|
||||
struct ItemFnParts<'a> {
|
||||
ident: ast::Ident,
|
||||
ident: Ident,
|
||||
decl: &'a ast::FnDecl,
|
||||
unsafety: ast::Unsafety,
|
||||
constness: ast::Constness,
|
||||
@ -114,7 +115,7 @@ struct ItemFnParts<'a> {
|
||||
vis: ast::Visibility,
|
||||
generics: &'a ast::Generics,
|
||||
body: &'a Block,
|
||||
id: ast::NodeId,
|
||||
id: NodeId,
|
||||
span: Span
|
||||
}
|
||||
|
||||
@ -137,10 +138,10 @@ impl<'a> FnLikeNode<'a> {
|
||||
/// Attempts to construct a FnLikeNode from presumed FnLike node input.
|
||||
pub fn from_node(node: Node) -> Option<FnLikeNode> {
|
||||
let fn_like = match node {
|
||||
ast_map::NodeItem(item) => item.is_fn_like(),
|
||||
ast_map::NodeTraitItem(tm) => tm.is_fn_like(),
|
||||
ast_map::NodeImplItem(_) => true,
|
||||
ast_map::NodeExpr(e) => e.is_fn_like(),
|
||||
map::NodeItem(item) => item.is_fn_like(),
|
||||
map::NodeTraitItem(tm) => tm.is_fn_like(),
|
||||
map::NodeImplItem(_) => true,
|
||||
map::NodeExpr(e) => e.is_fn_like(),
|
||||
_ => false
|
||||
};
|
||||
if fn_like {
|
||||
@ -202,7 +203,7 @@ impl<'a> FnLikeNode<'a> {
|
||||
fn handle<A, I, M, C>(self, item_fn: I, method: M, closure: C) -> A where
|
||||
I: FnOnce(ItemFnParts<'a>) -> A,
|
||||
M: FnOnce(NodeId,
|
||||
ast::Ident,
|
||||
Ident,
|
||||
&'a ast::MethodSig,
|
||||
Option<ast::Visibility>,
|
||||
&'a ast::Block,
|
||||
@ -211,7 +212,7 @@ impl<'a> FnLikeNode<'a> {
|
||||
C: FnOnce(ClosureParts<'a>) -> A,
|
||||
{
|
||||
match self.node {
|
||||
ast_map::NodeItem(i) => match i.node {
|
||||
map::NodeItem(i) => match i.node {
|
||||
ast::ItemFn(ref decl, unsafety, constness, abi, ref generics, ref block) =>
|
||||
item_fn(ItemFnParts {
|
||||
id: i.id,
|
||||
@ -227,13 +228,13 @@ impl<'a> FnLikeNode<'a> {
|
||||
}),
|
||||
_ => panic!("item FnLikeNode that is not fn-like"),
|
||||
},
|
||||
ast_map::NodeTraitItem(ti) => match ti.node {
|
||||
map::NodeTraitItem(ti) => match ti.node {
|
||||
ast::MethodTraitItem(ref sig, Some(ref body)) => {
|
||||
method(ti.id, ti.ident, sig, None, body, ti.span)
|
||||
}
|
||||
_ => panic!("trait method FnLikeNode that is not fn-like"),
|
||||
},
|
||||
ast_map::NodeImplItem(ii) => {
|
||||
map::NodeImplItem(ii) => {
|
||||
match ii.node {
|
||||
ast::MethodImplItem(ref sig, ref body) => {
|
||||
method(ii.id, ii.ident, sig, Some(ii.vis), body, ii.span)
|
||||
@ -243,7 +244,7 @@ impl<'a> FnLikeNode<'a> {
|
||||
}
|
||||
}
|
||||
}
|
||||
ast_map::NodeExpr(e) => match e.node {
|
||||
map::NodeExpr(e) => match e.node {
|
||||
ast::ExprClosure(_, ref decl, ref block) =>
|
||||
closure(ClosureParts::new(&**decl, &**block, e.id, e.span)),
|
||||
_ => panic!("expr FnLikeNode that is not fn-like"),
|
@ -1,4 +1,4 @@
|
||||
// Copyright 2012-2013 The Rust Project Developers. See the COPYRIGHT
|
||||
// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
|
||||
// file at the top-level directory of this distribution and at
|
||||
// http://rust-lang.org/COPYRIGHT.
|
||||
//
|
||||
@ -15,14 +15,17 @@ use self::MapEntry::*;
|
||||
use metadata::inline::InlinedItem;
|
||||
use metadata::inline::InlinedItem as II;
|
||||
use middle::def_id::DefId;
|
||||
|
||||
use syntax::abi;
|
||||
use syntax::ast::*;
|
||||
use syntax::ast_util;
|
||||
use syntax::codemap::{DUMMY_SP, Span, Spanned};
|
||||
use syntax::fold::Folder;
|
||||
use syntax::ast::{Name, NodeId, Ident, CRATE_NODE_ID, DUMMY_NODE_ID};
|
||||
use syntax::codemap::{Span, Spanned};
|
||||
use syntax::parse::token;
|
||||
use syntax::print::pprust;
|
||||
use syntax::visit::{self, Visitor};
|
||||
|
||||
use rustc_front::hir::*;
|
||||
use rustc_front::fold::Folder;
|
||||
use rustc_front::visit::{self, Visitor};
|
||||
use rustc_front::util;
|
||||
use rustc_front::print::pprust;
|
||||
|
||||
use arena::TypedArena;
|
||||
use std::cell::RefCell;
|
||||
@ -159,7 +162,7 @@ impl<'ast> Clone for MapEntry<'ast> {
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
struct InlinedParent {
|
||||
pub struct InlinedParent {
|
||||
path: Vec<PathElem>,
|
||||
ii: InlinedItem
|
||||
}
|
||||
@ -227,7 +230,7 @@ impl<'ast> MapEntry<'ast> {
|
||||
|
||||
/// Stores a crate and any number of inlined items from other crates.
|
||||
pub struct Forest {
|
||||
krate: Crate,
|
||||
pub krate: Crate,
|
||||
inlined_items: TypedArena<InlinedParent>
|
||||
}
|
||||
|
||||
@ -246,9 +249,10 @@ impl Forest {
|
||||
|
||||
/// Represents a mapping from Node IDs to AST elements and their parent
|
||||
/// Node IDs
|
||||
#[derive(Clone)]
|
||||
pub struct Map<'ast> {
|
||||
/// The backing storage for all the AST nodes.
|
||||
forest: &'ast Forest,
|
||||
pub forest: &'ast Forest,
|
||||
|
||||
/// NodeIds are sequential integers from 0, so we can be
|
||||
/// super-compact by storing them in a vector. Not everything with
|
||||
@ -870,7 +874,7 @@ impl<'ast> Visitor<'ast> for NodeCollector<'ast> {
|
||||
}
|
||||
|
||||
fn visit_stmt(&mut self, stmt: &'ast Stmt) {
|
||||
let id = ast_util::stmt_id(stmt);
|
||||
let id = util::stmt_id(stmt);
|
||||
self.insert(id, NodeStmt(stmt));
|
||||
let parent_node = self.parent_node;
|
||||
self.parent_node = id;
|
||||
@ -917,20 +921,7 @@ impl<'ast> Visitor<'ast> for NodeCollector<'ast> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn map_crate<'ast, F: FoldOps>(forest: &'ast mut Forest, fold_ops: F) -> Map<'ast> {
|
||||
// Replace the crate with an empty one to take it out.
|
||||
let krate = mem::replace(&mut forest.krate, Crate {
|
||||
module: Mod {
|
||||
inner: DUMMY_SP,
|
||||
items: vec![],
|
||||
},
|
||||
attrs: vec![],
|
||||
config: vec![],
|
||||
exported_macros: vec![],
|
||||
span: DUMMY_SP
|
||||
});
|
||||
forest.krate = IdAndSpanUpdater { fold_ops: fold_ops }.fold_crate(krate);
|
||||
|
||||
pub fn map_crate<'ast>(forest: &'ast mut Forest) -> Map<'ast> {
|
||||
let mut collector = NodeCollector {
|
||||
map: vec![],
|
||||
parent_node: CRATE_NODE_ID,
|
||||
@ -974,11 +965,11 @@ pub fn map_decoded_item<'ast, F: FoldOps>(map: &Map<'ast>,
|
||||
II::Item(i) => II::Item(fld.fold_item(i).expect_one("expected one item")),
|
||||
II::TraitItem(d, ti) => {
|
||||
II::TraitItem(fld.fold_ops.new_def_id(d),
|
||||
fld.fold_trait_item(ti).expect_one("expected one trait item"))
|
||||
fld.fold_trait_item(ti).expect_one("expected one trait item"))
|
||||
}
|
||||
II::ImplItem(d, ii) => {
|
||||
II::ImplItem(fld.fold_ops.new_def_id(d),
|
||||
fld.fold_impl_item(ii).expect_one("expected one impl item"))
|
||||
fld.fold_impl_item(ii).expect_one("expected one impl item"))
|
||||
}
|
||||
II::Foreign(i) => II::Foreign(fld.fold_foreign_item(i))
|
||||
};
|
||||
@ -1064,7 +1055,6 @@ fn node_id_to_string(map: &Map, id: NodeId, include_id: bool) -> String {
|
||||
ItemTrait(..) => "trait",
|
||||
ItemImpl(..) => "impl",
|
||||
ItemDefaultImpl(..) => "default impl",
|
||||
ItemMac(..) => "macro"
|
||||
};
|
||||
format!("{} {}{}", item_str, path_str, id_str)
|
||||
}
|
||||
@ -1091,10 +1081,6 @@ fn node_id_to_string(map: &Map, id: NodeId, include_id: bool) -> String {
|
||||
map.path_to_string(id),
|
||||
id_str)
|
||||
}
|
||||
MacImplItem(ref mac) => {
|
||||
format!("method macro {}{}",
|
||||
pprust::mac_to_string(mac), id_str)
|
||||
}
|
||||
}
|
||||
}
|
||||
Some(NodeTraitItem(ti)) => {
|
@ -73,6 +73,7 @@ extern crate graphviz;
|
||||
extern crate libc;
|
||||
extern crate rustc_llvm;
|
||||
extern crate rustc_back;
|
||||
extern crate rustc_front;
|
||||
extern crate rustc_data_structures;
|
||||
extern crate serialize;
|
||||
extern crate rbml;
|
||||
@ -101,7 +102,9 @@ pub mod back {
|
||||
pub use rustc_back::svh;
|
||||
}
|
||||
|
||||
pub mod ast_map;
|
||||
pub mod front {
|
||||
pub mod map;
|
||||
}
|
||||
|
||||
pub mod middle {
|
||||
pub mod astconv_util;
|
||||
|
@ -283,6 +283,7 @@ macro_rules! run_lints { ($cx:expr, $f:ident, $($args:expr),*) => ({
|
||||
|
||||
/// Parse the lint attributes into a vector, with `Err`s for malformed lint
|
||||
/// attributes. Writing this as an iterator is an enormous mess.
|
||||
// See also the hir version just below.
|
||||
pub fn gather_attrs(attrs: &[ast::Attribute])
|
||||
-> Vec<Result<(InternedString, Level, Span), Span>> {
|
||||
let mut out = vec!();
|
||||
@ -312,6 +313,40 @@ pub fn gather_attrs(attrs: &[ast::Attribute])
|
||||
}
|
||||
out
|
||||
}
|
||||
// Copy-pasted from the above function :-(
|
||||
pub fn gather_attrs_from_hir(attrs: &[::rustc_front::hir::Attribute])
|
||||
-> Vec<Result<(InternedString, Level, Span), Span>> {
|
||||
use ::rustc_front::attr::AttrMetaMethods;
|
||||
|
||||
let mut out = vec!();
|
||||
for attr in attrs {
|
||||
let level = match Level::from_str(&attr.name()) {
|
||||
None => continue,
|
||||
Some(lvl) => lvl,
|
||||
};
|
||||
|
||||
::rustc_front::attr::mark_used(attr);
|
||||
|
||||
let meta = &attr.node.value;
|
||||
let metas = match meta.node {
|
||||
::rustc_front::hir::MetaList(_, ref metas) => metas,
|
||||
_ => {
|
||||
out.push(Err(meta.span));
|
||||
continue;
|
||||
}
|
||||
};
|
||||
|
||||
for meta in metas {
|
||||
out.push(match meta.node {
|
||||
::rustc_front::hir::MetaWord(ref lint_name) => {
|
||||
Ok((lint_name.clone(), level, meta.span))
|
||||
}
|
||||
_ => Err(meta.span),
|
||||
});
|
||||
}
|
||||
}
|
||||
out
|
||||
}
|
||||
|
||||
/// Emit a lint as a warning or an error (or not at all)
|
||||
/// according to `level`.
|
||||
@ -696,9 +731,9 @@ impl LintPass for GatherNodeLevels {
|
||||
///
|
||||
/// Consumes the `lint_store` field of the `Session`.
|
||||
pub fn check_crate(tcx: &ty::ctxt,
|
||||
krate: &ast::Crate,
|
||||
exported_items: &ExportedItems) {
|
||||
|
||||
let krate = tcx.map.krate();
|
||||
let mut cx = Context::new(tcx, krate, exported_items);
|
||||
|
||||
// Visit the whole crate.
|
||||
|
@ -38,7 +38,7 @@ use syntax::visit::FnKind;
|
||||
use syntax::ast;
|
||||
|
||||
pub use lint::context::{Context, LintStore, raw_emit_lint, check_crate, gather_attrs,
|
||||
GatherNodeLevels};
|
||||
gather_attrs_from_hir, GatherNodeLevels};
|
||||
|
||||
/// Specification of a single lint.
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
|
@ -21,6 +21,7 @@ use metadata::decoder;
|
||||
use metadata::loader;
|
||||
use metadata::loader::CratePaths;
|
||||
use util::nodemap::FnvHashMap;
|
||||
use front::map as hir_map;
|
||||
|
||||
use std::cell::{RefCell, Cell};
|
||||
use std::path::PathBuf;
|
||||
@ -29,20 +30,22 @@ use std::fs;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::abi;
|
||||
use syntax::attr;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use syntax::codemap::{self, Span, mk_sp, Pos};
|
||||
use syntax::parse;
|
||||
use syntax::attr;
|
||||
use syntax::parse::token::InternedString;
|
||||
use syntax::visit;
|
||||
use syntax::util::small_vector::SmallVector;
|
||||
use ast_map;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::attr as attr_front;
|
||||
use rustc_front::attr::AttrMetaMethods;
|
||||
use rustc_front::lowering::unlower_attribute;
|
||||
use log;
|
||||
|
||||
pub struct LocalCrateReader<'a, 'b:'a> {
|
||||
sess: &'a Session,
|
||||
creader: CrateReader<'a>,
|
||||
ast_map: &'a ast_map::Map<'b>,
|
||||
ast_map: &'a hir_map::Map<'b>,
|
||||
}
|
||||
|
||||
pub struct CrateReader<'a> {
|
||||
@ -52,7 +55,7 @@ pub struct CrateReader<'a> {
|
||||
}
|
||||
|
||||
impl<'a, 'b, 'v> visit::Visitor<'v> for LocalCrateReader<'a, 'b> {
|
||||
fn visit_item(&mut self, a: &ast::Item) {
|
||||
fn visit_item(&mut self, a: &hir::Item) {
|
||||
self.process_item(a);
|
||||
visit::walk_item(self, a);
|
||||
}
|
||||
@ -77,6 +80,11 @@ fn should_link(i: &ast::Item) -> bool {
|
||||
!attr::contains_name(&i.attrs, "no_link")
|
||||
}
|
||||
|
||||
// Dup for the hir
|
||||
fn should_link_hir(i: &hir::Item) -> bool {
|
||||
!attr_front::contains_name(&i.attrs, "no_link")
|
||||
}
|
||||
|
||||
struct CrateInfo {
|
||||
ident: String,
|
||||
name: String,
|
||||
@ -188,6 +196,31 @@ impl<'a> CrateReader<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
// Dup of the above, but for the hir
|
||||
fn extract_crate_info_hir(&self, i: &hir::Item) -> Option<CrateInfo> {
|
||||
match i.node {
|
||||
hir::ItemExternCrate(ref path_opt) => {
|
||||
debug!("resolving extern crate stmt. ident: {} path_opt: {:?}",
|
||||
i.ident, path_opt);
|
||||
let name = match *path_opt {
|
||||
Some(name) => {
|
||||
validate_crate_name(Some(self.sess), &name.as_str(),
|
||||
Some(i.span));
|
||||
name.to_string()
|
||||
}
|
||||
None => i.ident.to_string(),
|
||||
};
|
||||
Some(CrateInfo {
|
||||
ident: i.ident.to_string(),
|
||||
name: name,
|
||||
id: i.id,
|
||||
should_link: should_link_hir(i),
|
||||
})
|
||||
}
|
||||
_ => None
|
||||
}
|
||||
}
|
||||
|
||||
fn existing_match(&self, name: &str, hash: Option<&Svh>, kind: PathKind)
|
||||
-> Option<ast::CrateNum> {
|
||||
let mut ret = None;
|
||||
@ -295,7 +328,7 @@ impl<'a> CrateReader<'a> {
|
||||
let attrs = decoder::get_crate_attributes(data);
|
||||
for attr in &attrs {
|
||||
if &attr.name()[..] == "staged_api" {
|
||||
match attr.node.value.node { ast::MetaWord(_) => return true, _ => (/*pass*/) }
|
||||
match attr.node.value.node { hir::MetaWord(_) => return true, _ => (/*pass*/) }
|
||||
}
|
||||
}
|
||||
|
||||
@ -425,11 +458,11 @@ impl<'a> CrateReader<'a> {
|
||||
}
|
||||
|
||||
/// Read exported macros.
|
||||
pub fn read_exported_macros(&mut self, krate: &ast::Item) -> Vec<ast::MacroDef> {
|
||||
let ci = self.extract_crate_info(krate).unwrap();
|
||||
let ekrate = self.read_extension_crate(krate.span, &ci);
|
||||
pub fn read_exported_macros(&mut self, item: &ast::Item) -> Vec<ast::MacroDef> {
|
||||
let ci = self.extract_crate_info(item).unwrap();
|
||||
let ekrate = self.read_extension_crate(item.span, &ci);
|
||||
|
||||
let source_name = format!("<{} macros>", krate.ident);
|
||||
let source_name = format!("<{} macros>", item.ident);
|
||||
let mut macros = vec![];
|
||||
decoder::each_exported_macro(ekrate.metadata.as_slice(),
|
||||
&*self.sess.cstore.intr,
|
||||
@ -449,10 +482,10 @@ impl<'a> CrateReader<'a> {
|
||||
p.abort_if_errors();
|
||||
macros.push(ast::MacroDef {
|
||||
ident: name.ident(),
|
||||
attrs: attrs,
|
||||
attrs: attrs.iter().map(|a| unlower_attribute(a)).collect(),
|
||||
id: ast::DUMMY_NODE_ID,
|
||||
span: span,
|
||||
imported_from: Some(krate.ident),
|
||||
imported_from: Some(item.ident),
|
||||
// overridden in plugin/load.rs
|
||||
export: false,
|
||||
use_locally: false,
|
||||
@ -639,7 +672,7 @@ impl<'a> CrateReader<'a> {
|
||||
}
|
||||
|
||||
impl<'a, 'b> LocalCrateReader<'a, 'b> {
|
||||
pub fn new(sess: &'a Session, map: &'a ast_map::Map<'b>) -> LocalCrateReader<'a, 'b> {
|
||||
pub fn new(sess: &'a Session, map: &'a hir_map::Map<'b>) -> LocalCrateReader<'a, 'b> {
|
||||
LocalCrateReader {
|
||||
sess: sess,
|
||||
creader: CrateReader::new(sess),
|
||||
@ -650,7 +683,7 @@ impl<'a, 'b> LocalCrateReader<'a, 'b> {
|
||||
// Traverses an AST, reading all the information about use'd crates and
|
||||
// extern libraries necessary for later resolving, typechecking, linking,
|
||||
// etc.
|
||||
pub fn read_crates(&mut self, krate: &ast::Crate) {
|
||||
pub fn read_crates(&mut self, krate: &hir::Crate) {
|
||||
self.process_crate(krate);
|
||||
visit::walk_crate(self, krate);
|
||||
self.creader.inject_allocator_crate();
|
||||
@ -665,7 +698,7 @@ impl<'a, 'b> LocalCrateReader<'a, 'b> {
|
||||
self.creader.register_statically_included_foreign_items();
|
||||
}
|
||||
|
||||
fn process_crate(&self, c: &ast::Crate) {
|
||||
fn process_crate(&self, c: &hir::Crate) {
|
||||
for a in c.attrs.iter().filter(|m| m.name() == "link_args") {
|
||||
match a.value_str() {
|
||||
Some(ref linkarg) => self.sess.cstore.add_used_link_args(&linkarg),
|
||||
@ -674,14 +707,14 @@ impl<'a, 'b> LocalCrateReader<'a, 'b> {
|
||||
}
|
||||
}
|
||||
|
||||
fn process_item(&mut self, i: &ast::Item) {
|
||||
fn process_item(&mut self, i: &hir::Item) {
|
||||
match i.node {
|
||||
ast::ItemExternCrate(_) => {
|
||||
if !should_link(i) {
|
||||
hir::ItemExternCrate(_) => {
|
||||
if !should_link_hir(i) {
|
||||
return;
|
||||
}
|
||||
|
||||
match self.creader.extract_crate_info(i) {
|
||||
match self.creader.extract_crate_info_hir(i) {
|
||||
Some(info) => {
|
||||
let (cnum, cmeta, _) = self.creader.resolve_crate(&None,
|
||||
&info.ident,
|
||||
@ -698,12 +731,12 @@ impl<'a, 'b> LocalCrateReader<'a, 'b> {
|
||||
None => ()
|
||||
}
|
||||
}
|
||||
ast::ItemForeignMod(ref fm) => self.process_foreign_mod(i, fm),
|
||||
hir::ItemForeignMod(ref fm) => self.process_foreign_mod(i, fm),
|
||||
_ => { }
|
||||
}
|
||||
}
|
||||
|
||||
fn process_foreign_mod(&mut self, i: &ast::Item, fm: &ast::ForeignMod) {
|
||||
fn process_foreign_mod(&mut self, i: &hir::Item, fm: &hir::ForeignMod) {
|
||||
if fm.abi == abi::Rust || fm.abi == abi::RustIntrinsic || fm.abi == abi::PlatformIntrinsic {
|
||||
return;
|
||||
}
|
||||
|
@ -10,7 +10,7 @@
|
||||
|
||||
// Searching for information from the cstore
|
||||
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
use metadata::common::*;
|
||||
use metadata::cstore;
|
||||
use metadata::decoder;
|
||||
@ -23,7 +23,8 @@ use rbml;
|
||||
use rbml::reader;
|
||||
use std::rc::Rc;
|
||||
use syntax::ast;
|
||||
use syntax::attr;
|
||||
use rustc_front::attr;
|
||||
use rustc_front::hir;
|
||||
use syntax::diagnostic::expect;
|
||||
|
||||
use std::collections::hash_map::HashMap;
|
||||
@ -32,7 +33,7 @@ use std::collections::hash_map::HashMap;
|
||||
pub struct MethodInfo {
|
||||
pub name: ast::Name,
|
||||
pub def_id: DefId,
|
||||
pub vis: ast::Visibility,
|
||||
pub vis: hir::Visibility,
|
||||
}
|
||||
|
||||
pub fn get_symbol(cstore: &cstore::CStore, def: DefId) -> String {
|
||||
@ -55,7 +56,7 @@ pub fn each_lang_item<F>(cstore: &cstore::CStore,
|
||||
pub fn each_child_of_item<F>(cstore: &cstore::CStore,
|
||||
def_id: DefId,
|
||||
callback: F) where
|
||||
F: FnMut(decoder::DefLike, ast::Name, ast::Visibility),
|
||||
F: FnMut(decoder::DefLike, ast::Name, hir::Visibility),
|
||||
{
|
||||
let crate_data = cstore.get_crate_data(def_id.krate);
|
||||
let get_crate_data = |cnum| {
|
||||
@ -72,7 +73,7 @@ pub fn each_child_of_item<F>(cstore: &cstore::CStore,
|
||||
pub fn each_top_level_item_of_crate<F>(cstore: &cstore::CStore,
|
||||
cnum: ast::CrateNum,
|
||||
callback: F) where
|
||||
F: FnMut(decoder::DefLike, ast::Name, ast::Visibility),
|
||||
F: FnMut(decoder::DefLike, ast::Name, hir::Visibility),
|
||||
{
|
||||
let crate_data = cstore.get_crate_data(cnum);
|
||||
let get_crate_data = |cnum| {
|
||||
@ -190,7 +191,7 @@ pub fn get_methods_if_impl(cstore: &cstore::CStore,
|
||||
|
||||
pub fn get_item_attrs(cstore: &cstore::CStore,
|
||||
def_id: DefId)
|
||||
-> Vec<ast::Attribute> {
|
||||
-> Vec<hir::Attribute> {
|
||||
let cdata = cstore.get_crate_data(def_id.krate);
|
||||
decoder::get_item_attrs(&*cdata, def_id.node)
|
||||
}
|
||||
@ -201,7 +202,7 @@ pub fn get_struct_field_names(cstore: &cstore::CStore, def: DefId) -> Vec<ast::N
|
||||
}
|
||||
|
||||
pub fn get_struct_field_attrs(cstore: &cstore::CStore, def: DefId) -> HashMap<ast::NodeId,
|
||||
Vec<ast::Attribute>> {
|
||||
Vec<hir::Attribute>> {
|
||||
let cdata = cstore.get_crate_data(def.krate);
|
||||
decoder::get_struct_field_attrs(&*cdata)
|
||||
}
|
||||
@ -269,7 +270,7 @@ pub fn get_field_type<'tcx>(tcx: &ty::ctxt<'tcx>, class_id: DefId,
|
||||
|
||||
pub fn get_impl_polarity<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
def: DefId)
|
||||
-> Option<ast::ImplPolarity>
|
||||
-> Option<hir::ImplPolarity>
|
||||
{
|
||||
let cstore = &tcx.sess.cstore;
|
||||
let cdata = cstore.get_crate_data(def.krate);
|
||||
|
@ -27,12 +27,12 @@ use std::rc::Rc;
|
||||
use std::path::PathBuf;
|
||||
use flate::Bytes;
|
||||
use syntax::ast;
|
||||
use syntax::attr;
|
||||
use rustc_front::attr;
|
||||
use syntax::codemap;
|
||||
use syntax::parse::token;
|
||||
use syntax::parse::token::IdentInterner;
|
||||
use syntax::util::small_vector::SmallVector;
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
|
||||
// A map from external crate numbers (as decoded from some crate file) to
|
||||
// local crate numbers (as generated during this session). Each external
|
||||
|
@ -15,7 +15,10 @@
|
||||
pub use self::DefLike::*;
|
||||
use self::Family::*;
|
||||
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
use rustc_front::print::pprust;
|
||||
use rustc_front::hir;
|
||||
|
||||
use back::svh::Svh;
|
||||
use metadata::cstore::crate_metadata;
|
||||
use metadata::common::*;
|
||||
@ -45,15 +48,15 @@ use std::str;
|
||||
use rbml::reader;
|
||||
use rbml;
|
||||
use serialize::Decodable;
|
||||
use syntax::abi;
|
||||
use syntax::attr;
|
||||
use rustc_front::attr;
|
||||
use syntax::parse::token::{IdentInterner, special_idents};
|
||||
use syntax::parse::token;
|
||||
use syntax::print::pprust;
|
||||
use syntax::ast;
|
||||
use syntax::abi;
|
||||
use syntax::codemap;
|
||||
use syntax::ptr::P;
|
||||
|
||||
|
||||
pub type Cmd<'a> = &'a crate_metadata;
|
||||
|
||||
// A function that takes a def_id relative to the crate being searched and
|
||||
@ -158,26 +161,26 @@ fn item_family(item: rbml::Doc) -> Family {
|
||||
}
|
||||
}
|
||||
|
||||
fn item_visibility(item: rbml::Doc) -> ast::Visibility {
|
||||
fn item_visibility(item: rbml::Doc) -> hir::Visibility {
|
||||
match reader::maybe_get_doc(item, tag_items_data_item_visibility) {
|
||||
None => ast::Public,
|
||||
None => hir::Public,
|
||||
Some(visibility_doc) => {
|
||||
match reader::doc_as_u8(visibility_doc) as char {
|
||||
'y' => ast::Public,
|
||||
'i' => ast::Inherited,
|
||||
'y' => hir::Public,
|
||||
'i' => hir::Inherited,
|
||||
_ => panic!("unknown visibility character")
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn fn_constness(item: rbml::Doc) -> ast::Constness {
|
||||
fn fn_constness(item: rbml::Doc) -> hir::Constness {
|
||||
match reader::maybe_get_doc(item, tag_items_data_item_constness) {
|
||||
None => ast::Constness::NotConst,
|
||||
None => hir::Constness::NotConst,
|
||||
Some(constness_doc) => {
|
||||
match reader::doc_as_u8(constness_doc) as char {
|
||||
'c' => ast::Constness::Const,
|
||||
'n' => ast::Constness::NotConst,
|
||||
'c' => hir::Constness::Const,
|
||||
'n' => hir::Constness::NotConst,
|
||||
_ => panic!("unknown constness character")
|
||||
}
|
||||
}
|
||||
@ -343,12 +346,12 @@ fn item_to_def_like(cdata: Cmd, item: rbml::Doc, did: DefId) -> DefLike {
|
||||
}
|
||||
}
|
||||
|
||||
fn parse_unsafety(item_doc: rbml::Doc) -> ast::Unsafety {
|
||||
fn parse_unsafety(item_doc: rbml::Doc) -> hir::Unsafety {
|
||||
let unsafety_doc = reader::get_doc(item_doc, tag_unsafety);
|
||||
if reader::doc_as_u8(unsafety_doc) != 0 {
|
||||
ast::Unsafety::Unsafe
|
||||
hir::Unsafety::Unsafe
|
||||
} else {
|
||||
ast::Unsafety::Normal
|
||||
hir::Unsafety::Normal
|
||||
}
|
||||
}
|
||||
|
||||
@ -357,12 +360,12 @@ fn parse_paren_sugar(item_doc: rbml::Doc) -> bool {
|
||||
reader::doc_as_u8(paren_sugar_doc) != 0
|
||||
}
|
||||
|
||||
fn parse_polarity(item_doc: rbml::Doc) -> ast::ImplPolarity {
|
||||
fn parse_polarity(item_doc: rbml::Doc) -> hir::ImplPolarity {
|
||||
let polarity_doc = reader::get_doc(item_doc, tag_polarity);
|
||||
if reader::doc_as_u8(polarity_doc) != 0 {
|
||||
ast::ImplPolarity::Negative
|
||||
hir::ImplPolarity::Negative
|
||||
} else {
|
||||
ast::ImplPolarity::Positive
|
||||
hir::ImplPolarity::Positive
|
||||
}
|
||||
}
|
||||
|
||||
@ -560,7 +563,7 @@ pub fn get_repr_attrs(cdata: Cmd, id: ast::NodeId) -> Vec<attr::ReprAttr> {
|
||||
|
||||
pub fn get_impl_polarity<'tcx>(cdata: Cmd,
|
||||
id: ast::NodeId)
|
||||
-> Option<ast::ImplPolarity>
|
||||
-> Option<hir::ImplPolarity>
|
||||
{
|
||||
let item_doc = lookup_item(id, cdata.data());
|
||||
let fam = item_family(item_doc);
|
||||
@ -633,7 +636,7 @@ fn each_child_of_item_or_crate<F, G>(intr: Rc<IdentInterner>,
|
||||
item_doc: rbml::Doc,
|
||||
mut get_crate_data: G,
|
||||
mut callback: F) where
|
||||
F: FnMut(DefLike, ast::Name, ast::Visibility),
|
||||
F: FnMut(DefLike, ast::Name, hir::Visibility),
|
||||
G: FnMut(ast::CrateNum) -> Rc<crate_metadata>,
|
||||
{
|
||||
// Iterate over all children.
|
||||
@ -722,7 +725,7 @@ fn each_child_of_item_or_crate<F, G>(intr: Rc<IdentInterner>,
|
||||
let def_like = item_to_def_like(crate_data, child_item_doc, child_def_id);
|
||||
// These items have a public visibility because they're part of
|
||||
// a public re-export.
|
||||
callback(def_like, token::intern(name), ast::Public);
|
||||
callback(def_like, token::intern(name), hir::Public);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -733,7 +736,7 @@ pub fn each_child_of_item<F, G>(intr: Rc<IdentInterner>,
|
||||
id: ast::NodeId,
|
||||
get_crate_data: G,
|
||||
callback: F) where
|
||||
F: FnMut(DefLike, ast::Name, ast::Visibility),
|
||||
F: FnMut(DefLike, ast::Name, hir::Visibility),
|
||||
G: FnMut(ast::CrateNum) -> Rc<crate_metadata>,
|
||||
{
|
||||
// Find the item.
|
||||
@ -756,7 +759,7 @@ pub fn each_top_level_item_of_crate<F, G>(intr: Rc<IdentInterner>,
|
||||
cdata: Cmd,
|
||||
get_crate_data: G,
|
||||
callback: F) where
|
||||
F: FnMut(DefLike, ast::Name, ast::Visibility),
|
||||
F: FnMut(DefLike, ast::Name, hir::Visibility),
|
||||
G: FnMut(ast::CrateNum) -> Rc<crate_metadata>,
|
||||
{
|
||||
let root_doc = rbml::Doc::new(cdata.data());
|
||||
@ -810,10 +813,10 @@ pub fn maybe_get_item_ast<'tcx>(cdata: Cmd, tcx: &ty::ctxt<'tcx>, id: ast::NodeI
|
||||
}
|
||||
|
||||
fn get_explicit_self(item: rbml::Doc) -> ty::ExplicitSelfCategory {
|
||||
fn get_mutability(ch: u8) -> ast::Mutability {
|
||||
fn get_mutability(ch: u8) -> hir::Mutability {
|
||||
match ch as char {
|
||||
'i' => ast::MutImmutable,
|
||||
'm' => ast::MutMutable,
|
||||
'i' => hir::MutImmutable,
|
||||
'm' => hir::MutMutable,
|
||||
_ => panic!("unknown mutability character: `{}`", ch as char),
|
||||
}
|
||||
}
|
||||
@ -1074,7 +1077,7 @@ pub fn get_tuple_struct_definition_if_ctor(cdata: Cmd,
|
||||
|
||||
pub fn get_item_attrs(cdata: Cmd,
|
||||
orig_node_id: ast::NodeId)
|
||||
-> Vec<ast::Attribute> {
|
||||
-> Vec<hir::Attribute> {
|
||||
// The attributes for a tuple struct are attached to the definition, not the ctor;
|
||||
// we assume that someone passing in a tuple struct ctor is actually wanting to
|
||||
// look at the definition
|
||||
@ -1084,7 +1087,7 @@ pub fn get_item_attrs(cdata: Cmd,
|
||||
get_attributes(item)
|
||||
}
|
||||
|
||||
pub fn get_struct_field_attrs(cdata: Cmd) -> HashMap<ast::NodeId, Vec<ast::Attribute>> {
|
||||
pub fn get_struct_field_attrs(cdata: Cmd) -> HashMap<ast::NodeId, Vec<hir::Attribute>> {
|
||||
let data = rbml::Doc::new(cdata.data());
|
||||
let fields = reader::get_doc(data, tag_struct_fields);
|
||||
reader::tagged_docs(fields, tag_struct_field).map(|field| {
|
||||
@ -1094,10 +1097,10 @@ pub fn get_struct_field_attrs(cdata: Cmd) -> HashMap<ast::NodeId, Vec<ast::Attri
|
||||
}).collect()
|
||||
}
|
||||
|
||||
fn struct_field_family_to_visibility(family: Family) -> ast::Visibility {
|
||||
fn struct_field_family_to_visibility(family: Family) -> hir::Visibility {
|
||||
match family {
|
||||
PublicField => ast::Public,
|
||||
InheritedField => ast::Inherited,
|
||||
PublicField => hir::Public,
|
||||
InheritedField => hir::Inherited,
|
||||
_ => panic!()
|
||||
}
|
||||
}
|
||||
@ -1113,7 +1116,7 @@ pub fn get_struct_field_names(intr: &IdentInterner, cdata: Cmd, id: ast::NodeId)
|
||||
})).collect()
|
||||
}
|
||||
|
||||
fn get_meta_items(md: rbml::Doc) -> Vec<P<ast::MetaItem>> {
|
||||
fn get_meta_items(md: rbml::Doc) -> Vec<P<hir::MetaItem>> {
|
||||
reader::tagged_docs(md, tag_meta_item_word).map(|meta_item_doc| {
|
||||
let nd = reader::get_doc(meta_item_doc, tag_meta_item_name);
|
||||
let n = token::intern_and_get_ident(nd.as_str_slice());
|
||||
@ -1134,7 +1137,7 @@ fn get_meta_items(md: rbml::Doc) -> Vec<P<ast::MetaItem>> {
|
||||
})).collect()
|
||||
}
|
||||
|
||||
fn get_attributes(md: rbml::Doc) -> Vec<ast::Attribute> {
|
||||
fn get_attributes(md: rbml::Doc) -> Vec<hir::Attribute> {
|
||||
match reader::maybe_get_doc(md, tag_attributes) {
|
||||
Some(attrs_d) => {
|
||||
reader::tagged_docs(attrs_d, tag_attribute).map(|attr_doc| {
|
||||
@ -1147,9 +1150,9 @@ fn get_attributes(md: rbml::Doc) -> Vec<ast::Attribute> {
|
||||
assert_eq!(meta_items.len(), 1);
|
||||
let meta_item = meta_items.into_iter().nth(0).unwrap();
|
||||
codemap::Spanned {
|
||||
node: ast::Attribute_ {
|
||||
node: hir::Attribute_ {
|
||||
id: attr::mk_attr_id(),
|
||||
style: ast::AttrOuter,
|
||||
style: hir::AttrOuter,
|
||||
value: meta_item,
|
||||
is_sugared_doc: is_sugared_doc,
|
||||
},
|
||||
@ -1173,7 +1176,7 @@ fn list_crate_attributes(md: rbml::Doc, hash: &Svh,
|
||||
write!(out, "\n\n")
|
||||
}
|
||||
|
||||
pub fn get_crate_attributes(data: &[u8]) -> Vec<ast::Attribute> {
|
||||
pub fn get_crate_attributes(data: &[u8]) -> Vec<hir::Attribute> {
|
||||
get_attributes(rbml::Doc::new(data))
|
||||
}
|
||||
|
||||
@ -1371,7 +1374,7 @@ pub fn get_plugin_registrar_fn(data: &[u8]) -> Option<ast::NodeId> {
|
||||
}
|
||||
|
||||
pub fn each_exported_macro<F>(data: &[u8], intr: &IdentInterner, mut f: F) where
|
||||
F: FnMut(ast::Name, Vec<ast::Attribute>, String) -> bool,
|
||||
F: FnMut(ast::Name, Vec<hir::Attribute>, String) -> bool,
|
||||
{
|
||||
let macros = reader::get_doc(rbml::Doc::new(data), tag_macro_defs);
|
||||
for macro_doc in reader::tagged_docs(macros, tag_macro_def) {
|
||||
@ -1453,8 +1456,8 @@ pub fn is_typedef(cdata: Cmd, id: ast::NodeId) -> bool {
|
||||
pub fn is_const_fn(cdata: Cmd, id: ast::NodeId) -> bool {
|
||||
let item_doc = lookup_item(id, cdata.data());
|
||||
match fn_constness(item_doc) {
|
||||
ast::Constness::Const => true,
|
||||
ast::Constness::NotConst => false,
|
||||
hir::Constness::Const => true,
|
||||
hir::Constness::NotConst => false,
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -13,7 +13,6 @@
|
||||
#![allow(unused_must_use)] // everything is just a MemWriter, can't fail
|
||||
#![allow(non_camel_case_types)]
|
||||
|
||||
use ast_map::{self, LinkedPath, PathElem, PathElems};
|
||||
use back::svh::Svh;
|
||||
use session::config;
|
||||
use metadata::common::*;
|
||||
@ -35,17 +34,20 @@ use std::io::prelude::*;
|
||||
use std::io::{Cursor, SeekFrom};
|
||||
use std::rc::Rc;
|
||||
use syntax::abi;
|
||||
use syntax::ast::{self, NodeId};
|
||||
use syntax::attr;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use syntax::ast::{NodeId, Name, CRATE_NODE_ID, CrateNum};
|
||||
use syntax::diagnostic::SpanHandler;
|
||||
use syntax::parse::token::special_idents;
|
||||
use syntax::print::pprust;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::visit;
|
||||
use syntax;
|
||||
use rbml::writer::Encoder;
|
||||
|
||||
use rustc_front::hir as ast;
|
||||
use rustc_front::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::attr;
|
||||
use rustc_front::attr::AttrMetaMethods;
|
||||
use front::map::{LinkedPath, PathElem, PathElems};
|
||||
use front::map as ast_map;
|
||||
|
||||
pub type EncodeInlinedItem<'a> =
|
||||
Box<FnMut(&EncodeContext, &mut Encoder, InlinedItemRef) + 'a>;
|
||||
|
||||
@ -72,11 +74,11 @@ pub struct EncodeContext<'a, 'tcx: 'a> {
|
||||
pub reachable: &'a NodeSet,
|
||||
}
|
||||
|
||||
fn encode_name(rbml_w: &mut Encoder, name: ast::Name) {
|
||||
fn encode_name(rbml_w: &mut Encoder, name: Name) {
|
||||
rbml_w.wr_tagged_str(tag_paths_data_name, &name.as_str());
|
||||
}
|
||||
|
||||
fn encode_impl_type_basename(rbml_w: &mut Encoder, name: ast::Name) {
|
||||
fn encode_impl_type_basename(rbml_w: &mut Encoder, name: Name) {
|
||||
rbml_w.wr_tagged_str(tag_item_impl_type_basename, &name.as_str());
|
||||
}
|
||||
|
||||
@ -130,7 +132,7 @@ fn encode_item_variances(rbml_w: &mut Encoder,
|
||||
|
||||
fn encode_bounds_and_type_for_item<'a, 'tcx>(rbml_w: &mut Encoder,
|
||||
ecx: &EncodeContext<'a, 'tcx>,
|
||||
id: ast::NodeId) {
|
||||
id: NodeId) {
|
||||
encode_bounds_and_type(rbml_w,
|
||||
ecx,
|
||||
&ecx.tcx.lookup_item_type(DefId::local(id)),
|
||||
@ -343,7 +345,7 @@ fn encode_path<PI: Iterator<Item=PathElem>>(rbml_w: &mut Encoder, path: PI) {
|
||||
fn encode_reexported_static_method(rbml_w: &mut Encoder,
|
||||
exp: &def::Export,
|
||||
method_def_id: DefId,
|
||||
method_name: ast::Name) {
|
||||
method_name: Name) {
|
||||
debug!("(encode reexported static method) {}::{}",
|
||||
exp.name, method_name);
|
||||
rbml_w.start_tag(tag_items_data_item_reexport);
|
||||
@ -500,7 +502,7 @@ fn encode_info_for_mod(ecx: &EncodeContext,
|
||||
attrs: &[ast::Attribute],
|
||||
id: NodeId,
|
||||
path: PathElems,
|
||||
name: ast::Name,
|
||||
name: Name,
|
||||
vis: ast::Visibility) {
|
||||
rbml_w.start_tag(tag_items_data_item);
|
||||
encode_def_id(rbml_w, DefId::local(id));
|
||||
@ -655,7 +657,7 @@ fn encode_info_for_struct<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
|
||||
|
||||
fn encode_info_for_struct_ctor(ecx: &EncodeContext,
|
||||
rbml_w: &mut Encoder,
|
||||
name: ast::Name,
|
||||
name: Name,
|
||||
ctor_id: NodeId,
|
||||
index: &mut Vec<entry<i64>>,
|
||||
struct_id: NodeId) {
|
||||
@ -1475,7 +1477,7 @@ fn encode_info_for_item(ecx: &EncodeContext,
|
||||
rbml_w.end_tag();
|
||||
}
|
||||
}
|
||||
ast::ItemExternCrate(_) | ast::ItemUse(_) |ast::ItemMac(..) => {
|
||||
ast::ItemExternCrate(_) | ast::ItemUse(_) => {
|
||||
// these are encoded separately
|
||||
}
|
||||
}
|
||||
@ -1588,14 +1590,14 @@ fn encode_info_for_items(ecx: &EncodeContext,
|
||||
let mut index = Vec::new();
|
||||
rbml_w.start_tag(tag_items_data);
|
||||
index.push(entry {
|
||||
val: ast::CRATE_NODE_ID as i64,
|
||||
val: CRATE_NODE_ID as i64,
|
||||
pos: rbml_w.mark_stable_position(),
|
||||
});
|
||||
encode_info_for_mod(ecx,
|
||||
rbml_w,
|
||||
&krate.module,
|
||||
&[],
|
||||
ast::CRATE_NODE_ID,
|
||||
CRATE_NODE_ID,
|
||||
[].iter().cloned().chain(LinkedPath::empty()),
|
||||
syntax::parse::token::special_idents::invalid.name,
|
||||
ast::Public);
|
||||
@ -1727,7 +1729,7 @@ fn encode_defaulted(rbml_w: &mut Encoder, is_defaulted: bool) {
|
||||
rbml_w.wr_tagged_u8(tag_defaulted_trait, byte);
|
||||
}
|
||||
|
||||
fn encode_associated_type_names(rbml_w: &mut Encoder, names: &[ast::Name]) {
|
||||
fn encode_associated_type_names(rbml_w: &mut Encoder, names: &[Name]) {
|
||||
rbml_w.start_tag(tag_associated_type_names);
|
||||
for &name in names {
|
||||
rbml_w.wr_tagged_str(tag_associated_type_name, &name.as_str());
|
||||
@ -1745,7 +1747,7 @@ fn encode_polarity(rbml_w: &mut Encoder, polarity: ast::ImplPolarity) {
|
||||
|
||||
fn encode_crate_deps(rbml_w: &mut Encoder, cstore: &cstore::CStore) {
|
||||
fn get_ordered_deps(cstore: &cstore::CStore)
|
||||
-> Vec<(ast::CrateNum, Rc<cstore::crate_metadata>)> {
|
||||
-> Vec<(CrateNum, Rc<cstore::crate_metadata>)> {
|
||||
// Pull the cnums and name,vers,hash out of cstore
|
||||
let mut deps = Vec::new();
|
||||
cstore.iter_crate_data(|cnum, val| {
|
||||
@ -1856,7 +1858,7 @@ fn encode_macro_defs(rbml_w: &mut Encoder,
|
||||
encode_attributes(rbml_w, &def.attrs);
|
||||
|
||||
rbml_w.wr_tagged_str(tag_macro_def_body,
|
||||
&pprust::tts_to_string(&def.body));
|
||||
&::syntax::print::pprust::tts_to_string(&def.body));
|
||||
|
||||
rbml_w.end_tag();
|
||||
}
|
||||
|
@ -9,11 +9,11 @@
|
||||
// except according to those terms.
|
||||
|
||||
use middle::def_id::DefId;
|
||||
use syntax::ast;
|
||||
use syntax::ast_util::{IdRange, IdRangeComputingVisitor,
|
||||
IdVisitor, IdVisitingOperation};
|
||||
use rustc_front::hir;
|
||||
use rustc_front::util::IdVisitor;
|
||||
use syntax::ast_util::{IdRange, IdRangeComputingVisitor, IdVisitingOperation};
|
||||
use syntax::ptr::P;
|
||||
use syntax::visit::Visitor;
|
||||
use rustc_front::visit::Visitor;
|
||||
use self::InlinedItem::*;
|
||||
|
||||
/// The data we save and restore about an inlined item or method. This is not
|
||||
@ -21,18 +21,18 @@ use self::InlinedItem::*;
|
||||
/// that we trans.
|
||||
#[derive(Clone, PartialEq, Eq, RustcEncodable, RustcDecodable, Hash, Debug)]
|
||||
pub enum InlinedItem {
|
||||
Item(P<ast::Item>),
|
||||
TraitItem(DefId /* impl id */, P<ast::TraitItem>),
|
||||
ImplItem(DefId /* impl id */, P<ast::ImplItem>),
|
||||
Foreign(P<ast::ForeignItem>),
|
||||
Item(P<hir::Item>),
|
||||
TraitItem(DefId /* impl id */, P<hir::TraitItem>),
|
||||
ImplItem(DefId /* impl id */, P<hir::ImplItem>),
|
||||
Foreign(P<hir::ForeignItem>),
|
||||
}
|
||||
|
||||
/// A borrowed version of `ast::InlinedItem`.
|
||||
/// A borrowed version of `hir::InlinedItem`.
|
||||
pub enum InlinedItemRef<'a> {
|
||||
Item(&'a ast::Item),
|
||||
TraitItem(DefId, &'a ast::TraitItem),
|
||||
ImplItem(DefId, &'a ast::ImplItem),
|
||||
Foreign(&'a ast::ForeignItem)
|
||||
Item(&'a hir::Item),
|
||||
TraitItem(DefId, &'a hir::TraitItem),
|
||||
ImplItem(DefId, &'a hir::ImplItem),
|
||||
Foreign(&'a hir::ForeignItem)
|
||||
}
|
||||
|
||||
impl InlinedItem {
|
||||
@ -62,4 +62,3 @@ impl InlinedItem {
|
||||
visitor.result()
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -14,13 +14,14 @@ use session::Session;
|
||||
use metadata::creader::CrateReader;
|
||||
|
||||
use std::collections::{HashSet, HashMap};
|
||||
use syntax::ast;
|
||||
use syntax::attr;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::parse::token;
|
||||
use syntax::ast;
|
||||
use syntax::attr;
|
||||
use syntax::visit;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use rustc_front::attr::AttrMetaMethods as FrontAttrMetaMethods;
|
||||
|
||||
struct MacroLoader<'a> {
|
||||
sess: &'a Session,
|
||||
|
@ -18,6 +18,8 @@
|
||||
|
||||
pub use self::DefIdSource::*;
|
||||
|
||||
use rustc_front::hir;
|
||||
|
||||
use middle::def_id::DefId;
|
||||
use middle::region;
|
||||
use middle::subst;
|
||||
@ -467,10 +469,10 @@ impl<'a,'tcx> TyDecoder<'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn parse_mutability(&mut self) -> ast::Mutability {
|
||||
fn parse_mutability(&mut self) -> hir::Mutability {
|
||||
match self.peek() {
|
||||
'm' => { self.next(); ast::MutMutable }
|
||||
_ => { ast::MutImmutable }
|
||||
'm' => { self.next(); hir::MutMutable }
|
||||
_ => { hir::MutImmutable }
|
||||
}
|
||||
}
|
||||
|
||||
@ -742,10 +744,10 @@ fn parse_defid(buf: &[u8]) -> DefId {
|
||||
DefId { krate: crate_num, node: def_num }
|
||||
}
|
||||
|
||||
fn parse_unsafety(c: char) -> ast::Unsafety {
|
||||
fn parse_unsafety(c: char) -> hir::Unsafety {
|
||||
match c {
|
||||
'u' => ast::Unsafety::Unsafe,
|
||||
'n' => ast::Unsafety::Normal,
|
||||
'u' => hir::Unsafety::Unsafe,
|
||||
'n' => hir::Unsafety::Normal,
|
||||
_ => panic!("parse_unsafety: bad unsafety {}", c)
|
||||
}
|
||||
}
|
||||
|
@ -24,8 +24,9 @@ use middle::ty::ParamTy;
|
||||
use middle::ty::{self, Ty};
|
||||
use util::nodemap::FnvHashMap;
|
||||
|
||||
use rustc_front::hir;
|
||||
|
||||
use syntax::abi::Abi;
|
||||
use syntax::ast;
|
||||
use syntax::diagnostic::SpanHandler;
|
||||
|
||||
use rbml::writer::Encoder;
|
||||
@ -64,26 +65,26 @@ pub fn enc_ty<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>, t: Ty<'tcx>) {
|
||||
ty::TyChar => mywrite!(w, "c"),
|
||||
ty::TyInt(t) => {
|
||||
match t {
|
||||
ast::TyIs => mywrite!(w, "is"),
|
||||
ast::TyI8 => mywrite!(w, "MB"),
|
||||
ast::TyI16 => mywrite!(w, "MW"),
|
||||
ast::TyI32 => mywrite!(w, "ML"),
|
||||
ast::TyI64 => mywrite!(w, "MD")
|
||||
hir::TyIs => mywrite!(w, "is"),
|
||||
hir::TyI8 => mywrite!(w, "MB"),
|
||||
hir::TyI16 => mywrite!(w, "MW"),
|
||||
hir::TyI32 => mywrite!(w, "ML"),
|
||||
hir::TyI64 => mywrite!(w, "MD")
|
||||
}
|
||||
}
|
||||
ty::TyUint(t) => {
|
||||
match t {
|
||||
ast::TyUs => mywrite!(w, "us"),
|
||||
ast::TyU8 => mywrite!(w, "Mb"),
|
||||
ast::TyU16 => mywrite!(w, "Mw"),
|
||||
ast::TyU32 => mywrite!(w, "Ml"),
|
||||
ast::TyU64 => mywrite!(w, "Md")
|
||||
hir::TyUs => mywrite!(w, "us"),
|
||||
hir::TyU8 => mywrite!(w, "Mb"),
|
||||
hir::TyU16 => mywrite!(w, "Mw"),
|
||||
hir::TyU32 => mywrite!(w, "Ml"),
|
||||
hir::TyU64 => mywrite!(w, "Md")
|
||||
}
|
||||
}
|
||||
ty::TyFloat(t) => {
|
||||
match t {
|
||||
ast::TyF32 => mywrite!(w, "Mf"),
|
||||
ast::TyF64 => mywrite!(w, "MF"),
|
||||
hir::TyF32 => mywrite!(w, "Mf"),
|
||||
hir::TyF64 => mywrite!(w, "MF"),
|
||||
}
|
||||
}
|
||||
ty::TyEnum(def, substs) => {
|
||||
@ -179,10 +180,10 @@ pub fn enc_ty<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>, t: Ty<'tcx>) {
|
||||
}
|
||||
}
|
||||
|
||||
fn enc_mutability(w: &mut Encoder, mt: ast::Mutability) {
|
||||
fn enc_mutability(w: &mut Encoder, mt: hir::Mutability) {
|
||||
match mt {
|
||||
ast::MutImmutable => (),
|
||||
ast::MutMutable => mywrite!(w, "m"),
|
||||
hir::MutImmutable => (),
|
||||
hir::MutMutable => mywrite!(w, "m"),
|
||||
}
|
||||
}
|
||||
|
||||
@ -314,10 +315,10 @@ pub fn enc_trait_ref<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
|
||||
enc_substs(w, cx, s.substs);
|
||||
}
|
||||
|
||||
fn enc_unsafety(w: &mut Encoder, p: ast::Unsafety) {
|
||||
fn enc_unsafety(w: &mut Encoder, p: hir::Unsafety) {
|
||||
match p {
|
||||
ast::Unsafety::Normal => mywrite!(w, "n"),
|
||||
ast::Unsafety::Unsafe => mywrite!(w, "u"),
|
||||
hir::Unsafety::Normal => mywrite!(w, "n"),
|
||||
hir::Unsafety::Unsafe => mywrite!(w, "u"),
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -16,7 +16,7 @@
|
||||
|
||||
use middle::def;
|
||||
use middle::ty::{self, Ty};
|
||||
use syntax::ast;
|
||||
use rustc_front::hir as ast;
|
||||
|
||||
pub const NO_REGIONS: usize = 1;
|
||||
pub const NO_TPS: usize = 2;
|
||||
|
@ -12,7 +12,11 @@
|
||||
// FIXME: remove this after snapshot, and Results are handled
|
||||
#![allow(unused_must_use)]
|
||||
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::fold;
|
||||
use rustc_front::fold::Folder;
|
||||
|
||||
use metadata::common as c;
|
||||
use metadata::cstore as cstore;
|
||||
use session::Session;
|
||||
@ -33,11 +37,9 @@ use middle::subst;
|
||||
use middle::subst::VecPerParamSpace;
|
||||
use middle::ty::{self, Ty};
|
||||
|
||||
use syntax::{ast, ast_util, codemap, fold};
|
||||
use syntax::{ast, ast_util, codemap};
|
||||
use syntax::codemap::Span;
|
||||
use syntax::fold::Folder;
|
||||
use syntax::ptr::P;
|
||||
use syntax;
|
||||
|
||||
use std::cell::Cell;
|
||||
use std::io::SeekFrom;
|
||||
@ -53,7 +55,8 @@ use serialize::EncoderHelpers;
|
||||
|
||||
#[cfg(test)] use std::io::Cursor;
|
||||
#[cfg(test)] use syntax::parse;
|
||||
#[cfg(test)] use syntax::print::pprust;
|
||||
#[cfg(test)] use rustc_front::print::pprust;
|
||||
#[cfg(test)] use rustc_front::lowering::lower_item;
|
||||
|
||||
struct DecodeContext<'a, 'b, 'tcx: 'a> {
|
||||
tcx: &'a ty::ctxt<'tcx>,
|
||||
@ -166,7 +169,7 @@ pub fn decode_inlined_item<'tcx>(cdata: &cstore::crate_metadata,
|
||||
match *ii {
|
||||
InlinedItem::Item(ref i) => {
|
||||
debug!(">>> DECODED ITEM >>>\n{}\n<<< DECODED ITEM <<<",
|
||||
syntax::print::pprust::item_to_string(&**i));
|
||||
::rustc_front::print::pprust::item_to_string(&**i));
|
||||
}
|
||||
_ => { }
|
||||
}
|
||||
@ -360,18 +363,17 @@ fn encode_ast(rbml_w: &mut Encoder, item: &InlinedItem) {
|
||||
struct NestedItemsDropper;
|
||||
|
||||
impl Folder for NestedItemsDropper {
|
||||
fn fold_block(&mut self, blk: P<ast::Block>) -> P<ast::Block> {
|
||||
blk.and_then(|ast::Block {id, stmts, expr, rules, span, ..}| {
|
||||
fn fold_block(&mut self, blk: P<hir::Block>) -> P<hir::Block> {
|
||||
blk.and_then(|hir::Block {id, stmts, expr, rules, span, ..}| {
|
||||
let stmts_sans_items = stmts.into_iter().filter_map(|stmt| {
|
||||
let use_stmt = match stmt.node {
|
||||
ast::StmtExpr(_, _) | ast::StmtSemi(_, _) => true,
|
||||
ast::StmtDecl(ref decl, _) => {
|
||||
hir::StmtExpr(_, _) | hir::StmtSemi(_, _) => true,
|
||||
hir::StmtDecl(ref decl, _) => {
|
||||
match decl.node {
|
||||
ast::DeclLocal(_) => true,
|
||||
ast::DeclItem(_) => false,
|
||||
hir::DeclLocal(_) => true,
|
||||
hir::DeclItem(_) => false,
|
||||
}
|
||||
}
|
||||
ast::StmtMac(..) => panic!("unexpanded macro in astencode")
|
||||
};
|
||||
if use_stmt {
|
||||
Some(stmt)
|
||||
@ -379,7 +381,7 @@ impl Folder for NestedItemsDropper {
|
||||
None
|
||||
}
|
||||
}).collect();
|
||||
let blk_sans_items = P(ast::Block {
|
||||
let blk_sans_items = P(hir::Block {
|
||||
stmts: stmts_sans_items,
|
||||
expr: expr,
|
||||
id: id,
|
||||
@ -488,7 +490,7 @@ fn encode_freevar_entry(rbml_w: &mut Encoder, fv: &ty::Freevar) {
|
||||
trait rbml_decoder_helper {
|
||||
fn read_freevar_entry(&mut self, dcx: &DecodeContext)
|
||||
-> ty::Freevar;
|
||||
fn read_capture_mode(&mut self) -> ast::CaptureClause;
|
||||
fn read_capture_mode(&mut self) -> hir::CaptureClause;
|
||||
}
|
||||
|
||||
impl<'a> rbml_decoder_helper for reader::Decoder<'a> {
|
||||
@ -498,8 +500,8 @@ impl<'a> rbml_decoder_helper for reader::Decoder<'a> {
|
||||
fv.tr(dcx)
|
||||
}
|
||||
|
||||
fn read_capture_mode(&mut self) -> ast::CaptureClause {
|
||||
let cm: ast::CaptureClause = Decodable::decode(self).unwrap();
|
||||
fn read_capture_mode(&mut self) -> hir::CaptureClause {
|
||||
let cm: hir::CaptureClause = Decodable::decode(self).unwrap();
|
||||
cm
|
||||
}
|
||||
}
|
||||
@ -1304,7 +1306,7 @@ impl<'a, 'tcx> rbml_decoder_decoder_helpers<'tcx> for reader::Decoder<'a> {
|
||||
this.read_enum_variant_arg(0, |this| {
|
||||
Ok(this.read_region(dcx))
|
||||
}).unwrap();
|
||||
let m: ast::Mutability =
|
||||
let m: hir::Mutability =
|
||||
this.read_enum_variant_arg(1, |this| {
|
||||
Decodable::decode(this)
|
||||
}).unwrap();
|
||||
@ -1312,7 +1314,7 @@ impl<'a, 'tcx> rbml_decoder_decoder_helpers<'tcx> for reader::Decoder<'a> {
|
||||
ty::AutoPtr(dcx.tcx.mk_region(r), m)
|
||||
}
|
||||
1 => {
|
||||
let m: ast::Mutability =
|
||||
let m: hir::Mutability =
|
||||
this.read_enum_variant_arg(0, |this| Decodable::decode(this)).unwrap();
|
||||
|
||||
ty::AutoUnsafe(m)
|
||||
@ -1506,14 +1508,14 @@ fn decode_side_tables(dcx: &DecodeContext,
|
||||
// Testing of astencode_gen
|
||||
|
||||
#[cfg(test)]
|
||||
fn encode_item_ast(rbml_w: &mut Encoder, item: &ast::Item) {
|
||||
fn encode_item_ast(rbml_w: &mut Encoder, item: &hir::Item) {
|
||||
rbml_w.start_tag(c::tag_tree as usize);
|
||||
(*item).encode(rbml_w);
|
||||
rbml_w.end_tag();
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
fn decode_item_ast(par_doc: rbml::Doc) -> ast::Item {
|
||||
fn decode_item_ast(par_doc: rbml::Doc) -> hir::Item {
|
||||
let chi_doc = par_doc.get(c::tag_tree as usize);
|
||||
let mut d = reader::Decoder::new(chi_doc);
|
||||
Decodable::decode(&mut d).unwrap()
|
||||
@ -1553,8 +1555,7 @@ fn mk_ctxt() -> parse::ParseSess {
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
fn roundtrip(in_item: Option<P<ast::Item>>) {
|
||||
let in_item = in_item.unwrap();
|
||||
fn roundtrip(in_item: P<hir::Item>) {
|
||||
let mut wr = Cursor::new(Vec::new());
|
||||
encode_item_ast(&mut Encoder::new(&mut wr), &*in_item);
|
||||
let rbml_doc = rbml::Doc::new(wr.get_ref());
|
||||
@ -1566,28 +1567,28 @@ fn roundtrip(in_item: Option<P<ast::Item>>) {
|
||||
#[test]
|
||||
fn test_basic() {
|
||||
let cx = mk_ctxt();
|
||||
roundtrip(quote_item!(&cx,
|
||||
roundtrip(lower_item("e_item!(&cx,
|
||||
fn foo() {}
|
||||
));
|
||||
).unwrap()));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_smalltalk() {
|
||||
let cx = mk_ctxt();
|
||||
roundtrip(quote_item!(&cx,
|
||||
roundtrip(lower_item("e_item!(&cx,
|
||||
fn foo() -> isize { 3 + 4 } // first smalltalk program ever executed.
|
||||
));
|
||||
).unwrap()));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_more() {
|
||||
let cx = mk_ctxt();
|
||||
roundtrip(quote_item!(&cx,
|
||||
roundtrip(lower_item("e_item!(&cx,
|
||||
fn foo(x: usize, y: usize) -> usize {
|
||||
let z = x + y;
|
||||
return z;
|
||||
}
|
||||
));
|
||||
).unwrap()));
|
||||
}
|
||||
|
||||
#[test]
|
||||
@ -1599,13 +1600,14 @@ fn test_simplification() {
|
||||
return alist {eq_fn: eq_int, data: Vec::new()};
|
||||
}
|
||||
).unwrap();
|
||||
let item_in = InlinedItemRef::Item(&*item);
|
||||
let hir_item = lower_item(&item);
|
||||
let item_in = InlinedItemRef::Item(&hir_item);
|
||||
let item_out = simplify_ast(item_in);
|
||||
let item_exp = InlinedItem::Item(quote_item!(&cx,
|
||||
let item_exp = InlinedItem::Item(lower_item("e_item!(&cx,
|
||||
fn new_int_alist<B>() -> alist<isize, B> {
|
||||
return alist {eq_fn: eq_int, data: Vec::new()};
|
||||
}
|
||||
).unwrap());
|
||||
).unwrap()));
|
||||
match (item_out, item_exp) {
|
||||
(InlinedItem::Item(item_out), InlinedItem::Item(item_exp)) => {
|
||||
assert!(pprust::item_to_string(&*item_out) ==
|
||||
|
@ -13,7 +13,7 @@
|
||||
|
||||
use middle::ty::{self, Ty};
|
||||
|
||||
use syntax::ast;
|
||||
use rustc_front::hir as ast;
|
||||
|
||||
/// Types that are represented as ints.
|
||||
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
|
||||
|
@ -14,9 +14,10 @@ use middle::def;
|
||||
use middle::pat_util;
|
||||
use middle::ty;
|
||||
use syntax::ast;
|
||||
use syntax::ast_util;
|
||||
use syntax::ptr::P;
|
||||
|
||||
use rustc_front::hir;
|
||||
|
||||
struct CFGBuilder<'a, 'tcx: 'a> {
|
||||
tcx: &'a ty::ctxt<'tcx>,
|
||||
graph: CFGGraph,
|
||||
@ -32,7 +33,7 @@ struct LoopScope {
|
||||
}
|
||||
|
||||
pub fn construct(tcx: &ty::ctxt,
|
||||
blk: &ast::Block) -> CFG {
|
||||
blk: &hir::Block) -> CFG {
|
||||
let mut graph = graph::Graph::new();
|
||||
let entry = graph.add_node(CFGNodeData::Entry);
|
||||
|
||||
@ -58,7 +59,7 @@ pub fn construct(tcx: &ty::ctxt,
|
||||
}
|
||||
|
||||
impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
fn block(&mut self, blk: &ast::Block, pred: CFGIndex) -> CFGIndex {
|
||||
fn block(&mut self, blk: &hir::Block, pred: CFGIndex) -> CFGIndex {
|
||||
let mut stmts_exit = pred;
|
||||
for stmt in &blk.stmts {
|
||||
stmts_exit = self.stmt(&**stmt, stmts_exit);
|
||||
@ -69,95 +70,87 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
self.add_ast_node(blk.id, &[expr_exit])
|
||||
}
|
||||
|
||||
fn stmt(&mut self, stmt: &ast::Stmt, pred: CFGIndex) -> CFGIndex {
|
||||
fn stmt(&mut self, stmt: &hir::Stmt, pred: CFGIndex) -> CFGIndex {
|
||||
match stmt.node {
|
||||
ast::StmtDecl(ref decl, id) => {
|
||||
hir::StmtDecl(ref decl, id) => {
|
||||
let exit = self.decl(&**decl, pred);
|
||||
self.add_ast_node(id, &[exit])
|
||||
}
|
||||
|
||||
ast::StmtExpr(ref expr, id) | ast::StmtSemi(ref expr, id) => {
|
||||
hir::StmtExpr(ref expr, id) | hir::StmtSemi(ref expr, id) => {
|
||||
let exit = self.expr(&**expr, pred);
|
||||
self.add_ast_node(id, &[exit])
|
||||
}
|
||||
|
||||
ast::StmtMac(..) => {
|
||||
self.tcx.sess.span_bug(stmt.span, "unexpanded macro");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn decl(&mut self, decl: &ast::Decl, pred: CFGIndex) -> CFGIndex {
|
||||
fn decl(&mut self, decl: &hir::Decl, pred: CFGIndex) -> CFGIndex {
|
||||
match decl.node {
|
||||
ast::DeclLocal(ref local) => {
|
||||
hir::DeclLocal(ref local) => {
|
||||
let init_exit = self.opt_expr(&local.init, pred);
|
||||
self.pat(&*local.pat, init_exit)
|
||||
}
|
||||
|
||||
ast::DeclItem(_) => {
|
||||
hir::DeclItem(_) => {
|
||||
pred
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn pat(&mut self, pat: &ast::Pat, pred: CFGIndex) -> CFGIndex {
|
||||
fn pat(&mut self, pat: &hir::Pat, pred: CFGIndex) -> CFGIndex {
|
||||
match pat.node {
|
||||
ast::PatIdent(_, _, None) |
|
||||
ast::PatEnum(_, None) |
|
||||
ast::PatQPath(..) |
|
||||
ast::PatLit(..) |
|
||||
ast::PatRange(..) |
|
||||
ast::PatWild(_) => {
|
||||
hir::PatIdent(_, _, None) |
|
||||
hir::PatEnum(_, None) |
|
||||
hir::PatQPath(..) |
|
||||
hir::PatLit(..) |
|
||||
hir::PatRange(..) |
|
||||
hir::PatWild(_) => {
|
||||
self.add_ast_node(pat.id, &[pred])
|
||||
}
|
||||
|
||||
ast::PatBox(ref subpat) |
|
||||
ast::PatRegion(ref subpat, _) |
|
||||
ast::PatIdent(_, _, Some(ref subpat)) => {
|
||||
hir::PatBox(ref subpat) |
|
||||
hir::PatRegion(ref subpat, _) |
|
||||
hir::PatIdent(_, _, Some(ref subpat)) => {
|
||||
let subpat_exit = self.pat(&**subpat, pred);
|
||||
self.add_ast_node(pat.id, &[subpat_exit])
|
||||
}
|
||||
|
||||
ast::PatEnum(_, Some(ref subpats)) |
|
||||
ast::PatTup(ref subpats) => {
|
||||
hir::PatEnum(_, Some(ref subpats)) |
|
||||
hir::PatTup(ref subpats) => {
|
||||
let pats_exit = self.pats_all(subpats.iter(), pred);
|
||||
self.add_ast_node(pat.id, &[pats_exit])
|
||||
}
|
||||
|
||||
ast::PatStruct(_, ref subpats, _) => {
|
||||
hir::PatStruct(_, ref subpats, _) => {
|
||||
let pats_exit =
|
||||
self.pats_all(subpats.iter().map(|f| &f.node.pat), pred);
|
||||
self.add_ast_node(pat.id, &[pats_exit])
|
||||
}
|
||||
|
||||
ast::PatVec(ref pre, ref vec, ref post) => {
|
||||
hir::PatVec(ref pre, ref vec, ref post) => {
|
||||
let pre_exit = self.pats_all(pre.iter(), pred);
|
||||
let vec_exit = self.pats_all(vec.iter(), pre_exit);
|
||||
let post_exit = self.pats_all(post.iter(), vec_exit);
|
||||
self.add_ast_node(pat.id, &[post_exit])
|
||||
}
|
||||
|
||||
ast::PatMac(_) => {
|
||||
self.tcx.sess.span_bug(pat.span, "unexpanded macro");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn pats_all<'b, I: Iterator<Item=&'b P<ast::Pat>>>(&mut self,
|
||||
fn pats_all<'b, I: Iterator<Item=&'b P<hir::Pat>>>(&mut self,
|
||||
pats: I,
|
||||
pred: CFGIndex) -> CFGIndex {
|
||||
//! Handles case where all of the patterns must match.
|
||||
pats.fold(pred, |pred, pat| self.pat(&**pat, pred))
|
||||
}
|
||||
|
||||
fn expr(&mut self, expr: &ast::Expr, pred: CFGIndex) -> CFGIndex {
|
||||
fn expr(&mut self, expr: &hir::Expr, pred: CFGIndex) -> CFGIndex {
|
||||
match expr.node {
|
||||
ast::ExprBlock(ref blk) => {
|
||||
hir::ExprBlock(ref blk) => {
|
||||
let blk_exit = self.block(&**blk, pred);
|
||||
self.add_ast_node(expr.id, &[blk_exit])
|
||||
}
|
||||
|
||||
ast::ExprIf(ref cond, ref then, None) => {
|
||||
hir::ExprIf(ref cond, ref then, None) => {
|
||||
//
|
||||
// [pred]
|
||||
// |
|
||||
@ -177,7 +170,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
self.add_ast_node(expr.id, &[cond_exit, then_exit]) // 3,4
|
||||
}
|
||||
|
||||
ast::ExprIf(ref cond, ref then, Some(ref otherwise)) => {
|
||||
hir::ExprIf(ref cond, ref then, Some(ref otherwise)) => {
|
||||
//
|
||||
// [pred]
|
||||
// |
|
||||
@ -198,11 +191,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
self.add_ast_node(expr.id, &[then_exit, else_exit]) // 4, 5
|
||||
}
|
||||
|
||||
ast::ExprIfLet(..) => {
|
||||
self.tcx.sess.span_bug(expr.span, "non-desugared ExprIfLet");
|
||||
}
|
||||
|
||||
ast::ExprWhile(ref cond, ref body, _) => {
|
||||
hir::ExprWhile(ref cond, ref body, _) => {
|
||||
//
|
||||
// [pred]
|
||||
// |
|
||||
@ -235,15 +224,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
expr_exit
|
||||
}
|
||||
|
||||
ast::ExprWhileLet(..) => {
|
||||
self.tcx.sess.span_bug(expr.span, "non-desugared ExprWhileLet");
|
||||
}
|
||||
|
||||
ast::ExprForLoop(..) => {
|
||||
self.tcx.sess.span_bug(expr.span, "non-desugared ExprForLoop");
|
||||
}
|
||||
|
||||
ast::ExprLoop(ref body, _) => {
|
||||
hir::ExprLoop(ref body, _) => {
|
||||
//
|
||||
// [pred]
|
||||
// |
|
||||
@ -271,11 +252,11 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
expr_exit
|
||||
}
|
||||
|
||||
ast::ExprMatch(ref discr, ref arms, _) => {
|
||||
hir::ExprMatch(ref discr, ref arms, _) => {
|
||||
self.match_(expr.id, &discr, &arms, pred)
|
||||
}
|
||||
|
||||
ast::ExprBinary(op, ref l, ref r) if ast_util::lazy_binop(op.node) => {
|
||||
hir::ExprBinary(op, ref l, ref r) if ::rustc_front::util::lazy_binop(op.node) => {
|
||||
//
|
||||
// [pred]
|
||||
// |
|
||||
@ -295,14 +276,14 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
self.add_ast_node(expr.id, &[l_exit, r_exit]) // 3,4
|
||||
}
|
||||
|
||||
ast::ExprRet(ref v) => {
|
||||
hir::ExprRet(ref v) => {
|
||||
let v_exit = self.opt_expr(v, pred);
|
||||
let b = self.add_ast_node(expr.id, &[v_exit]);
|
||||
self.add_returning_edge(expr, b);
|
||||
self.add_unreachable_node()
|
||||
}
|
||||
|
||||
ast::ExprBreak(label) => {
|
||||
hir::ExprBreak(label) => {
|
||||
let loop_scope = self.find_scope(expr, label);
|
||||
let b = self.add_ast_node(expr.id, &[pred]);
|
||||
self.add_exiting_edge(expr, b,
|
||||
@ -310,7 +291,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
self.add_unreachable_node()
|
||||
}
|
||||
|
||||
ast::ExprAgain(label) => {
|
||||
hir::ExprAgain(label) => {
|
||||
let loop_scope = self.find_scope(expr, label);
|
||||
let a = self.add_ast_node(expr.id, &[pred]);
|
||||
self.add_exiting_edge(expr, a,
|
||||
@ -318,68 +299,68 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
self.add_unreachable_node()
|
||||
}
|
||||
|
||||
ast::ExprVec(ref elems) => {
|
||||
hir::ExprVec(ref elems) => {
|
||||
self.straightline(expr, pred, elems.iter().map(|e| &**e))
|
||||
}
|
||||
|
||||
ast::ExprCall(ref func, ref args) => {
|
||||
hir::ExprCall(ref func, ref args) => {
|
||||
self.call(expr, pred, &**func, args.iter().map(|e| &**e))
|
||||
}
|
||||
|
||||
ast::ExprMethodCall(_, _, ref args) => {
|
||||
hir::ExprMethodCall(_, _, ref args) => {
|
||||
self.call(expr, pred, &*args[0], args[1..].iter().map(|e| &**e))
|
||||
}
|
||||
|
||||
ast::ExprIndex(ref l, ref r) |
|
||||
ast::ExprBinary(_, ref l, ref r) if self.tcx.is_method_call(expr.id) => {
|
||||
hir::ExprIndex(ref l, ref r) |
|
||||
hir::ExprBinary(_, ref l, ref r) if self.tcx.is_method_call(expr.id) => {
|
||||
self.call(expr, pred, &**l, Some(&**r).into_iter())
|
||||
}
|
||||
|
||||
ast::ExprRange(ref start, ref end) => {
|
||||
hir::ExprRange(ref start, ref end) => {
|
||||
let fields = start.as_ref().map(|e| &**e).into_iter()
|
||||
.chain(end.as_ref().map(|e| &**e));
|
||||
self.straightline(expr, pred, fields)
|
||||
}
|
||||
|
||||
ast::ExprUnary(_, ref e) if self.tcx.is_method_call(expr.id) => {
|
||||
self.call(expr, pred, &**e, None::<ast::Expr>.iter())
|
||||
hir::ExprUnary(_, ref e) if self.tcx.is_method_call(expr.id) => {
|
||||
self.call(expr, pred, &**e, None::<hir::Expr>.iter())
|
||||
}
|
||||
|
||||
ast::ExprTup(ref exprs) => {
|
||||
hir::ExprTup(ref exprs) => {
|
||||
self.straightline(expr, pred, exprs.iter().map(|e| &**e))
|
||||
}
|
||||
|
||||
ast::ExprStruct(_, ref fields, ref base) => {
|
||||
hir::ExprStruct(_, ref fields, ref base) => {
|
||||
let field_cfg = self.straightline(expr, pred, fields.iter().map(|f| &*f.expr));
|
||||
self.opt_expr(base, field_cfg)
|
||||
}
|
||||
|
||||
ast::ExprRepeat(ref elem, ref count) => {
|
||||
hir::ExprRepeat(ref elem, ref count) => {
|
||||
self.straightline(expr, pred, [elem, count].iter().map(|&e| &**e))
|
||||
}
|
||||
|
||||
ast::ExprAssign(ref l, ref r) |
|
||||
ast::ExprAssignOp(_, ref l, ref r) => {
|
||||
hir::ExprAssign(ref l, ref r) |
|
||||
hir::ExprAssignOp(_, ref l, ref r) => {
|
||||
self.straightline(expr, pred, [r, l].iter().map(|&e| &**e))
|
||||
}
|
||||
|
||||
ast::ExprBox(Some(ref l), ref r) |
|
||||
ast::ExprIndex(ref l, ref r) |
|
||||
ast::ExprBinary(_, ref l, ref r) => { // NB: && and || handled earlier
|
||||
hir::ExprBox(Some(ref l), ref r) |
|
||||
hir::ExprIndex(ref l, ref r) |
|
||||
hir::ExprBinary(_, ref l, ref r) => { // NB: && and || handled earlier
|
||||
self.straightline(expr, pred, [l, r].iter().map(|&e| &**e))
|
||||
}
|
||||
|
||||
ast::ExprBox(None, ref e) |
|
||||
ast::ExprAddrOf(_, ref e) |
|
||||
ast::ExprCast(ref e, _) |
|
||||
ast::ExprUnary(_, ref e) |
|
||||
ast::ExprParen(ref e) |
|
||||
ast::ExprField(ref e, _) |
|
||||
ast::ExprTupField(ref e, _) => {
|
||||
hir::ExprBox(None, ref e) |
|
||||
hir::ExprAddrOf(_, ref e) |
|
||||
hir::ExprCast(ref e, _) |
|
||||
hir::ExprUnary(_, ref e) |
|
||||
hir::ExprParen(ref e) |
|
||||
hir::ExprField(ref e, _) |
|
||||
hir::ExprTupField(ref e, _) => {
|
||||
self.straightline(expr, pred, Some(&**e).into_iter())
|
||||
}
|
||||
|
||||
ast::ExprInlineAsm(ref inline_asm) => {
|
||||
hir::ExprInlineAsm(ref inline_asm) => {
|
||||
let inputs = inline_asm.inputs.iter();
|
||||
let outputs = inline_asm.outputs.iter();
|
||||
let post_inputs = self.exprs(inputs.map(|a| {
|
||||
@ -395,19 +376,18 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
self.add_ast_node(expr.id, &[post_outputs])
|
||||
}
|
||||
|
||||
ast::ExprMac(..) |
|
||||
ast::ExprClosure(..) |
|
||||
ast::ExprLit(..) |
|
||||
ast::ExprPath(..) => {
|
||||
self.straightline(expr, pred, None::<ast::Expr>.iter())
|
||||
hir::ExprClosure(..) |
|
||||
hir::ExprLit(..) |
|
||||
hir::ExprPath(..) => {
|
||||
self.straightline(expr, pred, None::<hir::Expr>.iter())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn call<'b, I: Iterator<Item=&'b ast::Expr>>(&mut self,
|
||||
call_expr: &ast::Expr,
|
||||
fn call<'b, I: Iterator<Item=&'b hir::Expr>>(&mut self,
|
||||
call_expr: &hir::Expr,
|
||||
pred: CFGIndex,
|
||||
func_or_rcvr: &ast::Expr,
|
||||
func_or_rcvr: &hir::Expr,
|
||||
args: I) -> CFGIndex {
|
||||
let method_call = ty::MethodCall::expr(call_expr.id);
|
||||
let fn_ty = match self.tcx.tables.borrow().method_map.get(&method_call) {
|
||||
@ -424,7 +404,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn exprs<'b, I: Iterator<Item=&'b ast::Expr>>(&mut self,
|
||||
fn exprs<'b, I: Iterator<Item=&'b hir::Expr>>(&mut self,
|
||||
exprs: I,
|
||||
pred: CFGIndex) -> CFGIndex {
|
||||
//! Constructs graph for `exprs` evaluated in order
|
||||
@ -432,14 +412,14 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn opt_expr(&mut self,
|
||||
opt_expr: &Option<P<ast::Expr>>,
|
||||
opt_expr: &Option<P<hir::Expr>>,
|
||||
pred: CFGIndex) -> CFGIndex {
|
||||
//! Constructs graph for `opt_expr` evaluated, if Some
|
||||
opt_expr.iter().fold(pred, |p, e| self.expr(&**e, p))
|
||||
}
|
||||
|
||||
fn straightline<'b, I: Iterator<Item=&'b ast::Expr>>(&mut self,
|
||||
expr: &ast::Expr,
|
||||
fn straightline<'b, I: Iterator<Item=&'b hir::Expr>>(&mut self,
|
||||
expr: &hir::Expr,
|
||||
pred: CFGIndex,
|
||||
subexprs: I) -> CFGIndex {
|
||||
//! Handles case of an expression that evaluates `subexprs` in order
|
||||
@ -448,8 +428,8 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
self.add_ast_node(expr.id, &[subexprs_exit])
|
||||
}
|
||||
|
||||
fn match_(&mut self, id: ast::NodeId, discr: &ast::Expr,
|
||||
arms: &[ast::Arm], pred: CFGIndex) -> CFGIndex {
|
||||
fn match_(&mut self, id: ast::NodeId, discr: &hir::Expr,
|
||||
arms: &[hir::Arm], pred: CFGIndex) -> CFGIndex {
|
||||
// The CFG for match expression is quite complex, so no ASCII
|
||||
// art for it (yet).
|
||||
//
|
||||
@ -579,7 +559,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn add_exiting_edge(&mut self,
|
||||
from_expr: &ast::Expr,
|
||||
from_expr: &hir::Expr,
|
||||
from_index: CFGIndex,
|
||||
to_loop: LoopScope,
|
||||
to_index: CFGIndex) {
|
||||
@ -594,7 +574,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn add_returning_edge(&mut self,
|
||||
_from_expr: &ast::Expr,
|
||||
_from_expr: &hir::Expr,
|
||||
from_index: CFGIndex) {
|
||||
let mut data = CFGEdgeData {
|
||||
exiting_scopes: vec!(),
|
||||
@ -606,7 +586,7 @@ impl<'a, 'tcx> CFGBuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn find_scope(&self,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
label: Option<ast::Ident>) -> LoopScope {
|
||||
if label.is_none() {
|
||||
return *self.loop_scopes.last().unwrap();
|
||||
|
@ -18,7 +18,7 @@ use graphviz as dot;
|
||||
|
||||
use syntax::ast;
|
||||
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
use middle::cfg;
|
||||
|
||||
pub type Node<'a> = (cfg::CFGIndex, &'a cfg::CFGNode);
|
||||
|
@ -14,6 +14,7 @@
|
||||
use rustc_data_structures::graph;
|
||||
use middle::ty;
|
||||
use syntax::ast;
|
||||
use rustc_front::hir;
|
||||
|
||||
mod construct;
|
||||
pub mod graphviz;
|
||||
@ -58,7 +59,7 @@ pub type CFGEdge = graph::Edge<CFGEdgeData>;
|
||||
|
||||
impl CFG {
|
||||
pub fn new(tcx: &ty::ctxt,
|
||||
blk: &ast::Block) -> CFG {
|
||||
blk: &hir::Block) -> CFG {
|
||||
construct::construct(tcx, blk)
|
||||
}
|
||||
|
||||
|
@ -36,9 +36,10 @@ use middle::traits;
|
||||
use middle::ty::{self, Ty};
|
||||
use util::nodemap::NodeMap;
|
||||
|
||||
use rustc_front::hir;
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit::{self, FnKind, Visitor};
|
||||
use rustc_front::visit::{self, FnKind, Visitor};
|
||||
|
||||
use std::collections::hash_map::Entry;
|
||||
use std::cmp::Ordering;
|
||||
@ -96,7 +97,7 @@ struct CheckCrateVisitor<'a, 'tcx: 'a> {
|
||||
tcx: &'a ty::ctxt<'tcx>,
|
||||
mode: Mode,
|
||||
qualif: ConstQualif,
|
||||
rvalue_borrows: NodeMap<ast::Mutability>
|
||||
rvalue_borrows: NodeMap<hir::Mutability>
|
||||
}
|
||||
|
||||
impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
@ -125,7 +126,7 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
f(&mut euv::ExprUseVisitor::new(self, &infcx))
|
||||
}
|
||||
|
||||
fn global_expr(&mut self, mode: Mode, expr: &ast::Expr) -> ConstQualif {
|
||||
fn global_expr(&mut self, mode: Mode, expr: &hir::Expr) -> ConstQualif {
|
||||
assert!(mode != Mode::Var);
|
||||
match self.tcx.const_qualif_map.borrow_mut().entry(expr.id) {
|
||||
Entry::Occupied(entry) => return *entry.get(),
|
||||
@ -143,8 +144,8 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
|
||||
fn fn_like(&mut self,
|
||||
fk: FnKind,
|
||||
fd: &ast::FnDecl,
|
||||
b: &ast::Block,
|
||||
fd: &hir::FnDecl,
|
||||
b: &hir::Block,
|
||||
s: Span,
|
||||
fn_id: ast::NodeId)
|
||||
-> ConstQualif {
|
||||
@ -157,11 +158,11 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
let mode = match fk {
|
||||
FnKind::ItemFn(_, _, _, ast::Constness::Const, _, _) => {
|
||||
FnKind::ItemFn(_, _, _, hir::Constness::Const, _, _) => {
|
||||
Mode::ConstFn
|
||||
}
|
||||
FnKind::Method(_, m, _) => {
|
||||
if m.constness == ast::Constness::Const {
|
||||
if m.constness == hir::Constness::Const {
|
||||
Mode::ConstFn
|
||||
} else {
|
||||
Mode::Var
|
||||
@ -174,7 +175,7 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
if mode == Mode::ConstFn {
|
||||
for arg in &fd.inputs {
|
||||
match arg.pat.node {
|
||||
ast::PatIdent(ast::BindByValue(ast::MutImmutable), _, None) => {}
|
||||
hir::PatIdent(hir::BindByValue(hir::MutImmutable), _, None) => {}
|
||||
_ => {
|
||||
span_err!(self.tcx.sess, arg.pat.span, E0022,
|
||||
"arguments of constant functions can only \
|
||||
@ -204,7 +205,7 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
|
||||
/// Returns true if the call is to a const fn or method.
|
||||
fn handle_const_fn_call(&mut self,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
def_id: DefId,
|
||||
ret_ty: Ty<'tcx>)
|
||||
-> bool {
|
||||
@ -246,12 +247,12 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn record_borrow(&mut self, id: ast::NodeId, mutbl: ast::Mutability) {
|
||||
fn record_borrow(&mut self, id: ast::NodeId, mutbl: hir::Mutability) {
|
||||
match self.rvalue_borrows.entry(id) {
|
||||
Entry::Occupied(mut entry) => {
|
||||
// Merge the two borrows, taking the most demanding
|
||||
// one, mutability-wise.
|
||||
if mutbl == ast::MutMutable {
|
||||
if mutbl == hir::MutMutable {
|
||||
entry.insert(mutbl);
|
||||
}
|
||||
}
|
||||
@ -270,7 +271,7 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn check_static_mut_type(&self, e: &ast::Expr) {
|
||||
fn check_static_mut_type(&self, e: &hir::Expr) {
|
||||
let node_ty = self.tcx.node_id_to_type(e.id);
|
||||
let tcontents = node_ty.type_contents(self.tcx);
|
||||
|
||||
@ -286,7 +287,7 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
"mutable statics are not allowed to have {}", suffix);
|
||||
}
|
||||
|
||||
fn check_static_type(&self, e: &ast::Expr) {
|
||||
fn check_static_type(&self, e: &hir::Expr) {
|
||||
let ty = self.tcx.node_id_to_type(e.id);
|
||||
let infcx = infer::new_infer_ctxt(self.tcx, &self.tcx.tables, None, false);
|
||||
let cause = traits::ObligationCause::new(e.span, e.id, traits::SharedStatic);
|
||||
@ -302,21 +303,21 @@ impl<'a, 'tcx> CheckCrateVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
fn visit_item(&mut self, i: &ast::Item) {
|
||||
fn visit_item(&mut self, i: &hir::Item) {
|
||||
debug!("visit_item(item={})", self.tcx.map.node_to_string(i.id));
|
||||
match i.node {
|
||||
ast::ItemStatic(_, ast::MutImmutable, ref expr) => {
|
||||
hir::ItemStatic(_, hir::MutImmutable, ref expr) => {
|
||||
self.check_static_type(&**expr);
|
||||
self.global_expr(Mode::Static, &**expr);
|
||||
}
|
||||
ast::ItemStatic(_, ast::MutMutable, ref expr) => {
|
||||
hir::ItemStatic(_, hir::MutMutable, ref expr) => {
|
||||
self.check_static_mut_type(&**expr);
|
||||
self.global_expr(Mode::StaticMut, &**expr);
|
||||
}
|
||||
ast::ItemConst(_, ref expr) => {
|
||||
hir::ItemConst(_, ref expr) => {
|
||||
self.global_expr(Mode::Const, &**expr);
|
||||
}
|
||||
ast::ItemEnum(ref enum_definition, _) => {
|
||||
hir::ItemEnum(ref enum_definition, _) => {
|
||||
for var in &enum_definition.variants {
|
||||
if let Some(ref ex) = var.node.disr_expr {
|
||||
self.global_expr(Mode::Const, &**ex);
|
||||
@ -329,9 +330,9 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, t: &'v ast::TraitItem) {
|
||||
fn visit_trait_item(&mut self, t: &'v hir::TraitItem) {
|
||||
match t.node {
|
||||
ast::ConstTraitItem(_, ref default) => {
|
||||
hir::ConstTraitItem(_, ref default) => {
|
||||
if let Some(ref expr) = *default {
|
||||
self.global_expr(Mode::Const, &*expr);
|
||||
} else {
|
||||
@ -342,9 +343,9 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, i: &'v ast::ImplItem) {
|
||||
fn visit_impl_item(&mut self, i: &'v hir::ImplItem) {
|
||||
match i.node {
|
||||
ast::ConstImplItem(_, ref expr) => {
|
||||
hir::ConstImplItem(_, ref expr) => {
|
||||
self.global_expr(Mode::Const, &*expr);
|
||||
}
|
||||
_ => self.with_mode(Mode::Var, |v| visit::walk_impl_item(v, i)),
|
||||
@ -353,19 +354,19 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
|
||||
fn visit_fn(&mut self,
|
||||
fk: FnKind<'v>,
|
||||
fd: &'v ast::FnDecl,
|
||||
b: &'v ast::Block,
|
||||
fd: &'v hir::FnDecl,
|
||||
b: &'v hir::Block,
|
||||
s: Span,
|
||||
fn_id: ast::NodeId) {
|
||||
self.fn_like(fk, fd, b, s, fn_id);
|
||||
}
|
||||
|
||||
fn visit_pat(&mut self, p: &ast::Pat) {
|
||||
fn visit_pat(&mut self, p: &hir::Pat) {
|
||||
match p.node {
|
||||
ast::PatLit(ref lit) => {
|
||||
hir::PatLit(ref lit) => {
|
||||
self.global_expr(Mode::Const, &**lit);
|
||||
}
|
||||
ast::PatRange(ref start, ref end) => {
|
||||
hir::PatRange(ref start, ref end) => {
|
||||
self.global_expr(Mode::Const, &**start);
|
||||
self.global_expr(Mode::Const, &**end);
|
||||
|
||||
@ -386,24 +387,20 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_block(&mut self, block: &ast::Block) {
|
||||
fn visit_block(&mut self, block: &hir::Block) {
|
||||
// Check all statements in the block
|
||||
for stmt in &block.stmts {
|
||||
let span = match stmt.node {
|
||||
ast::StmtDecl(ref decl, _) => {
|
||||
hir::StmtDecl(ref decl, _) => {
|
||||
match decl.node {
|
||||
ast::DeclLocal(_) => decl.span,
|
||||
hir::DeclLocal(_) => decl.span,
|
||||
|
||||
// Item statements are allowed
|
||||
ast::DeclItem(_) => continue
|
||||
hir::DeclItem(_) => continue
|
||||
}
|
||||
}
|
||||
ast::StmtExpr(ref expr, _) => expr.span,
|
||||
ast::StmtSemi(ref semi, _) => semi.span,
|
||||
ast::StmtMac(..) => {
|
||||
self.tcx.sess.span_bug(stmt.span, "unexpanded statement \
|
||||
macro in const?!")
|
||||
}
|
||||
hir::StmtExpr(ref expr, _) => expr.span,
|
||||
hir::StmtSemi(ref semi, _) => semi.span,
|
||||
};
|
||||
self.add_qualif(ConstQualif::NOT_CONST);
|
||||
if self.mode != Mode::Var {
|
||||
@ -415,7 +412,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
visit::walk_block(self, block);
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, ex: &ast::Expr) {
|
||||
fn visit_expr(&mut self, ex: &hir::Expr) {
|
||||
let mut outer = self.qualif;
|
||||
self.qualif = ConstQualif::empty();
|
||||
|
||||
@ -425,7 +422,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
|
||||
// Special-case some expressions to avoid certain flags bubbling up.
|
||||
match ex.node {
|
||||
ast::ExprCall(ref callee, ref args) => {
|
||||
hir::ExprCall(ref callee, ref args) => {
|
||||
for arg in args {
|
||||
self.visit_expr(&**arg)
|
||||
}
|
||||
@ -436,7 +433,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
let added = self.qualif - inner;
|
||||
self.qualif = inner | (added - ConstQualif::NON_ZERO_SIZED);
|
||||
}
|
||||
ast::ExprRepeat(ref element, _) => {
|
||||
hir::ExprRepeat(ref element, _) => {
|
||||
self.visit_expr(&**element);
|
||||
// The count is checked elsewhere (typeck).
|
||||
let count = match node_ty.sty {
|
||||
@ -448,14 +445,14 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
self.qualif.remove(ConstQualif::NON_ZERO_SIZED | ConstQualif::PREFER_IN_PLACE);
|
||||
}
|
||||
}
|
||||
ast::ExprMatch(ref discr, ref arms, _) => {
|
||||
hir::ExprMatch(ref discr, ref arms, _) => {
|
||||
// Compute the most demanding borrow from all the arms'
|
||||
// patterns and set that on the discriminator.
|
||||
let mut borrow = None;
|
||||
for pat in arms.iter().flat_map(|arm| &arm.pats) {
|
||||
let pat_borrow = self.rvalue_borrows.remove(&pat.id);
|
||||
match (borrow, pat_borrow) {
|
||||
(None, _) | (_, Some(ast::MutMutable)) => {
|
||||
(None, _) | (_, Some(hir::MutMutable)) => {
|
||||
borrow = pat_borrow;
|
||||
}
|
||||
_ => {}
|
||||
@ -467,9 +464,9 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
visit::walk_expr(self, ex);
|
||||
}
|
||||
// Division by zero and overflow checking.
|
||||
ast::ExprBinary(op, _, _) => {
|
||||
hir::ExprBinary(op, _, _) => {
|
||||
visit::walk_expr(self, ex);
|
||||
let div_or_rem = op.node == ast::BiDiv || op.node == ast::BiRem;
|
||||
let div_or_rem = op.node == hir::BiDiv || op.node == hir::BiRem;
|
||||
match node_ty.sty {
|
||||
ty::TyUint(_) | ty::TyInt(_) if div_or_rem => {
|
||||
if !self.qualif.intersects(ConstQualif::NOT_CONST) {
|
||||
@ -492,7 +489,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
|
||||
// Handle borrows on (or inside the autorefs of) this expression.
|
||||
match self.rvalue_borrows.remove(&ex.id) {
|
||||
Some(ast::MutImmutable) => {
|
||||
Some(hir::MutImmutable) => {
|
||||
// Constants cannot be borrowed if they contain interior mutability as
|
||||
// it means that our "silent insertion of statics" could change
|
||||
// initializer values (very bad).
|
||||
@ -514,7 +511,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
self.add_qualif(ConstQualif::HAS_STATIC_BORROWS);
|
||||
}
|
||||
}
|
||||
Some(ast::MutMutable) => {
|
||||
Some(hir::MutMutable) => {
|
||||
// `&mut expr` means expr could be mutated, unless it's zero-sized.
|
||||
if self.qualif.intersects(ConstQualif::NON_ZERO_SIZED) {
|
||||
if self.mode == Mode::Var {
|
||||
@ -545,7 +542,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for CheckCrateVisitor<'a, 'tcx> {
|
||||
/// of a const/static item, it is qualified for promotion
|
||||
/// instead of producing errors.
|
||||
fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
e: &ast::Expr, node_ty: Ty<'tcx>) {
|
||||
e: &hir::Expr, node_ty: Ty<'tcx>) {
|
||||
match node_ty.sty {
|
||||
ty::TyStruct(def, _) |
|
||||
ty::TyEnum(def, _) if def.has_dtor() => {
|
||||
@ -561,27 +558,27 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
|
||||
let method_call = ty::MethodCall::expr(e.id);
|
||||
match e.node {
|
||||
ast::ExprUnary(..) |
|
||||
ast::ExprBinary(..) |
|
||||
ast::ExprIndex(..) if v.tcx.tables.borrow().method_map.contains_key(&method_call) => {
|
||||
hir::ExprUnary(..) |
|
||||
hir::ExprBinary(..) |
|
||||
hir::ExprIndex(..) if v.tcx.tables.borrow().method_map.contains_key(&method_call) => {
|
||||
v.add_qualif(ConstQualif::NOT_CONST);
|
||||
if v.mode != Mode::Var {
|
||||
span_err!(v.tcx.sess, e.span, E0011,
|
||||
"user-defined operators are not allowed in {}s", v.msg());
|
||||
}
|
||||
}
|
||||
ast::ExprBox(..) |
|
||||
ast::ExprUnary(ast::UnUniq, _) => {
|
||||
hir::ExprBox(..) |
|
||||
hir::ExprUnary(hir::UnUniq, _) => {
|
||||
v.add_qualif(ConstQualif::NOT_CONST);
|
||||
if v.mode != Mode::Var {
|
||||
span_err!(v.tcx.sess, e.span, E0010,
|
||||
"allocations are not allowed in {}s", v.msg());
|
||||
}
|
||||
}
|
||||
ast::ExprUnary(op, ref inner) => {
|
||||
hir::ExprUnary(op, ref inner) => {
|
||||
match v.tcx.node_id_to_type(inner.id).sty {
|
||||
ty::TyRawPtr(_) => {
|
||||
assert!(op == ast::UnDeref);
|
||||
assert!(op == hir::UnDeref);
|
||||
|
||||
v.add_qualif(ConstQualif::NOT_CONST);
|
||||
if v.mode != Mode::Var {
|
||||
@ -592,12 +589,12 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
ast::ExprBinary(op, ref lhs, _) => {
|
||||
hir::ExprBinary(op, ref lhs, _) => {
|
||||
match v.tcx.node_id_to_type(lhs.id).sty {
|
||||
ty::TyRawPtr(_) => {
|
||||
assert!(op.node == ast::BiEq || op.node == ast::BiNe ||
|
||||
op.node == ast::BiLe || op.node == ast::BiLt ||
|
||||
op.node == ast::BiGe || op.node == ast::BiGt);
|
||||
assert!(op.node == hir::BiEq || op.node == hir::BiNe ||
|
||||
op.node == hir::BiLe || op.node == hir::BiLt ||
|
||||
op.node == hir::BiGe || op.node == hir::BiGt);
|
||||
|
||||
v.add_qualif(ConstQualif::NOT_CONST);
|
||||
if v.mode != Mode::Var {
|
||||
@ -608,7 +605,7 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
ast::ExprCast(ref from, _) => {
|
||||
hir::ExprCast(ref from, _) => {
|
||||
debug!("Checking const cast(id={})", from.id);
|
||||
match v.tcx.cast_kinds.borrow().get(&from.id) {
|
||||
None => v.tcx.sess.span_bug(e.span, "no kind for cast"),
|
||||
@ -622,7 +619,7 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
let def = v.tcx.def_map.borrow().get(&e.id).map(|d| d.full_def());
|
||||
match def {
|
||||
Some(def::DefVariant(_, _, _)) => {
|
||||
@ -677,12 +674,12 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::ExprCall(ref callee, _) => {
|
||||
hir::ExprCall(ref callee, _) => {
|
||||
let mut callee = &**callee;
|
||||
loop {
|
||||
callee = match callee.node {
|
||||
ast::ExprParen(ref inner) => &**inner,
|
||||
ast::ExprBlock(ref block) => match block.expr {
|
||||
hir::ExprParen(ref inner) => &**inner,
|
||||
hir::ExprBlock(ref block) => match block.expr {
|
||||
Some(ref tail) => &**tail,
|
||||
None => break
|
||||
},
|
||||
@ -720,7 +717,7 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::ExprMethodCall(..) => {
|
||||
hir::ExprMethodCall(..) => {
|
||||
let method = v.tcx.tables.borrow().method_map[&method_call];
|
||||
let is_const = match v.tcx.impl_or_trait_item(method.def_id).container() {
|
||||
ty::ImplContainer(_) => v.handle_const_fn_call(e, method.def_id, node_ty),
|
||||
@ -735,23 +732,23 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::ExprStruct(..) => {
|
||||
hir::ExprStruct(..) => {
|
||||
let did = v.tcx.def_map.borrow().get(&e.id).map(|def| def.def_id());
|
||||
if did == v.tcx.lang_items.unsafe_cell_type() {
|
||||
v.add_qualif(ConstQualif::MUTABLE_MEM);
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprLit(_) |
|
||||
ast::ExprAddrOf(..) => {
|
||||
hir::ExprLit(_) |
|
||||
hir::ExprAddrOf(..) => {
|
||||
v.add_qualif(ConstQualif::NON_ZERO_SIZED);
|
||||
}
|
||||
|
||||
ast::ExprRepeat(..) => {
|
||||
hir::ExprRepeat(..) => {
|
||||
v.add_qualif(ConstQualif::PREFER_IN_PLACE);
|
||||
}
|
||||
|
||||
ast::ExprClosure(..) => {
|
||||
hir::ExprClosure(..) => {
|
||||
// Paths in constant contexts cannot refer to local variables,
|
||||
// as there are none, and thus closures can't have upvars there.
|
||||
if v.tcx.with_freevars(e.id, |fv| !fv.is_empty()) {
|
||||
@ -761,38 +758,34 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprBlock(_) |
|
||||
ast::ExprIndex(..) |
|
||||
ast::ExprField(..) |
|
||||
ast::ExprTupField(..) |
|
||||
ast::ExprVec(_) |
|
||||
ast::ExprParen(..) |
|
||||
ast::ExprTup(..) => {}
|
||||
hir::ExprBlock(_) |
|
||||
hir::ExprIndex(..) |
|
||||
hir::ExprField(..) |
|
||||
hir::ExprTupField(..) |
|
||||
hir::ExprVec(_) |
|
||||
hir::ExprParen(..) |
|
||||
hir::ExprTup(..) => {}
|
||||
|
||||
// Conditional control flow (possible to implement).
|
||||
ast::ExprMatch(..) |
|
||||
ast::ExprIf(..) |
|
||||
ast::ExprIfLet(..) |
|
||||
hir::ExprMatch(..) |
|
||||
hir::ExprIf(..) |
|
||||
|
||||
// Loops (not very meaningful in constants).
|
||||
ast::ExprWhile(..) |
|
||||
ast::ExprWhileLet(..) |
|
||||
ast::ExprForLoop(..) |
|
||||
ast::ExprLoop(..) |
|
||||
hir::ExprWhile(..) |
|
||||
hir::ExprLoop(..) |
|
||||
|
||||
// More control flow (also not very meaningful).
|
||||
ast::ExprBreak(_) |
|
||||
ast::ExprAgain(_) |
|
||||
ast::ExprRet(_) |
|
||||
hir::ExprBreak(_) |
|
||||
hir::ExprAgain(_) |
|
||||
hir::ExprRet(_) |
|
||||
|
||||
// Miscellaneous expressions that could be implemented.
|
||||
ast::ExprRange(..) |
|
||||
hir::ExprRange(..) |
|
||||
|
||||
// Expressions with side-effects.
|
||||
ast::ExprAssign(..) |
|
||||
ast::ExprAssignOp(..) |
|
||||
ast::ExprInlineAsm(_) |
|
||||
ast::ExprMac(_) => {
|
||||
hir::ExprAssign(..) |
|
||||
hir::ExprAssignOp(..) |
|
||||
hir::ExprInlineAsm(_) => {
|
||||
v.add_qualif(ConstQualif::NOT_CONST);
|
||||
if v.mode != Mode::Var {
|
||||
span_err!(v.tcx.sess, e.span, E0019,
|
||||
@ -803,7 +796,7 @@ fn check_expr<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>,
|
||||
}
|
||||
|
||||
/// Check the adjustments of an expression
|
||||
fn check_adjustments<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>, e: &ast::Expr) {
|
||||
fn check_adjustments<'a, 'tcx>(v: &mut CheckCrateVisitor<'a, 'tcx>, e: &hir::Expr) {
|
||||
match v.tcx.tables.borrow().adjustments.get(&e.id) {
|
||||
None | Some(&ty::AdjustReifyFnPointer) | Some(&ty::AdjustUnsafeFnPointer) => {}
|
||||
Some(&ty::AdjustDerefRef(ty::AutoDerefRef { autoderefs, .. })) => {
|
||||
@ -891,7 +884,7 @@ impl<'a, 'tcx> euv::Delegate<'tcx> for CheckCrateVisitor<'a, 'tcx> {
|
||||
break;
|
||||
}
|
||||
let mutbl = bk.to_mutbl_lossy();
|
||||
if mutbl == ast::MutMutable && self.mode == Mode::StaticMut {
|
||||
if mutbl == hir::MutMutable && self.mode == Mode::StaticMut {
|
||||
// Mutable slices are the only `&mut` allowed in
|
||||
// globals, but only in `static mut`, nowhere else.
|
||||
// FIXME: This exception is really weird... there isn't
|
||||
@ -940,12 +933,12 @@ impl<'a, 'tcx> euv::Delegate<'tcx> for CheckCrateVisitor<'a, 'tcx> {
|
||||
_mode: euv::MutateMode) {}
|
||||
|
||||
fn matched_pat(&mut self,
|
||||
_: &ast::Pat,
|
||||
_: &hir::Pat,
|
||||
_: mc::cmt,
|
||||
_: euv::MatchMode) {}
|
||||
|
||||
fn consume_pat(&mut self,
|
||||
_consume_pat: &ast::Pat,
|
||||
_consume_pat: &hir::Pat,
|
||||
_cmt: mc::cmt,
|
||||
_mode: euv::ConsumeMode) {}
|
||||
}
|
||||
|
@ -11,10 +11,10 @@ use self::Context::*;
|
||||
|
||||
use session::Session;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::visit;
|
||||
use rustc_front::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::hir;
|
||||
|
||||
#[derive(Clone, Copy, PartialEq)]
|
||||
enum Context {
|
||||
@ -27,29 +27,29 @@ struct CheckLoopVisitor<'a> {
|
||||
cx: Context
|
||||
}
|
||||
|
||||
pub fn check_crate(sess: &Session, krate: &ast::Crate) {
|
||||
pub fn check_crate(sess: &Session, krate: &hir::Crate) {
|
||||
visit::walk_crate(&mut CheckLoopVisitor { sess: sess, cx: Normal }, krate)
|
||||
}
|
||||
|
||||
impl<'a, 'v> Visitor<'v> for CheckLoopVisitor<'a> {
|
||||
fn visit_item(&mut self, i: &ast::Item) {
|
||||
fn visit_item(&mut self, i: &hir::Item) {
|
||||
self.with_context(Normal, |v| visit::walk_item(v, i));
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, e: &ast::Expr) {
|
||||
fn visit_expr(&mut self, e: &hir::Expr) {
|
||||
match e.node {
|
||||
ast::ExprWhile(ref e, ref b, _) => {
|
||||
hir::ExprWhile(ref e, ref b, _) => {
|
||||
self.visit_expr(&**e);
|
||||
self.with_context(Loop, |v| v.visit_block(&**b));
|
||||
}
|
||||
ast::ExprLoop(ref b, _) => {
|
||||
hir::ExprLoop(ref b, _) => {
|
||||
self.with_context(Loop, |v| v.visit_block(&**b));
|
||||
}
|
||||
ast::ExprClosure(_, _, ref b) => {
|
||||
hir::ExprClosure(_, _, ref b) => {
|
||||
self.with_context(Closure, |v| v.visit_block(&**b));
|
||||
}
|
||||
ast::ExprBreak(_) => self.require_loop("break", e.span),
|
||||
ast::ExprAgain(_) => self.require_loop("continue", e.span),
|
||||
hir::ExprBreak(_) => self.require_loop("break", e.span),
|
||||
hir::ExprAgain(_) => self.require_loop("continue", e.span),
|
||||
_ => visit::walk_expr(self, e)
|
||||
}
|
||||
}
|
||||
|
@ -31,18 +31,23 @@ use std::cmp::Ordering;
|
||||
use std::fmt;
|
||||
use std::iter::{range_inclusive, FromIterator, IntoIterator, repeat};
|
||||
use std::slice;
|
||||
use syntax::ast::{self, DUMMY_NODE_ID, NodeId, Pat};
|
||||
|
||||
use rustc_front::hir;
|
||||
use rustc_front::hir::Pat;
|
||||
use rustc_front::visit::{self, Visitor, FnKind};
|
||||
use rustc_front::util as front_util;
|
||||
|
||||
use syntax::ast::{self, DUMMY_NODE_ID, NodeId};
|
||||
use syntax::ast_util;
|
||||
use syntax::codemap::{Span, Spanned, DUMMY_SP};
|
||||
use syntax::fold::{Folder, noop_fold_pat};
|
||||
use syntax::print::pprust::pat_to_string;
|
||||
use rustc_front::fold::{Folder, noop_fold_pat};
|
||||
use rustc_front::print::pprust::pat_to_string;
|
||||
use syntax::ptr::P;
|
||||
use syntax::visit::{self, Visitor, FnKind};
|
||||
use util::nodemap::FnvHashMap;
|
||||
|
||||
pub const DUMMY_WILD_PAT: &'static Pat = &Pat {
|
||||
id: DUMMY_NODE_ID,
|
||||
node: ast::PatWild(ast::PatWildSingle),
|
||||
node: hir::PatWild(hir::PatWildSingle),
|
||||
span: DUMMY_SP
|
||||
};
|
||||
|
||||
@ -137,14 +142,14 @@ enum WitnessPreference {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for MatchCheckCtxt<'a, 'tcx> {
|
||||
fn visit_expr(&mut self, ex: &ast::Expr) {
|
||||
fn visit_expr(&mut self, ex: &hir::Expr) {
|
||||
check_expr(self, ex);
|
||||
}
|
||||
fn visit_local(&mut self, l: &ast::Local) {
|
||||
fn visit_local(&mut self, l: &hir::Local) {
|
||||
check_local(self, l);
|
||||
}
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v ast::FnDecl,
|
||||
b: &'v ast::Block, s: Span, n: NodeId) {
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v hir::FnDecl,
|
||||
b: &'v hir::Block, s: Span, n: NodeId) {
|
||||
check_fn(self, fk, fd, b, s, n);
|
||||
}
|
||||
}
|
||||
@ -157,10 +162,10 @@ pub fn check_crate(tcx: &ty::ctxt) {
|
||||
tcx.sess.abort_if_errors();
|
||||
}
|
||||
|
||||
fn check_expr(cx: &mut MatchCheckCtxt, ex: &ast::Expr) {
|
||||
fn check_expr(cx: &mut MatchCheckCtxt, ex: &hir::Expr) {
|
||||
visit::walk_expr(cx, ex);
|
||||
match ex.node {
|
||||
ast::ExprMatch(ref scrut, ref arms, source) => {
|
||||
hir::ExprMatch(ref scrut, ref arms, source) => {
|
||||
for arm in arms {
|
||||
// First, check legality of move bindings.
|
||||
check_legality_of_move_bindings(cx,
|
||||
@ -180,7 +185,7 @@ fn check_expr(cx: &mut MatchCheckCtxt, ex: &ast::Expr) {
|
||||
(arm.pats.iter().map(|pat| {
|
||||
static_inliner.fold_pat((*pat).clone())
|
||||
}).collect(), arm.guard.as_ref().map(|e| &**e))
|
||||
}).collect::<Vec<(Vec<P<Pat>>, Option<&ast::Expr>)>>();
|
||||
}).collect::<Vec<(Vec<P<Pat>>, Option<&hir::Expr>)>>();
|
||||
|
||||
// Bail out early if inlining failed.
|
||||
if static_inliner.failed {
|
||||
@ -231,9 +236,9 @@ fn check_expr(cx: &mut MatchCheckCtxt, ex: &ast::Expr) {
|
||||
}
|
||||
|
||||
fn check_for_bindings_named_the_same_as_variants(cx: &MatchCheckCtxt, pat: &Pat) {
|
||||
ast_util::walk_pat(pat, |p| {
|
||||
front_util::walk_pat(pat, |p| {
|
||||
match p.node {
|
||||
ast::PatIdent(ast::BindByValue(ast::MutImmutable), ident, None) => {
|
||||
hir::PatIdent(hir::BindByValue(hir::MutImmutable), ident, None) => {
|
||||
let pat_ty = cx.tcx.pat_ty(p);
|
||||
if let ty::TyEnum(edef, _) = pat_ty.sty {
|
||||
let def = cx.tcx.def_map.borrow().get(&p.id).map(|d| d.full_def());
|
||||
@ -262,8 +267,8 @@ fn check_for_bindings_named_the_same_as_variants(cx: &MatchCheckCtxt, pat: &Pat)
|
||||
|
||||
// Check that we do not match against a static NaN (#6804)
|
||||
fn check_for_static_nan(cx: &MatchCheckCtxt, pat: &Pat) {
|
||||
ast_util::walk_pat(pat, |p| {
|
||||
if let ast::PatLit(ref expr) = p.node {
|
||||
front_util::walk_pat(pat, |p| {
|
||||
if let hir::PatLit(ref expr) = p.node {
|
||||
match eval_const_expr_partial(cx.tcx, &**expr, ExprTypeChecked) {
|
||||
Ok(ConstVal::Float(f)) if f.is_nan() => {
|
||||
span_warn!(cx.tcx.sess, p.span, E0003,
|
||||
@ -290,8 +295,8 @@ fn check_for_static_nan(cx: &MatchCheckCtxt, pat: &Pat) {
|
||||
|
||||
// Check for unreachable patterns
|
||||
fn check_arms(cx: &MatchCheckCtxt,
|
||||
arms: &[(Vec<P<Pat>>, Option<&ast::Expr>)],
|
||||
source: ast::MatchSource) {
|
||||
arms: &[(Vec<P<Pat>>, Option<&hir::Expr>)],
|
||||
source: hir::MatchSource) {
|
||||
let mut seen = Matrix(vec![]);
|
||||
let mut printed_if_let_err = false;
|
||||
for &(ref pats, guard) in arms {
|
||||
@ -301,7 +306,7 @@ fn check_arms(cx: &MatchCheckCtxt,
|
||||
match is_useful(cx, &seen, &v[..], LeaveOutWitness) {
|
||||
NotUseful => {
|
||||
match source {
|
||||
ast::MatchSource::IfLetDesugar { .. } => {
|
||||
hir::MatchSource::IfLetDesugar { .. } => {
|
||||
if printed_if_let_err {
|
||||
// we already printed an irrefutable if-let pattern error.
|
||||
// We don't want two, that's just confusing.
|
||||
@ -315,7 +320,7 @@ fn check_arms(cx: &MatchCheckCtxt,
|
||||
}
|
||||
},
|
||||
|
||||
ast::MatchSource::WhileLetDesugar => {
|
||||
hir::MatchSource::WhileLetDesugar => {
|
||||
// find the first arm pattern so we can use its span
|
||||
let &(ref first_arm_pats, _) = &arms[0];
|
||||
let first_pat = &first_arm_pats[0];
|
||||
@ -323,7 +328,7 @@ fn check_arms(cx: &MatchCheckCtxt,
|
||||
span_err!(cx.tcx.sess, span, E0165, "irrefutable while-let pattern");
|
||||
},
|
||||
|
||||
ast::MatchSource::ForLoopDesugar => {
|
||||
hir::MatchSource::ForLoopDesugar => {
|
||||
// this is a bug, because on `match iter.next()` we cover
|
||||
// `Some(<head>)` and `None`. It's impossible to have an unreachable
|
||||
// pattern
|
||||
@ -331,7 +336,7 @@ fn check_arms(cx: &MatchCheckCtxt,
|
||||
cx.tcx.sess.span_bug(pat.span, "unreachable for-loop pattern")
|
||||
},
|
||||
|
||||
ast::MatchSource::Normal => {
|
||||
hir::MatchSource::Normal => {
|
||||
span_err!(cx.tcx.sess, pat.span, E0001, "unreachable pattern")
|
||||
},
|
||||
}
|
||||
@ -350,12 +355,12 @@ fn check_arms(cx: &MatchCheckCtxt,
|
||||
|
||||
fn raw_pat<'a>(p: &'a Pat) -> &'a Pat {
|
||||
match p.node {
|
||||
ast::PatIdent(_, _, Some(ref s)) => raw_pat(&**s),
|
||||
hir::PatIdent(_, _, Some(ref s)) => raw_pat(&**s),
|
||||
_ => p
|
||||
}
|
||||
}
|
||||
|
||||
fn check_exhaustive(cx: &MatchCheckCtxt, sp: Span, matrix: &Matrix, source: ast::MatchSource) {
|
||||
fn check_exhaustive(cx: &MatchCheckCtxt, sp: Span, matrix: &Matrix, source: hir::MatchSource) {
|
||||
match is_useful(cx, matrix, &[DUMMY_WILD_PAT], ConstructWitness) {
|
||||
UsefulWithWitness(pats) => {
|
||||
let witness = match &pats[..] {
|
||||
@ -364,10 +369,10 @@ fn check_exhaustive(cx: &MatchCheckCtxt, sp: Span, matrix: &Matrix, source: ast:
|
||||
_ => unreachable!()
|
||||
};
|
||||
match source {
|
||||
ast::MatchSource::ForLoopDesugar => {
|
||||
hir::MatchSource::ForLoopDesugar => {
|
||||
// `witness` has the form `Some(<head>)`, peel off the `Some`
|
||||
let witness = match witness.node {
|
||||
ast::PatEnum(_, Some(ref pats)) => match &pats[..] {
|
||||
hir::PatEnum(_, Some(ref pats)) => match &pats[..] {
|
||||
[ref pat] => &**pat,
|
||||
_ => unreachable!(),
|
||||
},
|
||||
@ -394,14 +399,14 @@ fn check_exhaustive(cx: &MatchCheckCtxt, sp: Span, matrix: &Matrix, source: ast:
|
||||
}
|
||||
}
|
||||
|
||||
fn const_val_to_expr(value: &ConstVal) -> P<ast::Expr> {
|
||||
fn const_val_to_expr(value: &ConstVal) -> P<hir::Expr> {
|
||||
let node = match value {
|
||||
&ConstVal::Bool(b) => ast::LitBool(b),
|
||||
&ConstVal::Bool(b) => hir::LitBool(b),
|
||||
_ => unreachable!()
|
||||
};
|
||||
P(ast::Expr {
|
||||
P(hir::Expr {
|
||||
id: 0,
|
||||
node: ast::ExprLit(P(Spanned { node: node, span: DUMMY_SP })),
|
||||
node: hir::ExprLit(P(Spanned { node: node, span: DUMMY_SP })),
|
||||
span: DUMMY_SP
|
||||
})
|
||||
}
|
||||
@ -440,7 +445,7 @@ impl<'map> ast_util::IdVisitingOperation for RenamingRecorder<'map> {
|
||||
impl<'a, 'tcx> Folder for StaticInliner<'a, 'tcx> {
|
||||
fn fold_pat(&mut self, pat: P<Pat>) -> P<Pat> {
|
||||
return match pat.node {
|
||||
ast::PatIdent(..) | ast::PatEnum(..) | ast::PatQPath(..) => {
|
||||
hir::PatIdent(..) | hir::PatEnum(..) | hir::PatQPath(..) => {
|
||||
let def = self.tcx.def_map.borrow().get(&pat.id).map(|d| d.full_def());
|
||||
match def {
|
||||
Some(DefAssociatedConst(did)) |
|
||||
@ -469,8 +474,8 @@ impl<'a, 'tcx> Folder for StaticInliner<'a, 'tcx> {
|
||||
_ => noop_fold_pat(pat, self)
|
||||
};
|
||||
|
||||
fn record_renamings(const_expr: &ast::Expr,
|
||||
substituted_pat: &ast::Pat,
|
||||
fn record_renamings(const_expr: &hir::Expr,
|
||||
substituted_pat: &hir::Pat,
|
||||
renaming_map: &mut FnvHashMap<(NodeId, Span), NodeId>) {
|
||||
let mut renaming_recorder = RenamingRecorder {
|
||||
substituted_node_id: substituted_pat.id,
|
||||
@ -478,7 +483,7 @@ impl<'a, 'tcx> Folder for StaticInliner<'a, 'tcx> {
|
||||
renaming_map: renaming_map,
|
||||
};
|
||||
|
||||
let mut id_visitor = ast_util::IdVisitor {
|
||||
let mut id_visitor = front_util::IdVisitor {
|
||||
operation: &mut renaming_recorder,
|
||||
pass_through_items: true,
|
||||
visited_outermost: false,
|
||||
@ -507,26 +512,26 @@ fn construct_witness<'a,'tcx>(cx: &MatchCheckCtxt<'a,'tcx>, ctor: &Constructor,
|
||||
let pats_len = pats.len();
|
||||
let mut pats = pats.into_iter().map(|p| P((*p).clone()));
|
||||
let pat = match left_ty.sty {
|
||||
ty::TyTuple(_) => ast::PatTup(pats.collect()),
|
||||
ty::TyTuple(_) => hir::PatTup(pats.collect()),
|
||||
|
||||
ty::TyEnum(adt, _) | ty::TyStruct(adt, _) => {
|
||||
let v = adt.variant_of_ctor(ctor);
|
||||
if let VariantKind::Dict = v.kind() {
|
||||
let field_pats: Vec<_> = v.fields.iter()
|
||||
.zip(pats)
|
||||
.filter(|&(_, ref pat)| pat.node != ast::PatWild(ast::PatWildSingle))
|
||||
.filter(|&(_, ref pat)| pat.node != hir::PatWild(hir::PatWildSingle))
|
||||
.map(|(field, pat)| Spanned {
|
||||
span: DUMMY_SP,
|
||||
node: ast::FieldPat {
|
||||
node: hir::FieldPat {
|
||||
ident: ast::Ident::new(field.name),
|
||||
pat: pat,
|
||||
is_shorthand: false,
|
||||
}
|
||||
}).collect();
|
||||
let has_more_fields = field_pats.len() < pats_len;
|
||||
ast::PatStruct(def_to_path(cx.tcx, v.did), field_pats, has_more_fields)
|
||||
hir::PatStruct(def_to_path(cx.tcx, v.did), field_pats, has_more_fields)
|
||||
} else {
|
||||
ast::PatEnum(def_to_path(cx.tcx, v.did), Some(pats.collect()))
|
||||
hir::PatEnum(def_to_path(cx.tcx, v.did), Some(pats.collect()))
|
||||
}
|
||||
}
|
||||
|
||||
@ -535,40 +540,40 @@ fn construct_witness<'a,'tcx>(cx: &MatchCheckCtxt<'a,'tcx>, ctor: &Constructor,
|
||||
ty::TyArray(_, n) => match ctor {
|
||||
&Single => {
|
||||
assert_eq!(pats_len, n);
|
||||
ast::PatVec(pats.collect(), None, vec!())
|
||||
hir::PatVec(pats.collect(), None, vec!())
|
||||
},
|
||||
_ => unreachable!()
|
||||
},
|
||||
ty::TySlice(_) => match ctor {
|
||||
&Slice(n) => {
|
||||
assert_eq!(pats_len, n);
|
||||
ast::PatVec(pats.collect(), None, vec!())
|
||||
hir::PatVec(pats.collect(), None, vec!())
|
||||
},
|
||||
_ => unreachable!()
|
||||
},
|
||||
ty::TyStr => ast::PatWild(ast::PatWildSingle),
|
||||
ty::TyStr => hir::PatWild(hir::PatWildSingle),
|
||||
|
||||
_ => {
|
||||
assert_eq!(pats_len, 1);
|
||||
ast::PatRegion(pats.nth(0).unwrap(), mutbl)
|
||||
hir::PatRegion(pats.nth(0).unwrap(), mutbl)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ty::TyArray(_, len) => {
|
||||
assert_eq!(pats_len, len);
|
||||
ast::PatVec(pats.collect(), None, vec![])
|
||||
hir::PatVec(pats.collect(), None, vec![])
|
||||
}
|
||||
|
||||
_ => {
|
||||
match *ctor {
|
||||
ConstantValue(ref v) => ast::PatLit(const_val_to_expr(v)),
|
||||
_ => ast::PatWild(ast::PatWildSingle),
|
||||
ConstantValue(ref v) => hir::PatLit(const_val_to_expr(v)),
|
||||
_ => hir::PatWild(hir::PatWildSingle),
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
P(ast::Pat {
|
||||
P(hir::Pat {
|
||||
id: 0,
|
||||
node: pat,
|
||||
span: DUMMY_SP
|
||||
@ -658,7 +663,7 @@ fn is_useful(cx: &MatchCheckCtxt,
|
||||
let left_ty = cx.tcx.pat_ty(&*real_pat);
|
||||
|
||||
match real_pat.node {
|
||||
ast::PatIdent(ast::BindByRef(..), _, _) => {
|
||||
hir::PatIdent(hir::BindByRef(..), _, _) => {
|
||||
left_ty.builtin_deref(false).unwrap().ty
|
||||
}
|
||||
_ => left_ty,
|
||||
@ -666,7 +671,7 @@ fn is_useful(cx: &MatchCheckCtxt,
|
||||
};
|
||||
|
||||
let max_slice_length = rows.iter().filter_map(|row| match row[0].node {
|
||||
ast::PatVec(ref before, _, ref after) => Some(before.len() + after.len()),
|
||||
hir::PatVec(ref before, _, ref after) => Some(before.len() + after.len()),
|
||||
_ => None
|
||||
}).max().map_or(0, |v| v + 1);
|
||||
|
||||
@ -747,7 +752,7 @@ fn pat_constructors(cx: &MatchCheckCtxt, p: &Pat,
|
||||
left_ty: Ty, max_slice_length: usize) -> Vec<Constructor> {
|
||||
let pat = raw_pat(p);
|
||||
match pat.node {
|
||||
ast::PatIdent(..) =>
|
||||
hir::PatIdent(..) =>
|
||||
match cx.tcx.def_map.borrow().get(&pat.id).map(|d| d.full_def()) {
|
||||
Some(DefConst(..)) | Some(DefAssociatedConst(..)) =>
|
||||
cx.tcx.sess.span_bug(pat.span, "const pattern should've \
|
||||
@ -756,7 +761,7 @@ fn pat_constructors(cx: &MatchCheckCtxt, p: &Pat,
|
||||
Some(DefVariant(_, id, _)) => vec!(Variant(id)),
|
||||
_ => vec!()
|
||||
},
|
||||
ast::PatEnum(..) =>
|
||||
hir::PatEnum(..) =>
|
||||
match cx.tcx.def_map.borrow().get(&pat.id).map(|d| d.full_def()) {
|
||||
Some(DefConst(..)) | Some(DefAssociatedConst(..)) =>
|
||||
cx.tcx.sess.span_bug(pat.span, "const pattern should've \
|
||||
@ -764,10 +769,10 @@ fn pat_constructors(cx: &MatchCheckCtxt, p: &Pat,
|
||||
Some(DefVariant(_, id, _)) => vec!(Variant(id)),
|
||||
_ => vec!(Single)
|
||||
},
|
||||
ast::PatQPath(..) =>
|
||||
hir::PatQPath(..) =>
|
||||
cx.tcx.sess.span_bug(pat.span, "const pattern should've \
|
||||
been rewritten"),
|
||||
ast::PatStruct(..) =>
|
||||
hir::PatStruct(..) =>
|
||||
match cx.tcx.def_map.borrow().get(&pat.id).map(|d| d.full_def()) {
|
||||
Some(DefConst(..)) | Some(DefAssociatedConst(..)) =>
|
||||
cx.tcx.sess.span_bug(pat.span, "const pattern should've \
|
||||
@ -775,11 +780,11 @@ fn pat_constructors(cx: &MatchCheckCtxt, p: &Pat,
|
||||
Some(DefVariant(_, id, _)) => vec!(Variant(id)),
|
||||
_ => vec!(Single)
|
||||
},
|
||||
ast::PatLit(ref expr) =>
|
||||
hir::PatLit(ref expr) =>
|
||||
vec!(ConstantValue(eval_const_expr(cx.tcx, &**expr))),
|
||||
ast::PatRange(ref lo, ref hi) =>
|
||||
hir::PatRange(ref lo, ref hi) =>
|
||||
vec!(ConstantRange(eval_const_expr(cx.tcx, &**lo), eval_const_expr(cx.tcx, &**hi))),
|
||||
ast::PatVec(ref before, ref slice, ref after) =>
|
||||
hir::PatVec(ref before, ref slice, ref after) =>
|
||||
match left_ty.sty {
|
||||
ty::TyArray(_, _) => vec!(Single),
|
||||
_ => if slice.is_some() {
|
||||
@ -790,12 +795,10 @@ fn pat_constructors(cx: &MatchCheckCtxt, p: &Pat,
|
||||
vec!(Slice(before.len() + after.len()))
|
||||
}
|
||||
},
|
||||
ast::PatBox(_) | ast::PatTup(_) | ast::PatRegion(..) =>
|
||||
hir::PatBox(_) | hir::PatTup(_) | hir::PatRegion(..) =>
|
||||
vec!(Single),
|
||||
ast::PatWild(_) =>
|
||||
hir::PatWild(_) =>
|
||||
vec!(),
|
||||
ast::PatMac(_) =>
|
||||
cx.tcx.sess.bug("unexpanded macro")
|
||||
}
|
||||
}
|
||||
|
||||
@ -857,10 +860,10 @@ pub fn specialize<'a>(cx: &MatchCheckCtxt, r: &[&'a Pat],
|
||||
id: pat_id, ref node, span: pat_span
|
||||
} = raw_pat(r[col]);
|
||||
let head: Option<Vec<&Pat>> = match *node {
|
||||
ast::PatWild(_) =>
|
||||
hir::PatWild(_) =>
|
||||
Some(vec![DUMMY_WILD_PAT; arity]),
|
||||
|
||||
ast::PatIdent(_, _, _) => {
|
||||
hir::PatIdent(_, _, _) => {
|
||||
let opt_def = cx.tcx.def_map.borrow().get(&pat_id).map(|d| d.full_def());
|
||||
match opt_def {
|
||||
Some(DefConst(..)) | Some(DefAssociatedConst(..)) =>
|
||||
@ -875,7 +878,7 @@ pub fn specialize<'a>(cx: &MatchCheckCtxt, r: &[&'a Pat],
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatEnum(_, ref args) => {
|
||||
hir::PatEnum(_, ref args) => {
|
||||
let def = cx.tcx.def_map.borrow().get(&pat_id).unwrap().full_def();
|
||||
match def {
|
||||
DefConst(..) | DefAssociatedConst(..) =>
|
||||
@ -892,12 +895,12 @@ pub fn specialize<'a>(cx: &MatchCheckCtxt, r: &[&'a Pat],
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatQPath(_, _) => {
|
||||
hir::PatQPath(_, _) => {
|
||||
cx.tcx.sess.span_bug(pat_span, "const pattern should've \
|
||||
been rewritten")
|
||||
}
|
||||
|
||||
ast::PatStruct(_, ref pattern_fields, _) => {
|
||||
hir::PatStruct(_, ref pattern_fields, _) => {
|
||||
let def = cx.tcx.def_map.borrow().get(&pat_id).unwrap().full_def();
|
||||
let adt = cx.tcx.node_id_to_type(pat_id).ty_adt_def().unwrap();
|
||||
let variant = adt.variant_of_ctor(constructor);
|
||||
@ -914,13 +917,13 @@ pub fn specialize<'a>(cx: &MatchCheckCtxt, r: &[&'a Pat],
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatTup(ref args) =>
|
||||
hir::PatTup(ref args) =>
|
||||
Some(args.iter().map(|p| &**p).collect()),
|
||||
|
||||
ast::PatBox(ref inner) | ast::PatRegion(ref inner, _) =>
|
||||
hir::PatBox(ref inner) | hir::PatRegion(ref inner, _) =>
|
||||
Some(vec![&**inner]),
|
||||
|
||||
ast::PatLit(ref expr) => {
|
||||
hir::PatLit(ref expr) => {
|
||||
let expr_value = eval_const_expr(cx.tcx, &**expr);
|
||||
match range_covered_by_constructor(constructor, &expr_value, &expr_value) {
|
||||
Some(true) => Some(vec![]),
|
||||
@ -932,7 +935,7 @@ pub fn specialize<'a>(cx: &MatchCheckCtxt, r: &[&'a Pat],
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatRange(ref from, ref to) => {
|
||||
hir::PatRange(ref from, ref to) => {
|
||||
let from_value = eval_const_expr(cx.tcx, &**from);
|
||||
let to_value = eval_const_expr(cx.tcx, &**to);
|
||||
match range_covered_by_constructor(constructor, &from_value, &to_value) {
|
||||
@ -945,7 +948,7 @@ pub fn specialize<'a>(cx: &MatchCheckCtxt, r: &[&'a Pat],
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatVec(ref before, ref slice, ref after) => {
|
||||
hir::PatVec(ref before, ref slice, ref after) => {
|
||||
match *constructor {
|
||||
// Fixed-length vectors.
|
||||
Single => {
|
||||
@ -976,11 +979,6 @@ pub fn specialize<'a>(cx: &MatchCheckCtxt, r: &[&'a Pat],
|
||||
_ => None
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatMac(_) => {
|
||||
span_err!(cx.tcx.sess, pat_span, E0300, "unexpanded macro");
|
||||
None
|
||||
}
|
||||
};
|
||||
head.map(|mut head| {
|
||||
head.push_all(&r[..col]);
|
||||
@ -989,7 +987,7 @@ pub fn specialize<'a>(cx: &MatchCheckCtxt, r: &[&'a Pat],
|
||||
})
|
||||
}
|
||||
|
||||
fn check_local(cx: &mut MatchCheckCtxt, loc: &ast::Local) {
|
||||
fn check_local(cx: &mut MatchCheckCtxt, loc: &hir::Local) {
|
||||
visit::walk_local(cx, loc);
|
||||
|
||||
let pat = StaticInliner::new(cx.tcx, None).fold_pat(loc.pat.clone());
|
||||
@ -1002,8 +1000,8 @@ fn check_local(cx: &mut MatchCheckCtxt, loc: &ast::Local) {
|
||||
|
||||
fn check_fn(cx: &mut MatchCheckCtxt,
|
||||
kind: FnKind,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block,
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block,
|
||||
sp: Span,
|
||||
fn_id: NodeId) {
|
||||
match kind {
|
||||
@ -1060,10 +1058,10 @@ fn check_legality_of_move_bindings(cx: &MatchCheckCtxt,
|
||||
for pat in pats {
|
||||
pat_bindings(def_map, &**pat, |bm, _, span, _path| {
|
||||
match bm {
|
||||
ast::BindByRef(_) => {
|
||||
hir::BindByRef(_) => {
|
||||
by_ref_span = Some(span);
|
||||
}
|
||||
ast::BindByValue(_) => {
|
||||
hir::BindByValue(_) => {
|
||||
}
|
||||
}
|
||||
})
|
||||
@ -1085,10 +1083,10 @@ fn check_legality_of_move_bindings(cx: &MatchCheckCtxt,
|
||||
};
|
||||
|
||||
for pat in pats {
|
||||
ast_util::walk_pat(&**pat, |p| {
|
||||
front_util::walk_pat(&**pat, |p| {
|
||||
if pat_is_binding(def_map, &*p) {
|
||||
match p.node {
|
||||
ast::PatIdent(ast::BindByValue(_), _, ref sub) => {
|
||||
hir::PatIdent(hir::BindByValue(_), _, ref sub) => {
|
||||
let pat_ty = tcx.node_id_to_type(p.id);
|
||||
//FIXME: (@jroesch) this code should be floated up as well
|
||||
let infcx = infer::new_infer_ctxt(cx.tcx,
|
||||
@ -1099,7 +1097,7 @@ fn check_legality_of_move_bindings(cx: &MatchCheckCtxt,
|
||||
check_move(p, sub.as_ref().map(|p| &**p));
|
||||
}
|
||||
}
|
||||
ast::PatIdent(ast::BindByRef(_), _, _) => {
|
||||
hir::PatIdent(hir::BindByRef(_), _, _) => {
|
||||
}
|
||||
_ => {
|
||||
cx.tcx.sess.span_bug(
|
||||
@ -1119,7 +1117,7 @@ fn check_legality_of_move_bindings(cx: &MatchCheckCtxt,
|
||||
/// Ensures that a pattern guard doesn't borrow by mutable reference or
|
||||
/// assign.
|
||||
fn check_for_mutation_in_guard<'a, 'tcx>(cx: &'a MatchCheckCtxt<'a, 'tcx>,
|
||||
guard: &ast::Expr) {
|
||||
guard: &hir::Expr) {
|
||||
let mut checker = MutationChecker {
|
||||
cx: cx,
|
||||
};
|
||||
@ -1188,7 +1186,7 @@ impl<'a, 'b, 'tcx, 'v> Visitor<'v> for AtBindingPatternVisitor<'a, 'b, 'tcx> {
|
||||
}
|
||||
|
||||
match pat.node {
|
||||
ast::PatIdent(_, _, Some(_)) => {
|
||||
hir::PatIdent(_, _, Some(_)) => {
|
||||
let bindings_were_allowed = self.bindings_allowed;
|
||||
self.bindings_allowed = false;
|
||||
visit::walk_pat(self, pat);
|
||||
|
@ -18,11 +18,12 @@ use middle::ty::ParameterEnvironment;
|
||||
use middle::ty;
|
||||
|
||||
use syntax::ast;
|
||||
use rustc_front::hir;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit;
|
||||
use rustc_front::visit;
|
||||
|
||||
pub fn check_crate(tcx: &ty::ctxt,
|
||||
krate: &ast::Crate) {
|
||||
krate: &hir::Crate) {
|
||||
let mut rvcx = RvalueContext { tcx: tcx };
|
||||
visit::walk_crate(&mut rvcx, krate);
|
||||
}
|
||||
@ -34,8 +35,8 @@ struct RvalueContext<'a, 'tcx: 'a> {
|
||||
impl<'a, 'tcx, 'v> visit::Visitor<'v> for RvalueContext<'a, 'tcx> {
|
||||
fn visit_fn(&mut self,
|
||||
fk: visit::FnKind<'v>,
|
||||
fd: &'v ast::FnDecl,
|
||||
b: &'v ast::Block,
|
||||
fd: &'v hir::FnDecl,
|
||||
b: &'v hir::Block,
|
||||
s: Span,
|
||||
fn_id: ast::NodeId) {
|
||||
{
|
||||
@ -73,12 +74,12 @@ impl<'a, 'tcx> euv::Delegate<'tcx> for RvalueContextDelegate<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn matched_pat(&mut self,
|
||||
_matched_pat: &ast::Pat,
|
||||
_matched_pat: &hir::Pat,
|
||||
_cmt: mc::cmt,
|
||||
_mode: euv::MatchMode) {}
|
||||
|
||||
fn consume_pat(&mut self,
|
||||
_consume_pat: &ast::Pat,
|
||||
_consume_pat: &hir::Pat,
|
||||
_cmt: mc::cmt,
|
||||
_mode: euv::ConsumeMode) {
|
||||
}
|
||||
|
@ -11,7 +11,7 @@
|
||||
// This compiler pass detects constants that refer to themselves
|
||||
// recursively.
|
||||
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
use session::Session;
|
||||
use middle::def::{DefStatic, DefConst, DefAssociatedConst, DefVariant, DefMap};
|
||||
use util::nodemap::NodeMap;
|
||||
@ -19,8 +19,9 @@ use util::nodemap::NodeMap;
|
||||
use syntax::{ast};
|
||||
use syntax::codemap::Span;
|
||||
use syntax::feature_gate::emit_feature_err;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::visit;
|
||||
use rustc_front::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::hir;
|
||||
|
||||
use std::cell::RefCell;
|
||||
|
||||
@ -32,19 +33,19 @@ struct CheckCrateVisitor<'a, 'ast: 'a> {
|
||||
// variant definitions with the discriminant expression that applies to
|
||||
// each one. If the variant uses the default values (starting from `0`),
|
||||
// then `None` is stored.
|
||||
discriminant_map: RefCell<NodeMap<Option<&'ast ast::Expr>>>,
|
||||
discriminant_map: RefCell<NodeMap<Option<&'ast hir::Expr>>>,
|
||||
}
|
||||
|
||||
impl<'a, 'ast: 'a> Visitor<'ast> for CheckCrateVisitor<'a, 'ast> {
|
||||
fn visit_item(&mut self, it: &'ast ast::Item) {
|
||||
fn visit_item(&mut self, it: &'ast hir::Item) {
|
||||
match it.node {
|
||||
ast::ItemStatic(..) |
|
||||
ast::ItemConst(..) => {
|
||||
hir::ItemStatic(..) |
|
||||
hir::ItemConst(..) => {
|
||||
let mut recursion_visitor =
|
||||
CheckItemRecursionVisitor::new(self, &it.span);
|
||||
recursion_visitor.visit_item(it);
|
||||
},
|
||||
ast::ItemEnum(ref enum_def, ref generics) => {
|
||||
hir::ItemEnum(ref enum_def, ref generics) => {
|
||||
// We could process the whole enum, but handling the variants
|
||||
// with discriminant expressions one by one gives more specific,
|
||||
// less redundant output.
|
||||
@ -62,9 +63,9 @@ impl<'a, 'ast: 'a> Visitor<'ast> for CheckCrateVisitor<'a, 'ast> {
|
||||
visit::walk_item(self, it)
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, ti: &'ast ast::TraitItem) {
|
||||
fn visit_trait_item(&mut self, ti: &'ast hir::TraitItem) {
|
||||
match ti.node {
|
||||
ast::ConstTraitItem(_, ref default) => {
|
||||
hir::ConstTraitItem(_, ref default) => {
|
||||
if let Some(_) = *default {
|
||||
let mut recursion_visitor =
|
||||
CheckItemRecursionVisitor::new(self, &ti.span);
|
||||
@ -76,9 +77,9 @@ impl<'a, 'ast: 'a> Visitor<'ast> for CheckCrateVisitor<'a, 'ast> {
|
||||
visit::walk_trait_item(self, ti)
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, ii: &'ast ast::ImplItem) {
|
||||
fn visit_impl_item(&mut self, ii: &'ast hir::ImplItem) {
|
||||
match ii.node {
|
||||
ast::ConstImplItem(..) => {
|
||||
hir::ConstImplItem(..) => {
|
||||
let mut recursion_visitor =
|
||||
CheckItemRecursionVisitor::new(self, &ii.span);
|
||||
recursion_visitor.visit_impl_item(ii);
|
||||
@ -90,7 +91,7 @@ impl<'a, 'ast: 'a> Visitor<'ast> for CheckCrateVisitor<'a, 'ast> {
|
||||
}
|
||||
|
||||
pub fn check_crate<'ast>(sess: &Session,
|
||||
krate: &'ast ast::Crate,
|
||||
krate: &'ast hir::Crate,
|
||||
def_map: &DefMap,
|
||||
ast_map: &ast_map::Map<'ast>) {
|
||||
let mut visitor = CheckCrateVisitor {
|
||||
@ -108,7 +109,7 @@ struct CheckItemRecursionVisitor<'a, 'ast: 'a> {
|
||||
sess: &'a Session,
|
||||
ast_map: &'a ast_map::Map<'ast>,
|
||||
def_map: &'a DefMap,
|
||||
discriminant_map: &'a RefCell<NodeMap<Option<&'ast ast::Expr>>>,
|
||||
discriminant_map: &'a RefCell<NodeMap<Option<&'ast hir::Expr>>>,
|
||||
idstack: Vec<ast::NodeId>,
|
||||
}
|
||||
|
||||
@ -129,7 +130,7 @@ impl<'a, 'ast: 'a> CheckItemRecursionVisitor<'a, 'ast> {
|
||||
if self.idstack.iter().any(|&x| x == id) {
|
||||
let any_static = self.idstack.iter().any(|&x| {
|
||||
if let ast_map::NodeItem(item) = self.ast_map.get(x) {
|
||||
if let ast::ItemStatic(..) = item.node {
|
||||
if let hir::ItemStatic(..) = item.node {
|
||||
true
|
||||
} else {
|
||||
false
|
||||
@ -161,7 +162,7 @@ impl<'a, 'ast: 'a> CheckItemRecursionVisitor<'a, 'ast> {
|
||||
// So for every variant, we need to track whether there is an expression
|
||||
// somewhere in the enum definition that controls its discriminant. We do
|
||||
// this by starting from the end and searching backward.
|
||||
fn populate_enum_discriminants(&self, enum_definition: &'ast ast::EnumDef) {
|
||||
fn populate_enum_discriminants(&self, enum_definition: &'ast hir::EnumDef) {
|
||||
// Get the map, and return if we already processed this enum or if it
|
||||
// has no variants.
|
||||
let mut discriminant_map = self.discriminant_map.borrow_mut();
|
||||
@ -195,18 +196,18 @@ impl<'a, 'ast: 'a> CheckItemRecursionVisitor<'a, 'ast> {
|
||||
}
|
||||
|
||||
impl<'a, 'ast: 'a> Visitor<'ast> for CheckItemRecursionVisitor<'a, 'ast> {
|
||||
fn visit_item(&mut self, it: &'ast ast::Item) {
|
||||
fn visit_item(&mut self, it: &'ast hir::Item) {
|
||||
self.with_item_id_pushed(it.id, |v| visit::walk_item(v, it));
|
||||
}
|
||||
|
||||
fn visit_enum_def(&mut self, enum_definition: &'ast ast::EnumDef,
|
||||
generics: &'ast ast::Generics) {
|
||||
fn visit_enum_def(&mut self, enum_definition: &'ast hir::EnumDef,
|
||||
generics: &'ast hir::Generics) {
|
||||
self.populate_enum_discriminants(enum_definition);
|
||||
visit::walk_enum_def(self, enum_definition, generics);
|
||||
}
|
||||
|
||||
fn visit_variant(&mut self, variant: &'ast ast::Variant,
|
||||
_: &'ast ast::Generics) {
|
||||
fn visit_variant(&mut self, variant: &'ast hir::Variant,
|
||||
_: &'ast hir::Generics) {
|
||||
let variant_id = variant.node.id;
|
||||
let maybe_expr;
|
||||
if let Some(get_expr) = self.discriminant_map.borrow().get(&variant_id) {
|
||||
@ -225,17 +226,17 @@ impl<'a, 'ast: 'a> Visitor<'ast> for CheckItemRecursionVisitor<'a, 'ast> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, ti: &'ast ast::TraitItem) {
|
||||
fn visit_trait_item(&mut self, ti: &'ast hir::TraitItem) {
|
||||
self.with_item_id_pushed(ti.id, |v| visit::walk_trait_item(v, ti));
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, ii: &'ast ast::ImplItem) {
|
||||
fn visit_impl_item(&mut self, ii: &'ast hir::ImplItem) {
|
||||
self.with_item_id_pushed(ii.id, |v| visit::walk_impl_item(v, ii));
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, e: &'ast ast::Expr) {
|
||||
fn visit_expr(&mut self, e: &'ast hir::Expr) {
|
||||
match e.node {
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
match self.def_map.borrow().get(&e.id).map(|d| d.base_def) {
|
||||
Some(DefStatic(def_id, _)) |
|
||||
Some(DefAssociatedConst(def_id)) |
|
||||
@ -261,7 +262,7 @@ impl<'a, 'ast: 'a> Visitor<'ast> for CheckItemRecursionVisitor<'a, 'ast> {
|
||||
// the whole enum definition to see what expression that
|
||||
// might be (if any).
|
||||
Some(DefVariant(enum_id, variant_id, false)) if enum_id.is_local() => {
|
||||
if let ast::ItemEnum(ref enum_def, ref generics) =
|
||||
if let hir::ItemEnum(ref enum_def, ref generics) =
|
||||
self.ast_map.expect_item(enum_id.local_id()).node {
|
||||
self.populate_enum_discriminants(enum_def);
|
||||
let variant = self.ast_map.expect_variant(variant_id.local_id());
|
||||
|
@ -14,8 +14,8 @@ use self::ConstVal::*;
|
||||
use self::ErrKind::*;
|
||||
use self::EvalHint::*;
|
||||
|
||||
use ast_map;
|
||||
use ast_map::blocks::FnLikeNode;
|
||||
use front::map as ast_map;
|
||||
use front::map::blocks::FnLikeNode;
|
||||
use metadata::csearch;
|
||||
use metadata::inline::InlinedItem;
|
||||
use middle::{astencode, def, infer, subst, traits};
|
||||
@ -25,11 +25,14 @@ use middle::ty::{self, Ty};
|
||||
use middle::astconv_util::ast_ty_to_prim_ty;
|
||||
use util::num::ToPrimitive;
|
||||
|
||||
use syntax::ast::{self, Expr};
|
||||
use syntax::codemap::{self, Span};
|
||||
use syntax::ast;
|
||||
use rustc_front::hir::Expr;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::visit::FnKind;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::parse::token::InternedString;
|
||||
use syntax::ptr::P;
|
||||
use syntax::visit::FnKind;
|
||||
use syntax::codemap;
|
||||
|
||||
use std::borrow::{Cow, IntoCow};
|
||||
use std::num::wrapping::OverflowingOps;
|
||||
@ -56,7 +59,7 @@ fn lookup_variant_by_id<'a>(tcx: &'a ty::ctxt,
|
||||
enum_def: DefId,
|
||||
variant_def: DefId)
|
||||
-> Option<&'a Expr> {
|
||||
fn variant_expr<'a>(variants: &'a [P<ast::Variant>], id: ast::NodeId)
|
||||
fn variant_expr<'a>(variants: &'a [P<hir::Variant>], id: ast::NodeId)
|
||||
-> Option<&'a Expr> {
|
||||
for variant in variants {
|
||||
if variant.node.id == id {
|
||||
@ -70,7 +73,7 @@ fn lookup_variant_by_id<'a>(tcx: &'a ty::ctxt,
|
||||
match tcx.map.find(enum_def.node) {
|
||||
None => None,
|
||||
Some(ast_map::NodeItem(it)) => match it.node {
|
||||
ast::ItemEnum(ast::EnumDef { ref variants }, _) => {
|
||||
hir::ItemEnum(hir::EnumDef { ref variants }, _) => {
|
||||
variant_expr(&variants[..], variant_def.node)
|
||||
}
|
||||
_ => None
|
||||
@ -88,7 +91,7 @@ fn lookup_variant_by_id<'a>(tcx: &'a ty::ctxt,
|
||||
let expr_id = match csearch::maybe_get_item_ast(tcx, enum_def,
|
||||
Box::new(|a, b, c, d| astencode::decode_inlined_item(a, b, c, d))) {
|
||||
csearch::FoundAst::Found(&InlinedItem::Item(ref item)) => match item.node {
|
||||
ast::ItemEnum(ast::EnumDef { ref variants }, _) => {
|
||||
hir::ItemEnum(hir::EnumDef { ref variants }, _) => {
|
||||
// NOTE this doesn't do the right thing, it compares inlined
|
||||
// NodeId's to the original variant_def's NodeId, but they
|
||||
// come from different crates, so they will likely never match.
|
||||
@ -112,13 +115,13 @@ pub fn lookup_const_by_id<'a, 'tcx: 'a>(tcx: &'a ty::ctxt<'tcx>,
|
||||
match tcx.map.find(def_id.node) {
|
||||
None => None,
|
||||
Some(ast_map::NodeItem(it)) => match it.node {
|
||||
ast::ItemConst(_, ref const_expr) => {
|
||||
hir::ItemConst(_, ref const_expr) => {
|
||||
Some(&*const_expr)
|
||||
}
|
||||
_ => None
|
||||
},
|
||||
Some(ast_map::NodeTraitItem(ti)) => match ti.node {
|
||||
ast::ConstTraitItem(_, _) => {
|
||||
hir::ConstTraitItem(_, _) => {
|
||||
match maybe_ref_id {
|
||||
// If we have a trait item, and we know the expression
|
||||
// that's the source of the obligation to resolve it,
|
||||
@ -144,7 +147,7 @@ pub fn lookup_const_by_id<'a, 'tcx: 'a>(tcx: &'a ty::ctxt<'tcx>,
|
||||
_ => None
|
||||
},
|
||||
Some(ast_map::NodeImplItem(ii)) => match ii.node {
|
||||
ast::ConstImplItem(_, ref expr) => {
|
||||
hir::ConstImplItem(_, ref expr) => {
|
||||
Some(&*expr)
|
||||
}
|
||||
_ => None
|
||||
@ -163,11 +166,11 @@ pub fn lookup_const_by_id<'a, 'tcx: 'a>(tcx: &'a ty::ctxt<'tcx>,
|
||||
let expr_id = match csearch::maybe_get_item_ast(tcx, def_id,
|
||||
Box::new(|a, b, c, d| astencode::decode_inlined_item(a, b, c, d))) {
|
||||
csearch::FoundAst::Found(&InlinedItem::Item(ref item)) => match item.node {
|
||||
ast::ItemConst(_, ref const_expr) => Some(const_expr.id),
|
||||
hir::ItemConst(_, ref const_expr) => Some(const_expr.id),
|
||||
_ => None
|
||||
},
|
||||
csearch::FoundAst::Found(&InlinedItem::TraitItem(trait_id, ref ti)) => match ti.node {
|
||||
ast::ConstTraitItem(_, _) => {
|
||||
hir::ConstTraitItem(_, _) => {
|
||||
used_ref_id = true;
|
||||
match maybe_ref_id {
|
||||
// As mentioned in the comments above for in-crate
|
||||
@ -186,7 +189,7 @@ pub fn lookup_const_by_id<'a, 'tcx: 'a>(tcx: &'a ty::ctxt<'tcx>,
|
||||
_ => None
|
||||
},
|
||||
csearch::FoundAst::Found(&InlinedItem::ImplItem(_, ref ii)) => match ii.node {
|
||||
ast::ConstImplItem(_, ref expr) => Some(expr.id),
|
||||
hir::ConstImplItem(_, ref expr) => Some(expr.id),
|
||||
_ => None
|
||||
},
|
||||
_ => None
|
||||
@ -246,11 +249,11 @@ pub fn lookup_const_fn_by_id<'tcx>(tcx: &ty::ctxt<'tcx>, def_id: DefId)
|
||||
};
|
||||
|
||||
match fn_like.kind() {
|
||||
FnKind::ItemFn(_, _, _, ast::Constness::Const, _, _) => {
|
||||
FnKind::ItemFn(_, _, _, hir::Constness::Const, _, _) => {
|
||||
Some(fn_like)
|
||||
}
|
||||
FnKind::Method(_, m, _) => {
|
||||
if m.constness == ast::Constness::Const {
|
||||
if m.constness == hir::Constness::Const {
|
||||
Some(fn_like)
|
||||
} else {
|
||||
None
|
||||
@ -288,12 +291,12 @@ impl ConstVal {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn const_expr_to_pat(tcx: &ty::ctxt, expr: &Expr, span: Span) -> P<ast::Pat> {
|
||||
pub fn const_expr_to_pat(tcx: &ty::ctxt, expr: &Expr, span: Span) -> P<hir::Pat> {
|
||||
let pat = match expr.node {
|
||||
ast::ExprTup(ref exprs) =>
|
||||
ast::PatTup(exprs.iter().map(|expr| const_expr_to_pat(tcx, &**expr, span)).collect()),
|
||||
hir::ExprTup(ref exprs) =>
|
||||
hir::PatTup(exprs.iter().map(|expr| const_expr_to_pat(tcx, &**expr, span)).collect()),
|
||||
|
||||
ast::ExprCall(ref callee, ref args) => {
|
||||
hir::ExprCall(ref callee, ref args) => {
|
||||
let def = *tcx.def_map.borrow().get(&callee.id).unwrap();
|
||||
if let Vacant(entry) = tcx.def_map.borrow_mut().entry(expr.id) {
|
||||
entry.insert(def);
|
||||
@ -304,33 +307,33 @@ pub fn const_expr_to_pat(tcx: &ty::ctxt, expr: &Expr, span: Span) -> P<ast::Pat>
|
||||
_ => unreachable!()
|
||||
};
|
||||
let pats = args.iter().map(|expr| const_expr_to_pat(tcx, &**expr, span)).collect();
|
||||
ast::PatEnum(path, Some(pats))
|
||||
hir::PatEnum(path, Some(pats))
|
||||
}
|
||||
|
||||
ast::ExprStruct(ref path, ref fields, None) => {
|
||||
hir::ExprStruct(ref path, ref fields, None) => {
|
||||
let field_pats = fields.iter().map(|field| codemap::Spanned {
|
||||
span: codemap::DUMMY_SP,
|
||||
node: ast::FieldPat {
|
||||
node: hir::FieldPat {
|
||||
ident: field.ident.node,
|
||||
pat: const_expr_to_pat(tcx, &*field.expr, span),
|
||||
is_shorthand: false,
|
||||
},
|
||||
}).collect();
|
||||
ast::PatStruct(path.clone(), field_pats, false)
|
||||
hir::PatStruct(path.clone(), field_pats, false)
|
||||
}
|
||||
|
||||
ast::ExprVec(ref exprs) => {
|
||||
hir::ExprVec(ref exprs) => {
|
||||
let pats = exprs.iter().map(|expr| const_expr_to_pat(tcx, &**expr, span)).collect();
|
||||
ast::PatVec(pats, None, vec![])
|
||||
hir::PatVec(pats, None, vec![])
|
||||
}
|
||||
|
||||
ast::ExprPath(_, ref path) => {
|
||||
hir::ExprPath(_, ref path) => {
|
||||
let opt_def = tcx.def_map.borrow().get(&expr.id).map(|d| d.full_def());
|
||||
match opt_def {
|
||||
Some(def::DefStruct(..)) =>
|
||||
ast::PatStruct(path.clone(), vec![], false),
|
||||
hir::PatStruct(path.clone(), vec![], false),
|
||||
Some(def::DefVariant(..)) =>
|
||||
ast::PatEnum(path.clone(), None),
|
||||
hir::PatEnum(path.clone(), None),
|
||||
_ => {
|
||||
match lookup_const(tcx, expr) {
|
||||
Some(actual) => return const_expr_to_pat(tcx, actual, span),
|
||||
@ -340,9 +343,9 @@ pub fn const_expr_to_pat(tcx: &ty::ctxt, expr: &Expr, span: Span) -> P<ast::Pat>
|
||||
}
|
||||
}
|
||||
|
||||
_ => ast::PatLit(P(expr.clone()))
|
||||
_ => hir::PatLit(P(expr.clone()))
|
||||
};
|
||||
P(ast::Pat { id: expr.id, node: pat, span: span })
|
||||
P(hir::Pat { id: expr.id, node: pat, span: span })
|
||||
}
|
||||
|
||||
pub fn eval_const_expr(tcx: &ty::ctxt, e: &Expr) -> ConstVal {
|
||||
@ -363,10 +366,10 @@ pub struct ConstEvalErr {
|
||||
pub enum ErrKind {
|
||||
CannotCast,
|
||||
CannotCastTo(&'static str),
|
||||
InvalidOpForBools(ast::BinOp_),
|
||||
InvalidOpForFloats(ast::BinOp_),
|
||||
InvalidOpForIntUint(ast::BinOp_),
|
||||
InvalidOpForUintInt(ast::BinOp_),
|
||||
InvalidOpForBools(hir::BinOp_),
|
||||
InvalidOpForFloats(hir::BinOp_),
|
||||
InvalidOpForIntUint(hir::BinOp_),
|
||||
InvalidOpForUintInt(hir::BinOp_),
|
||||
NegateOn(ConstVal),
|
||||
NotOn(ConstVal),
|
||||
|
||||
@ -463,35 +466,35 @@ pub enum IntTy { I8, I16, I32, I64 }
|
||||
pub enum UintTy { U8, U16, U32, U64 }
|
||||
|
||||
impl IntTy {
|
||||
pub fn from(tcx: &ty::ctxt, t: ast::IntTy) -> IntTy {
|
||||
let t = if let ast::TyIs = t {
|
||||
pub fn from(tcx: &ty::ctxt, t: hir::IntTy) -> IntTy {
|
||||
let t = if let hir::TyIs = t {
|
||||
tcx.sess.target.int_type
|
||||
} else {
|
||||
t
|
||||
};
|
||||
match t {
|
||||
ast::TyIs => unreachable!(),
|
||||
ast::TyI8 => IntTy::I8,
|
||||
ast::TyI16 => IntTy::I16,
|
||||
ast::TyI32 => IntTy::I32,
|
||||
ast::TyI64 => IntTy::I64,
|
||||
hir::TyIs => unreachable!(),
|
||||
hir::TyI8 => IntTy::I8,
|
||||
hir::TyI16 => IntTy::I16,
|
||||
hir::TyI32 => IntTy::I32,
|
||||
hir::TyI64 => IntTy::I64,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl UintTy {
|
||||
pub fn from(tcx: &ty::ctxt, t: ast::UintTy) -> UintTy {
|
||||
let t = if let ast::TyUs = t {
|
||||
pub fn from(tcx: &ty::ctxt, t: hir::UintTy) -> UintTy {
|
||||
let t = if let hir::TyUs = t {
|
||||
tcx.sess.target.uint_type
|
||||
} else {
|
||||
t
|
||||
};
|
||||
match t {
|
||||
ast::TyUs => unreachable!(),
|
||||
ast::TyU8 => UintTy::U8,
|
||||
ast::TyU16 => UintTy::U16,
|
||||
ast::TyU32 => UintTy::U32,
|
||||
ast::TyU64 => UintTy::U64,
|
||||
hir::TyUs => unreachable!(),
|
||||
hir::TyU8 => UintTy::U8,
|
||||
hir::TyU16 => UintTy::U16,
|
||||
hir::TyU32 => UintTy::U32,
|
||||
hir::TyU64 => UintTy::U64,
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -769,7 +772,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
});
|
||||
|
||||
let result = match e.node {
|
||||
ast::ExprUnary(ast::UnNeg, ref inner) => {
|
||||
hir::ExprUnary(hir::UnNeg, ref inner) => {
|
||||
match try!(eval_const_expr_partial(tcx, &**inner, ty_hint)) {
|
||||
Float(f) => Float(-f),
|
||||
Int(n) => try!(const_int_checked_neg(n, e, expr_int_type)),
|
||||
@ -779,7 +782,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
const_val => signal!(e, NegateOn(const_val)),
|
||||
}
|
||||
}
|
||||
ast::ExprUnary(ast::UnNot, ref inner) => {
|
||||
hir::ExprUnary(hir::UnNot, ref inner) => {
|
||||
match try!(eval_const_expr_partial(tcx, &**inner, ty_hint)) {
|
||||
Int(i) => Int(!i),
|
||||
Uint(i) => const_uint_not(i, expr_uint_type),
|
||||
@ -787,9 +790,9 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
const_val => signal!(e, NotOn(const_val)),
|
||||
}
|
||||
}
|
||||
ast::ExprBinary(op, ref a, ref b) => {
|
||||
hir::ExprBinary(op, ref a, ref b) => {
|
||||
let b_ty = match op.node {
|
||||
ast::BiShl | ast::BiShr => {
|
||||
hir::BiShl | hir::BiShr => {
|
||||
if let ExprTypeChecked = ty_hint {
|
||||
ExprTypeChecked
|
||||
} else {
|
||||
@ -802,84 +805,84 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
try!(eval_const_expr_partial(tcx, &**b, b_ty))) {
|
||||
(Float(a), Float(b)) => {
|
||||
match op.node {
|
||||
ast::BiAdd => Float(a + b),
|
||||
ast::BiSub => Float(a - b),
|
||||
ast::BiMul => Float(a * b),
|
||||
ast::BiDiv => Float(a / b),
|
||||
ast::BiRem => Float(a % b),
|
||||
ast::BiEq => fromb(a == b),
|
||||
ast::BiLt => fromb(a < b),
|
||||
ast::BiLe => fromb(a <= b),
|
||||
ast::BiNe => fromb(a != b),
|
||||
ast::BiGe => fromb(a >= b),
|
||||
ast::BiGt => fromb(a > b),
|
||||
hir::BiAdd => Float(a + b),
|
||||
hir::BiSub => Float(a - b),
|
||||
hir::BiMul => Float(a * b),
|
||||
hir::BiDiv => Float(a / b),
|
||||
hir::BiRem => Float(a % b),
|
||||
hir::BiEq => fromb(a == b),
|
||||
hir::BiLt => fromb(a < b),
|
||||
hir::BiLe => fromb(a <= b),
|
||||
hir::BiNe => fromb(a != b),
|
||||
hir::BiGe => fromb(a >= b),
|
||||
hir::BiGt => fromb(a > b),
|
||||
_ => signal!(e, InvalidOpForFloats(op.node))
|
||||
}
|
||||
}
|
||||
(Int(a), Int(b)) => {
|
||||
match op.node {
|
||||
ast::BiAdd => try!(const_int_checked_add(a,b,e,expr_int_type)),
|
||||
ast::BiSub => try!(const_int_checked_sub(a,b,e,expr_int_type)),
|
||||
ast::BiMul => try!(const_int_checked_mul(a,b,e,expr_int_type)),
|
||||
ast::BiDiv => try!(const_int_checked_div(a,b,e,expr_int_type)),
|
||||
ast::BiRem => try!(const_int_checked_rem(a,b,e,expr_int_type)),
|
||||
ast::BiAnd | ast::BiBitAnd => Int(a & b),
|
||||
ast::BiOr | ast::BiBitOr => Int(a | b),
|
||||
ast::BiBitXor => Int(a ^ b),
|
||||
ast::BiShl => try!(const_int_checked_shl(a,b,e,expr_int_type)),
|
||||
ast::BiShr => try!(const_int_checked_shr(a,b,e,expr_int_type)),
|
||||
ast::BiEq => fromb(a == b),
|
||||
ast::BiLt => fromb(a < b),
|
||||
ast::BiLe => fromb(a <= b),
|
||||
ast::BiNe => fromb(a != b),
|
||||
ast::BiGe => fromb(a >= b),
|
||||
ast::BiGt => fromb(a > b)
|
||||
hir::BiAdd => try!(const_int_checked_add(a,b,e,expr_int_type)),
|
||||
hir::BiSub => try!(const_int_checked_sub(a,b,e,expr_int_type)),
|
||||
hir::BiMul => try!(const_int_checked_mul(a,b,e,expr_int_type)),
|
||||
hir::BiDiv => try!(const_int_checked_div(a,b,e,expr_int_type)),
|
||||
hir::BiRem => try!(const_int_checked_rem(a,b,e,expr_int_type)),
|
||||
hir::BiAnd | hir::BiBitAnd => Int(a & b),
|
||||
hir::BiOr | hir::BiBitOr => Int(a | b),
|
||||
hir::BiBitXor => Int(a ^ b),
|
||||
hir::BiShl => try!(const_int_checked_shl(a,b,e,expr_int_type)),
|
||||
hir::BiShr => try!(const_int_checked_shr(a,b,e,expr_int_type)),
|
||||
hir::BiEq => fromb(a == b),
|
||||
hir::BiLt => fromb(a < b),
|
||||
hir::BiLe => fromb(a <= b),
|
||||
hir::BiNe => fromb(a != b),
|
||||
hir::BiGe => fromb(a >= b),
|
||||
hir::BiGt => fromb(a > b)
|
||||
}
|
||||
}
|
||||
(Uint(a), Uint(b)) => {
|
||||
match op.node {
|
||||
ast::BiAdd => try!(const_uint_checked_add(a,b,e,expr_uint_type)),
|
||||
ast::BiSub => try!(const_uint_checked_sub(a,b,e,expr_uint_type)),
|
||||
ast::BiMul => try!(const_uint_checked_mul(a,b,e,expr_uint_type)),
|
||||
ast::BiDiv => try!(const_uint_checked_div(a,b,e,expr_uint_type)),
|
||||
ast::BiRem => try!(const_uint_checked_rem(a,b,e,expr_uint_type)),
|
||||
ast::BiAnd | ast::BiBitAnd => Uint(a & b),
|
||||
ast::BiOr | ast::BiBitOr => Uint(a | b),
|
||||
ast::BiBitXor => Uint(a ^ b),
|
||||
ast::BiShl => try!(const_uint_checked_shl(a,b,e,expr_uint_type)),
|
||||
ast::BiShr => try!(const_uint_checked_shr(a,b,e,expr_uint_type)),
|
||||
ast::BiEq => fromb(a == b),
|
||||
ast::BiLt => fromb(a < b),
|
||||
ast::BiLe => fromb(a <= b),
|
||||
ast::BiNe => fromb(a != b),
|
||||
ast::BiGe => fromb(a >= b),
|
||||
ast::BiGt => fromb(a > b),
|
||||
hir::BiAdd => try!(const_uint_checked_add(a,b,e,expr_uint_type)),
|
||||
hir::BiSub => try!(const_uint_checked_sub(a,b,e,expr_uint_type)),
|
||||
hir::BiMul => try!(const_uint_checked_mul(a,b,e,expr_uint_type)),
|
||||
hir::BiDiv => try!(const_uint_checked_div(a,b,e,expr_uint_type)),
|
||||
hir::BiRem => try!(const_uint_checked_rem(a,b,e,expr_uint_type)),
|
||||
hir::BiAnd | hir::BiBitAnd => Uint(a & b),
|
||||
hir::BiOr | hir::BiBitOr => Uint(a | b),
|
||||
hir::BiBitXor => Uint(a ^ b),
|
||||
hir::BiShl => try!(const_uint_checked_shl(a,b,e,expr_uint_type)),
|
||||
hir::BiShr => try!(const_uint_checked_shr(a,b,e,expr_uint_type)),
|
||||
hir::BiEq => fromb(a == b),
|
||||
hir::BiLt => fromb(a < b),
|
||||
hir::BiLe => fromb(a <= b),
|
||||
hir::BiNe => fromb(a != b),
|
||||
hir::BiGe => fromb(a >= b),
|
||||
hir::BiGt => fromb(a > b),
|
||||
}
|
||||
}
|
||||
// shifts can have any integral type as their rhs
|
||||
(Int(a), Uint(b)) => {
|
||||
match op.node {
|
||||
ast::BiShl => try!(const_int_checked_shl_via_uint(a,b,e,expr_int_type)),
|
||||
ast::BiShr => try!(const_int_checked_shr_via_uint(a,b,e,expr_int_type)),
|
||||
hir::BiShl => try!(const_int_checked_shl_via_uint(a,b,e,expr_int_type)),
|
||||
hir::BiShr => try!(const_int_checked_shr_via_uint(a,b,e,expr_int_type)),
|
||||
_ => signal!(e, InvalidOpForIntUint(op.node)),
|
||||
}
|
||||
}
|
||||
(Uint(a), Int(b)) => {
|
||||
match op.node {
|
||||
ast::BiShl => try!(const_uint_checked_shl_via_int(a,b,e,expr_uint_type)),
|
||||
ast::BiShr => try!(const_uint_checked_shr_via_int(a,b,e,expr_uint_type)),
|
||||
hir::BiShl => try!(const_uint_checked_shl_via_int(a,b,e,expr_uint_type)),
|
||||
hir::BiShr => try!(const_uint_checked_shr_via_int(a,b,e,expr_uint_type)),
|
||||
_ => signal!(e, InvalidOpForUintInt(op.node)),
|
||||
}
|
||||
}
|
||||
(Bool(a), Bool(b)) => {
|
||||
Bool(match op.node {
|
||||
ast::BiAnd => a && b,
|
||||
ast::BiOr => a || b,
|
||||
ast::BiBitXor => a ^ b,
|
||||
ast::BiBitAnd => a & b,
|
||||
ast::BiBitOr => a | b,
|
||||
ast::BiEq => a == b,
|
||||
ast::BiNe => a != b,
|
||||
hir::BiAnd => a && b,
|
||||
hir::BiOr => a || b,
|
||||
hir::BiBitXor => a ^ b,
|
||||
hir::BiBitAnd => a & b,
|
||||
hir::BiBitOr => a | b,
|
||||
hir::BiEq => a == b,
|
||||
hir::BiNe => a != b,
|
||||
_ => signal!(e, InvalidOpForBools(op.node)),
|
||||
})
|
||||
}
|
||||
@ -887,7 +890,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
_ => signal!(e, MiscBinaryOp),
|
||||
}
|
||||
}
|
||||
ast::ExprCast(ref base, ref target_ty) => {
|
||||
hir::ExprCast(ref base, ref target_ty) => {
|
||||
let ety = ety.or_else(|| ast_ty_to_prim_ty(tcx, &**target_ty))
|
||||
.unwrap_or_else(|| {
|
||||
tcx.sess.span_fatal(target_ty.span,
|
||||
@ -912,14 +915,14 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
Err(kind) => return Err(ConstEvalErr { span: e.span, kind: kind }),
|
||||
}
|
||||
}
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
let opt_def = tcx.def_map.borrow().get(&e.id).map(|d| d.full_def());
|
||||
let (const_expr, const_ty) = match opt_def {
|
||||
Some(def::DefConst(def_id)) => {
|
||||
if def_id.is_local() {
|
||||
match tcx.map.find(def_id.node) {
|
||||
Some(ast_map::NodeItem(it)) => match it.node {
|
||||
ast::ItemConst(ref ty, ref expr) => {
|
||||
hir::ItemConst(ref ty, ref expr) => {
|
||||
(Some(&**expr), Some(&**ty))
|
||||
}
|
||||
_ => (None, None)
|
||||
@ -935,7 +938,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
match tcx.impl_or_trait_item(def_id).container() {
|
||||
ty::TraitContainer(trait_id) => match tcx.map.find(def_id.node) {
|
||||
Some(ast_map::NodeTraitItem(ti)) => match ti.node {
|
||||
ast::ConstTraitItem(ref ty, _) => {
|
||||
hir::ConstTraitItem(ref ty, _) => {
|
||||
if let ExprTypeChecked = ty_hint {
|
||||
let substs = tcx.node_id_item_substs(e.id).substs;
|
||||
(resolve_trait_associated_const(tcx,
|
||||
@ -953,7 +956,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
},
|
||||
ty::ImplContainer(_) => match tcx.map.find(def_id.node) {
|
||||
Some(ast_map::NodeImplItem(ii)) => match ii.node {
|
||||
ast::ConstImplItem(ref ty, ref expr) => {
|
||||
hir::ConstImplItem(ref ty, ref expr) => {
|
||||
(Some(&**expr), Some(&**ty))
|
||||
}
|
||||
_ => (None, None)
|
||||
@ -990,19 +993,19 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
};
|
||||
try!(eval_const_expr_partial(tcx, const_expr, item_hint))
|
||||
}
|
||||
ast::ExprLit(ref lit) => {
|
||||
hir::ExprLit(ref lit) => {
|
||||
lit_to_const(&**lit, ety)
|
||||
}
|
||||
ast::ExprParen(ref e) => try!(eval_const_expr_partial(tcx, &**e, ty_hint)),
|
||||
ast::ExprBlock(ref block) => {
|
||||
hir::ExprParen(ref e) => try!(eval_const_expr_partial(tcx, &**e, ty_hint)),
|
||||
hir::ExprBlock(ref block) => {
|
||||
match block.expr {
|
||||
Some(ref expr) => try!(eval_const_expr_partial(tcx, &**expr, ty_hint)),
|
||||
None => Int(0)
|
||||
}
|
||||
}
|
||||
ast::ExprTup(_) => Tuple(e.id),
|
||||
ast::ExprStruct(..) => Struct(e.id),
|
||||
ast::ExprTupField(ref base, index) => {
|
||||
hir::ExprTup(_) => Tuple(e.id),
|
||||
hir::ExprStruct(..) => Struct(e.id),
|
||||
hir::ExprTupField(ref base, index) => {
|
||||
let base_hint = if let ExprTypeChecked = ty_hint {
|
||||
ExprTypeChecked
|
||||
} else {
|
||||
@ -1010,7 +1013,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
};
|
||||
if let Ok(c) = eval_const_expr_partial(tcx, base, base_hint) {
|
||||
if let Tuple(tup_id) = c {
|
||||
if let ast::ExprTup(ref fields) = tcx.map.expect_expr(tup_id).node {
|
||||
if let hir::ExprTup(ref fields) = tcx.map.expect_expr(tup_id).node {
|
||||
if index.node < fields.len() {
|
||||
return eval_const_expr_partial(tcx, &fields[index.node], base_hint)
|
||||
} else {
|
||||
@ -1026,7 +1029,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
signal!(base, NonConstPath)
|
||||
}
|
||||
}
|
||||
ast::ExprField(ref base, field_name) => {
|
||||
hir::ExprField(ref base, field_name) => {
|
||||
// Get the base expression if it is a struct and it is constant
|
||||
let base_hint = if let ExprTypeChecked = ty_hint {
|
||||
ExprTypeChecked
|
||||
@ -1035,7 +1038,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
};
|
||||
if let Ok(c) = eval_const_expr_partial(tcx, base, base_hint) {
|
||||
if let Struct(struct_id) = c {
|
||||
if let ast::ExprStruct(_, ref fields, _) = tcx.map.expect_expr(struct_id).node {
|
||||
if let hir::ExprStruct(_, ref fields, _) = tcx.map.expect_expr(struct_id).node {
|
||||
// Check that the given field exists and evaluate it
|
||||
// if the idents are compared run-pass/issue-19244 fails
|
||||
if let Some(f) = fields.iter().find(|f| f.ident.node.name
|
||||
@ -1061,7 +1064,7 @@ pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
|
||||
}
|
||||
|
||||
fn resolve_trait_associated_const<'a, 'tcx: 'a>(tcx: &'a ty::ctxt<'tcx>,
|
||||
ti: &'tcx ast::TraitItem,
|
||||
ti: &'tcx hir::TraitItem,
|
||||
trait_id: DefId,
|
||||
rcvr_substs: subst::Substs<'tcx>)
|
||||
-> Option<&'tcx Expr>
|
||||
@ -1110,7 +1113,7 @@ fn resolve_trait_associated_const<'a, 'tcx: 'a>(tcx: &'a ty::ctxt<'tcx>,
|
||||
.iter().find(|ic| ic.name == ti.ident.name) {
|
||||
Some(ic) => lookup_const_by_id(tcx, ic.def_id, None),
|
||||
None => match ti.node {
|
||||
ast::ConstTraitItem(_, Some(ref expr)) => Some(&*expr),
|
||||
hir::ConstTraitItem(_, Some(ref expr)) => Some(&*expr),
|
||||
_ => None,
|
||||
},
|
||||
}
|
||||
@ -1138,60 +1141,60 @@ fn cast_const<'tcx>(tcx: &ty::ctxt<'tcx>, val: ConstVal, ty: Ty) -> CastResult {
|
||||
|
||||
// Issue #23890: If isize/usize, then dispatch to appropriate target representation type
|
||||
match (&ty.sty, tcx.sess.target.int_type, tcx.sess.target.uint_type) {
|
||||
(&ty::TyInt(ast::TyIs), ast::TyI32, _) => return convert_val!(i32, Int, i64),
|
||||
(&ty::TyInt(ast::TyIs), ast::TyI64, _) => return convert_val!(i64, Int, i64),
|
||||
(&ty::TyInt(ast::TyIs), _, _) => panic!("unexpected target.int_type"),
|
||||
(&ty::TyInt(hir::TyIs), hir::TyI32, _) => return convert_val!(i32, Int, i64),
|
||||
(&ty::TyInt(hir::TyIs), hir::TyI64, _) => return convert_val!(i64, Int, i64),
|
||||
(&ty::TyInt(hir::TyIs), _, _) => panic!("unexpected target.int_type"),
|
||||
|
||||
(&ty::TyUint(ast::TyUs), _, ast::TyU32) => return convert_val!(u32, Uint, u64),
|
||||
(&ty::TyUint(ast::TyUs), _, ast::TyU64) => return convert_val!(u64, Uint, u64),
|
||||
(&ty::TyUint(ast::TyUs), _, _) => panic!("unexpected target.uint_type"),
|
||||
(&ty::TyUint(hir::TyUs), _, hir::TyU32) => return convert_val!(u32, Uint, u64),
|
||||
(&ty::TyUint(hir::TyUs), _, hir::TyU64) => return convert_val!(u64, Uint, u64),
|
||||
(&ty::TyUint(hir::TyUs), _, _) => panic!("unexpected target.uint_type"),
|
||||
|
||||
_ => {}
|
||||
}
|
||||
|
||||
match ty.sty {
|
||||
ty::TyInt(ast::TyIs) => unreachable!(),
|
||||
ty::TyUint(ast::TyUs) => unreachable!(),
|
||||
ty::TyInt(hir::TyIs) => unreachable!(),
|
||||
ty::TyUint(hir::TyUs) => unreachable!(),
|
||||
|
||||
ty::TyInt(ast::TyI8) => convert_val!(i8, Int, i64),
|
||||
ty::TyInt(ast::TyI16) => convert_val!(i16, Int, i64),
|
||||
ty::TyInt(ast::TyI32) => convert_val!(i32, Int, i64),
|
||||
ty::TyInt(ast::TyI64) => convert_val!(i64, Int, i64),
|
||||
ty::TyInt(hir::TyI8) => convert_val!(i8, Int, i64),
|
||||
ty::TyInt(hir::TyI16) => convert_val!(i16, Int, i64),
|
||||
ty::TyInt(hir::TyI32) => convert_val!(i32, Int, i64),
|
||||
ty::TyInt(hir::TyI64) => convert_val!(i64, Int, i64),
|
||||
|
||||
ty::TyUint(ast::TyU8) => convert_val!(u8, Uint, u64),
|
||||
ty::TyUint(ast::TyU16) => convert_val!(u16, Uint, u64),
|
||||
ty::TyUint(ast::TyU32) => convert_val!(u32, Uint, u64),
|
||||
ty::TyUint(ast::TyU64) => convert_val!(u64, Uint, u64),
|
||||
ty::TyUint(hir::TyU8) => convert_val!(u8, Uint, u64),
|
||||
ty::TyUint(hir::TyU16) => convert_val!(u16, Uint, u64),
|
||||
ty::TyUint(hir::TyU32) => convert_val!(u32, Uint, u64),
|
||||
ty::TyUint(hir::TyU64) => convert_val!(u64, Uint, u64),
|
||||
|
||||
ty::TyFloat(ast::TyF32) => convert_val!(f32, Float, f64),
|
||||
ty::TyFloat(ast::TyF64) => convert_val!(f64, Float, f64),
|
||||
ty::TyFloat(hir::TyF32) => convert_val!(f32, Float, f64),
|
||||
ty::TyFloat(hir::TyF64) => convert_val!(f64, Float, f64),
|
||||
_ => Err(ErrKind::CannotCast),
|
||||
}
|
||||
}
|
||||
|
||||
fn lit_to_const(lit: &ast::Lit, ty_hint: Option<Ty>) -> ConstVal {
|
||||
fn lit_to_const(lit: &hir::Lit, ty_hint: Option<Ty>) -> ConstVal {
|
||||
match lit.node {
|
||||
ast::LitStr(ref s, _) => Str((*s).clone()),
|
||||
ast::LitBinary(ref data) => {
|
||||
hir::LitStr(ref s, _) => Str((*s).clone()),
|
||||
hir::LitBinary(ref data) => {
|
||||
Binary(data.clone())
|
||||
}
|
||||
ast::LitByte(n) => Uint(n as u64),
|
||||
ast::LitChar(n) => Uint(n as u64),
|
||||
ast::LitInt(n, ast::SignedIntLit(_, ast::Plus)) => Int(n as i64),
|
||||
ast::LitInt(n, ast::UnsuffixedIntLit(ast::Plus)) => {
|
||||
hir::LitByte(n) => Uint(n as u64),
|
||||
hir::LitChar(n) => Uint(n as u64),
|
||||
hir::LitInt(n, hir::SignedIntLit(_, hir::Plus)) => Int(n as i64),
|
||||
hir::LitInt(n, hir::UnsuffixedIntLit(hir::Plus)) => {
|
||||
match ty_hint.map(|ty| &ty.sty) {
|
||||
Some(&ty::TyUint(_)) => Uint(n),
|
||||
_ => Int(n as i64)
|
||||
}
|
||||
}
|
||||
ast::LitInt(n, ast::SignedIntLit(_, ast::Minus)) |
|
||||
ast::LitInt(n, ast::UnsuffixedIntLit(ast::Minus)) => Int(-(n as i64)),
|
||||
ast::LitInt(n, ast::UnsignedIntLit(_)) => Uint(n),
|
||||
ast::LitFloat(ref n, _) |
|
||||
ast::LitFloatUnsuffixed(ref n) => {
|
||||
hir::LitInt(n, hir::SignedIntLit(_, hir::Minus)) |
|
||||
hir::LitInt(n, hir::UnsuffixedIntLit(hir::Minus)) => Int(-(n as i64)),
|
||||
hir::LitInt(n, hir::UnsignedIntLit(_)) => Uint(n),
|
||||
hir::LitFloat(ref n, _) |
|
||||
hir::LitFloatUnsuffixed(ref n) => {
|
||||
Float(n.parse::<f64>().unwrap() as f64)
|
||||
}
|
||||
ast::LitBool(b) => Bool(b)
|
||||
hir::LitBool(b) => Bool(b)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -23,9 +23,12 @@ use std::io;
|
||||
use std::usize;
|
||||
use syntax::ast;
|
||||
use syntax::ast_util::IdRange;
|
||||
use syntax::visit;
|
||||
use syntax::print::{pp, pprust};
|
||||
use syntax::print::pp;
|
||||
use util::nodemap::NodeMap;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::print::pprust;
|
||||
|
||||
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
pub enum EntryOrExit {
|
||||
@ -158,7 +161,7 @@ impl<'a, 'tcx, O:DataFlowOperator> pprust::PpAnn for DataFlowContext<'a, 'tcx, O
|
||||
}
|
||||
}
|
||||
|
||||
fn build_nodeid_to_index(decl: Option<&ast::FnDecl>,
|
||||
fn build_nodeid_to_index(decl: Option<&hir::FnDecl>,
|
||||
cfg: &cfg::CFG) -> NodeMap<Vec<CFGIndex>> {
|
||||
let mut index = NodeMap();
|
||||
|
||||
@ -181,7 +184,7 @@ fn build_nodeid_to_index(decl: Option<&ast::FnDecl>,
|
||||
return index;
|
||||
|
||||
fn add_entries_from_fn_decl(index: &mut NodeMap<Vec<CFGIndex>>,
|
||||
decl: &ast::FnDecl,
|
||||
decl: &hir::FnDecl,
|
||||
entry: CFGIndex) {
|
||||
//! add mappings from the ast nodes for the formal bindings to
|
||||
//! the entry-node in the graph.
|
||||
@ -192,7 +195,7 @@ fn build_nodeid_to_index(decl: Option<&ast::FnDecl>,
|
||||
let mut formals = Formals { entry: entry, index: index };
|
||||
visit::walk_fn_decl(&mut formals, decl);
|
||||
impl<'a, 'v> visit::Visitor<'v> for Formals<'a> {
|
||||
fn visit_pat(&mut self, p: &ast::Pat) {
|
||||
fn visit_pat(&mut self, p: &hir::Pat) {
|
||||
self.index.entry(p.id).or_insert(vec![]).push(self.entry);
|
||||
visit::walk_pat(self, p)
|
||||
}
|
||||
@ -222,7 +225,7 @@ pub enum KillFrom {
|
||||
impl<'a, 'tcx, O:DataFlowOperator> DataFlowContext<'a, 'tcx, O> {
|
||||
pub fn new(tcx: &'a ty::ctxt<'tcx>,
|
||||
analysis_name: &'static str,
|
||||
decl: Option<&ast::FnDecl>,
|
||||
decl: Option<&hir::FnDecl>,
|
||||
cfg: &cfg::CFG,
|
||||
oper: O,
|
||||
id_range: IdRange,
|
||||
@ -495,7 +498,7 @@ impl<'a, 'tcx, O:DataFlowOperator> DataFlowContext<'a, 'tcx, O> {
|
||||
|
||||
impl<'a, 'tcx, O:DataFlowOperator+Clone+'static> DataFlowContext<'a, 'tcx, O> {
|
||||
// ^^^^^^^^^^^^^ only needed for pretty printing
|
||||
pub fn propagate(&mut self, cfg: &cfg::CFG, blk: &ast::Block) {
|
||||
pub fn propagate(&mut self, cfg: &cfg::CFG, blk: &hir::Block) {
|
||||
//! Performs the data flow analysis.
|
||||
|
||||
if self.bits_per_id == 0 {
|
||||
@ -528,7 +531,7 @@ impl<'a, 'tcx, O:DataFlowOperator+Clone+'static> DataFlowContext<'a, 'tcx, O> {
|
||||
}
|
||||
|
||||
fn pretty_print_to<'b>(&self, wr: Box<io::Write + 'b>,
|
||||
blk: &ast::Block) -> io::Result<()> {
|
||||
blk: &hir::Block) -> io::Result<()> {
|
||||
let mut ps = pprust::rust_printer_annotated(wr, self);
|
||||
try!(ps.cbox(pprust::indent_unit));
|
||||
try!(ps.ibox(0));
|
||||
|
@ -12,7 +12,11 @@
|
||||
// closely. The idea is that all reachable symbols are live, codes called
|
||||
// from live codes are live, and everything else is dead.
|
||||
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::visit::{self, Visitor};
|
||||
use rustc_front::attr::{self, AttrMetaMethods};
|
||||
|
||||
use middle::{def, pat_util, privacy, ty};
|
||||
use middle::def_id::{DefId};
|
||||
use lint;
|
||||
@ -20,8 +24,6 @@ use util::nodemap::NodeSet;
|
||||
|
||||
use std::collections::HashSet;
|
||||
use syntax::{ast, codemap};
|
||||
use syntax::attr::{self, AttrMetaMethods};
|
||||
use syntax::visit::{self, Visitor};
|
||||
|
||||
// Any local node that may call something in its body block should be
|
||||
// explored. For example, if it's a live NodeItem that is a
|
||||
@ -109,7 +111,7 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
|
||||
self.check_def_id(method.def_id);
|
||||
}
|
||||
|
||||
fn handle_field_access(&mut self, lhs: &ast::Expr, name: ast::Name) {
|
||||
fn handle_field_access(&mut self, lhs: &hir::Expr, name: ast::Name) {
|
||||
if let ty::TyStruct(def, _) = self.tcx.expr_ty_adjusted(lhs).sty {
|
||||
self.live_symbols.insert(def.struct_variant().field_named(name).did.node);
|
||||
} else {
|
||||
@ -117,14 +119,14 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn handle_tup_field_access(&mut self, lhs: &ast::Expr, idx: usize) {
|
||||
fn handle_tup_field_access(&mut self, lhs: &hir::Expr, idx: usize) {
|
||||
if let ty::TyStruct(def, _) = self.tcx.expr_ty_adjusted(lhs).sty {
|
||||
self.live_symbols.insert(def.struct_variant().fields[idx].did.node);
|
||||
}
|
||||
}
|
||||
|
||||
fn handle_field_pattern_match(&mut self, lhs: &ast::Pat,
|
||||
pats: &[codemap::Spanned<ast::FieldPat>]) {
|
||||
fn handle_field_pattern_match(&mut self, lhs: &hir::Pat,
|
||||
pats: &[codemap::Spanned<hir::FieldPat>]) {
|
||||
let def = self.tcx.def_map.borrow().get(&lhs.id).unwrap().full_def();
|
||||
let pat_ty = self.tcx.node_id_to_type(lhs.id);
|
||||
let variant = match pat_ty.sty {
|
||||
@ -132,7 +134,7 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
|
||||
_ => self.tcx.sess.span_bug(lhs.span, "non-ADT in struct pattern")
|
||||
};
|
||||
for pat in pats {
|
||||
if let ast::PatWild(ast::PatWildSingle) = pat.node.pat.node {
|
||||
if let hir::PatWild(hir::PatWildSingle) = pat.node.pat.node {
|
||||
continue;
|
||||
}
|
||||
self.live_symbols.insert(variant.field_named(pat.node.ident.name).did.node);
|
||||
@ -166,7 +168,7 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
|
||||
match *node {
|
||||
ast_map::NodeItem(item) => {
|
||||
match item.node {
|
||||
ast::ItemStruct(..) => {
|
||||
hir::ItemStruct(..) => {
|
||||
self.struct_has_extern_repr = item.attrs.iter().any(|attr| {
|
||||
attr::find_repr_attrs(self.tcx.sess.diagnostic(), attr)
|
||||
.contains(&attr::ReprExtern)
|
||||
@ -174,14 +176,14 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
|
||||
|
||||
visit::walk_item(self, &*item);
|
||||
}
|
||||
ast::ItemEnum(..) => {
|
||||
self.inherited_pub_visibility = item.vis == ast::Public;
|
||||
hir::ItemEnum(..) => {
|
||||
self.inherited_pub_visibility = item.vis == hir::Public;
|
||||
visit::walk_item(self, &*item);
|
||||
}
|
||||
ast::ItemFn(..)
|
||||
| ast::ItemTy(..)
|
||||
| ast::ItemStatic(..)
|
||||
| ast::ItemConst(..) => {
|
||||
hir::ItemFn(..)
|
||||
| hir::ItemTy(..)
|
||||
| hir::ItemStatic(..)
|
||||
| hir::ItemConst(..) => {
|
||||
visit::walk_item(self, &*item);
|
||||
}
|
||||
_ => ()
|
||||
@ -205,13 +207,13 @@ impl<'a, 'tcx> MarkSymbolVisitor<'a, 'tcx> {
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for MarkSymbolVisitor<'a, 'tcx> {
|
||||
|
||||
fn visit_struct_def(&mut self, def: &ast::StructDef, _: ast::Ident,
|
||||
_: &ast::Generics, _: ast::NodeId) {
|
||||
fn visit_struct_def(&mut self, def: &hir::StructDef, _: ast::Ident,
|
||||
_: &hir::Generics, _: ast::NodeId) {
|
||||
let has_extern_repr = self.struct_has_extern_repr;
|
||||
let inherited_pub_visibility = self.inherited_pub_visibility;
|
||||
let live_fields = def.fields.iter().filter(|f| {
|
||||
has_extern_repr || inherited_pub_visibility || match f.node.kind {
|
||||
ast::NamedField(_, ast::Public) => true,
|
||||
hir::NamedField(_, hir::Public) => true,
|
||||
_ => false
|
||||
}
|
||||
});
|
||||
@ -220,15 +222,15 @@ impl<'a, 'tcx, 'v> Visitor<'v> for MarkSymbolVisitor<'a, 'tcx> {
|
||||
visit::walk_struct_def(self, def);
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, expr: &ast::Expr) {
|
||||
fn visit_expr(&mut self, expr: &hir::Expr) {
|
||||
match expr.node {
|
||||
ast::ExprMethodCall(..) => {
|
||||
hir::ExprMethodCall(..) => {
|
||||
self.lookup_and_handle_method(expr.id);
|
||||
}
|
||||
ast::ExprField(ref lhs, ref ident) => {
|
||||
hir::ExprField(ref lhs, ref ident) => {
|
||||
self.handle_field_access(&**lhs, ident.node.name);
|
||||
}
|
||||
ast::ExprTupField(ref lhs, idx) => {
|
||||
hir::ExprTupField(ref lhs, idx) => {
|
||||
self.handle_tup_field_access(&**lhs, idx.node);
|
||||
}
|
||||
_ => ()
|
||||
@ -237,7 +239,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for MarkSymbolVisitor<'a, 'tcx> {
|
||||
visit::walk_expr(self, expr);
|
||||
}
|
||||
|
||||
fn visit_arm(&mut self, arm: &ast::Arm) {
|
||||
fn visit_arm(&mut self, arm: &hir::Arm) {
|
||||
if arm.pats.len() == 1 {
|
||||
let pat = &*arm.pats[0];
|
||||
let variants = pat_util::necessary_variants(&self.tcx.def_map, pat);
|
||||
@ -254,10 +256,10 @@ impl<'a, 'tcx, 'v> Visitor<'v> for MarkSymbolVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_pat(&mut self, pat: &ast::Pat) {
|
||||
fn visit_pat(&mut self, pat: &hir::Pat) {
|
||||
let def_map = &self.tcx.def_map;
|
||||
match pat.node {
|
||||
ast::PatStruct(_, ref fields, _) => {
|
||||
hir::PatStruct(_, ref fields, _) => {
|
||||
self.handle_field_pattern_match(pat, fields);
|
||||
}
|
||||
_ if pat_util::pat_is_const(def_map, pat) => {
|
||||
@ -272,24 +274,24 @@ impl<'a, 'tcx, 'v> Visitor<'v> for MarkSymbolVisitor<'a, 'tcx> {
|
||||
self.ignore_non_const_paths = false;
|
||||
}
|
||||
|
||||
fn visit_path(&mut self, path: &ast::Path, id: ast::NodeId) {
|
||||
fn visit_path(&mut self, path: &hir::Path, id: ast::NodeId) {
|
||||
self.lookup_and_handle_definition(&id);
|
||||
visit::walk_path(self, path);
|
||||
}
|
||||
|
||||
fn visit_item(&mut self, _: &ast::Item) {
|
||||
fn visit_item(&mut self, _: &hir::Item) {
|
||||
// Do not recurse into items. These items will be added to the
|
||||
// worklist and recursed into manually if necessary.
|
||||
}
|
||||
}
|
||||
|
||||
fn has_allow_dead_code_or_lang_attr(attrs: &[ast::Attribute]) -> bool {
|
||||
fn has_allow_dead_code_or_lang_attr(attrs: &[hir::Attribute]) -> bool {
|
||||
if attr::contains_name(attrs, "lang") {
|
||||
return true;
|
||||
}
|
||||
|
||||
let dead_code = lint::builtin::DEAD_CODE.name_lower();
|
||||
for attr in lint::gather_attrs(attrs) {
|
||||
for attr in lint::gather_attrs_from_hir(attrs) {
|
||||
match attr {
|
||||
Ok((ref name, lint::Allow, _))
|
||||
if &name[..] == dead_code => return true,
|
||||
@ -317,20 +319,20 @@ struct LifeSeeder {
|
||||
}
|
||||
|
||||
impl<'v> Visitor<'v> for LifeSeeder {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
let allow_dead_code = has_allow_dead_code_or_lang_attr(&item.attrs);
|
||||
if allow_dead_code {
|
||||
self.worklist.push(item.id);
|
||||
}
|
||||
match item.node {
|
||||
ast::ItemEnum(ref enum_def, _) if allow_dead_code => {
|
||||
hir::ItemEnum(ref enum_def, _) if allow_dead_code => {
|
||||
self.worklist.extend(enum_def.variants.iter().map(|variant| variant.node.id));
|
||||
}
|
||||
ast::ItemTrait(_, _, _, ref trait_items) => {
|
||||
hir::ItemTrait(_, _, _, ref trait_items) => {
|
||||
for trait_item in trait_items {
|
||||
match trait_item.node {
|
||||
ast::ConstTraitItem(_, Some(_)) |
|
||||
ast::MethodTraitItem(_, Some(_)) => {
|
||||
hir::ConstTraitItem(_, Some(_)) |
|
||||
hir::MethodTraitItem(_, Some(_)) => {
|
||||
if has_allow_dead_code_or_lang_attr(&trait_item.attrs) {
|
||||
self.worklist.push(trait_item.id);
|
||||
}
|
||||
@ -339,18 +341,17 @@ impl<'v> Visitor<'v> for LifeSeeder {
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::ItemImpl(_, _, _, ref opt_trait, _, ref impl_items) => {
|
||||
hir::ItemImpl(_, _, _, ref opt_trait, _, ref impl_items) => {
|
||||
for impl_item in impl_items {
|
||||
match impl_item.node {
|
||||
ast::ConstImplItem(..) |
|
||||
ast::MethodImplItem(..) => {
|
||||
hir::ConstImplItem(..) |
|
||||
hir::MethodImplItem(..) => {
|
||||
if opt_trait.is_some() ||
|
||||
has_allow_dead_code_or_lang_attr(&impl_item.attrs) {
|
||||
self.worklist.push(impl_item.id);
|
||||
}
|
||||
}
|
||||
ast::TypeImplItem(_) => {}
|
||||
ast::MacImplItem(_) => panic!("unexpanded macro")
|
||||
hir::TypeImplItem(_) => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -363,7 +364,7 @@ impl<'v> Visitor<'v> for LifeSeeder {
|
||||
fn create_and_seed_worklist(tcx: &ty::ctxt,
|
||||
exported_items: &privacy::ExportedItems,
|
||||
reachable_symbols: &NodeSet,
|
||||
krate: &ast::Crate) -> Vec<ast::NodeId> {
|
||||
krate: &hir::Crate) -> Vec<ast::NodeId> {
|
||||
let mut worklist = Vec::new();
|
||||
|
||||
// Preferably, we would only need to seed the worklist with reachable
|
||||
@ -401,7 +402,7 @@ fn create_and_seed_worklist(tcx: &ty::ctxt,
|
||||
fn find_live(tcx: &ty::ctxt,
|
||||
exported_items: &privacy::ExportedItems,
|
||||
reachable_symbols: &NodeSet,
|
||||
krate: &ast::Crate)
|
||||
krate: &hir::Crate)
|
||||
-> Box<HashSet<ast::NodeId>> {
|
||||
let worklist = create_and_seed_worklist(tcx, exported_items,
|
||||
reachable_symbols, krate);
|
||||
@ -410,9 +411,9 @@ fn find_live(tcx: &ty::ctxt,
|
||||
symbol_visitor.live_symbols
|
||||
}
|
||||
|
||||
fn get_struct_ctor_id(item: &ast::Item) -> Option<ast::NodeId> {
|
||||
fn get_struct_ctor_id(item: &hir::Item) -> Option<ast::NodeId> {
|
||||
match item.node {
|
||||
ast::ItemStruct(ref struct_def, _) => struct_def.ctor_id,
|
||||
hir::ItemStruct(ref struct_def, _) => struct_def.ctor_id,
|
||||
_ => None
|
||||
}
|
||||
}
|
||||
@ -423,20 +424,20 @@ struct DeadVisitor<'a, 'tcx: 'a> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx> DeadVisitor<'a, 'tcx> {
|
||||
fn should_warn_about_item(&mut self, item: &ast::Item) -> bool {
|
||||
fn should_warn_about_item(&mut self, item: &hir::Item) -> bool {
|
||||
let should_warn = match item.node {
|
||||
ast::ItemStatic(..)
|
||||
| ast::ItemConst(..)
|
||||
| ast::ItemFn(..)
|
||||
| ast::ItemEnum(..)
|
||||
| ast::ItemStruct(..) => true,
|
||||
hir::ItemStatic(..)
|
||||
| hir::ItemConst(..)
|
||||
| hir::ItemFn(..)
|
||||
| hir::ItemEnum(..)
|
||||
| hir::ItemStruct(..) => true,
|
||||
_ => false
|
||||
};
|
||||
let ctor_id = get_struct_ctor_id(item);
|
||||
should_warn && !self.symbol_is_live(item.id, ctor_id)
|
||||
}
|
||||
|
||||
fn should_warn_about_field(&mut self, node: &ast::StructField_) -> bool {
|
||||
fn should_warn_about_field(&mut self, node: &hir::StructField_) -> bool {
|
||||
let is_named = node.ident().is_some();
|
||||
let field_type = self.tcx.node_id_to_type(node.id);
|
||||
let is_marker_field = match field_type.ty_to_def_id() {
|
||||
@ -449,7 +450,7 @@ impl<'a, 'tcx> DeadVisitor<'a, 'tcx> {
|
||||
&& !has_allow_dead_code_or_lang_attr(&node.attrs)
|
||||
}
|
||||
|
||||
fn should_warn_about_variant(&mut self, variant: &ast::Variant_) -> bool {
|
||||
fn should_warn_about_variant(&mut self, variant: &hir::Variant_) -> bool {
|
||||
!self.symbol_is_live(variant.id, None)
|
||||
&& !has_allow_dead_code_or_lang_attr(&variant.attrs)
|
||||
}
|
||||
@ -509,7 +510,7 @@ impl<'a, 'tcx> DeadVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for DeadVisitor<'a, 'tcx> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
if self.should_warn_about_item(item) {
|
||||
self.warn_dead_code(
|
||||
item.id,
|
||||
@ -519,7 +520,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for DeadVisitor<'a, 'tcx> {
|
||||
);
|
||||
} else {
|
||||
match item.node {
|
||||
ast::ItemEnum(ref enum_def, _) => {
|
||||
hir::ItemEnum(ref enum_def, _) => {
|
||||
for variant in &enum_def.variants {
|
||||
if self.should_warn_about_variant(&variant.node) {
|
||||
self.warn_dead_code(variant.node.id, variant.span,
|
||||
@ -533,14 +534,14 @@ impl<'a, 'tcx, 'v> Visitor<'v> for DeadVisitor<'a, 'tcx> {
|
||||
visit::walk_item(self, item);
|
||||
}
|
||||
|
||||
fn visit_foreign_item(&mut self, fi: &ast::ForeignItem) {
|
||||
fn visit_foreign_item(&mut self, fi: &hir::ForeignItem) {
|
||||
if !self.symbol_is_live(fi.id, None) {
|
||||
self.warn_dead_code(fi.id, fi.span, fi.ident.name, fi.node.descriptive_variant());
|
||||
}
|
||||
visit::walk_foreign_item(self, fi);
|
||||
}
|
||||
|
||||
fn visit_struct_field(&mut self, field: &ast::StructField) {
|
||||
fn visit_struct_field(&mut self, field: &hir::StructField) {
|
||||
if self.should_warn_about_field(&field.node) {
|
||||
self.warn_dead_code(field.node.id, field.span,
|
||||
field.node.ident().unwrap().name, "struct field");
|
||||
@ -549,39 +550,38 @@ impl<'a, 'tcx, 'v> Visitor<'v> for DeadVisitor<'a, 'tcx> {
|
||||
visit::walk_struct_field(self, field);
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, impl_item: &ast::ImplItem) {
|
||||
fn visit_impl_item(&mut self, impl_item: &hir::ImplItem) {
|
||||
match impl_item.node {
|
||||
ast::ConstImplItem(_, ref expr) => {
|
||||
hir::ConstImplItem(_, ref expr) => {
|
||||
if !self.symbol_is_live(impl_item.id, None) {
|
||||
self.warn_dead_code(impl_item.id, impl_item.span,
|
||||
impl_item.ident.name, "associated const");
|
||||
}
|
||||
visit::walk_expr(self, expr)
|
||||
}
|
||||
ast::MethodImplItem(_, ref body) => {
|
||||
hir::MethodImplItem(_, ref body) => {
|
||||
if !self.symbol_is_live(impl_item.id, None) {
|
||||
self.warn_dead_code(impl_item.id, impl_item.span,
|
||||
impl_item.ident.name, "method");
|
||||
}
|
||||
visit::walk_block(self, body)
|
||||
}
|
||||
ast::TypeImplItem(..) |
|
||||
ast::MacImplItem(..) => {}
|
||||
hir::TypeImplItem(..) => {}
|
||||
}
|
||||
}
|
||||
|
||||
// Overwrite so that we don't warn the trait item itself.
|
||||
fn visit_trait_item(&mut self, trait_item: &ast::TraitItem) {
|
||||
fn visit_trait_item(&mut self, trait_item: &hir::TraitItem) {
|
||||
match trait_item.node {
|
||||
ast::ConstTraitItem(_, Some(ref expr)) => {
|
||||
hir::ConstTraitItem(_, Some(ref expr)) => {
|
||||
visit::walk_expr(self, expr)
|
||||
}
|
||||
ast::MethodTraitItem(_, Some(ref body)) => {
|
||||
hir::MethodTraitItem(_, Some(ref body)) => {
|
||||
visit::walk_block(self, body)
|
||||
}
|
||||
ast::ConstTraitItem(_, None) |
|
||||
ast::MethodTraitItem(_, None) |
|
||||
ast::TypeTraitItem(..) => {}
|
||||
hir::ConstTraitItem(_, None) |
|
||||
hir::MethodTraitItem(_, None) |
|
||||
hir::TypeTraitItem(..) => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -15,6 +15,7 @@ use middle::privacy::LastPrivate;
|
||||
use middle::subst::ParamSpace;
|
||||
use util::nodemap::NodeMap;
|
||||
use syntax::ast;
|
||||
use rustc_front::hir;
|
||||
|
||||
use std::cell::RefCell;
|
||||
|
||||
@ -33,7 +34,7 @@ pub enum Def {
|
||||
DefTy(DefId, bool /* is_enum */),
|
||||
DefAssociatedTy(DefId /* trait */, DefId),
|
||||
DefTrait(DefId),
|
||||
DefPrimTy(ast::PrimTy),
|
||||
DefPrimTy(hir::PrimTy),
|
||||
DefTyParam(ParamSpace, u32, DefId, ast::Name),
|
||||
DefUse(DefId),
|
||||
DefUpvar(ast::NodeId, // id of closed over local
|
||||
|
@ -18,8 +18,9 @@ use middle::ty::MethodCall;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit;
|
||||
use syntax::visit::{FnKind, Visitor};
|
||||
use rustc_front::hir;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::visit::{FnKind, Visitor};
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
struct UnsafeContext {
|
||||
@ -42,7 +43,7 @@ enum RootUnsafeContext {
|
||||
|
||||
fn type_is_unsafe_function(ty: Ty) -> bool {
|
||||
match ty.sty {
|
||||
ty::TyBareFn(_, ref f) => f.unsafety == ast::Unsafety::Unsafe,
|
||||
ty::TyBareFn(_, ref f) => f.unsafety == hir::Unsafety::Unsafe,
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
@ -75,14 +76,14 @@ impl<'a, 'tcx> EffectCheckVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> {
|
||||
fn visit_fn(&mut self, fn_kind: FnKind<'v>, fn_decl: &'v ast::FnDecl,
|
||||
block: &'v ast::Block, span: Span, _: ast::NodeId) {
|
||||
fn visit_fn(&mut self, fn_kind: FnKind<'v>, fn_decl: &'v hir::FnDecl,
|
||||
block: &'v hir::Block, span: Span, _: ast::NodeId) {
|
||||
|
||||
let (is_item_fn, is_unsafe_fn) = match fn_kind {
|
||||
FnKind::ItemFn(_, _, unsafety, _, _, _) =>
|
||||
(true, unsafety == ast::Unsafety::Unsafe),
|
||||
(true, unsafety == hir::Unsafety::Unsafe),
|
||||
FnKind::Method(_, sig, _) =>
|
||||
(true, sig.unsafety == ast::Unsafety::Unsafe),
|
||||
(true, sig.unsafety == hir::Unsafety::Unsafe),
|
||||
_ => (false, false),
|
||||
};
|
||||
|
||||
@ -98,11 +99,11 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> {
|
||||
self.unsafe_context = old_unsafe_context
|
||||
}
|
||||
|
||||
fn visit_block(&mut self, block: &ast::Block) {
|
||||
fn visit_block(&mut self, block: &hir::Block) {
|
||||
let old_unsafe_context = self.unsafe_context;
|
||||
match block.rules {
|
||||
ast::DefaultBlock => {}
|
||||
ast::UnsafeBlock(source) => {
|
||||
hir::DefaultBlock => {}
|
||||
hir::UnsafeBlock(source) => {
|
||||
// By default only the outermost `unsafe` block is
|
||||
// "used" and so nested unsafe blocks are pointless
|
||||
// (the inner ones are unnecessary and we actually
|
||||
@ -118,15 +119,15 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> {
|
||||
// external blocks (e.g. `unsafe { println("") }`,
|
||||
// expands to `unsafe { ... unsafe { ... } }` where
|
||||
// the inner one is compiler generated).
|
||||
if self.unsafe_context.root == SafeContext || source == ast::CompilerGenerated {
|
||||
if self.unsafe_context.root == SafeContext || source == hir::CompilerGenerated {
|
||||
self.unsafe_context.root = UnsafeBlock(block.id)
|
||||
}
|
||||
}
|
||||
ast::PushUnsafeBlock(..) => {
|
||||
hir::PushUnsafeBlock(..) => {
|
||||
self.unsafe_context.push_unsafe_count =
|
||||
self.unsafe_context.push_unsafe_count.checked_add(1).unwrap();
|
||||
}
|
||||
ast::PopUnsafeBlock(..) => {
|
||||
hir::PopUnsafeBlock(..) => {
|
||||
self.unsafe_context.push_unsafe_count =
|
||||
self.unsafe_context.push_unsafe_count.checked_sub(1).unwrap();
|
||||
}
|
||||
@ -137,9 +138,9 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> {
|
||||
self.unsafe_context = old_unsafe_context
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, expr: &ast::Expr) {
|
||||
fn visit_expr(&mut self, expr: &hir::Expr) {
|
||||
match expr.node {
|
||||
ast::ExprMethodCall(_, _, _) => {
|
||||
hir::ExprMethodCall(_, _, _) => {
|
||||
let method_call = MethodCall::expr(expr.id);
|
||||
let base_type = self.tcx.tables.borrow().method_map[&method_call].ty;
|
||||
debug!("effect: method call case, base type is {:?}",
|
||||
@ -149,7 +150,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> {
|
||||
"invocation of unsafe method")
|
||||
}
|
||||
}
|
||||
ast::ExprCall(ref base, _) => {
|
||||
hir::ExprCall(ref base, _) => {
|
||||
let base_type = self.tcx.node_id_to_type(base.id);
|
||||
debug!("effect: call case, base type is {:?}",
|
||||
base_type);
|
||||
@ -157,7 +158,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> {
|
||||
self.require_unsafe(expr.span, "call to unsafe function")
|
||||
}
|
||||
}
|
||||
ast::ExprUnary(ast::UnDeref, ref base) => {
|
||||
hir::ExprUnary(hir::UnDeref, ref base) => {
|
||||
let base_type = self.tcx.node_id_to_type(base.id);
|
||||
debug!("effect: unary case, base type is {:?}",
|
||||
base_type);
|
||||
@ -165,10 +166,10 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EffectCheckVisitor<'a, 'tcx> {
|
||||
self.require_unsafe(expr.span, "dereference of raw pointer")
|
||||
}
|
||||
}
|
||||
ast::ExprInlineAsm(..) => {
|
||||
hir::ExprInlineAsm(..) => {
|
||||
self.require_unsafe(expr.span, "use of inline assembly");
|
||||
}
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
if let def::DefStatic(_, true) = self.tcx.resolve_expr(expr) {
|
||||
self.require_unsafe(expr.span, "use of mutable static");
|
||||
}
|
||||
|
@ -9,15 +9,15 @@
|
||||
// except according to those terms.
|
||||
|
||||
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
use session::{config, Session};
|
||||
use syntax;
|
||||
use syntax::ast::{NodeId, Item};
|
||||
use syntax::attr;
|
||||
use syntax::ast::NodeId;
|
||||
use rustc_front::hir::{Item, ItemFn};
|
||||
use rustc_front::attr;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::entry::EntryPointType;
|
||||
use syntax::visit;
|
||||
use syntax::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::visit::Visitor;
|
||||
|
||||
struct EntryContext<'a> {
|
||||
session: &'a Session,
|
||||
@ -76,8 +76,33 @@ pub fn find_entry_point(session: &Session, ast_map: &ast_map::Map) {
|
||||
configure_main(&mut ctxt);
|
||||
}
|
||||
|
||||
// Beware, this is duplicated in libsyntax/entry.rs, make sure to keep
|
||||
// them in sync.
|
||||
fn entry_point_type(item: &Item, depth: usize) -> EntryPointType {
|
||||
match item.node {
|
||||
ItemFn(..) => {
|
||||
if attr::contains_name(&item.attrs, "start") {
|
||||
EntryPointType::Start
|
||||
} else if attr::contains_name(&item.attrs, "main") {
|
||||
EntryPointType::MainAttr
|
||||
} else if item.ident.name == "main" {
|
||||
if depth == 1 {
|
||||
// This is a top-level function so can be 'main'
|
||||
EntryPointType::MainNamed
|
||||
} else {
|
||||
EntryPointType::OtherMain
|
||||
}
|
||||
} else {
|
||||
EntryPointType::None
|
||||
}
|
||||
}
|
||||
_ => EntryPointType::None,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
fn find_item(item: &Item, ctxt: &mut EntryContext) {
|
||||
match syntax::entry::entry_point_type(item, ctxt.depth) {
|
||||
match entry_point_type(item, ctxt.depth) {
|
||||
EntryPointType::MainNamed => {
|
||||
if ctxt.main_fn.is_none() {
|
||||
ctxt.main_fn = Some((item.id, item.span));
|
||||
|
@ -26,7 +26,9 @@ use middle::infer;
|
||||
use middle::mem_categorization as mc;
|
||||
use middle::ty;
|
||||
|
||||
use syntax::{ast, ast_util};
|
||||
use rustc_front::hir;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::ptr::P;
|
||||
use syntax::codemap::Span;
|
||||
|
||||
@ -57,14 +59,14 @@ pub trait Delegate<'tcx> {
|
||||
// same input pattern structure (though of `consume_pat` can be
|
||||
// called on a subpart of an input passed to `matched_pat).
|
||||
fn matched_pat(&mut self,
|
||||
matched_pat: &ast::Pat,
|
||||
matched_pat: &hir::Pat,
|
||||
cmt: mc::cmt<'tcx>,
|
||||
mode: MatchMode);
|
||||
|
||||
// The value found at `cmt` is either copied or moved via the
|
||||
// pattern binding `consume_pat`, depending on mode.
|
||||
fn consume_pat(&mut self,
|
||||
consume_pat: &ast::Pat,
|
||||
consume_pat: &hir::Pat,
|
||||
cmt: mc::cmt<'tcx>,
|
||||
mode: ConsumeMode);
|
||||
|
||||
@ -277,23 +279,25 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
typer: &'t infer::InferCtxt<'a, 'tcx>)
|
||||
-> ExprUseVisitor<'d,'t,'a,'tcx>
|
||||
{
|
||||
ExprUseVisitor {
|
||||
let result = ExprUseVisitor {
|
||||
typer: typer,
|
||||
mc: mc::MemCategorizationContext::new(typer),
|
||||
delegate: delegate,
|
||||
}
|
||||
};
|
||||
|
||||
result
|
||||
}
|
||||
|
||||
pub fn walk_fn(&mut self,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block) {
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block) {
|
||||
self.walk_arg_patterns(decl, body);
|
||||
self.walk_block(body);
|
||||
}
|
||||
|
||||
fn walk_arg_patterns(&mut self,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block) {
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block) {
|
||||
for arg in &decl.inputs {
|
||||
let arg_ty = return_if_err!(self.typer.node_ty(arg.pat.id));
|
||||
|
||||
@ -323,13 +327,13 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
self.delegate.consume(consume_id, consume_span, cmt, mode);
|
||||
}
|
||||
|
||||
fn consume_exprs(&mut self, exprs: &Vec<P<ast::Expr>>) {
|
||||
fn consume_exprs(&mut self, exprs: &Vec<P<hir::Expr>>) {
|
||||
for expr in exprs {
|
||||
self.consume_expr(&**expr);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn consume_expr(&mut self, expr: &ast::Expr) {
|
||||
pub fn consume_expr(&mut self, expr: &hir::Expr) {
|
||||
debug!("consume_expr(expr={:?})", expr);
|
||||
|
||||
let cmt = return_if_err!(self.mc.cat_expr(expr));
|
||||
@ -338,8 +342,8 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
|
||||
fn mutate_expr(&mut self,
|
||||
assignment_expr: &ast::Expr,
|
||||
expr: &ast::Expr,
|
||||
assignment_expr: &hir::Expr,
|
||||
expr: &hir::Expr,
|
||||
mode: MutateMode) {
|
||||
let cmt = return_if_err!(self.mc.cat_expr(expr));
|
||||
self.delegate.mutate(assignment_expr.id, assignment_expr.span, cmt, mode);
|
||||
@ -347,7 +351,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
|
||||
fn borrow_expr(&mut self,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
r: ty::Region,
|
||||
bk: ty::BorrowKind,
|
||||
cause: LoanCause) {
|
||||
@ -363,37 +367,37 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
self.walk_expr(expr)
|
||||
}
|
||||
|
||||
fn select_from_expr(&mut self, expr: &ast::Expr) {
|
||||
fn select_from_expr(&mut self, expr: &hir::Expr) {
|
||||
self.walk_expr(expr)
|
||||
}
|
||||
|
||||
pub fn walk_expr(&mut self, expr: &ast::Expr) {
|
||||
pub fn walk_expr(&mut self, expr: &hir::Expr) {
|
||||
debug!("walk_expr(expr={:?})", expr);
|
||||
|
||||
self.walk_adjustment(expr);
|
||||
|
||||
match expr.node {
|
||||
ast::ExprParen(ref subexpr) => {
|
||||
hir::ExprParen(ref subexpr) => {
|
||||
self.walk_expr(&**subexpr)
|
||||
}
|
||||
|
||||
ast::ExprPath(..) => { }
|
||||
hir::ExprPath(..) => { }
|
||||
|
||||
ast::ExprUnary(ast::UnDeref, ref base) => { // *base
|
||||
hir::ExprUnary(hir::UnDeref, ref base) => { // *base
|
||||
if !self.walk_overloaded_operator(expr, &**base, Vec::new(), PassArgs::ByRef) {
|
||||
self.select_from_expr(&**base);
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprField(ref base, _) => { // base.f
|
||||
hir::ExprField(ref base, _) => { // base.f
|
||||
self.select_from_expr(&**base);
|
||||
}
|
||||
|
||||
ast::ExprTupField(ref base, _) => { // base.<n>
|
||||
hir::ExprTupField(ref base, _) => { // base.<n>
|
||||
self.select_from_expr(&**base);
|
||||
}
|
||||
|
||||
ast::ExprIndex(ref lhs, ref rhs) => { // lhs[rhs]
|
||||
hir::ExprIndex(ref lhs, ref rhs) => { // lhs[rhs]
|
||||
if !self.walk_overloaded_operator(expr,
|
||||
&**lhs,
|
||||
vec![&**rhs],
|
||||
@ -403,29 +407,29 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprRange(ref start, ref end) => {
|
||||
hir::ExprRange(ref start, ref end) => {
|
||||
start.as_ref().map(|e| self.consume_expr(&**e));
|
||||
end.as_ref().map(|e| self.consume_expr(&**e));
|
||||
}
|
||||
|
||||
ast::ExprCall(ref callee, ref args) => { // callee(args)
|
||||
hir::ExprCall(ref callee, ref args) => { // callee(args)
|
||||
self.walk_callee(expr, &**callee);
|
||||
self.consume_exprs(args);
|
||||
}
|
||||
|
||||
ast::ExprMethodCall(_, _, ref args) => { // callee.m(args)
|
||||
hir::ExprMethodCall(_, _, ref args) => { // callee.m(args)
|
||||
self.consume_exprs(args);
|
||||
}
|
||||
|
||||
ast::ExprStruct(_, ref fields, ref opt_with) => {
|
||||
hir::ExprStruct(_, ref fields, ref opt_with) => {
|
||||
self.walk_struct_expr(expr, fields, opt_with);
|
||||
}
|
||||
|
||||
ast::ExprTup(ref exprs) => {
|
||||
hir::ExprTup(ref exprs) => {
|
||||
self.consume_exprs(exprs);
|
||||
}
|
||||
|
||||
ast::ExprIf(ref cond_expr, ref then_blk, ref opt_else_expr) => {
|
||||
hir::ExprIf(ref cond_expr, ref then_blk, ref opt_else_expr) => {
|
||||
self.consume_expr(&**cond_expr);
|
||||
self.walk_block(&**then_blk);
|
||||
if let Some(ref else_expr) = *opt_else_expr {
|
||||
@ -433,11 +437,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprIfLet(..) => {
|
||||
self.tcx().sess.span_bug(expr.span, "non-desugared ExprIfLet");
|
||||
}
|
||||
|
||||
ast::ExprMatch(ref discr, ref arms, _) => {
|
||||
hir::ExprMatch(ref discr, ref arms, _) => {
|
||||
let discr_cmt = return_if_err!(self.mc.cat_expr(&**discr));
|
||||
self.borrow_expr(&**discr, ty::ReEmpty, ty::ImmBorrow, MatchDiscriminant);
|
||||
|
||||
@ -449,11 +449,11 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprVec(ref exprs) => {
|
||||
hir::ExprVec(ref exprs) => {
|
||||
self.consume_exprs(exprs);
|
||||
}
|
||||
|
||||
ast::ExprAddrOf(m, ref base) => { // &base
|
||||
hir::ExprAddrOf(m, ref base) => { // &base
|
||||
// make sure that the thing we are pointing out stays valid
|
||||
// for the lifetime `scope_r` of the resulting ptr:
|
||||
let expr_ty = return_if_err!(self.typer.node_ty(expr.id));
|
||||
@ -463,7 +463,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprInlineAsm(ref ia) => {
|
||||
hir::ExprInlineAsm(ref ia) => {
|
||||
for &(_, ref input) in &ia.inputs {
|
||||
self.consume_expr(&**input);
|
||||
}
|
||||
@ -474,29 +474,21 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprBreak(..) |
|
||||
ast::ExprAgain(..) |
|
||||
ast::ExprLit(..) => {}
|
||||
hir::ExprBreak(..) |
|
||||
hir::ExprAgain(..) |
|
||||
hir::ExprLit(..) => {}
|
||||
|
||||
ast::ExprLoop(ref blk, _) => {
|
||||
hir::ExprLoop(ref blk, _) => {
|
||||
self.walk_block(&**blk);
|
||||
}
|
||||
|
||||
ast::ExprWhile(ref cond_expr, ref blk, _) => {
|
||||
hir::ExprWhile(ref cond_expr, ref blk, _) => {
|
||||
self.consume_expr(&**cond_expr);
|
||||
self.walk_block(&**blk);
|
||||
}
|
||||
|
||||
ast::ExprWhileLet(..) => {
|
||||
self.tcx().sess.span_bug(expr.span, "non-desugared ExprWhileLet");
|
||||
}
|
||||
|
||||
ast::ExprForLoop(..) => {
|
||||
self.tcx().sess.span_bug(expr.span, "non-desugared ExprForLoop");
|
||||
}
|
||||
|
||||
ast::ExprUnary(op, ref lhs) => {
|
||||
let pass_args = if ast_util::is_by_value_unop(op) {
|
||||
hir::ExprUnary(op, ref lhs) => {
|
||||
let pass_args = if ::rustc_front::util::is_by_value_unop(op) {
|
||||
PassArgs::ByValue
|
||||
} else {
|
||||
PassArgs::ByRef
|
||||
@ -507,8 +499,8 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprBinary(op, ref lhs, ref rhs) => {
|
||||
let pass_args = if ast_util::is_by_value_binop(op.node) {
|
||||
hir::ExprBinary(op, ref lhs, ref rhs) => {
|
||||
let pass_args = if ::rustc_front::util::is_by_value_binop(op.node) {
|
||||
PassArgs::ByValue
|
||||
} else {
|
||||
PassArgs::ByRef
|
||||
@ -520,42 +512,42 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprBlock(ref blk) => {
|
||||
hir::ExprBlock(ref blk) => {
|
||||
self.walk_block(&**blk);
|
||||
}
|
||||
|
||||
ast::ExprRet(ref opt_expr) => {
|
||||
hir::ExprRet(ref opt_expr) => {
|
||||
if let Some(ref expr) = *opt_expr {
|
||||
self.consume_expr(&**expr);
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprAssign(ref lhs, ref rhs) => {
|
||||
hir::ExprAssign(ref lhs, ref rhs) => {
|
||||
self.mutate_expr(expr, &**lhs, JustWrite);
|
||||
self.consume_expr(&**rhs);
|
||||
}
|
||||
|
||||
ast::ExprCast(ref base, _) => {
|
||||
hir::ExprCast(ref base, _) => {
|
||||
self.consume_expr(&**base);
|
||||
}
|
||||
|
||||
ast::ExprAssignOp(_, ref lhs, ref rhs) => {
|
||||
hir::ExprAssignOp(_, ref lhs, ref rhs) => {
|
||||
// This will have to change if/when we support
|
||||
// overloaded operators for `+=` and so forth.
|
||||
self.mutate_expr(expr, &**lhs, WriteAndRead);
|
||||
self.consume_expr(&**rhs);
|
||||
}
|
||||
|
||||
ast::ExprRepeat(ref base, ref count) => {
|
||||
hir::ExprRepeat(ref base, ref count) => {
|
||||
self.consume_expr(&**base);
|
||||
self.consume_expr(&**count);
|
||||
}
|
||||
|
||||
ast::ExprClosure(..) => {
|
||||
hir::ExprClosure(..) => {
|
||||
self.walk_captures(expr)
|
||||
}
|
||||
|
||||
ast::ExprBox(ref place, ref base) => {
|
||||
hir::ExprBox(ref place, ref base) => {
|
||||
match *place {
|
||||
Some(ref place) => self.consume_expr(&**place),
|
||||
None => {}
|
||||
@ -567,16 +559,10 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
"box with explicit place remains after expansion");
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprMac(..) => {
|
||||
self.tcx().sess.span_bug(
|
||||
expr.span,
|
||||
"macro expression remains after expansion");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn walk_callee(&mut self, call: &ast::Expr, callee: &ast::Expr) {
|
||||
fn walk_callee(&mut self, call: &hir::Expr, callee: &hir::Expr) {
|
||||
let callee_ty = return_if_err!(self.typer.expr_ty_adjusted(callee));
|
||||
debug!("walk_callee: callee={:?} callee_ty={:?}",
|
||||
callee, callee_ty);
|
||||
@ -617,33 +603,29 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn walk_stmt(&mut self, stmt: &ast::Stmt) {
|
||||
fn walk_stmt(&mut self, stmt: &hir::Stmt) {
|
||||
match stmt.node {
|
||||
ast::StmtDecl(ref decl, _) => {
|
||||
hir::StmtDecl(ref decl, _) => {
|
||||
match decl.node {
|
||||
ast::DeclLocal(ref local) => {
|
||||
hir::DeclLocal(ref local) => {
|
||||
self.walk_local(&**local);
|
||||
}
|
||||
|
||||
ast::DeclItem(_) => {
|
||||
hir::DeclItem(_) => {
|
||||
// we don't visit nested items in this visitor,
|
||||
// only the fn body we were given.
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ast::StmtExpr(ref expr, _) |
|
||||
ast::StmtSemi(ref expr, _) => {
|
||||
hir::StmtExpr(ref expr, _) |
|
||||
hir::StmtSemi(ref expr, _) => {
|
||||
self.consume_expr(&**expr);
|
||||
}
|
||||
|
||||
ast::StmtMac(..) => {
|
||||
self.tcx().sess.span_bug(stmt.span, "unexpanded stmt macro");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn walk_local(&mut self, local: &ast::Local) {
|
||||
fn walk_local(&mut self, local: &hir::Local) {
|
||||
match local.init {
|
||||
None => {
|
||||
let delegate = &mut self.delegate;
|
||||
@ -667,7 +649,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
|
||||
/// Indicates that the value of `blk` will be consumed, meaning either copied or moved
|
||||
/// depending on its type.
|
||||
fn walk_block(&mut self, blk: &ast::Block) {
|
||||
fn walk_block(&mut self, blk: &hir::Block) {
|
||||
debug!("walk_block(blk.id={})", blk.id);
|
||||
|
||||
for stmt in &blk.stmts {
|
||||
@ -680,9 +662,9 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
|
||||
fn walk_struct_expr(&mut self,
|
||||
_expr: &ast::Expr,
|
||||
fields: &Vec<ast::Field>,
|
||||
opt_with: &Option<P<ast::Expr>>) {
|
||||
_expr: &hir::Expr,
|
||||
fields: &Vec<hir::Field>,
|
||||
opt_with: &Option<P<hir::Expr>>) {
|
||||
// Consume the expressions supplying values for each field.
|
||||
for field in fields {
|
||||
self.consume_expr(&*field.expr);
|
||||
@ -727,7 +709,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
self.walk_expr(with_expr);
|
||||
|
||||
fn contains_field_named(field: ty::FieldDef,
|
||||
fields: &Vec<ast::Field>)
|
||||
fields: &Vec<hir::Field>)
|
||||
-> bool
|
||||
{
|
||||
fields.iter().any(
|
||||
@ -738,7 +720,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
// Invoke the appropriate delegate calls for anything that gets
|
||||
// consumed or borrowed as part of the automatic adjustment
|
||||
// process.
|
||||
fn walk_adjustment(&mut self, expr: &ast::Expr) {
|
||||
fn walk_adjustment(&mut self, expr: &hir::Expr) {
|
||||
let typer = self.typer;
|
||||
//NOTE(@jroesch): mixed RefCell borrow causes crash
|
||||
let adj = typer.adjustments().get(&expr.id).map(|x| x.clone());
|
||||
@ -764,7 +746,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
/// `(*x)` where `x` is of type `Rc<T>`, then this in fact is equivalent to `x.deref()`. Since
|
||||
/// `deref()` is declared with `&self`, this is an autoref of `x`.
|
||||
fn walk_autoderefs(&mut self,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
autoderefs: usize) {
|
||||
debug!("walk_autoderefs expr={:?} autoderefs={}", expr, autoderefs);
|
||||
|
||||
@ -795,7 +777,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
|
||||
fn walk_autoderefref(&mut self,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
adj: &ty::AutoDerefRef<'tcx>) {
|
||||
debug!("walk_autoderefref expr={:?} adj={:?}",
|
||||
expr,
|
||||
@ -825,7 +807,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
/// `cmt` for the rvalue that will be produced by introduced an
|
||||
/// autoref.
|
||||
fn walk_autoref(&mut self,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
cmt_base: mc::cmt<'tcx>,
|
||||
opt_autoref: Option<ty::AutoRef<'tcx>>)
|
||||
-> mc::cmt<'tcx>
|
||||
@ -890,9 +872,9 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
// recursively processing the input arguments, and thus the caller
|
||||
// should not do so.
|
||||
fn walk_overloaded_operator(&mut self,
|
||||
expr: &ast::Expr,
|
||||
receiver: &ast::Expr,
|
||||
rhs: Vec<&ast::Expr>,
|
||||
expr: &hir::Expr,
|
||||
receiver: &hir::Expr,
|
||||
rhs: Vec<&hir::Expr>,
|
||||
pass_args: PassArgs)
|
||||
-> bool
|
||||
{
|
||||
@ -927,7 +909,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
return true;
|
||||
}
|
||||
|
||||
fn arm_move_mode(&mut self, discr_cmt: mc::cmt<'tcx>, arm: &ast::Arm) -> TrackMatchMode {
|
||||
fn arm_move_mode(&mut self, discr_cmt: mc::cmt<'tcx>, arm: &hir::Arm) -> TrackMatchMode {
|
||||
let mut mode = Unknown;
|
||||
for pat in &arm.pats {
|
||||
self.determine_pat_move_mode(discr_cmt.clone(), &**pat, &mut mode);
|
||||
@ -935,7 +917,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
mode
|
||||
}
|
||||
|
||||
fn walk_arm(&mut self, discr_cmt: mc::cmt<'tcx>, arm: &ast::Arm, mode: MatchMode) {
|
||||
fn walk_arm(&mut self, discr_cmt: mc::cmt<'tcx>, arm: &hir::Arm, mode: MatchMode) {
|
||||
for pat in &arm.pats {
|
||||
self.walk_pat(discr_cmt.clone(), &**pat, mode);
|
||||
}
|
||||
@ -949,7 +931,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
|
||||
/// Walks an pat that occurs in isolation (i.e. top-level of fn
|
||||
/// arg or let binding. *Not* a match arm or nested pat.)
|
||||
fn walk_irrefutable_pat(&mut self, cmt_discr: mc::cmt<'tcx>, pat: &ast::Pat) {
|
||||
fn walk_irrefutable_pat(&mut self, cmt_discr: mc::cmt<'tcx>, pat: &hir::Pat) {
|
||||
let mut mode = Unknown;
|
||||
self.determine_pat_move_mode(cmt_discr.clone(), pat, &mut mode);
|
||||
let mode = mode.match_mode();
|
||||
@ -961,7 +943,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
/// copy, or borrow.
|
||||
fn determine_pat_move_mode(&mut self,
|
||||
cmt_discr: mc::cmt<'tcx>,
|
||||
pat: &ast::Pat,
|
||||
pat: &hir::Pat,
|
||||
mode: &mut TrackMatchMode) {
|
||||
debug!("determine_pat_move_mode cmt_discr={:?} pat={:?}", cmt_discr,
|
||||
pat);
|
||||
@ -970,9 +952,9 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
let def_map = &self.tcx().def_map;
|
||||
if pat_util::pat_is_binding(def_map, pat) {
|
||||
match pat.node {
|
||||
ast::PatIdent(ast::BindByRef(_), _, _) =>
|
||||
hir::PatIdent(hir::BindByRef(_), _, _) =>
|
||||
mode.lub(BorrowingMatch),
|
||||
ast::PatIdent(ast::BindByValue(_), _, _) => {
|
||||
hir::PatIdent(hir::BindByValue(_), _, _) => {
|
||||
match copy_or_move(self.typer, &cmt_pat, PatBindingMove) {
|
||||
Copy => mode.lub(CopyingMatch),
|
||||
Move(_) => mode.lub(MovingMatch),
|
||||
@ -993,7 +975,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
/// also `walk_irrefutable_pat` for patterns that stand alone).
|
||||
fn walk_pat(&mut self,
|
||||
cmt_discr: mc::cmt<'tcx>,
|
||||
pat: &ast::Pat,
|
||||
pat: &hir::Pat,
|
||||
match_mode: MatchMode) {
|
||||
debug!("walk_pat cmt_discr={:?} pat={:?}", cmt_discr,
|
||||
pat);
|
||||
@ -1026,14 +1008,14 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
|
||||
// It is also a borrow or copy/move of the value being matched.
|
||||
match pat.node {
|
||||
ast::PatIdent(ast::BindByRef(m), _, _) => {
|
||||
hir::PatIdent(hir::BindByRef(m), _, _) => {
|
||||
if let ty::TyRef(&r, _) = pat_ty.sty {
|
||||
let bk = ty::BorrowKind::from_mutbl(m);
|
||||
delegate.borrow(pat.id, pat.span, cmt_pat,
|
||||
r, bk, RefBinding);
|
||||
}
|
||||
}
|
||||
ast::PatIdent(ast::BindByValue(_), _, _) => {
|
||||
hir::PatIdent(hir::BindByValue(_), _, _) => {
|
||||
let mode = copy_or_move(typer, &cmt_pat, PatBindingMove);
|
||||
debug!("walk_pat binding consuming pat");
|
||||
delegate.consume_pat(pat, cmt_pat, mode);
|
||||
@ -1046,7 +1028,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
} else {
|
||||
match pat.node {
|
||||
ast::PatVec(_, Some(ref slice_pat), _) => {
|
||||
hir::PatVec(_, Some(ref slice_pat), _) => {
|
||||
// The `slice_pat` here creates a slice into
|
||||
// the original vector. This is effectively a
|
||||
// borrow of the elements of the vector being
|
||||
@ -1094,8 +1076,8 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
let tcx = typer.tcx;
|
||||
|
||||
match pat.node {
|
||||
ast::PatEnum(_, _) | ast::PatQPath(..) |
|
||||
ast::PatIdent(_, _, None) | ast::PatStruct(..) => {
|
||||
hir::PatEnum(_, _) | hir::PatQPath(..) |
|
||||
hir::PatIdent(_, _, None) | hir::PatStruct(..) => {
|
||||
match def_map.get(&pat.id).map(|d| d.full_def()) {
|
||||
None => {
|
||||
// no definition found: pat is not a
|
||||
@ -1169,15 +1151,15 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatIdent(_, _, Some(_)) => {
|
||||
hir::PatIdent(_, _, Some(_)) => {
|
||||
// Do nothing; this is a binding (not a enum
|
||||
// variant or struct), and the cat_pattern call
|
||||
// will visit the substructure recursively.
|
||||
}
|
||||
|
||||
ast::PatWild(_) | ast::PatTup(..) | ast::PatBox(..) |
|
||||
ast::PatRegion(..) | ast::PatLit(..) | ast::PatRange(..) |
|
||||
ast::PatVec(..) | ast::PatMac(..) => {
|
||||
hir::PatWild(_) | hir::PatTup(..) | hir::PatBox(..) |
|
||||
hir::PatRegion(..) | hir::PatLit(..) | hir::PatRange(..) |
|
||||
hir::PatVec(..) => {
|
||||
// Similarly, each of these cases does not
|
||||
// correspond to a enum variant or struct, so we
|
||||
// do not do any `matched_pat` calls for these
|
||||
@ -1187,7 +1169,7 @@ impl<'d,'t,'a,'tcx> ExprUseVisitor<'d,'t,'a,'tcx> {
|
||||
}));
|
||||
}
|
||||
|
||||
fn walk_captures(&mut self, closure_expr: &ast::Expr) {
|
||||
fn walk_captures(&mut self, closure_expr: &hir::Expr) {
|
||||
debug!("walk_captures({:?})", closure_expr);
|
||||
|
||||
self.tcx().with_freevars(closure_expr.id, |freevars| {
|
||||
|
@ -10,7 +10,7 @@
|
||||
|
||||
use middle::def_id::DefId;
|
||||
use middle::ty::{self, Ty};
|
||||
use syntax::ast;
|
||||
use rustc_front::hir;
|
||||
|
||||
use self::SimplifiedType::*;
|
||||
|
||||
@ -19,9 +19,9 @@ use self::SimplifiedType::*;
|
||||
pub enum SimplifiedType {
|
||||
BoolSimplifiedType,
|
||||
CharSimplifiedType,
|
||||
IntSimplifiedType(ast::IntTy),
|
||||
UintSimplifiedType(ast::UintTy),
|
||||
FloatSimplifiedType(ast::FloatTy),
|
||||
IntSimplifiedType(hir::IntTy),
|
||||
UintSimplifiedType(hir::UintTy),
|
||||
FloatSimplifiedType(hir::FloatTy),
|
||||
EnumSimplifiedType(DefId),
|
||||
StrSimplifiedType,
|
||||
VecSimplifiedType,
|
||||
|
@ -48,8 +48,8 @@ use middle::ty_fold;
|
||||
use middle::ty_fold::{TypeFolder, TypeFoldable};
|
||||
use middle::ty_relate::{self, Relate, RelateResult, TypeRelation};
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use rustc_front::hir;
|
||||
|
||||
#[derive(Clone)]
|
||||
pub struct CombineFields<'a, 'tcx: 'a> {
|
||||
@ -138,7 +138,7 @@ fn unify_integral_variable<'a,'tcx>(infcx: &InferCtxt<'a,'tcx>,
|
||||
fn unify_float_variable<'a,'tcx>(infcx: &InferCtxt<'a,'tcx>,
|
||||
vid_is_expected: bool,
|
||||
vid: ty::FloatVid,
|
||||
val: ast::FloatTy)
|
||||
val: hir::FloatTy)
|
||||
-> RelateResult<'tcx, Ty<'tcx>>
|
||||
{
|
||||
try!(infcx
|
||||
@ -388,7 +388,7 @@ fn int_unification_error<'tcx>(a_is_expected: bool, v: (ty::IntVarValue, ty::Int
|
||||
}
|
||||
|
||||
fn float_unification_error<'tcx>(a_is_expected: bool,
|
||||
v: (ast::FloatTy, ast::FloatTy))
|
||||
v: (hir::FloatTy, hir::FloatTy))
|
||||
-> ty::TypeError<'tcx>
|
||||
{
|
||||
let (a, b) = v;
|
||||
|
@ -72,7 +72,11 @@ use super::region_inference::ProcessedErrors;
|
||||
use super::region_inference::SameRegions;
|
||||
|
||||
use std::collections::HashSet;
|
||||
use ast_map;
|
||||
|
||||
use front::map as ast_map;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::print::pprust;
|
||||
|
||||
use middle::def;
|
||||
use middle::infer;
|
||||
use middle::region;
|
||||
@ -84,11 +88,9 @@ use std::cell::{Cell, RefCell};
|
||||
use std::char::from_u32;
|
||||
use std::fmt;
|
||||
use syntax::ast;
|
||||
use syntax::ast_util::name_to_dummy_lifetime;
|
||||
use syntax::owned_slice::OwnedSlice;
|
||||
use syntax::codemap::{Pos, Span};
|
||||
use syntax::codemap::{self, Pos, Span};
|
||||
use syntax::parse::token;
|
||||
use syntax::print::pprust;
|
||||
use syntax::ptr::P;
|
||||
|
||||
impl<'tcx> ty::ctxt<'tcx> {
|
||||
@ -96,13 +98,13 @@ impl<'tcx> ty::ctxt<'tcx> {
|
||||
prefix: &str,
|
||||
region: ty::Region,
|
||||
suffix: &str) {
|
||||
fn item_scope_tag(item: &ast::Item) -> &'static str {
|
||||
fn item_scope_tag(item: &hir::Item) -> &'static str {
|
||||
match item.node {
|
||||
ast::ItemImpl(..) => "impl",
|
||||
ast::ItemStruct(..) => "struct",
|
||||
ast::ItemEnum(..) => "enum",
|
||||
ast::ItemTrait(..) => "trait",
|
||||
ast::ItemFn(..) => "function body",
|
||||
hir::ItemImpl(..) => "impl",
|
||||
hir::ItemStruct(..) => "struct",
|
||||
hir::ItemEnum(..) => "enum",
|
||||
hir::ItemTrait(..) => "trait",
|
||||
hir::ItemFn(..) => "function body",
|
||||
_ => "item"
|
||||
}
|
||||
}
|
||||
@ -128,12 +130,12 @@ impl<'tcx> ty::ctxt<'tcx> {
|
||||
let tag = match self.map.find(scope.node_id(&self.region_maps)) {
|
||||
Some(ast_map::NodeBlock(_)) => "block",
|
||||
Some(ast_map::NodeExpr(expr)) => match expr.node {
|
||||
ast::ExprCall(..) => "call",
|
||||
ast::ExprMethodCall(..) => "method call",
|
||||
ast::ExprMatch(_, _, ast::MatchSource::IfLetDesugar { .. }) => "if let",
|
||||
ast::ExprMatch(_, _, ast::MatchSource::WhileLetDesugar) => "while let",
|
||||
ast::ExprMatch(_, _, ast::MatchSource::ForLoopDesugar) => "for",
|
||||
ast::ExprMatch(..) => "match",
|
||||
hir::ExprCall(..) => "call",
|
||||
hir::ExprMethodCall(..) => "method call",
|
||||
hir::ExprMatch(_, _, hir::MatchSource::IfLetDesugar { .. }) => "if let",
|
||||
hir::ExprMatch(_, _, hir::MatchSource::WhileLetDesugar) => "while let",
|
||||
hir::ExprMatch(_, _, hir::MatchSource::ForLoopDesugar) => "for",
|
||||
hir::ExprMatch(..) => "match",
|
||||
_ => "expression",
|
||||
},
|
||||
Some(ast_map::NodeStmt(_)) => "statement",
|
||||
@ -275,12 +277,12 @@ trait ErrorReportingHelpers<'tcx> {
|
||||
origin: &SubregionOrigin<'tcx>);
|
||||
|
||||
fn give_expl_lifetime_param(&self,
|
||||
decl: &ast::FnDecl,
|
||||
unsafety: ast::Unsafety,
|
||||
constness: ast::Constness,
|
||||
decl: &hir::FnDecl,
|
||||
unsafety: hir::Unsafety,
|
||||
constness: hir::Constness,
|
||||
ident: ast::Ident,
|
||||
opt_explicit_self: Option<&ast::ExplicitSelf_>,
|
||||
generics: &ast::Generics,
|
||||
opt_explicit_self: Option<&hir::ExplicitSelf_>,
|
||||
generics: &hir::Generics,
|
||||
span: Span);
|
||||
}
|
||||
|
||||
@ -432,7 +434,7 @@ impl<'a, 'tcx> ErrorReporting<'tcx> for InferCtxt<'a, 'tcx> {
|
||||
match parent_node {
|
||||
Some(node) => match node {
|
||||
ast_map::NodeItem(item) => match item.node {
|
||||
ast::ItemFn(..) => {
|
||||
hir::ItemFn(..) => {
|
||||
Some(FreeRegionsFromSameFn::new(fr1, fr2, scope_id))
|
||||
},
|
||||
_ => None
|
||||
@ -944,7 +946,7 @@ impl<'a, 'tcx> ErrorReporting<'tcx> for InferCtxt<'a, 'tcx> {
|
||||
Some(ref node) => match *node {
|
||||
ast_map::NodeItem(ref item) => {
|
||||
match item.node {
|
||||
ast::ItemFn(ref fn_decl, unsafety, constness, _, ref gen, _) => {
|
||||
hir::ItemFn(ref fn_decl, unsafety, constness, _, ref gen, _) => {
|
||||
Some((fn_decl, gen, unsafety, constness,
|
||||
item.ident, None, item.span))
|
||||
},
|
||||
@ -953,7 +955,7 @@ impl<'a, 'tcx> ErrorReporting<'tcx> for InferCtxt<'a, 'tcx> {
|
||||
}
|
||||
ast_map::NodeImplItem(item) => {
|
||||
match item.node {
|
||||
ast::MethodImplItem(ref sig, _) => {
|
||||
hir::MethodImplItem(ref sig, _) => {
|
||||
Some((&sig.decl,
|
||||
&sig.generics,
|
||||
sig.unsafety,
|
||||
@ -962,13 +964,12 @@ impl<'a, 'tcx> ErrorReporting<'tcx> for InferCtxt<'a, 'tcx> {
|
||||
Some(&sig.explicit_self.node),
|
||||
item.span))
|
||||
}
|
||||
ast::MacImplItem(_) => self.tcx.sess.bug("unexpanded macro"),
|
||||
_ => None,
|
||||
}
|
||||
},
|
||||
ast_map::NodeTraitItem(item) => {
|
||||
match item.node {
|
||||
ast::MethodTraitItem(ref sig, Some(_)) => {
|
||||
hir::MethodTraitItem(ref sig, Some(_)) => {
|
||||
Some((&sig.decl,
|
||||
&sig.generics,
|
||||
sig.unsafety,
|
||||
@ -995,7 +996,7 @@ impl<'a, 'tcx> ErrorReporting<'tcx> for InferCtxt<'a, 'tcx> {
|
||||
}
|
||||
|
||||
struct RebuildPathInfo<'a> {
|
||||
path: &'a ast::Path,
|
||||
path: &'a hir::Path,
|
||||
// indexes to insert lifetime on path.lifetimes
|
||||
indexes: Vec<u32>,
|
||||
// number of lifetimes we expect to see on the type referred by `path`
|
||||
@ -1007,9 +1008,9 @@ struct RebuildPathInfo<'a> {
|
||||
|
||||
struct Rebuilder<'a, 'tcx: 'a> {
|
||||
tcx: &'a ty::ctxt<'tcx>,
|
||||
fn_decl: &'a ast::FnDecl,
|
||||
expl_self_opt: Option<&'a ast::ExplicitSelf_>,
|
||||
generics: &'a ast::Generics,
|
||||
fn_decl: &'a hir::FnDecl,
|
||||
expl_self_opt: Option<&'a hir::ExplicitSelf_>,
|
||||
generics: &'a hir::Generics,
|
||||
same_regions: &'a [SameRegions],
|
||||
life_giver: &'a LifeGiver,
|
||||
cur_anon: Cell<u32>,
|
||||
@ -1023,9 +1024,9 @@ enum FreshOrKept {
|
||||
|
||||
impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
fn new(tcx: &'a ty::ctxt<'tcx>,
|
||||
fn_decl: &'a ast::FnDecl,
|
||||
expl_self_opt: Option<&'a ast::ExplicitSelf_>,
|
||||
generics: &'a ast::Generics,
|
||||
fn_decl: &'a hir::FnDecl,
|
||||
expl_self_opt: Option<&'a hir::ExplicitSelf_>,
|
||||
generics: &'a hir::Generics,
|
||||
same_regions: &'a [SameRegions],
|
||||
life_giver: &'a LifeGiver)
|
||||
-> Rebuilder<'a, 'tcx> {
|
||||
@ -1042,7 +1043,7 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn rebuild(&self)
|
||||
-> (ast::FnDecl, Option<ast::ExplicitSelf_>, ast::Generics) {
|
||||
-> (hir::FnDecl, Option<hir::ExplicitSelf_>, hir::Generics) {
|
||||
let mut expl_self_opt = self.expl_self_opt.cloned();
|
||||
let mut inputs = self.fn_decl.inputs.clone();
|
||||
let mut output = self.fn_decl.output.clone();
|
||||
@ -1075,7 +1076,7 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
&all_region_names,
|
||||
ty_params,
|
||||
where_clause);
|
||||
let new_fn_decl = ast::FnDecl {
|
||||
let new_fn_decl = hir::FnDecl {
|
||||
inputs: inputs,
|
||||
output: output,
|
||||
variadic: self.fn_decl.variadic
|
||||
@ -1085,7 +1086,7 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
|
||||
fn pick_lifetime(&self,
|
||||
region_names: &HashSet<ast::Name>)
|
||||
-> (ast::Lifetime, FreshOrKept) {
|
||||
-> (hir::Lifetime, FreshOrKept) {
|
||||
if !region_names.is_empty() {
|
||||
// It's not necessary to convert the set of region names to a
|
||||
// vector of string and then sort them. However, it makes the
|
||||
@ -1158,15 +1159,15 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn rebuild_ty_params(&self,
|
||||
ty_params: OwnedSlice<ast::TyParam>,
|
||||
lifetime: ast::Lifetime,
|
||||
ty_params: OwnedSlice<hir::TyParam>,
|
||||
lifetime: hir::Lifetime,
|
||||
region_names: &HashSet<ast::Name>)
|
||||
-> OwnedSlice<ast::TyParam> {
|
||||
-> OwnedSlice<hir::TyParam> {
|
||||
ty_params.map(|ty_param| {
|
||||
let bounds = self.rebuild_ty_param_bounds(ty_param.bounds.clone(),
|
||||
lifetime,
|
||||
region_names);
|
||||
ast::TyParam {
|
||||
hir::TyParam {
|
||||
ident: ty_param.ident,
|
||||
id: ty_param.id,
|
||||
bounds: bounds,
|
||||
@ -1177,19 +1178,19 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn rebuild_ty_param_bounds(&self,
|
||||
ty_param_bounds: OwnedSlice<ast::TyParamBound>,
|
||||
lifetime: ast::Lifetime,
|
||||
ty_param_bounds: OwnedSlice<hir::TyParamBound>,
|
||||
lifetime: hir::Lifetime,
|
||||
region_names: &HashSet<ast::Name>)
|
||||
-> OwnedSlice<ast::TyParamBound> {
|
||||
-> OwnedSlice<hir::TyParamBound> {
|
||||
ty_param_bounds.map(|tpb| {
|
||||
match tpb {
|
||||
&ast::RegionTyParamBound(lt) => {
|
||||
&hir::RegionTyParamBound(lt) => {
|
||||
// FIXME -- it's unclear whether I'm supposed to
|
||||
// substitute lifetime here. I suspect we need to
|
||||
// be passing down a map.
|
||||
ast::RegionTyParamBound(lt)
|
||||
hir::RegionTyParamBound(lt)
|
||||
}
|
||||
&ast::TraitTyParamBound(ref poly_tr, modifier) => {
|
||||
&hir::TraitTyParamBound(ref poly_tr, modifier) => {
|
||||
let tr = &poly_tr.trait_ref;
|
||||
let last_seg = tr.path.segments.last().unwrap();
|
||||
let mut insert = Vec::new();
|
||||
@ -1207,9 +1208,9 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
region_names: region_names
|
||||
};
|
||||
let new_path = self.rebuild_path(rebuild_info, lifetime);
|
||||
ast::TraitTyParamBound(ast::PolyTraitRef {
|
||||
hir::TraitTyParamBound(hir::PolyTraitRef {
|
||||
bound_lifetimes: poly_tr.bound_lifetimes.clone(),
|
||||
trait_ref: ast::TraitRef {
|
||||
trait_ref: hir::TraitRef {
|
||||
path: new_path,
|
||||
ref_id: tr.ref_id,
|
||||
},
|
||||
@ -1221,23 +1222,23 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn rebuild_expl_self(&self,
|
||||
expl_self_opt: Option<ast::ExplicitSelf_>,
|
||||
lifetime: ast::Lifetime,
|
||||
expl_self_opt: Option<hir::ExplicitSelf_>,
|
||||
lifetime: hir::Lifetime,
|
||||
anon_nums: &HashSet<u32>,
|
||||
region_names: &HashSet<ast::Name>)
|
||||
-> Option<ast::ExplicitSelf_> {
|
||||
-> Option<hir::ExplicitSelf_> {
|
||||
match expl_self_opt {
|
||||
Some(ref expl_self) => match *expl_self {
|
||||
ast::SelfRegion(lt_opt, muta, id) => match lt_opt {
|
||||
hir::SelfRegion(lt_opt, muta, id) => match lt_opt {
|
||||
Some(lt) => if region_names.contains(<.name) {
|
||||
return Some(ast::SelfRegion(Some(lifetime), muta, id));
|
||||
return Some(hir::SelfRegion(Some(lifetime), muta, id));
|
||||
},
|
||||
None => {
|
||||
let anon = self.cur_anon.get();
|
||||
self.inc_and_offset_cur_anon(1);
|
||||
if anon_nums.contains(&anon) {
|
||||
self.track_anon(anon);
|
||||
return Some(ast::SelfRegion(Some(lifetime), muta, id));
|
||||
return Some(hir::SelfRegion(Some(lifetime), muta, id));
|
||||
}
|
||||
}
|
||||
},
|
||||
@ -1249,16 +1250,16 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn rebuild_generics(&self,
|
||||
generics: &ast::Generics,
|
||||
add: &Vec<ast::Lifetime>,
|
||||
generics: &hir::Generics,
|
||||
add: &Vec<hir::Lifetime>,
|
||||
keep: &HashSet<ast::Name>,
|
||||
remove: &HashSet<ast::Name>,
|
||||
ty_params: OwnedSlice<ast::TyParam>,
|
||||
where_clause: ast::WhereClause)
|
||||
-> ast::Generics {
|
||||
ty_params: OwnedSlice<hir::TyParam>,
|
||||
where_clause: hir::WhereClause)
|
||||
-> hir::Generics {
|
||||
let mut lifetimes = Vec::new();
|
||||
for lt in add {
|
||||
lifetimes.push(ast::LifetimeDef { lifetime: *lt,
|
||||
lifetimes.push(hir::LifetimeDef { lifetime: *lt,
|
||||
bounds: Vec::new() });
|
||||
}
|
||||
for lt in &generics.lifetimes {
|
||||
@ -1267,7 +1268,7 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
lifetimes.push((*lt).clone());
|
||||
}
|
||||
}
|
||||
ast::Generics {
|
||||
hir::Generics {
|
||||
lifetimes: lifetimes,
|
||||
ty_params: ty_params,
|
||||
where_clause: where_clause,
|
||||
@ -1275,16 +1276,16 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn rebuild_args_ty(&self,
|
||||
inputs: &[ast::Arg],
|
||||
lifetime: ast::Lifetime,
|
||||
inputs: &[hir::Arg],
|
||||
lifetime: hir::Lifetime,
|
||||
anon_nums: &HashSet<u32>,
|
||||
region_names: &HashSet<ast::Name>)
|
||||
-> Vec<ast::Arg> {
|
||||
-> Vec<hir::Arg> {
|
||||
let mut new_inputs = Vec::new();
|
||||
for arg in inputs {
|
||||
let new_ty = self.rebuild_arg_ty_or_output(&*arg.ty, lifetime,
|
||||
anon_nums, region_names);
|
||||
let possibly_new_arg = ast::Arg {
|
||||
let possibly_new_arg = hir::Arg {
|
||||
ty: new_ty,
|
||||
pat: arg.pat.clone(),
|
||||
id: arg.id
|
||||
@ -1294,31 +1295,31 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
new_inputs
|
||||
}
|
||||
|
||||
fn rebuild_output(&self, ty: &ast::FunctionRetTy,
|
||||
lifetime: ast::Lifetime,
|
||||
fn rebuild_output(&self, ty: &hir::FunctionRetTy,
|
||||
lifetime: hir::Lifetime,
|
||||
anon_nums: &HashSet<u32>,
|
||||
region_names: &HashSet<ast::Name>) -> ast::FunctionRetTy {
|
||||
region_names: &HashSet<ast::Name>) -> hir::FunctionRetTy {
|
||||
match *ty {
|
||||
ast::Return(ref ret_ty) => ast::Return(
|
||||
hir::Return(ref ret_ty) => hir::Return(
|
||||
self.rebuild_arg_ty_or_output(&**ret_ty, lifetime, anon_nums, region_names)
|
||||
),
|
||||
ast::DefaultReturn(span) => ast::DefaultReturn(span),
|
||||
ast::NoReturn(span) => ast::NoReturn(span)
|
||||
hir::DefaultReturn(span) => hir::DefaultReturn(span),
|
||||
hir::NoReturn(span) => hir::NoReturn(span)
|
||||
}
|
||||
}
|
||||
|
||||
fn rebuild_arg_ty_or_output(&self,
|
||||
ty: &ast::Ty,
|
||||
lifetime: ast::Lifetime,
|
||||
ty: &hir::Ty,
|
||||
lifetime: hir::Lifetime,
|
||||
anon_nums: &HashSet<u32>,
|
||||
region_names: &HashSet<ast::Name>)
|
||||
-> P<ast::Ty> {
|
||||
-> P<hir::Ty> {
|
||||
let mut new_ty = P(ty.clone());
|
||||
let mut ty_queue = vec!(ty);
|
||||
while !ty_queue.is_empty() {
|
||||
let cur_ty = ty_queue.remove(0);
|
||||
match cur_ty.node {
|
||||
ast::TyRptr(lt_opt, ref mut_ty) => {
|
||||
hir::TyRptr(lt_opt, ref mut_ty) => {
|
||||
let rebuild = match lt_opt {
|
||||
Some(lt) => region_names.contains(<.name),
|
||||
None => {
|
||||
@ -1332,16 +1333,16 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
}
|
||||
};
|
||||
if rebuild {
|
||||
let to = ast::Ty {
|
||||
let to = hir::Ty {
|
||||
id: cur_ty.id,
|
||||
node: ast::TyRptr(Some(lifetime), mut_ty.clone()),
|
||||
node: hir::TyRptr(Some(lifetime), mut_ty.clone()),
|
||||
span: cur_ty.span
|
||||
};
|
||||
new_ty = self.rebuild_ty(new_ty, P(to));
|
||||
}
|
||||
ty_queue.push(&*mut_ty.ty);
|
||||
}
|
||||
ast::TyPath(ref maybe_qself, ref path) => {
|
||||
hir::TyPath(ref maybe_qself, ref path) => {
|
||||
let a_def = match self.tcx.def_map.borrow().get(&cur_ty.id) {
|
||||
None => {
|
||||
self.tcx
|
||||
@ -1386,15 +1387,15 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
};
|
||||
let new_path = self.rebuild_path(rebuild_info, lifetime);
|
||||
let qself = maybe_qself.as_ref().map(|qself| {
|
||||
ast::QSelf {
|
||||
hir::QSelf {
|
||||
ty: self.rebuild_arg_ty_or_output(&qself.ty, lifetime,
|
||||
anon_nums, region_names),
|
||||
position: qself.position
|
||||
}
|
||||
});
|
||||
let to = ast::Ty {
|
||||
let to = hir::Ty {
|
||||
id: cur_ty.id,
|
||||
node: ast::TyPath(qself, new_path),
|
||||
node: hir::TyPath(qself, new_path),
|
||||
span: cur_ty.span
|
||||
};
|
||||
new_ty = self.rebuild_ty(new_ty, P(to));
|
||||
@ -1404,14 +1405,14 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
|
||||
}
|
||||
|
||||
ast::TyPtr(ref mut_ty) => {
|
||||
hir::TyPtr(ref mut_ty) => {
|
||||
ty_queue.push(&*mut_ty.ty);
|
||||
}
|
||||
ast::TyVec(ref ty) |
|
||||
ast::TyFixedLengthVec(ref ty, _) => {
|
||||
hir::TyVec(ref ty) |
|
||||
hir::TyFixedLengthVec(ref ty, _) => {
|
||||
ty_queue.push(&**ty);
|
||||
}
|
||||
ast::TyTup(ref tys) => ty_queue.extend(tys.iter().map(|ty| &**ty)),
|
||||
hir::TyTup(ref tys) => ty_queue.extend(tys.iter().map(|ty| &**ty)),
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
@ -1419,41 +1420,41 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn rebuild_ty(&self,
|
||||
from: P<ast::Ty>,
|
||||
to: P<ast::Ty>)
|
||||
-> P<ast::Ty> {
|
||||
from: P<hir::Ty>,
|
||||
to: P<hir::Ty>)
|
||||
-> P<hir::Ty> {
|
||||
|
||||
fn build_to(from: P<ast::Ty>,
|
||||
to: &mut Option<P<ast::Ty>>)
|
||||
-> P<ast::Ty> {
|
||||
fn build_to(from: P<hir::Ty>,
|
||||
to: &mut Option<P<hir::Ty>>)
|
||||
-> P<hir::Ty> {
|
||||
if Some(from.id) == to.as_ref().map(|ty| ty.id) {
|
||||
return to.take().expect("`to` type found more than once during rebuild");
|
||||
}
|
||||
from.map(|ast::Ty {id, node, span}| {
|
||||
from.map(|hir::Ty {id, node, span}| {
|
||||
let new_node = match node {
|
||||
ast::TyRptr(lifetime, mut_ty) => {
|
||||
ast::TyRptr(lifetime, ast::MutTy {
|
||||
hir::TyRptr(lifetime, mut_ty) => {
|
||||
hir::TyRptr(lifetime, hir::MutTy {
|
||||
mutbl: mut_ty.mutbl,
|
||||
ty: build_to(mut_ty.ty, to),
|
||||
})
|
||||
}
|
||||
ast::TyPtr(mut_ty) => {
|
||||
ast::TyPtr(ast::MutTy {
|
||||
hir::TyPtr(mut_ty) => {
|
||||
hir::TyPtr(hir::MutTy {
|
||||
mutbl: mut_ty.mutbl,
|
||||
ty: build_to(mut_ty.ty, to),
|
||||
})
|
||||
}
|
||||
ast::TyVec(ty) => ast::TyVec(build_to(ty, to)),
|
||||
ast::TyFixedLengthVec(ty, e) => {
|
||||
ast::TyFixedLengthVec(build_to(ty, to), e)
|
||||
hir::TyVec(ty) => hir::TyVec(build_to(ty, to)),
|
||||
hir::TyFixedLengthVec(ty, e) => {
|
||||
hir::TyFixedLengthVec(build_to(ty, to), e)
|
||||
}
|
||||
ast::TyTup(tys) => {
|
||||
ast::TyTup(tys.into_iter().map(|ty| build_to(ty, to)).collect())
|
||||
hir::TyTup(tys) => {
|
||||
hir::TyTup(tys.into_iter().map(|ty| build_to(ty, to)).collect())
|
||||
}
|
||||
ast::TyParen(typ) => ast::TyParen(build_to(typ, to)),
|
||||
hir::TyParen(typ) => hir::TyParen(build_to(typ, to)),
|
||||
other => other
|
||||
};
|
||||
ast::Ty { id: id, node: new_node, span: span }
|
||||
hir::Ty { id: id, node: new_node, span: span }
|
||||
})
|
||||
}
|
||||
|
||||
@ -1462,8 +1463,8 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
|
||||
fn rebuild_path(&self,
|
||||
rebuild_info: RebuildPathInfo,
|
||||
lifetime: ast::Lifetime)
|
||||
-> ast::Path
|
||||
lifetime: hir::Lifetime)
|
||||
-> hir::Path
|
||||
{
|
||||
let RebuildPathInfo {
|
||||
path,
|
||||
@ -1475,11 +1476,11 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
|
||||
let last_seg = path.segments.last().unwrap();
|
||||
let new_parameters = match last_seg.parameters {
|
||||
ast::ParenthesizedParameters(..) => {
|
||||
hir::ParenthesizedParameters(..) => {
|
||||
last_seg.parameters.clone()
|
||||
}
|
||||
|
||||
ast::AngleBracketedParameters(ref data) => {
|
||||
hir::AngleBracketedParameters(ref data) => {
|
||||
let mut new_lts = Vec::new();
|
||||
if data.lifetimes.is_empty() {
|
||||
// traverse once to see if there's a need to insert lifetime
|
||||
@ -1508,7 +1509,7 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
self.rebuild_arg_ty_or_output(&**t, lifetime, anon_nums, region_names)
|
||||
});
|
||||
let new_bindings = data.bindings.map(|b| {
|
||||
P(ast::TypeBinding {
|
||||
P(hir::TypeBinding {
|
||||
id: b.id,
|
||||
ident: b.ident,
|
||||
ty: self.rebuild_arg_ty_or_output(&*b.ty,
|
||||
@ -1518,21 +1519,21 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
span: b.span
|
||||
})
|
||||
});
|
||||
ast::AngleBracketedParameters(ast::AngleBracketedParameterData {
|
||||
hir::AngleBracketedParameters(hir::AngleBracketedParameterData {
|
||||
lifetimes: new_lts,
|
||||
types: new_types,
|
||||
bindings: new_bindings,
|
||||
})
|
||||
}
|
||||
};
|
||||
let new_seg = ast::PathSegment {
|
||||
let new_seg = hir::PathSegment {
|
||||
identifier: last_seg.identifier,
|
||||
parameters: new_parameters
|
||||
};
|
||||
let mut new_segs = Vec::new();
|
||||
new_segs.push_all(path.segments.split_last().unwrap().1);
|
||||
new_segs.push(new_seg);
|
||||
ast::Path {
|
||||
hir::Path {
|
||||
span: path.span,
|
||||
global: path.global,
|
||||
segments: new_segs
|
||||
@ -1542,12 +1543,12 @@ impl<'a, 'tcx> Rebuilder<'a, 'tcx> {
|
||||
|
||||
impl<'a, 'tcx> ErrorReportingHelpers<'tcx> for InferCtxt<'a, 'tcx> {
|
||||
fn give_expl_lifetime_param(&self,
|
||||
decl: &ast::FnDecl,
|
||||
unsafety: ast::Unsafety,
|
||||
constness: ast::Constness,
|
||||
decl: &hir::FnDecl,
|
||||
unsafety: hir::Unsafety,
|
||||
constness: hir::Constness,
|
||||
ident: ast::Ident,
|
||||
opt_explicit_self: Option<&ast::ExplicitSelf_>,
|
||||
generics: &ast::Generics,
|
||||
opt_explicit_self: Option<&hir::ExplicitSelf_>,
|
||||
generics: &hir::Generics,
|
||||
span: Span) {
|
||||
let suggested_fn = pprust::fun_to_string(decl, unsafety, constness, ident,
|
||||
opt_explicit_self, generics);
|
||||
@ -1832,13 +1833,13 @@ impl<'tcx> Resolvable<'tcx> for ty::PolyTraitRef<'tcx> {
|
||||
|
||||
fn lifetimes_in_scope(tcx: &ty::ctxt,
|
||||
scope_id: ast::NodeId)
|
||||
-> Vec<ast::LifetimeDef> {
|
||||
-> Vec<hir::LifetimeDef> {
|
||||
let mut taken = Vec::new();
|
||||
let parent = tcx.map.get_parent(scope_id);
|
||||
let method_id_opt = match tcx.map.find(parent) {
|
||||
Some(node) => match node {
|
||||
ast_map::NodeItem(item) => match item.node {
|
||||
ast::ItemFn(_, _, _, _, ref gen, _) => {
|
||||
hir::ItemFn(_, _, _, _, ref gen, _) => {
|
||||
taken.push_all(&gen.lifetimes);
|
||||
None
|
||||
},
|
||||
@ -1846,11 +1847,10 @@ fn lifetimes_in_scope(tcx: &ty::ctxt,
|
||||
},
|
||||
ast_map::NodeImplItem(ii) => {
|
||||
match ii.node {
|
||||
ast::MethodImplItem(ref sig, _) => {
|
||||
hir::MethodImplItem(ref sig, _) => {
|
||||
taken.push_all(&sig.generics.lifetimes);
|
||||
Some(ii.id)
|
||||
}
|
||||
ast::MacImplItem(_) => tcx.sess.bug("unexpanded macro"),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
@ -1864,7 +1864,7 @@ fn lifetimes_in_scope(tcx: &ty::ctxt,
|
||||
match tcx.map.find(parent) {
|
||||
Some(node) => match node {
|
||||
ast_map::NodeItem(item) => match item.node {
|
||||
ast::ItemImpl(_, _, ref gen, _, _, _) => {
|
||||
hir::ItemImpl(_, _, ref gen, _, _, _) => {
|
||||
taken.push_all(&gen.lifetimes);
|
||||
}
|
||||
_ => ()
|
||||
@ -1881,11 +1881,11 @@ fn lifetimes_in_scope(tcx: &ty::ctxt,
|
||||
struct LifeGiver {
|
||||
taken: HashSet<String>,
|
||||
counter: Cell<usize>,
|
||||
generated: RefCell<Vec<ast::Lifetime>>,
|
||||
generated: RefCell<Vec<hir::Lifetime>>,
|
||||
}
|
||||
|
||||
impl LifeGiver {
|
||||
fn with_taken(taken: &[ast::LifetimeDef]) -> LifeGiver {
|
||||
fn with_taken(taken: &[hir::LifetimeDef]) -> LifeGiver {
|
||||
let mut taken_ = HashSet::new();
|
||||
for lt in taken {
|
||||
let lt_name = lt.lifetime.name.to_string();
|
||||
@ -1903,7 +1903,7 @@ impl LifeGiver {
|
||||
self.counter.set(c+1);
|
||||
}
|
||||
|
||||
fn give_lifetime(&self) -> ast::Lifetime {
|
||||
fn give_lifetime(&self) -> hir::Lifetime {
|
||||
let lifetime;
|
||||
loop {
|
||||
let mut s = String::from("'");
|
||||
@ -1931,7 +1931,13 @@ impl LifeGiver {
|
||||
}
|
||||
}
|
||||
|
||||
fn get_generated_lifetimes(&self) -> Vec<ast::Lifetime> {
|
||||
fn get_generated_lifetimes(&self) -> Vec<hir::Lifetime> {
|
||||
self.generated.borrow().clone()
|
||||
}
|
||||
}
|
||||
|
||||
fn name_to_dummy_lifetime(name: ast::Name) -> hir::Lifetime {
|
||||
hir::Lifetime { id: ast::DUMMY_NODE_ID,
|
||||
span: codemap::DUMMY_SP,
|
||||
name: name }
|
||||
}
|
||||
|
@ -20,6 +20,7 @@ pub use self::freshen::TypeFreshener;
|
||||
pub use self::region_inference::{GenericKind, VerifyBound};
|
||||
|
||||
use middle::def_id::DefId;
|
||||
use rustc_front::hir;
|
||||
use middle::free_region::FreeRegionMap;
|
||||
use middle::mem_categorization as mc;
|
||||
use middle::mem_categorization::McResult;
|
||||
@ -1147,7 +1148,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
||||
|
||||
/// Apply `adjustment` to the type of `expr`
|
||||
pub fn adjust_expr_ty(&self,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
adjustment: Option<&ty::AutoAdjustment<'tcx>>)
|
||||
-> Ty<'tcx>
|
||||
{
|
||||
@ -1179,7 +1180,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn expr_ty(&self, ex: &ast::Expr) -> Ty<'tcx> {
|
||||
pub fn expr_ty(&self, ex: &hir::Expr) -> Ty<'tcx> {
|
||||
match self.tables.borrow().node_types.get(&ex.id) {
|
||||
Some(&t) => t,
|
||||
None => {
|
||||
@ -1446,7 +1447,7 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
|
||||
self.resolve_type_vars_or_error(&ty)
|
||||
}
|
||||
|
||||
pub fn expr_ty_adjusted(&self, expr: &ast::Expr) -> McResult<Ty<'tcx>> {
|
||||
pub fn expr_ty_adjusted(&self, expr: &hir::Expr) -> McResult<Ty<'tcx>> {
|
||||
let ty = self.adjust_expr_ty(expr, self.tables.borrow().adjustments.get(&expr.id));
|
||||
self.resolve_type_vars_or_error(&ty)
|
||||
}
|
||||
|
@ -10,7 +10,7 @@
|
||||
|
||||
use middle::ty::{self, IntVarValue, Ty};
|
||||
use rustc_data_structures::unify::UnifyKey;
|
||||
use syntax::ast;
|
||||
use rustc_front::hir as ast;
|
||||
|
||||
pub trait ToType<'tcx> {
|
||||
fn to_type(&self, tcx: &ty::ctxt<'tcx>) -> Ty<'tcx>;
|
||||
|
@ -19,8 +19,8 @@ use std::fmt;
|
||||
use syntax::abi::RustIntrinsic;
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit::{FnKind, Visitor};
|
||||
use syntax::visit;
|
||||
use rustc_front::visit::{self, Visitor, FnKind};
|
||||
use rustc_front::hir;
|
||||
|
||||
pub fn check_crate(tcx: &ctxt) {
|
||||
let mut visitor = IntrinsicCheckingVisitor {
|
||||
@ -216,8 +216,8 @@ impl<'a, 'tcx> IntrinsicCheckingVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for IntrinsicCheckingVisitor<'a, 'tcx> {
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v ast::FnDecl,
|
||||
b: &'v ast::Block, s: Span, id: ast::NodeId) {
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v hir::FnDecl,
|
||||
b: &'v hir::Block, s: Span, id: ast::NodeId) {
|
||||
match fk {
|
||||
FnKind::ItemFn(..) | FnKind::Method(..) => {
|
||||
let param_env = ty::ParameterEnvironment::for_item(self.tcx, id);
|
||||
@ -232,8 +232,8 @@ impl<'a, 'tcx, 'v> Visitor<'v> for IntrinsicCheckingVisitor<'a, 'tcx> {
|
||||
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, expr: &ast::Expr) {
|
||||
if let ast::ExprPath(..) = expr.node {
|
||||
fn visit_expr(&mut self, expr: &hir::Expr) {
|
||||
if let hir::ExprPath(..) = expr.node {
|
||||
match self.tcx.resolve_expr(expr) {
|
||||
DefFn(did, _) if self.def_id_is_transmute(did) => {
|
||||
let typ = self.tcx.node_id_to_type(expr.id);
|
||||
|
@ -28,12 +28,12 @@ use middle::ty;
|
||||
use middle::weak_lang_items;
|
||||
use util::nodemap::FnvHashMap;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use rustc_front::attr::AttrMetaMethods;
|
||||
use syntax::codemap::{DUMMY_SP, Span};
|
||||
use syntax::parse::token::InternedString;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::visit;
|
||||
use rustc_front::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::hir;
|
||||
|
||||
use std::iter::Enumerate;
|
||||
use std::slice;
|
||||
@ -152,7 +152,7 @@ struct LanguageItemCollector<'a> {
|
||||
}
|
||||
|
||||
impl<'a, 'v> Visitor<'v> for LanguageItemCollector<'a> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
if let Some(value) = extract(&item.attrs) {
|
||||
let item_index = self.item_refs.get(&value[..]).cloned();
|
||||
|
||||
@ -195,7 +195,7 @@ impl<'a> LanguageItemCollector<'a> {
|
||||
self.items.items[item_index] = Some(item_def_id);
|
||||
}
|
||||
|
||||
pub fn collect_local_language_items(&mut self, krate: &ast::Crate) {
|
||||
pub fn collect_local_language_items(&mut self, krate: &hir::Crate) {
|
||||
visit::walk_crate(self, krate);
|
||||
}
|
||||
|
||||
@ -210,13 +210,13 @@ impl<'a> LanguageItemCollector<'a> {
|
||||
})
|
||||
}
|
||||
|
||||
pub fn collect(&mut self, krate: &ast::Crate) {
|
||||
pub fn collect(&mut self, krate: &hir::Crate) {
|
||||
self.collect_local_language_items(krate);
|
||||
self.collect_external_language_items();
|
||||
}
|
||||
}
|
||||
|
||||
pub fn extract(attrs: &[ast::Attribute]) -> Option<InternedString> {
|
||||
pub fn extract(attrs: &[hir::Attribute]) -> Option<InternedString> {
|
||||
for attribute in attrs {
|
||||
match attribute.value_str() {
|
||||
Some(ref value) if attribute.check_name("lang") => {
|
||||
@ -229,7 +229,7 @@ pub fn extract(attrs: &[ast::Attribute]) -> Option<InternedString> {
|
||||
return None;
|
||||
}
|
||||
|
||||
pub fn collect_language_items(krate: &ast::Crate,
|
||||
pub fn collect_language_items(krate: &hir::Crate,
|
||||
session: &Session) -> LanguageItems {
|
||||
let mut collector = LanguageItemCollector::new(session);
|
||||
collector.collect(krate);
|
||||
|
@ -119,13 +119,15 @@ use std::{fmt, usize};
|
||||
use std::io::prelude::*;
|
||||
use std::io;
|
||||
use std::rc::Rc;
|
||||
use syntax::ast::{self, NodeId, Expr};
|
||||
use syntax::ast::{self, NodeId};
|
||||
use syntax::codemap::{BytePos, original_sp, Span};
|
||||
use syntax::parse::token::special_idents;
|
||||
use syntax::print::pprust::{expr_to_string, block_to_string};
|
||||
use syntax::ptr::P;
|
||||
use syntax::ast_util;
|
||||
use syntax::visit::{self, Visitor, FnKind};
|
||||
|
||||
use rustc_front::hir::Expr;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::print::pprust::{expr_to_string, block_to_string};
|
||||
use rustc_front::visit::{self, Visitor, FnKind};
|
||||
|
||||
/// For use with `propagate_through_loop`.
|
||||
enum LoopKind<'a> {
|
||||
@ -180,13 +182,13 @@ fn live_node_kind_to_string(lnk: LiveNodeKind, cx: &ty::ctxt) -> String {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for IrMaps<'a, 'tcx> {
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v ast::FnDecl,
|
||||
b: &'v ast::Block, s: Span, id: NodeId) {
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v hir::FnDecl,
|
||||
b: &'v hir::Block, s: Span, id: NodeId) {
|
||||
visit_fn(self, fk, fd, b, s, id);
|
||||
}
|
||||
fn visit_local(&mut self, l: &ast::Local) { visit_local(self, l); }
|
||||
fn visit_local(&mut self, l: &hir::Local) { visit_local(self, l); }
|
||||
fn visit_expr(&mut self, ex: &Expr) { visit_expr(self, ex); }
|
||||
fn visit_arm(&mut self, a: &ast::Arm) { visit_arm(self, a); }
|
||||
fn visit_arm(&mut self, a: &hir::Arm) { visit_arm(self, a); }
|
||||
}
|
||||
|
||||
pub fn check_crate(tcx: &ty::ctxt) {
|
||||
@ -348,25 +350,25 @@ impl<'a, 'tcx> IrMaps<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for Liveness<'a, 'tcx> {
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v ast::FnDecl,
|
||||
b: &'v ast::Block, s: Span, n: NodeId) {
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v hir::FnDecl,
|
||||
b: &'v hir::Block, s: Span, n: NodeId) {
|
||||
check_fn(self, fk, fd, b, s, n);
|
||||
}
|
||||
fn visit_local(&mut self, l: &ast::Local) {
|
||||
fn visit_local(&mut self, l: &hir::Local) {
|
||||
check_local(self, l);
|
||||
}
|
||||
fn visit_expr(&mut self, ex: &Expr) {
|
||||
check_expr(self, ex);
|
||||
}
|
||||
fn visit_arm(&mut self, a: &ast::Arm) {
|
||||
fn visit_arm(&mut self, a: &hir::Arm) {
|
||||
check_arm(self, a);
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_fn(ir: &mut IrMaps,
|
||||
fk: FnKind,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block,
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block,
|
||||
sp: Span,
|
||||
id: ast::NodeId) {
|
||||
debug!("visit_fn");
|
||||
@ -411,7 +413,7 @@ fn visit_fn(ir: &mut IrMaps,
|
||||
lsets.warn_about_unused_args(decl, entry_ln);
|
||||
}
|
||||
|
||||
fn visit_local(ir: &mut IrMaps, local: &ast::Local) {
|
||||
fn visit_local(ir: &mut IrMaps, local: &hir::Local) {
|
||||
pat_util::pat_bindings(&ir.tcx.def_map, &*local.pat, |_, p_id, sp, path1| {
|
||||
debug!("adding local variable {}", p_id);
|
||||
let name = path1.node.name;
|
||||
@ -424,7 +426,7 @@ fn visit_local(ir: &mut IrMaps, local: &ast::Local) {
|
||||
visit::walk_local(ir, local);
|
||||
}
|
||||
|
||||
fn visit_arm(ir: &mut IrMaps, arm: &ast::Arm) {
|
||||
fn visit_arm(ir: &mut IrMaps, arm: &hir::Arm) {
|
||||
for pat in &arm.pats {
|
||||
pat_util::pat_bindings(&ir.tcx.def_map, &**pat, |bm, p_id, sp, path1| {
|
||||
debug!("adding local variable {} from match with bm {:?}",
|
||||
@ -443,7 +445,7 @@ fn visit_arm(ir: &mut IrMaps, arm: &ast::Arm) {
|
||||
fn visit_expr(ir: &mut IrMaps, expr: &Expr) {
|
||||
match expr.node {
|
||||
// live nodes required for uses or definitions of variables:
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
let def = ir.tcx.def_map.borrow().get(&expr.id).unwrap().full_def();
|
||||
debug!("expr {}: path that leads to {:?}", expr.id, def);
|
||||
if let DefLocal(..) = def {
|
||||
@ -451,7 +453,7 @@ fn visit_expr(ir: &mut IrMaps, expr: &Expr) {
|
||||
}
|
||||
visit::walk_expr(ir, expr);
|
||||
}
|
||||
ast::ExprClosure(..) => {
|
||||
hir::ExprClosure(..) => {
|
||||
// Interesting control flow (for loops can contain labeled
|
||||
// breaks or continues)
|
||||
ir.add_live_node_for_node(expr.id, ExprNode(expr.span));
|
||||
@ -476,34 +478,25 @@ fn visit_expr(ir: &mut IrMaps, expr: &Expr) {
|
||||
}
|
||||
|
||||
// live nodes required for interesting control flow:
|
||||
ast::ExprIf(..) | ast::ExprMatch(..) | ast::ExprWhile(..) | ast::ExprLoop(..) => {
|
||||
hir::ExprIf(..) | hir::ExprMatch(..) | hir::ExprWhile(..) | hir::ExprLoop(..) => {
|
||||
ir.add_live_node_for_node(expr.id, ExprNode(expr.span));
|
||||
visit::walk_expr(ir, expr);
|
||||
}
|
||||
ast::ExprIfLet(..) => {
|
||||
ir.tcx.sess.span_bug(expr.span, "non-desugared ExprIfLet");
|
||||
}
|
||||
ast::ExprWhileLet(..) => {
|
||||
ir.tcx.sess.span_bug(expr.span, "non-desugared ExprWhileLet");
|
||||
}
|
||||
ast::ExprForLoop(..) => {
|
||||
ir.tcx.sess.span_bug(expr.span, "non-desugared ExprForLoop");
|
||||
}
|
||||
ast::ExprBinary(op, _, _) if ast_util::lazy_binop(op.node) => {
|
||||
hir::ExprBinary(op, _, _) if ::rustc_front::util::lazy_binop(op.node) => {
|
||||
ir.add_live_node_for_node(expr.id, ExprNode(expr.span));
|
||||
visit::walk_expr(ir, expr);
|
||||
}
|
||||
|
||||
// otherwise, live nodes are not required:
|
||||
ast::ExprIndex(..) | ast::ExprField(..) | ast::ExprTupField(..) |
|
||||
ast::ExprVec(..) | ast::ExprCall(..) | ast::ExprMethodCall(..) |
|
||||
ast::ExprTup(..) | ast::ExprBinary(..) | ast::ExprAddrOf(..) |
|
||||
ast::ExprCast(..) | ast::ExprUnary(..) | ast::ExprBreak(_) |
|
||||
ast::ExprAgain(_) | ast::ExprLit(_) | ast::ExprRet(..) |
|
||||
ast::ExprBlock(..) | ast::ExprAssign(..) | ast::ExprAssignOp(..) |
|
||||
ast::ExprMac(..) | ast::ExprStruct(..) | ast::ExprRepeat(..) |
|
||||
ast::ExprParen(..) | ast::ExprInlineAsm(..) | ast::ExprBox(..) |
|
||||
ast::ExprRange(..) => {
|
||||
hir::ExprIndex(..) | hir::ExprField(..) | hir::ExprTupField(..) |
|
||||
hir::ExprVec(..) | hir::ExprCall(..) | hir::ExprMethodCall(..) |
|
||||
hir::ExprTup(..) | hir::ExprBinary(..) | hir::ExprAddrOf(..) |
|
||||
hir::ExprCast(..) | hir::ExprUnary(..) | hir::ExprBreak(_) |
|
||||
hir::ExprAgain(_) | hir::ExprLit(_) | hir::ExprRet(..) |
|
||||
hir::ExprBlock(..) | hir::ExprAssign(..) | hir::ExprAssignOp(..) |
|
||||
hir::ExprStruct(..) | hir::ExprRepeat(..) |
|
||||
hir::ExprParen(..) | hir::ExprInlineAsm(..) | hir::ExprBox(..) |
|
||||
hir::ExprRange(..) => {
|
||||
visit::walk_expr(ir, expr);
|
||||
}
|
||||
}
|
||||
@ -592,7 +585,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
self.ir.variable(node_id, span)
|
||||
}
|
||||
|
||||
fn pat_bindings<F>(&mut self, pat: &ast::Pat, mut f: F) where
|
||||
fn pat_bindings<F>(&mut self, pat: &hir::Pat, mut f: F) where
|
||||
F: FnMut(&mut Liveness<'a, 'tcx>, LiveNode, Variable, Span, NodeId),
|
||||
{
|
||||
pat_util::pat_bindings(&self.ir.tcx.def_map, pat, |_bm, p_id, sp, _n| {
|
||||
@ -602,7 +595,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
})
|
||||
}
|
||||
|
||||
fn arm_pats_bindings<F>(&mut self, pat: Option<&ast::Pat>, f: F) where
|
||||
fn arm_pats_bindings<F>(&mut self, pat: Option<&hir::Pat>, f: F) where
|
||||
F: FnMut(&mut Liveness<'a, 'tcx>, LiveNode, Variable, Span, NodeId),
|
||||
{
|
||||
match pat {
|
||||
@ -613,12 +606,12 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn define_bindings_in_pat(&mut self, pat: &ast::Pat, succ: LiveNode)
|
||||
fn define_bindings_in_pat(&mut self, pat: &hir::Pat, succ: LiveNode)
|
||||
-> LiveNode {
|
||||
self.define_bindings_in_arm_pats(Some(pat), succ)
|
||||
}
|
||||
|
||||
fn define_bindings_in_arm_pats(&mut self, pat: Option<&ast::Pat>, succ: LiveNode)
|
||||
fn define_bindings_in_arm_pats(&mut self, pat: Option<&hir::Pat>, succ: LiveNode)
|
||||
-> LiveNode {
|
||||
let mut succ = succ;
|
||||
self.arm_pats_bindings(pat, |this, ln, var, _sp, _id| {
|
||||
@ -830,7 +823,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
|
||||
// _______________________________________________________________________
|
||||
|
||||
fn compute(&mut self, decl: &ast::FnDecl, body: &ast::Block) -> LiveNode {
|
||||
fn compute(&mut self, decl: &hir::FnDecl, body: &hir::Block) -> LiveNode {
|
||||
// if there is a `break` or `again` at the top level, then it's
|
||||
// effectively a return---this only occurs in `for` loops,
|
||||
// where the body is really a closure.
|
||||
@ -855,7 +848,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
entry_ln
|
||||
}
|
||||
|
||||
fn propagate_through_fn_block(&mut self, _: &ast::FnDecl, blk: &ast::Block)
|
||||
fn propagate_through_fn_block(&mut self, _: &hir::FnDecl, blk: &hir::Block)
|
||||
-> LiveNode {
|
||||
// the fallthrough exit is only for those cases where we do not
|
||||
// explicitly return:
|
||||
@ -869,7 +862,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
self.propagate_through_block(blk, s.fallthrough_ln)
|
||||
}
|
||||
|
||||
fn propagate_through_block(&mut self, blk: &ast::Block, succ: LiveNode)
|
||||
fn propagate_through_block(&mut self, blk: &hir::Block, succ: LiveNode)
|
||||
-> LiveNode {
|
||||
let succ = self.propagate_through_opt_expr(blk.expr.as_ref().map(|e| &**e), succ);
|
||||
blk.stmts.iter().rev().fold(succ, |succ, stmt| {
|
||||
@ -877,34 +870,30 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
})
|
||||
}
|
||||
|
||||
fn propagate_through_stmt(&mut self, stmt: &ast::Stmt, succ: LiveNode)
|
||||
fn propagate_through_stmt(&mut self, stmt: &hir::Stmt, succ: LiveNode)
|
||||
-> LiveNode {
|
||||
match stmt.node {
|
||||
ast::StmtDecl(ref decl, _) => {
|
||||
hir::StmtDecl(ref decl, _) => {
|
||||
self.propagate_through_decl(&**decl, succ)
|
||||
}
|
||||
|
||||
ast::StmtExpr(ref expr, _) | ast::StmtSemi(ref expr, _) => {
|
||||
hir::StmtExpr(ref expr, _) | hir::StmtSemi(ref expr, _) => {
|
||||
self.propagate_through_expr(&**expr, succ)
|
||||
}
|
||||
|
||||
ast::StmtMac(..) => {
|
||||
self.ir.tcx.sess.span_bug(stmt.span, "unexpanded macro");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn propagate_through_decl(&mut self, decl: &ast::Decl, succ: LiveNode)
|
||||
fn propagate_through_decl(&mut self, decl: &hir::Decl, succ: LiveNode)
|
||||
-> LiveNode {
|
||||
match decl.node {
|
||||
ast::DeclLocal(ref local) => {
|
||||
hir::DeclLocal(ref local) => {
|
||||
self.propagate_through_local(&**local, succ)
|
||||
}
|
||||
ast::DeclItem(_) => succ,
|
||||
hir::DeclItem(_) => succ,
|
||||
}
|
||||
}
|
||||
|
||||
fn propagate_through_local(&mut self, local: &ast::Local, succ: LiveNode)
|
||||
fn propagate_through_local(&mut self, local: &hir::Local, succ: LiveNode)
|
||||
-> LiveNode {
|
||||
// Note: we mark the variable as defined regardless of whether
|
||||
// there is an initializer. Initially I had thought to only mark
|
||||
@ -945,19 +934,19 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
match expr.node {
|
||||
// Interesting cases with control flow or which gen/kill
|
||||
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
self.access_path(expr, succ, ACC_READ | ACC_USE)
|
||||
}
|
||||
|
||||
ast::ExprField(ref e, _) => {
|
||||
hir::ExprField(ref e, _) => {
|
||||
self.propagate_through_expr(&**e, succ)
|
||||
}
|
||||
|
||||
ast::ExprTupField(ref e, _) => {
|
||||
hir::ExprTupField(ref e, _) => {
|
||||
self.propagate_through_expr(&**e, succ)
|
||||
}
|
||||
|
||||
ast::ExprClosure(_, _, ref blk) => {
|
||||
hir::ExprClosure(_, _, ref blk) => {
|
||||
debug!("{} is an ExprClosure",
|
||||
expr_to_string(expr));
|
||||
|
||||
@ -985,7 +974,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
})
|
||||
}
|
||||
|
||||
ast::ExprIf(ref cond, ref then, ref els) => {
|
||||
hir::ExprIf(ref cond, ref then, ref els) => {
|
||||
//
|
||||
// (cond)
|
||||
// |
|
||||
@ -1007,29 +996,17 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
self.propagate_through_expr(&**cond, ln)
|
||||
}
|
||||
|
||||
ast::ExprIfLet(..) => {
|
||||
self.ir.tcx.sess.span_bug(expr.span, "non-desugared ExprIfLet");
|
||||
}
|
||||
|
||||
ast::ExprWhile(ref cond, ref blk, _) => {
|
||||
hir::ExprWhile(ref cond, ref blk, _) => {
|
||||
self.propagate_through_loop(expr, WhileLoop(&**cond), &**blk, succ)
|
||||
}
|
||||
|
||||
ast::ExprWhileLet(..) => {
|
||||
self.ir.tcx.sess.span_bug(expr.span, "non-desugared ExprWhileLet");
|
||||
}
|
||||
|
||||
ast::ExprForLoop(..) => {
|
||||
self.ir.tcx.sess.span_bug(expr.span, "non-desugared ExprForLoop");
|
||||
}
|
||||
|
||||
// Note that labels have been resolved, so we don't need to look
|
||||
// at the label ident
|
||||
ast::ExprLoop(ref blk, _) => {
|
||||
hir::ExprLoop(ref blk, _) => {
|
||||
self.propagate_through_loop(expr, LoopLoop, &**blk, succ)
|
||||
}
|
||||
|
||||
ast::ExprMatch(ref e, ref arms, _) => {
|
||||
hir::ExprMatch(ref e, ref arms, _) => {
|
||||
//
|
||||
// (e)
|
||||
// |
|
||||
@ -1064,13 +1041,13 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
self.propagate_through_expr(&**e, ln)
|
||||
}
|
||||
|
||||
ast::ExprRet(ref o_e) => {
|
||||
hir::ExprRet(ref o_e) => {
|
||||
// ignore succ and subst exit_ln:
|
||||
let exit_ln = self.s.exit_ln;
|
||||
self.propagate_through_opt_expr(o_e.as_ref().map(|e| &**e), exit_ln)
|
||||
}
|
||||
|
||||
ast::ExprBreak(opt_label) => {
|
||||
hir::ExprBreak(opt_label) => {
|
||||
// Find which label this break jumps to
|
||||
let sc = self.find_loop_scope(opt_label, expr.id, expr.span);
|
||||
|
||||
@ -1084,7 +1061,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprAgain(opt_label) => {
|
||||
hir::ExprAgain(opt_label) => {
|
||||
// Find which label this expr continues to
|
||||
let sc = self.find_loop_scope(opt_label, expr.id, expr.span);
|
||||
|
||||
@ -1098,7 +1075,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprAssign(ref l, ref r) => {
|
||||
hir::ExprAssign(ref l, ref r) => {
|
||||
// see comment on lvalues in
|
||||
// propagate_through_lvalue_components()
|
||||
let succ = self.write_lvalue(&**l, succ, ACC_WRITE);
|
||||
@ -1106,7 +1083,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
self.propagate_through_expr(&**r, succ)
|
||||
}
|
||||
|
||||
ast::ExprAssignOp(_, ref l, ref r) => {
|
||||
hir::ExprAssignOp(_, ref l, ref r) => {
|
||||
// see comment on lvalues in
|
||||
// propagate_through_lvalue_components()
|
||||
let succ = self.write_lvalue(&**l, succ, ACC_WRITE|ACC_READ);
|
||||
@ -1116,23 +1093,23 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
|
||||
// Uninteresting cases: just propagate in rev exec order
|
||||
|
||||
ast::ExprVec(ref exprs) => {
|
||||
hir::ExprVec(ref exprs) => {
|
||||
self.propagate_through_exprs(&exprs[..], succ)
|
||||
}
|
||||
|
||||
ast::ExprRepeat(ref element, ref count) => {
|
||||
hir::ExprRepeat(ref element, ref count) => {
|
||||
let succ = self.propagate_through_expr(&**count, succ);
|
||||
self.propagate_through_expr(&**element, succ)
|
||||
}
|
||||
|
||||
ast::ExprStruct(_, ref fields, ref with_expr) => {
|
||||
hir::ExprStruct(_, ref fields, ref with_expr) => {
|
||||
let succ = self.propagate_through_opt_expr(with_expr.as_ref().map(|e| &**e), succ);
|
||||
fields.iter().rev().fold(succ, |succ, field| {
|
||||
self.propagate_through_expr(&*field.expr, succ)
|
||||
})
|
||||
}
|
||||
|
||||
ast::ExprCall(ref f, ref args) => {
|
||||
hir::ExprCall(ref f, ref args) => {
|
||||
let diverges = !self.ir.tcx.is_method_call(expr.id) &&
|
||||
self.ir.tcx.expr_ty_adjusted(&**f).fn_ret().diverges();
|
||||
let succ = if diverges {
|
||||
@ -1144,7 +1121,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
self.propagate_through_expr(&**f, succ)
|
||||
}
|
||||
|
||||
ast::ExprMethodCall(_, _, ref args) => {
|
||||
hir::ExprMethodCall(_, _, ref args) => {
|
||||
let method_call = ty::MethodCall::expr(expr.id);
|
||||
let method_ty = self.ir.tcx.tables.borrow().method_map[&method_call].ty;
|
||||
let succ = if method_ty.fn_ret().diverges() {
|
||||
@ -1155,11 +1132,11 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
self.propagate_through_exprs(&args[..], succ)
|
||||
}
|
||||
|
||||
ast::ExprTup(ref exprs) => {
|
||||
hir::ExprTup(ref exprs) => {
|
||||
self.propagate_through_exprs(&exprs[..], succ)
|
||||
}
|
||||
|
||||
ast::ExprBinary(op, ref l, ref r) if ast_util::lazy_binop(op.node) => {
|
||||
hir::ExprBinary(op, ref l, ref r) if ::rustc_front::util::lazy_binop(op.node) => {
|
||||
let r_succ = self.propagate_through_expr(&**r, succ);
|
||||
|
||||
let ln = self.live_node(expr.id, expr.span);
|
||||
@ -1169,27 +1146,27 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
self.propagate_through_expr(&**l, ln)
|
||||
}
|
||||
|
||||
ast::ExprIndex(ref l, ref r) |
|
||||
ast::ExprBinary(_, ref l, ref r) |
|
||||
ast::ExprBox(Some(ref l), ref r) => {
|
||||
hir::ExprIndex(ref l, ref r) |
|
||||
hir::ExprBinary(_, ref l, ref r) |
|
||||
hir::ExprBox(Some(ref l), ref r) => {
|
||||
let r_succ = self.propagate_through_expr(&**r, succ);
|
||||
self.propagate_through_expr(&**l, r_succ)
|
||||
}
|
||||
|
||||
ast::ExprRange(ref e1, ref e2) => {
|
||||
hir::ExprRange(ref e1, ref e2) => {
|
||||
let succ = e2.as_ref().map_or(succ, |e| self.propagate_through_expr(&**e, succ));
|
||||
e1.as_ref().map_or(succ, |e| self.propagate_through_expr(&**e, succ))
|
||||
}
|
||||
|
||||
ast::ExprBox(None, ref e) |
|
||||
ast::ExprAddrOf(_, ref e) |
|
||||
ast::ExprCast(ref e, _) |
|
||||
ast::ExprUnary(_, ref e) |
|
||||
ast::ExprParen(ref e) => {
|
||||
hir::ExprBox(None, ref e) |
|
||||
hir::ExprAddrOf(_, ref e) |
|
||||
hir::ExprCast(ref e, _) |
|
||||
hir::ExprUnary(_, ref e) |
|
||||
hir::ExprParen(ref e) => {
|
||||
self.propagate_through_expr(&**e, succ)
|
||||
}
|
||||
|
||||
ast::ExprInlineAsm(ref ia) => {
|
||||
hir::ExprInlineAsm(ref ia) => {
|
||||
|
||||
let succ = ia.outputs.iter().rev().fold(succ, |succ, &(_, ref expr, _)| {
|
||||
// see comment on lvalues
|
||||
@ -1203,17 +1180,13 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
})
|
||||
}
|
||||
|
||||
ast::ExprLit(..) => {
|
||||
hir::ExprLit(..) => {
|
||||
succ
|
||||
}
|
||||
|
||||
ast::ExprBlock(ref blk) => {
|
||||
hir::ExprBlock(ref blk) => {
|
||||
self.propagate_through_block(&**blk, succ)
|
||||
}
|
||||
|
||||
ast::ExprMac(..) => {
|
||||
self.ir.tcx.sess.span_bug(expr.span, "unexpanded macro");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1271,9 +1244,9 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
// just ignore such cases and treat them as reads.
|
||||
|
||||
match expr.node {
|
||||
ast::ExprPath(..) => succ,
|
||||
ast::ExprField(ref e, _) => self.propagate_through_expr(&**e, succ),
|
||||
ast::ExprTupField(ref e, _) => self.propagate_through_expr(&**e, succ),
|
||||
hir::ExprPath(..) => succ,
|
||||
hir::ExprField(ref e, _) => self.propagate_through_expr(&**e, succ),
|
||||
hir::ExprTupField(ref e, _) => self.propagate_through_expr(&**e, succ),
|
||||
_ => self.propagate_through_expr(expr, succ)
|
||||
}
|
||||
}
|
||||
@ -1282,7 +1255,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
fn write_lvalue(&mut self, expr: &Expr, succ: LiveNode, acc: u32)
|
||||
-> LiveNode {
|
||||
match expr.node {
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
self.access_path(expr, succ, acc)
|
||||
}
|
||||
|
||||
@ -1313,7 +1286,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
fn propagate_through_loop(&mut self,
|
||||
expr: &Expr,
|
||||
kind: LoopKind,
|
||||
body: &ast::Block,
|
||||
body: &hir::Block,
|
||||
succ: LiveNode)
|
||||
-> LiveNode {
|
||||
|
||||
@ -1400,7 +1373,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
// _______________________________________________________________________
|
||||
// Checking for error conditions
|
||||
|
||||
fn check_local(this: &mut Liveness, local: &ast::Local) {
|
||||
fn check_local(this: &mut Liveness, local: &hir::Local) {
|
||||
match local.init {
|
||||
Some(_) => {
|
||||
this.warn_about_unused_or_dead_vars_in_pat(&*local.pat);
|
||||
@ -1415,7 +1388,7 @@ fn check_local(this: &mut Liveness, local: &ast::Local) {
|
||||
visit::walk_local(this, local);
|
||||
}
|
||||
|
||||
fn check_arm(this: &mut Liveness, arm: &ast::Arm) {
|
||||
fn check_arm(this: &mut Liveness, arm: &hir::Arm) {
|
||||
// only consider the first pattern; any later patterns must have
|
||||
// the same bindings, and we also consider the first pattern to be
|
||||
// the "authoritative" set of ids
|
||||
@ -1427,20 +1400,20 @@ fn check_arm(this: &mut Liveness, arm: &ast::Arm) {
|
||||
|
||||
fn check_expr(this: &mut Liveness, expr: &Expr) {
|
||||
match expr.node {
|
||||
ast::ExprAssign(ref l, ref r) => {
|
||||
hir::ExprAssign(ref l, ref r) => {
|
||||
this.check_lvalue(&**l);
|
||||
this.visit_expr(&**r);
|
||||
|
||||
visit::walk_expr(this, expr);
|
||||
}
|
||||
|
||||
ast::ExprAssignOp(_, ref l, _) => {
|
||||
hir::ExprAssignOp(_, ref l, _) => {
|
||||
this.check_lvalue(&**l);
|
||||
|
||||
visit::walk_expr(this, expr);
|
||||
}
|
||||
|
||||
ast::ExprInlineAsm(ref ia) => {
|
||||
hir::ExprInlineAsm(ref ia) => {
|
||||
for &(_, ref input) in &ia.inputs {
|
||||
this.visit_expr(&**input);
|
||||
}
|
||||
@ -1455,34 +1428,25 @@ fn check_expr(this: &mut Liveness, expr: &Expr) {
|
||||
}
|
||||
|
||||
// no correctness conditions related to liveness
|
||||
ast::ExprCall(..) | ast::ExprMethodCall(..) | ast::ExprIf(..) |
|
||||
ast::ExprMatch(..) | ast::ExprWhile(..) | ast::ExprLoop(..) |
|
||||
ast::ExprIndex(..) | ast::ExprField(..) | ast::ExprTupField(..) |
|
||||
ast::ExprVec(..) | ast::ExprTup(..) | ast::ExprBinary(..) |
|
||||
ast::ExprCast(..) | ast::ExprUnary(..) | ast::ExprRet(..) |
|
||||
ast::ExprBreak(..) | ast::ExprAgain(..) | ast::ExprLit(_) |
|
||||
ast::ExprBlock(..) | ast::ExprMac(..) | ast::ExprAddrOf(..) |
|
||||
ast::ExprStruct(..) | ast::ExprRepeat(..) | ast::ExprParen(..) |
|
||||
ast::ExprClosure(..) | ast::ExprPath(..) | ast::ExprBox(..) |
|
||||
ast::ExprRange(..) => {
|
||||
hir::ExprCall(..) | hir::ExprMethodCall(..) | hir::ExprIf(..) |
|
||||
hir::ExprMatch(..) | hir::ExprWhile(..) | hir::ExprLoop(..) |
|
||||
hir::ExprIndex(..) | hir::ExprField(..) | hir::ExprTupField(..) |
|
||||
hir::ExprVec(..) | hir::ExprTup(..) | hir::ExprBinary(..) |
|
||||
hir::ExprCast(..) | hir::ExprUnary(..) | hir::ExprRet(..) |
|
||||
hir::ExprBreak(..) | hir::ExprAgain(..) | hir::ExprLit(_) |
|
||||
hir::ExprBlock(..) | hir::ExprAddrOf(..) |
|
||||
hir::ExprStruct(..) | hir::ExprRepeat(..) | hir::ExprParen(..) |
|
||||
hir::ExprClosure(..) | hir::ExprPath(..) | hir::ExprBox(..) |
|
||||
hir::ExprRange(..) => {
|
||||
visit::walk_expr(this, expr);
|
||||
}
|
||||
ast::ExprIfLet(..) => {
|
||||
this.ir.tcx.sess.span_bug(expr.span, "non-desugared ExprIfLet");
|
||||
}
|
||||
ast::ExprWhileLet(..) => {
|
||||
this.ir.tcx.sess.span_bug(expr.span, "non-desugared ExprWhileLet");
|
||||
}
|
||||
ast::ExprForLoop(..) => {
|
||||
this.ir.tcx.sess.span_bug(expr.span, "non-desugared ExprForLoop");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn check_fn(_v: &Liveness,
|
||||
_fk: FnKind,
|
||||
_decl: &ast::FnDecl,
|
||||
_body: &ast::Block,
|
||||
_decl: &hir::FnDecl,
|
||||
_body: &hir::Block,
|
||||
_sp: Span,
|
||||
_id: NodeId) {
|
||||
// do not check contents of nested fns
|
||||
@ -1503,7 +1467,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
sp: Span,
|
||||
_fk: FnKind,
|
||||
entry_ln: LiveNode,
|
||||
body: &ast::Block)
|
||||
body: &hir::Block)
|
||||
{
|
||||
// within the fn body, late-bound regions are liberated:
|
||||
let fn_ret =
|
||||
@ -1521,7 +1485,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
let ends_with_stmt = match body.expr {
|
||||
None if !body.stmts.is_empty() =>
|
||||
match body.stmts.first().unwrap().node {
|
||||
ast::StmtSemi(ref e, _) => {
|
||||
hir::StmtSemi(ref e, _) => {
|
||||
self.ir.tcx.expr_ty(&**e) == t_ret
|
||||
},
|
||||
_ => false
|
||||
@ -1555,7 +1519,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
|
||||
fn check_lvalue(&mut self, expr: &Expr) {
|
||||
match expr.node {
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
if let DefLocal(nid) = self.ir.tcx.def_map.borrow().get(&expr.id)
|
||||
.unwrap()
|
||||
.full_def() {
|
||||
@ -1585,7 +1549,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn warn_about_unused_args(&self, decl: &ast::FnDecl, entry_ln: LiveNode) {
|
||||
fn warn_about_unused_args(&self, decl: &hir::FnDecl, entry_ln: LiveNode) {
|
||||
for arg in &decl.inputs {
|
||||
pat_util::pat_bindings(&self.ir.tcx.def_map,
|
||||
&*arg.pat,
|
||||
@ -1600,7 +1564,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn warn_about_unused_or_dead_vars_in_pat(&mut self, pat: &ast::Pat) {
|
||||
fn warn_about_unused_or_dead_vars_in_pat(&mut self, pat: &hir::Pat) {
|
||||
self.pat_bindings(pat, |this, ln, var, sp, id| {
|
||||
if !this.warn_about_unused(sp, id, ln, var) {
|
||||
this.warn_about_dead_assign(sp, id, ln, var);
|
||||
|
@ -72,14 +72,15 @@ pub use self::categorization::*;
|
||||
|
||||
use self::Aliasability::*;
|
||||
|
||||
use ast_map;
|
||||
use middle::def_id::DefId;
|
||||
use front::map as ast_map;
|
||||
use middle::infer;
|
||||
use middle::check_const;
|
||||
use middle::def;
|
||||
use middle::ty::{self, Ty};
|
||||
|
||||
use syntax::ast::{MutImmutable, MutMutable};
|
||||
use rustc_front::hir::{MutImmutable, MutMutable};
|
||||
use rustc_front::hir;
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
|
||||
@ -116,7 +117,7 @@ pub enum PointerKind {
|
||||
BorrowedPtr(ty::BorrowKind, ty::Region),
|
||||
|
||||
/// `*T`
|
||||
UnsafePtr(ast::Mutability),
|
||||
UnsafePtr(hir::Mutability),
|
||||
|
||||
/// Implicit deref of the `&T` that results from an overloaded index `[]`.
|
||||
Implicit(ty::BorrowKind, ty::Region),
|
||||
@ -244,12 +245,12 @@ pub trait ast_node {
|
||||
fn span(&self) -> Span;
|
||||
}
|
||||
|
||||
impl ast_node for ast::Expr {
|
||||
impl ast_node for hir::Expr {
|
||||
fn id(&self) -> ast::NodeId { self.id }
|
||||
fn span(&self) -> Span { self.span }
|
||||
}
|
||||
|
||||
impl ast_node for ast::Pat {
|
||||
impl ast_node for hir::Pat {
|
||||
fn id(&self) -> ast::NodeId { self.id }
|
||||
fn span(&self) -> Span { self.span }
|
||||
}
|
||||
@ -262,7 +263,7 @@ pub struct MemCategorizationContext<'t, 'a: 't, 'tcx : 'a> {
|
||||
pub type McResult<T> = Result<T, ()>;
|
||||
|
||||
impl MutabilityCategory {
|
||||
pub fn from_mutbl(m: ast::Mutability) -> MutabilityCategory {
|
||||
pub fn from_mutbl(m: hir::Mutability) -> MutabilityCategory {
|
||||
let ret = match m {
|
||||
MutImmutable => McImmutable,
|
||||
MutMutable => McDeclared
|
||||
@ -304,8 +305,8 @@ impl MutabilityCategory {
|
||||
fn from_local(tcx: &ty::ctxt, id: ast::NodeId) -> MutabilityCategory {
|
||||
let ret = match tcx.map.get(id) {
|
||||
ast_map::NodeLocal(p) | ast_map::NodeArg(p) => match p.node {
|
||||
ast::PatIdent(bind_mode, _, _) => {
|
||||
if bind_mode == ast::BindByValue(ast::MutMutable) {
|
||||
hir::PatIdent(bind_mode, _, _) => {
|
||||
if bind_mode == hir::BindByValue(hir::MutMutable) {
|
||||
McDeclared
|
||||
} else {
|
||||
McImmutable
|
||||
@ -366,7 +367,7 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
self.typer.tcx
|
||||
}
|
||||
|
||||
fn expr_ty(&self, expr: &ast::Expr) -> McResult<Ty<'tcx>> {
|
||||
fn expr_ty(&self, expr: &hir::Expr) -> McResult<Ty<'tcx>> {
|
||||
match self.typer.node_ty(expr.id) {
|
||||
Ok(t) => Ok(t),
|
||||
Err(()) => {
|
||||
@ -376,7 +377,7 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn expr_ty_adjusted(&self, expr: &ast::Expr) -> McResult<Ty<'tcx>> {
|
||||
fn expr_ty_adjusted(&self, expr: &hir::Expr) -> McResult<Ty<'tcx>> {
|
||||
let unadjusted_ty = try!(self.expr_ty(expr));
|
||||
Ok(unadjusted_ty.adjust(
|
||||
self.tcx(), expr.span, expr.id,
|
||||
@ -388,14 +389,14 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
self.typer.node_ty(id)
|
||||
}
|
||||
|
||||
fn pat_ty(&self, pat: &ast::Pat) -> McResult<Ty<'tcx>> {
|
||||
fn pat_ty(&self, pat: &hir::Pat) -> McResult<Ty<'tcx>> {
|
||||
let base_ty = try!(self.typer.node_ty(pat.id));
|
||||
// FIXME (Issue #18207): This code detects whether we are
|
||||
// looking at a `ref x`, and if so, figures out what the type
|
||||
// *being borrowed* is. But ideally we would put in a more
|
||||
// fundamental fix to this conflated use of the node id.
|
||||
let ret_ty = match pat.node {
|
||||
ast::PatIdent(ast::BindByRef(_), _, _) => {
|
||||
hir::PatIdent(hir::BindByRef(_), _, _) => {
|
||||
// a bind-by-ref means that the base_ty will be the type of the ident itself,
|
||||
// but what we want here is the type of the underlying value being borrowed.
|
||||
// So peel off one-level, turning the &T into T.
|
||||
@ -411,7 +412,7 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
Ok(ret_ty)
|
||||
}
|
||||
|
||||
pub fn cat_expr(&self, expr: &ast::Expr) -> McResult<cmt<'tcx>> {
|
||||
pub fn cat_expr(&self, expr: &hir::Expr) -> McResult<cmt<'tcx>> {
|
||||
match self.typer.adjustments().get(&expr.id) {
|
||||
None => {
|
||||
// No adjustments.
|
||||
@ -443,7 +444,7 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
}
|
||||
|
||||
pub fn cat_expr_autoderefd(&self,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
autoderefs: usize)
|
||||
-> McResult<cmt<'tcx>> {
|
||||
let mut cmt = try!(self.cat_expr_unadjusted(expr));
|
||||
@ -456,17 +457,17 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
return Ok(cmt);
|
||||
}
|
||||
|
||||
pub fn cat_expr_unadjusted(&self, expr: &ast::Expr) -> McResult<cmt<'tcx>> {
|
||||
pub fn cat_expr_unadjusted(&self, expr: &hir::Expr) -> McResult<cmt<'tcx>> {
|
||||
debug!("cat_expr: id={} expr={:?}", expr.id, expr);
|
||||
|
||||
let expr_ty = try!(self.expr_ty(expr));
|
||||
match expr.node {
|
||||
ast::ExprUnary(ast::UnDeref, ref e_base) => {
|
||||
hir::ExprUnary(hir::UnDeref, ref e_base) => {
|
||||
let base_cmt = try!(self.cat_expr(&**e_base));
|
||||
self.cat_deref(expr, base_cmt, 0, None)
|
||||
}
|
||||
|
||||
ast::ExprField(ref base, f_name) => {
|
||||
hir::ExprField(ref base, f_name) => {
|
||||
let base_cmt = try!(self.cat_expr(&**base));
|
||||
debug!("cat_expr(cat_field): id={} expr={:?} base={:?}",
|
||||
expr.id,
|
||||
@ -475,12 +476,12 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
Ok(self.cat_field(expr, base_cmt, f_name.node.name, expr_ty))
|
||||
}
|
||||
|
||||
ast::ExprTupField(ref base, idx) => {
|
||||
hir::ExprTupField(ref base, idx) => {
|
||||
let base_cmt = try!(self.cat_expr(&**base));
|
||||
Ok(self.cat_tup_field(expr, base_cmt, idx.node, expr_ty))
|
||||
}
|
||||
|
||||
ast::ExprIndex(ref base, _) => {
|
||||
hir::ExprIndex(ref base, _) => {
|
||||
let method_call = ty::MethodCall::expr(expr.id());
|
||||
let context = InteriorOffsetKind::Index;
|
||||
match self.typer.node_method_ty(method_call) {
|
||||
@ -512,38 +513,28 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
let def = self.tcx().def_map.borrow().get(&expr.id).unwrap().full_def();
|
||||
self.cat_def(expr.id, expr.span, expr_ty, def)
|
||||
}
|
||||
|
||||
ast::ExprParen(ref e) => {
|
||||
hir::ExprParen(ref e) => {
|
||||
self.cat_expr(&**e)
|
||||
}
|
||||
|
||||
ast::ExprAddrOf(..) | ast::ExprCall(..) |
|
||||
ast::ExprAssign(..) | ast::ExprAssignOp(..) |
|
||||
ast::ExprClosure(..) | ast::ExprRet(..) |
|
||||
ast::ExprUnary(..) | ast::ExprRange(..) |
|
||||
ast::ExprMethodCall(..) | ast::ExprCast(..) |
|
||||
ast::ExprVec(..) | ast::ExprTup(..) | ast::ExprIf(..) |
|
||||
ast::ExprBinary(..) | ast::ExprWhile(..) |
|
||||
ast::ExprBlock(..) | ast::ExprLoop(..) | ast::ExprMatch(..) |
|
||||
ast::ExprLit(..) | ast::ExprBreak(..) | ast::ExprMac(..) |
|
||||
ast::ExprAgain(..) | ast::ExprStruct(..) | ast::ExprRepeat(..) |
|
||||
ast::ExprInlineAsm(..) | ast::ExprBox(..) => {
|
||||
hir::ExprAddrOf(..) | hir::ExprCall(..) |
|
||||
hir::ExprAssign(..) | hir::ExprAssignOp(..) |
|
||||
hir::ExprClosure(..) | hir::ExprRet(..) |
|
||||
hir::ExprUnary(..) | hir::ExprRange(..) |
|
||||
hir::ExprMethodCall(..) | hir::ExprCast(..) |
|
||||
hir::ExprVec(..) | hir::ExprTup(..) | hir::ExprIf(..) |
|
||||
hir::ExprBinary(..) | hir::ExprWhile(..) |
|
||||
hir::ExprBlock(..) | hir::ExprLoop(..) | hir::ExprMatch(..) |
|
||||
hir::ExprLit(..) | hir::ExprBreak(..) |
|
||||
hir::ExprAgain(..) | hir::ExprStruct(..) | hir::ExprRepeat(..) |
|
||||
hir::ExprInlineAsm(..) | hir::ExprBox(..) => {
|
||||
Ok(self.cat_rvalue_node(expr.id(), expr.span(), expr_ty))
|
||||
}
|
||||
|
||||
ast::ExprIfLet(..) => {
|
||||
self.tcx().sess.span_bug(expr.span, "non-desugared ExprIfLet");
|
||||
}
|
||||
ast::ExprWhileLet(..) => {
|
||||
self.tcx().sess.span_bug(expr.span, "non-desugared ExprWhileLet");
|
||||
}
|
||||
ast::ExprForLoop(..) => {
|
||||
self.tcx().sess.span_bug(expr.span, "non-desugared ExprForLoop");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -738,7 +729,7 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
};
|
||||
|
||||
match fn_expr.node {
|
||||
ast::ExprClosure(_, _, ref body) => body.id,
|
||||
hir::ExprClosure(_, _, ref body) => body.id,
|
||||
_ => unreachable!()
|
||||
}
|
||||
};
|
||||
@ -1078,8 +1069,8 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
/// These last two bits of info happen to be things that borrowck needs.
|
||||
pub fn cat_slice_pattern(&self,
|
||||
vec_cmt: cmt<'tcx>,
|
||||
slice_pat: &ast::Pat)
|
||||
-> McResult<(cmt<'tcx>, ast::Mutability, ty::Region)> {
|
||||
slice_pat: &hir::Pat)
|
||||
-> McResult<(cmt<'tcx>, hir::Mutability, ty::Region)> {
|
||||
let slice_ty = try!(self.node_ty(slice_pat.id));
|
||||
let (slice_mutbl, slice_r) = vec_slice_info(self.tcx(),
|
||||
slice_pat,
|
||||
@ -1093,9 +1084,9 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
/// ..ref c], then the type of `ref c` will be `&&[]`, so to extract the slice details we
|
||||
/// have to recurse through rptrs.
|
||||
fn vec_slice_info(tcx: &ty::ctxt,
|
||||
pat: &ast::Pat,
|
||||
pat: &hir::Pat,
|
||||
slice_ty: Ty)
|
||||
-> (ast::Mutability, ty::Region) {
|
||||
-> (hir::Mutability, ty::Region) {
|
||||
match slice_ty.sty {
|
||||
ty::TyRef(r, ref mt) => match mt.ty.sty {
|
||||
ty::TySlice(_) => (mt.mutbl, *r),
|
||||
@ -1146,16 +1137,16 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
ret
|
||||
}
|
||||
|
||||
pub fn cat_pattern<F>(&self, cmt: cmt<'tcx>, pat: &ast::Pat, mut op: F) -> McResult<()>
|
||||
where F: FnMut(&MemCategorizationContext<'t, 'a, 'tcx>, cmt<'tcx>, &ast::Pat),
|
||||
pub fn cat_pattern<F>(&self, cmt: cmt<'tcx>, pat: &hir::Pat, mut op: F) -> McResult<()>
|
||||
where F: FnMut(&MemCategorizationContext<'t, 'a, 'tcx>, cmt<'tcx>, &hir::Pat),
|
||||
{
|
||||
self.cat_pattern_(cmt, pat, &mut op)
|
||||
}
|
||||
|
||||
// FIXME(#19596) This is a workaround, but there should be a better way to do this
|
||||
fn cat_pattern_<F>(&self, cmt: cmt<'tcx>, pat: &ast::Pat, op: &mut F)
|
||||
fn cat_pattern_<F>(&self, cmt: cmt<'tcx>, pat: &hir::Pat, op: &mut F)
|
||||
-> McResult<()>
|
||||
where F : FnMut(&MemCategorizationContext<'t, 'a, 'tcx>, cmt<'tcx>, &ast::Pat),
|
||||
where F : FnMut(&MemCategorizationContext<'t, 'a, 'tcx>, cmt<'tcx>, &hir::Pat),
|
||||
{
|
||||
// Here, `cmt` is the categorization for the value being
|
||||
// matched and pat is the pattern it is being matched against.
|
||||
@ -1223,14 +1214,14 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
};
|
||||
|
||||
match pat.node {
|
||||
ast::PatWild(_) => {
|
||||
hir::PatWild(_) => {
|
||||
// _
|
||||
}
|
||||
|
||||
ast::PatEnum(_, None) => {
|
||||
hir::PatEnum(_, None) => {
|
||||
// variant(..)
|
||||
}
|
||||
ast::PatEnum(_, Some(ref subpats)) => {
|
||||
hir::PatEnum(_, Some(ref subpats)) => {
|
||||
match opt_def {
|
||||
Some(def::DefVariant(..)) => {
|
||||
// variant(x, y, z)
|
||||
@ -1268,19 +1259,19 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatQPath(..) => {
|
||||
hir::PatQPath(..) => {
|
||||
// Lone constant: ignore
|
||||
}
|
||||
|
||||
ast::PatIdent(_, _, Some(ref subpat)) => {
|
||||
hir::PatIdent(_, _, Some(ref subpat)) => {
|
||||
try!(self.cat_pattern_(cmt, &**subpat, op));
|
||||
}
|
||||
|
||||
ast::PatIdent(_, _, None) => {
|
||||
hir::PatIdent(_, _, None) => {
|
||||
// nullary variant or identifier: ignore
|
||||
}
|
||||
|
||||
ast::PatStruct(_, ref field_pats, _) => {
|
||||
hir::PatStruct(_, ref field_pats, _) => {
|
||||
// {f1: p1, ..., fN: pN}
|
||||
for fp in field_pats {
|
||||
let field_ty = try!(self.pat_ty(&*fp.node.pat)); // see (*2)
|
||||
@ -1289,7 +1280,7 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatTup(ref subpats) => {
|
||||
hir::PatTup(ref subpats) => {
|
||||
// (p1, ..., pN)
|
||||
for (i, subpat) in subpats.iter().enumerate() {
|
||||
let subpat_ty = try!(self.pat_ty(&**subpat)); // see (*2)
|
||||
@ -1301,7 +1292,7 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatBox(ref subpat) | ast::PatRegion(ref subpat, _) => {
|
||||
hir::PatBox(ref subpat) | hir::PatRegion(ref subpat, _) => {
|
||||
// box p1, &p1, &mut p1. we can ignore the mutability of
|
||||
// PatRegion since that information is already contained
|
||||
// in the type.
|
||||
@ -1309,7 +1300,7 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
try!(self.cat_pattern_(subcmt, &**subpat, op));
|
||||
}
|
||||
|
||||
ast::PatVec(ref before, ref slice, ref after) => {
|
||||
hir::PatVec(ref before, ref slice, ref after) => {
|
||||
let context = InteriorOffsetKind::Pattern;
|
||||
let vec_cmt = try!(self.deref_vec(pat, cmt, context));
|
||||
let elt_cmt = try!(self.cat_index(pat, vec_cmt, context));
|
||||
@ -1326,13 +1317,9 @@ impl<'t, 'a,'tcx> MemCategorizationContext<'t, 'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::PatLit(_) | ast::PatRange(_, _) => {
|
||||
hir::PatLit(_) | hir::PatRange(_, _) => {
|
||||
/*always ok*/
|
||||
}
|
||||
|
||||
ast::PatMac(_) => {
|
||||
self.tcx().sess.span_bug(pat.span, "unexpanded macro");
|
||||
}
|
||||
}
|
||||
|
||||
Ok(())
|
||||
|
@ -14,14 +14,15 @@ use middle::ty;
|
||||
use util::nodemap::FnvHashMap;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::ast_util::walk_pat;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::util::walk_pat;
|
||||
use syntax::codemap::{Span, DUMMY_SP};
|
||||
|
||||
pub type PatIdMap = FnvHashMap<ast::Ident, ast::NodeId>;
|
||||
|
||||
// This is used because same-named variables in alternative patterns need to
|
||||
// use the NodeId of their namesake in the first pattern.
|
||||
pub fn pat_id_map(dm: &DefMap, pat: &ast::Pat) -> PatIdMap {
|
||||
pub fn pat_id_map(dm: &DefMap, pat: &hir::Pat) -> PatIdMap {
|
||||
let mut map = FnvHashMap();
|
||||
pat_bindings(dm, pat, |_bm, p_id, _s, path1| {
|
||||
map.insert(path1.node, p_id);
|
||||
@ -29,27 +30,27 @@ pub fn pat_id_map(dm: &DefMap, pat: &ast::Pat) -> PatIdMap {
|
||||
map
|
||||
}
|
||||
|
||||
pub fn pat_is_refutable(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
pub fn pat_is_refutable(dm: &DefMap, pat: &hir::Pat) -> bool {
|
||||
match pat.node {
|
||||
ast::PatLit(_) | ast::PatRange(_, _) | ast::PatQPath(..) => true,
|
||||
ast::PatEnum(_, _) |
|
||||
ast::PatIdent(_, _, None) |
|
||||
ast::PatStruct(..) => {
|
||||
hir::PatLit(_) | hir::PatRange(_, _) | hir::PatQPath(..) => true,
|
||||
hir::PatEnum(_, _) |
|
||||
hir::PatIdent(_, _, None) |
|
||||
hir::PatStruct(..) => {
|
||||
match dm.borrow().get(&pat.id).map(|d| d.full_def()) {
|
||||
Some(DefVariant(..)) => true,
|
||||
_ => false
|
||||
}
|
||||
}
|
||||
ast::PatVec(_, _, _) => true,
|
||||
hir::PatVec(_, _, _) => true,
|
||||
_ => false
|
||||
}
|
||||
}
|
||||
|
||||
pub fn pat_is_variant_or_struct(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
pub fn pat_is_variant_or_struct(dm: &DefMap, pat: &hir::Pat) -> bool {
|
||||
match pat.node {
|
||||
ast::PatEnum(_, _) |
|
||||
ast::PatIdent(_, _, None) |
|
||||
ast::PatStruct(..) => {
|
||||
hir::PatEnum(_, _) |
|
||||
hir::PatIdent(_, _, None) |
|
||||
hir::PatStruct(..) => {
|
||||
match dm.borrow().get(&pat.id).map(|d| d.full_def()) {
|
||||
Some(DefVariant(..)) | Some(DefStruct(..)) => true,
|
||||
_ => false
|
||||
@ -59,9 +60,9 @@ pub fn pat_is_variant_or_struct(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn pat_is_const(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
pub fn pat_is_const(dm: &DefMap, pat: &hir::Pat) -> bool {
|
||||
match pat.node {
|
||||
ast::PatIdent(_, _, None) | ast::PatEnum(..) | ast::PatQPath(..) => {
|
||||
hir::PatIdent(_, _, None) | hir::PatEnum(..) | hir::PatQPath(..) => {
|
||||
match dm.borrow().get(&pat.id).map(|d| d.full_def()) {
|
||||
Some(DefConst(..)) | Some(DefAssociatedConst(..)) => true,
|
||||
_ => false
|
||||
@ -73,9 +74,9 @@ pub fn pat_is_const(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
|
||||
// Same as above, except that partially-resolved defs cause `false` to be
|
||||
// returned instead of a panic.
|
||||
pub fn pat_is_resolved_const(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
pub fn pat_is_resolved_const(dm: &DefMap, pat: &hir::Pat) -> bool {
|
||||
match pat.node {
|
||||
ast::PatIdent(_, _, None) | ast::PatEnum(..) | ast::PatQPath(..) => {
|
||||
hir::PatIdent(_, _, None) | hir::PatEnum(..) | hir::PatQPath(..) => {
|
||||
match dm.borrow().get(&pat.id)
|
||||
.and_then(|d| if d.depth == 0 { Some(d.base_def) }
|
||||
else { None } ) {
|
||||
@ -87,9 +88,9 @@ pub fn pat_is_resolved_const(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn pat_is_binding(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
pub fn pat_is_binding(dm: &DefMap, pat: &hir::Pat) -> bool {
|
||||
match pat.node {
|
||||
ast::PatIdent(..) => {
|
||||
hir::PatIdent(..) => {
|
||||
!pat_is_variant_or_struct(dm, pat) &&
|
||||
!pat_is_const(dm, pat)
|
||||
}
|
||||
@ -97,22 +98,22 @@ pub fn pat_is_binding(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn pat_is_binding_or_wild(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
pub fn pat_is_binding_or_wild(dm: &DefMap, pat: &hir::Pat) -> bool {
|
||||
match pat.node {
|
||||
ast::PatIdent(..) => pat_is_binding(dm, pat),
|
||||
ast::PatWild(_) => true,
|
||||
hir::PatIdent(..) => pat_is_binding(dm, pat),
|
||||
hir::PatWild(_) => true,
|
||||
_ => false
|
||||
}
|
||||
}
|
||||
|
||||
/// Call `it` on every "binding" in a pattern, e.g., on `a` in
|
||||
/// `match foo() { Some(a) => (), None => () }`
|
||||
pub fn pat_bindings<I>(dm: &DefMap, pat: &ast::Pat, mut it: I) where
|
||||
I: FnMut(ast::BindingMode, ast::NodeId, Span, &ast::SpannedIdent),
|
||||
pub fn pat_bindings<I>(dm: &DefMap, pat: &hir::Pat, mut it: I) where
|
||||
I: FnMut(hir::BindingMode, ast::NodeId, Span, &hir::SpannedIdent),
|
||||
{
|
||||
walk_pat(pat, |p| {
|
||||
match p.node {
|
||||
ast::PatIdent(binding_mode, ref pth, _) if pat_is_binding(dm, p) => {
|
||||
hir::PatIdent(binding_mode, ref pth, _) if pat_is_binding(dm, p) => {
|
||||
it(binding_mode, p.id, p.span, pth);
|
||||
}
|
||||
_ => {}
|
||||
@ -123,7 +124,7 @@ pub fn pat_bindings<I>(dm: &DefMap, pat: &ast::Pat, mut it: I) where
|
||||
|
||||
/// Checks if the pattern contains any patterns that bind something to
|
||||
/// an ident, e.g. `foo`, or `Foo(foo)` or `foo @ Bar(..)`.
|
||||
pub fn pat_contains_bindings(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
pub fn pat_contains_bindings(dm: &DefMap, pat: &hir::Pat) -> bool {
|
||||
let mut contains_bindings = false;
|
||||
walk_pat(pat, |p| {
|
||||
if pat_is_binding(dm, p) {
|
||||
@ -138,18 +139,18 @@ pub fn pat_contains_bindings(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
|
||||
/// Checks if the pattern contains any `ref` or `ref mut` bindings,
|
||||
/// and if yes wether its containing mutable ones or just immutables ones.
|
||||
pub fn pat_contains_ref_binding(dm: &DefMap, pat: &ast::Pat) -> Option<ast::Mutability> {
|
||||
pub fn pat_contains_ref_binding(dm: &DefMap, pat: &hir::Pat) -> Option<hir::Mutability> {
|
||||
let mut result = None;
|
||||
pat_bindings(dm, pat, |mode, _, _, _| {
|
||||
match mode {
|
||||
ast::BindingMode::BindByRef(m) => {
|
||||
hir::BindingMode::BindByRef(m) => {
|
||||
// Pick Mutable as maximum
|
||||
match result {
|
||||
None | Some(ast::MutImmutable) => result = Some(m),
|
||||
None | Some(hir::MutImmutable) => result = Some(m),
|
||||
_ => (),
|
||||
}
|
||||
}
|
||||
ast::BindingMode::BindByValue(_) => { }
|
||||
hir::BindingMode::BindByValue(_) => { }
|
||||
}
|
||||
});
|
||||
result
|
||||
@ -157,18 +158,18 @@ pub fn pat_contains_ref_binding(dm: &DefMap, pat: &ast::Pat) -> Option<ast::Muta
|
||||
|
||||
/// Checks if the patterns for this arm contain any `ref` or `ref mut`
|
||||
/// bindings, and if yes wether its containing mutable ones or just immutables ones.
|
||||
pub fn arm_contains_ref_binding(dm: &DefMap, arm: &ast::Arm) -> Option<ast::Mutability> {
|
||||
pub fn arm_contains_ref_binding(dm: &DefMap, arm: &hir::Arm) -> Option<hir::Mutability> {
|
||||
arm.pats.iter()
|
||||
.filter_map(|pat| pat_contains_ref_binding(dm, pat))
|
||||
.max_by(|m| match *m {
|
||||
ast::MutMutable => 1,
|
||||
ast::MutImmutable => 0,
|
||||
hir::MutMutable => 1,
|
||||
hir::MutImmutable => 0,
|
||||
})
|
||||
}
|
||||
|
||||
/// Checks if the pattern contains any patterns that bind something to
|
||||
/// an ident or wildcard, e.g. `foo`, or `Foo(_)`, `foo @ Bar(..)`,
|
||||
pub fn pat_contains_bindings_or_wild(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
pub fn pat_contains_bindings_or_wild(dm: &DefMap, pat: &hir::Pat) -> bool {
|
||||
let mut contains_bindings = false;
|
||||
walk_pat(pat, |p| {
|
||||
if pat_is_binding_or_wild(dm, p) {
|
||||
@ -181,9 +182,9 @@ pub fn pat_contains_bindings_or_wild(dm: &DefMap, pat: &ast::Pat) -> bool {
|
||||
contains_bindings
|
||||
}
|
||||
|
||||
pub fn simple_identifier<'a>(pat: &'a ast::Pat) -> Option<&'a ast::Ident> {
|
||||
pub fn simple_identifier<'a>(pat: &'a hir::Pat) -> Option<&'a ast::Ident> {
|
||||
match pat.node {
|
||||
ast::PatIdent(ast::BindByValue(_), ref path1, None) => {
|
||||
hir::PatIdent(hir::BindByValue(_), ref path1, None) => {
|
||||
Some(&path1.node)
|
||||
}
|
||||
_ => {
|
||||
@ -192,25 +193,25 @@ pub fn simple_identifier<'a>(pat: &'a ast::Pat) -> Option<&'a ast::Ident> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn def_to_path(tcx: &ty::ctxt, id: DefId) -> ast::Path {
|
||||
tcx.with_path(id, |path| ast::Path {
|
||||
pub fn def_to_path(tcx: &ty::ctxt, id: DefId) -> hir::Path {
|
||||
tcx.with_path(id, |path| hir::Path {
|
||||
global: false,
|
||||
segments: path.last().map(|elem| ast::PathSegment {
|
||||
segments: path.last().map(|elem| hir::PathSegment {
|
||||
identifier: ast::Ident::new(elem.name()),
|
||||
parameters: ast::PathParameters::none(),
|
||||
parameters: hir::PathParameters::none(),
|
||||
}).into_iter().collect(),
|
||||
span: DUMMY_SP,
|
||||
})
|
||||
}
|
||||
|
||||
/// Return variants that are necessary to exist for the pattern to match.
|
||||
pub fn necessary_variants(dm: &DefMap, pat: &ast::Pat) -> Vec<ast::NodeId> {
|
||||
pub fn necessary_variants(dm: &DefMap, pat: &hir::Pat) -> Vec<ast::NodeId> {
|
||||
let mut variants = vec![];
|
||||
walk_pat(pat, |p| {
|
||||
match p.node {
|
||||
ast::PatEnum(_, _) |
|
||||
ast::PatIdent(_, _, None) |
|
||||
ast::PatStruct(..) => {
|
||||
hir::PatEnum(_, _) |
|
||||
hir::PatIdent(_, _, None) |
|
||||
hir::PatStruct(..) => {
|
||||
match dm.borrow().get(&p.id) {
|
||||
Some(&PathResolution { base_def: DefVariant(_, id, _), .. }) => {
|
||||
variants.push(id.node);
|
||||
|
@ -15,7 +15,7 @@
|
||||
// makes all other generics or inline functions that it references
|
||||
// reachable as well.
|
||||
|
||||
use ast_map;
|
||||
use front::map as ast_map;
|
||||
use middle::def;
|
||||
use middle::def_id::{DefId, LOCAL_CRATE};
|
||||
use middle::ty;
|
||||
@ -26,35 +26,36 @@ use util::nodemap::NodeSet;
|
||||
use std::collections::HashSet;
|
||||
use syntax::abi;
|
||||
use syntax::ast;
|
||||
use syntax::attr;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::visit;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::attr;
|
||||
use rustc_front::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
|
||||
// Returns true if the given set of generics implies that the item it's
|
||||
// associated with must be inlined.
|
||||
fn generics_require_inlining(generics: &ast::Generics) -> bool {
|
||||
fn generics_require_inlining(generics: &hir::Generics) -> bool {
|
||||
!generics.ty_params.is_empty()
|
||||
}
|
||||
|
||||
// Returns true if the given item must be inlined because it may be
|
||||
// monomorphized or it was marked with `#[inline]`. This will only return
|
||||
// true for functions.
|
||||
fn item_might_be_inlined(item: &ast::Item) -> bool {
|
||||
fn item_might_be_inlined(item: &hir::Item) -> bool {
|
||||
if attr::requests_inline(&item.attrs) {
|
||||
return true
|
||||
}
|
||||
|
||||
match item.node {
|
||||
ast::ItemImpl(_, _, ref generics, _, _, _) |
|
||||
ast::ItemFn(_, _, _, _, ref generics, _) => {
|
||||
hir::ItemImpl(_, _, ref generics, _, _, _) |
|
||||
hir::ItemFn(_, _, _, _, ref generics, _) => {
|
||||
generics_require_inlining(generics)
|
||||
}
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
|
||||
fn method_might_be_inlined(tcx: &ty::ctxt, sig: &ast::MethodSig,
|
||||
impl_item: &ast::ImplItem,
|
||||
fn method_might_be_inlined(tcx: &ty::ctxt, sig: &hir::MethodSig,
|
||||
impl_item: &hir::ImplItem,
|
||||
impl_src: DefId) -> bool {
|
||||
if attr::requests_inline(&impl_item.attrs) ||
|
||||
generics_require_inlining(&sig.generics) {
|
||||
@ -92,10 +93,10 @@ struct ReachableContext<'a, 'tcx: 'a> {
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for ReachableContext<'a, 'tcx> {
|
||||
|
||||
fn visit_expr(&mut self, expr: &ast::Expr) {
|
||||
fn visit_expr(&mut self, expr: &hir::Expr) {
|
||||
|
||||
match expr.node {
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
let def = match self.tcx.def_map.borrow().get(&expr.id) {
|
||||
Some(d) => d.full_def(),
|
||||
None => {
|
||||
@ -126,7 +127,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for ReachableContext<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::ExprMethodCall(..) => {
|
||||
hir::ExprMethodCall(..) => {
|
||||
let method_call = ty::MethodCall::expr(expr.id);
|
||||
let def_id = self.tcx.tables.borrow().method_map[&method_call].def_id;
|
||||
match self.tcx.impl_or_trait_item(def_id).container() {
|
||||
@ -147,7 +148,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for ReachableContext<'a, 'tcx> {
|
||||
visit::walk_expr(self, expr)
|
||||
}
|
||||
|
||||
fn visit_item(&mut self, _item: &ast::Item) {
|
||||
fn visit_item(&mut self, _item: &hir::Item) {
|
||||
// Do not recurse into items. These items will be added to the worklist
|
||||
// and recursed into manually if necessary.
|
||||
}
|
||||
@ -178,21 +179,21 @@ impl<'a, 'tcx> ReachableContext<'a, 'tcx> {
|
||||
match self.tcx.map.find(node_id) {
|
||||
Some(ast_map::NodeItem(item)) => {
|
||||
match item.node {
|
||||
ast::ItemFn(..) => item_might_be_inlined(&*item),
|
||||
hir::ItemFn(..) => item_might_be_inlined(&*item),
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
Some(ast_map::NodeTraitItem(trait_method)) => {
|
||||
match trait_method.node {
|
||||
ast::ConstTraitItem(_, ref default) => default.is_some(),
|
||||
ast::MethodTraitItem(_, ref body) => body.is_some(),
|
||||
ast::TypeTraitItem(..) => false,
|
||||
hir::ConstTraitItem(_, ref default) => default.is_some(),
|
||||
hir::MethodTraitItem(_, ref body) => body.is_some(),
|
||||
hir::TypeTraitItem(..) => false,
|
||||
}
|
||||
}
|
||||
Some(ast_map::NodeImplItem(impl_item)) => {
|
||||
match impl_item.node {
|
||||
ast::ConstImplItem(..) => true,
|
||||
ast::MethodImplItem(ref sig, _) => {
|
||||
hir::ConstImplItem(..) => true,
|
||||
hir::MethodImplItem(ref sig, _) => {
|
||||
if generics_require_inlining(&sig.generics) ||
|
||||
attr::requests_inline(&impl_item.attrs) {
|
||||
true
|
||||
@ -208,15 +209,14 @@ impl<'a, 'tcx> ReachableContext<'a, 'tcx> {
|
||||
.map
|
||||
.expect_item(impl_did.node)
|
||||
.node {
|
||||
ast::ItemImpl(_, _, ref generics, _, _, _) => {
|
||||
hir::ItemImpl(_, _, ref generics, _, _, _) => {
|
||||
generics_require_inlining(generics)
|
||||
}
|
||||
_ => false
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::TypeImplItem(_) => false,
|
||||
ast::MacImplItem(_) => self.tcx.sess.bug("unexpanded macro")
|
||||
hir::TypeImplItem(_) => false,
|
||||
}
|
||||
}
|
||||
Some(_) => false,
|
||||
@ -257,7 +257,7 @@ impl<'a, 'tcx> ReachableContext<'a, 'tcx> {
|
||||
// but all other rust-only interfaces can be private (they will not
|
||||
// participate in linkage after this product is produced)
|
||||
if let ast_map::NodeItem(item) = *node {
|
||||
if let ast::ItemFn(_, _, _, abi, _, _) = item.node {
|
||||
if let hir::ItemFn(_, _, _, abi, _, _) = item.node {
|
||||
if abi != abi::Rust {
|
||||
self.reachable_symbols.insert(search_item);
|
||||
}
|
||||
@ -274,7 +274,7 @@ impl<'a, 'tcx> ReachableContext<'a, 'tcx> {
|
||||
match *node {
|
||||
ast_map::NodeItem(item) => {
|
||||
match item.node {
|
||||
ast::ItemFn(_, _, _, _, _, ref search_block) => {
|
||||
hir::ItemFn(_, _, _, _, _, ref search_block) => {
|
||||
if item_might_be_inlined(&*item) {
|
||||
visit::walk_block(self, &**search_block)
|
||||
}
|
||||
@ -283,55 +283,48 @@ impl<'a, 'tcx> ReachableContext<'a, 'tcx> {
|
||||
// Reachable constants will be inlined into other crates
|
||||
// unconditionally, so we need to make sure that their
|
||||
// contents are also reachable.
|
||||
ast::ItemConst(_, ref init) => {
|
||||
hir::ItemConst(_, ref init) => {
|
||||
self.visit_expr(&**init);
|
||||
}
|
||||
|
||||
// These are normal, nothing reachable about these
|
||||
// inherently and their children are already in the
|
||||
// worklist, as determined by the privacy pass
|
||||
ast::ItemExternCrate(_) | ast::ItemUse(_) |
|
||||
ast::ItemTy(..) | ast::ItemStatic(_, _, _) |
|
||||
ast::ItemMod(..) | ast::ItemForeignMod(..) |
|
||||
ast::ItemImpl(..) | ast::ItemTrait(..) |
|
||||
ast::ItemStruct(..) | ast::ItemEnum(..) |
|
||||
ast::ItemDefaultImpl(..) => {}
|
||||
|
||||
_ => {
|
||||
self.tcx.sess.span_bug(item.span,
|
||||
"found non-function item \
|
||||
in worklist?!")
|
||||
}
|
||||
hir::ItemExternCrate(_) | hir::ItemUse(_) |
|
||||
hir::ItemTy(..) | hir::ItemStatic(_, _, _) |
|
||||
hir::ItemMod(..) | hir::ItemForeignMod(..) |
|
||||
hir::ItemImpl(..) | hir::ItemTrait(..) |
|
||||
hir::ItemStruct(..) | hir::ItemEnum(..) |
|
||||
hir::ItemDefaultImpl(..) => {}
|
||||
}
|
||||
}
|
||||
ast_map::NodeTraitItem(trait_method) => {
|
||||
match trait_method.node {
|
||||
ast::ConstTraitItem(_, None) |
|
||||
ast::MethodTraitItem(_, None) => {
|
||||
hir::ConstTraitItem(_, None) |
|
||||
hir::MethodTraitItem(_, None) => {
|
||||
// Keep going, nothing to get exported
|
||||
}
|
||||
ast::ConstTraitItem(_, Some(ref expr)) => {
|
||||
hir::ConstTraitItem(_, Some(ref expr)) => {
|
||||
self.visit_expr(&*expr);
|
||||
}
|
||||
ast::MethodTraitItem(_, Some(ref body)) => {
|
||||
hir::MethodTraitItem(_, Some(ref body)) => {
|
||||
visit::walk_block(self, body);
|
||||
}
|
||||
ast::TypeTraitItem(..) => {}
|
||||
hir::TypeTraitItem(..) => {}
|
||||
}
|
||||
}
|
||||
ast_map::NodeImplItem(impl_item) => {
|
||||
match impl_item.node {
|
||||
ast::ConstImplItem(_, ref expr) => {
|
||||
hir::ConstImplItem(_, ref expr) => {
|
||||
self.visit_expr(&*expr);
|
||||
}
|
||||
ast::MethodImplItem(ref sig, ref body) => {
|
||||
hir::MethodImplItem(ref sig, ref body) => {
|
||||
let did = self.tcx.map.get_parent_did(search_item);
|
||||
if method_might_be_inlined(self.tcx, sig, impl_item, did) {
|
||||
visit::walk_block(self, body)
|
||||
}
|
||||
}
|
||||
ast::TypeImplItem(_) => {}
|
||||
ast::MacImplItem(_) => self.tcx.sess.bug("unexpanded macro")
|
||||
hir::TypeImplItem(_) => {}
|
||||
}
|
||||
}
|
||||
// Nothing to recurse on for these
|
||||
|
@ -16,20 +16,22 @@
|
||||
//! Most of the documentation on regions can be found in
|
||||
//! `middle/typeck/infer/region_inference.rs`
|
||||
|
||||
use ast_map;
|
||||
use metadata::inline::InlinedItem;
|
||||
use middle::ty::{self, Ty};
|
||||
use front::map as ast_map;
|
||||
use session::Session;
|
||||
use util::nodemap::{FnvHashMap, NodeMap, NodeSet};
|
||||
use middle::ty::{self, Ty};
|
||||
|
||||
use std::cell::RefCell;
|
||||
use std::collections::hash_map::Entry;
|
||||
use std::mem;
|
||||
use syntax::codemap::{self, Span};
|
||||
use syntax::{ast, visit};
|
||||
use syntax::ast::{Block, Item, FnDecl, NodeId, Arm, Pat, Stmt, Expr, Local};
|
||||
use syntax::ast_util::stmt_id;
|
||||
use syntax::visit::{Visitor, FnKind};
|
||||
use syntax::ast::{self, NodeId};
|
||||
|
||||
use rustc_front::hir;
|
||||
use rustc_front::visit::{self, Visitor, FnKind};
|
||||
use rustc_front::hir::{Block, Item, FnDecl, Arm, Pat, Stmt, Expr, Local};
|
||||
use rustc_front::util::stmt_id;
|
||||
|
||||
#[derive(Clone, PartialEq, PartialOrd, Eq, Ord, Hash, RustcEncodable,
|
||||
RustcDecodable, Debug, Copy)]
|
||||
@ -632,7 +634,7 @@ fn record_var_lifetime(visitor: &mut RegionResolutionVisitor,
|
||||
}
|
||||
}
|
||||
|
||||
fn resolve_block(visitor: &mut RegionResolutionVisitor, blk: &ast::Block) {
|
||||
fn resolve_block(visitor: &mut RegionResolutionVisitor, blk: &hir::Block) {
|
||||
debug!("resolve_block(blk.id={:?})", blk.id);
|
||||
|
||||
let prev_cx = visitor.cx;
|
||||
@ -676,7 +678,7 @@ fn resolve_block(visitor: &mut RegionResolutionVisitor, blk: &ast::Block) {
|
||||
// index information.)
|
||||
|
||||
for (i, statement) in blk.stmts.iter().enumerate() {
|
||||
if let ast::StmtDecl(..) = statement.node {
|
||||
if let hir::StmtDecl(..) = statement.node {
|
||||
// Each StmtDecl introduces a subscope for bindings
|
||||
// introduced by the declaration; this subscope covers
|
||||
// a suffix of the block . Each subscope in a block
|
||||
@ -703,7 +705,7 @@ fn resolve_block(visitor: &mut RegionResolutionVisitor, blk: &ast::Block) {
|
||||
visitor.cx = prev_cx;
|
||||
}
|
||||
|
||||
fn resolve_arm(visitor: &mut RegionResolutionVisitor, arm: &ast::Arm) {
|
||||
fn resolve_arm(visitor: &mut RegionResolutionVisitor, arm: &hir::Arm) {
|
||||
visitor.terminating_scopes.insert(arm.body.id);
|
||||
|
||||
if let Some(ref expr) = arm.guard {
|
||||
@ -713,13 +715,13 @@ fn resolve_arm(visitor: &mut RegionResolutionVisitor, arm: &ast::Arm) {
|
||||
visit::walk_arm(visitor, arm);
|
||||
}
|
||||
|
||||
fn resolve_pat(visitor: &mut RegionResolutionVisitor, pat: &ast::Pat) {
|
||||
fn resolve_pat(visitor: &mut RegionResolutionVisitor, pat: &hir::Pat) {
|
||||
visitor.new_node_extent(pat.id);
|
||||
|
||||
// If this is a binding (or maybe a binding, I'm too lazy to check
|
||||
// the def map) then record the lifetime of that binding.
|
||||
match pat.node {
|
||||
ast::PatIdent(..) => {
|
||||
hir::PatIdent(..) => {
|
||||
record_var_lifetime(visitor, pat.id, pat.span);
|
||||
}
|
||||
_ => { }
|
||||
@ -728,7 +730,7 @@ fn resolve_pat(visitor: &mut RegionResolutionVisitor, pat: &ast::Pat) {
|
||||
visit::walk_pat(visitor, pat);
|
||||
}
|
||||
|
||||
fn resolve_stmt(visitor: &mut RegionResolutionVisitor, stmt: &ast::Stmt) {
|
||||
fn resolve_stmt(visitor: &mut RegionResolutionVisitor, stmt: &hir::Stmt) {
|
||||
let stmt_id = stmt_id(stmt);
|
||||
debug!("resolve_stmt(stmt.id={:?})", stmt_id);
|
||||
|
||||
@ -746,7 +748,7 @@ fn resolve_stmt(visitor: &mut RegionResolutionVisitor, stmt: &ast::Stmt) {
|
||||
visitor.cx.parent = prev_parent;
|
||||
}
|
||||
|
||||
fn resolve_expr(visitor: &mut RegionResolutionVisitor, expr: &ast::Expr) {
|
||||
fn resolve_expr(visitor: &mut RegionResolutionVisitor, expr: &hir::Expr) {
|
||||
debug!("resolve_expr(expr.id={:?})", expr.id);
|
||||
|
||||
let expr_extent = visitor.new_node_extent_with_dtor(expr.id);
|
||||
@ -763,38 +765,38 @@ fn resolve_expr(visitor: &mut RegionResolutionVisitor, expr: &ast::Expr) {
|
||||
// scopes, meaning that temporaries cannot outlive them.
|
||||
// This ensures fixed size stacks.
|
||||
|
||||
ast::ExprBinary(codemap::Spanned { node: ast::BiAnd, .. }, _, ref r) |
|
||||
ast::ExprBinary(codemap::Spanned { node: ast::BiOr, .. }, _, ref r) => {
|
||||
hir::ExprBinary(codemap::Spanned { node: hir::BiAnd, .. }, _, ref r) |
|
||||
hir::ExprBinary(codemap::Spanned { node: hir::BiOr, .. }, _, ref r) => {
|
||||
// For shortcircuiting operators, mark the RHS as a terminating
|
||||
// scope since it only executes conditionally.
|
||||
terminating(r.id);
|
||||
}
|
||||
|
||||
ast::ExprIf(_, ref then, Some(ref otherwise)) => {
|
||||
hir::ExprIf(_, ref then, Some(ref otherwise)) => {
|
||||
terminating(then.id);
|
||||
terminating(otherwise.id);
|
||||
}
|
||||
|
||||
ast::ExprIf(ref expr, ref then, None) => {
|
||||
hir::ExprIf(ref expr, ref then, None) => {
|
||||
terminating(expr.id);
|
||||
terminating(then.id);
|
||||
}
|
||||
|
||||
ast::ExprLoop(ref body, _) => {
|
||||
hir::ExprLoop(ref body, _) => {
|
||||
terminating(body.id);
|
||||
}
|
||||
|
||||
ast::ExprWhile(ref expr, ref body, _) => {
|
||||
hir::ExprWhile(ref expr, ref body, _) => {
|
||||
terminating(expr.id);
|
||||
terminating(body.id);
|
||||
}
|
||||
|
||||
ast::ExprMatch(..) => {
|
||||
hir::ExprMatch(..) => {
|
||||
visitor.cx.var_parent = expr_extent;
|
||||
}
|
||||
|
||||
ast::ExprAssignOp(..) | ast::ExprIndex(..) |
|
||||
ast::ExprUnary(..) | ast::ExprCall(..) | ast::ExprMethodCall(..) => {
|
||||
hir::ExprAssignOp(..) | hir::ExprIndex(..) |
|
||||
hir::ExprUnary(..) | hir::ExprCall(..) | hir::ExprMethodCall(..) => {
|
||||
// FIXME(#6268) Nested method calls
|
||||
//
|
||||
// The lifetimes for a call or method call look as follows:
|
||||
@ -823,7 +825,7 @@ fn resolve_expr(visitor: &mut RegionResolutionVisitor, expr: &ast::Expr) {
|
||||
visitor.cx = prev_cx;
|
||||
}
|
||||
|
||||
fn resolve_local(visitor: &mut RegionResolutionVisitor, local: &ast::Local) {
|
||||
fn resolve_local(visitor: &mut RegionResolutionVisitor, local: &hir::Local) {
|
||||
debug!("resolve_local(local.id={:?},local.init={:?})",
|
||||
local.id,local.init.is_some());
|
||||
|
||||
@ -920,26 +922,26 @@ fn resolve_local(visitor: &mut RegionResolutionVisitor, local: &ast::Local) {
|
||||
/// | [ ..., P&, ... ]
|
||||
/// | ( ..., P&, ... )
|
||||
/// | box P&
|
||||
fn is_binding_pat(pat: &ast::Pat) -> bool {
|
||||
fn is_binding_pat(pat: &hir::Pat) -> bool {
|
||||
match pat.node {
|
||||
ast::PatIdent(ast::BindByRef(_), _, _) => true,
|
||||
hir::PatIdent(hir::BindByRef(_), _, _) => true,
|
||||
|
||||
ast::PatStruct(_, ref field_pats, _) => {
|
||||
hir::PatStruct(_, ref field_pats, _) => {
|
||||
field_pats.iter().any(|fp| is_binding_pat(&*fp.node.pat))
|
||||
}
|
||||
|
||||
ast::PatVec(ref pats1, ref pats2, ref pats3) => {
|
||||
hir::PatVec(ref pats1, ref pats2, ref pats3) => {
|
||||
pats1.iter().any(|p| is_binding_pat(&**p)) ||
|
||||
pats2.iter().any(|p| is_binding_pat(&**p)) ||
|
||||
pats3.iter().any(|p| is_binding_pat(&**p))
|
||||
}
|
||||
|
||||
ast::PatEnum(_, Some(ref subpats)) |
|
||||
ast::PatTup(ref subpats) => {
|
||||
hir::PatEnum(_, Some(ref subpats)) |
|
||||
hir::PatTup(ref subpats) => {
|
||||
subpats.iter().any(|p| is_binding_pat(&**p))
|
||||
}
|
||||
|
||||
ast::PatBox(ref subpat) => {
|
||||
hir::PatBox(ref subpat) => {
|
||||
is_binding_pat(&**subpat)
|
||||
}
|
||||
|
||||
@ -948,9 +950,9 @@ fn resolve_local(visitor: &mut RegionResolutionVisitor, local: &ast::Local) {
|
||||
}
|
||||
|
||||
/// True if `ty` is a borrowed pointer type like `&int` or `&[...]`.
|
||||
fn is_borrowed_ty(ty: &ast::Ty) -> bool {
|
||||
fn is_borrowed_ty(ty: &hir::Ty) -> bool {
|
||||
match ty.node {
|
||||
ast::TyRptr(..) => true,
|
||||
hir::TyRptr(..) => true,
|
||||
_ => false
|
||||
}
|
||||
}
|
||||
@ -966,34 +968,34 @@ fn resolve_local(visitor: &mut RegionResolutionVisitor, local: &ast::Local) {
|
||||
/// | E& as ...
|
||||
/// | ( E& )
|
||||
fn record_rvalue_scope_if_borrow_expr(visitor: &mut RegionResolutionVisitor,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
blk_id: CodeExtent) {
|
||||
match expr.node {
|
||||
ast::ExprAddrOf(_, ref subexpr) => {
|
||||
hir::ExprAddrOf(_, ref subexpr) => {
|
||||
record_rvalue_scope_if_borrow_expr(visitor, &**subexpr, blk_id);
|
||||
record_rvalue_scope(visitor, &**subexpr, blk_id);
|
||||
}
|
||||
ast::ExprStruct(_, ref fields, _) => {
|
||||
hir::ExprStruct(_, ref fields, _) => {
|
||||
for field in fields {
|
||||
record_rvalue_scope_if_borrow_expr(
|
||||
visitor, &*field.expr, blk_id);
|
||||
}
|
||||
}
|
||||
ast::ExprVec(ref subexprs) |
|
||||
ast::ExprTup(ref subexprs) => {
|
||||
hir::ExprVec(ref subexprs) |
|
||||
hir::ExprTup(ref subexprs) => {
|
||||
for subexpr in subexprs {
|
||||
record_rvalue_scope_if_borrow_expr(
|
||||
visitor, &**subexpr, blk_id);
|
||||
}
|
||||
}
|
||||
ast::ExprUnary(ast::UnUniq, ref subexpr) => {
|
||||
hir::ExprUnary(hir::UnUniq, ref subexpr) => {
|
||||
record_rvalue_scope_if_borrow_expr(visitor, &**subexpr, blk_id);
|
||||
}
|
||||
ast::ExprCast(ref subexpr, _) |
|
||||
ast::ExprParen(ref subexpr) => {
|
||||
hir::ExprCast(ref subexpr, _) |
|
||||
hir::ExprParen(ref subexpr) => {
|
||||
record_rvalue_scope_if_borrow_expr(visitor, &**subexpr, blk_id)
|
||||
}
|
||||
ast::ExprBlock(ref block) => {
|
||||
hir::ExprBlock(ref block) => {
|
||||
match block.expr {
|
||||
Some(ref subexpr) => {
|
||||
record_rvalue_scope_if_borrow_expr(
|
||||
@ -1023,7 +1025,7 @@ fn resolve_local(visitor: &mut RegionResolutionVisitor, local: &ast::Local) {
|
||||
///
|
||||
/// Note: ET is intended to match "rvalues or lvalues based on rvalues".
|
||||
fn record_rvalue_scope<'a>(visitor: &mut RegionResolutionVisitor,
|
||||
expr: &'a ast::Expr,
|
||||
expr: &'a hir::Expr,
|
||||
blk_scope: CodeExtent) {
|
||||
let mut expr = expr;
|
||||
loop {
|
||||
@ -1035,12 +1037,12 @@ fn resolve_local(visitor: &mut RegionResolutionVisitor, local: &ast::Local) {
|
||||
visitor.region_maps.record_rvalue_scope(expr.id, blk_scope);
|
||||
|
||||
match expr.node {
|
||||
ast::ExprAddrOf(_, ref subexpr) |
|
||||
ast::ExprUnary(ast::UnDeref, ref subexpr) |
|
||||
ast::ExprField(ref subexpr, _) |
|
||||
ast::ExprTupField(ref subexpr, _) |
|
||||
ast::ExprIndex(ref subexpr, _) |
|
||||
ast::ExprParen(ref subexpr) => {
|
||||
hir::ExprAddrOf(_, ref subexpr) |
|
||||
hir::ExprUnary(hir::UnDeref, ref subexpr) |
|
||||
hir::ExprField(ref subexpr, _) |
|
||||
hir::ExprTupField(ref subexpr, _) |
|
||||
hir::ExprIndex(ref subexpr, _) |
|
||||
hir::ExprParen(ref subexpr) => {
|
||||
expr = &**subexpr;
|
||||
}
|
||||
_ => {
|
||||
@ -1051,7 +1053,7 @@ fn resolve_local(visitor: &mut RegionResolutionVisitor, local: &ast::Local) {
|
||||
}
|
||||
}
|
||||
|
||||
fn resolve_item(visitor: &mut RegionResolutionVisitor, item: &ast::Item) {
|
||||
fn resolve_item(visitor: &mut RegionResolutionVisitor, item: &hir::Item) {
|
||||
// Items create a new outer block scope as far as we're concerned.
|
||||
let prev_cx = visitor.cx;
|
||||
let prev_ts = mem::replace(&mut visitor.terminating_scopes, NodeSet());
|
||||
@ -1068,8 +1070,8 @@ fn resolve_item(visitor: &mut RegionResolutionVisitor, item: &ast::Item) {
|
||||
|
||||
fn resolve_fn(visitor: &mut RegionResolutionVisitor,
|
||||
_: FnKind,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block,
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block,
|
||||
sp: Span,
|
||||
id: ast::NodeId) {
|
||||
debug!("region::resolve_fn(id={:?}, \
|
||||
@ -1159,12 +1161,12 @@ impl<'a, 'v> Visitor<'v> for RegionResolutionVisitor<'a> {
|
||||
resolve_item(self, i);
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, ii: &ast::ImplItem) {
|
||||
fn visit_impl_item(&mut self, ii: &hir::ImplItem) {
|
||||
visit::walk_impl_item(self, ii);
|
||||
self.create_item_scope_if_needed(ii.id);
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, ti: &ast::TraitItem) {
|
||||
fn visit_trait_item(&mut self, ti: &hir::TraitItem) {
|
||||
visit::walk_trait_item(self, ti);
|
||||
self.create_item_scope_if_needed(ti.id);
|
||||
}
|
||||
@ -1190,7 +1192,7 @@ impl<'a, 'v> Visitor<'v> for RegionResolutionVisitor<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn resolve_crate(sess: &Session, krate: &ast::Crate) -> RegionMaps {
|
||||
pub fn resolve_crate(sess: &Session, krate: &hir::Crate) -> RegionMaps {
|
||||
let maps = RegionMaps {
|
||||
code_extents: RefCell::new(vec![]),
|
||||
code_extent_interner: RefCell::new(FnvHashMap()),
|
||||
|
@ -28,11 +28,12 @@ use std::mem::replace;
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::parse::token::special_idents;
|
||||
use syntax::print::pprust::lifetime_to_string;
|
||||
use syntax::visit;
|
||||
use syntax::visit::{FnKind, Visitor};
|
||||
use util::nodemap::NodeMap;
|
||||
|
||||
use rustc_front::hir;
|
||||
use rustc_front::print::pprust::lifetime_to_string;
|
||||
use rustc_front::visit::{self, Visitor, FnKind};
|
||||
|
||||
#[derive(Clone, Copy, PartialEq, Eq, Hash, RustcEncodable, RustcDecodable, Debug)]
|
||||
pub enum DefRegion {
|
||||
DefStaticRegion,
|
||||
@ -78,10 +79,10 @@ struct LifetimeContext<'a> {
|
||||
enum ScopeChain<'a> {
|
||||
/// EarlyScope(i, ['a, 'b, ...], s) extends s with early-bound
|
||||
/// lifetimes, assigning indexes 'a => i, 'b => i+1, ... etc.
|
||||
EarlyScope(subst::ParamSpace, &'a Vec<ast::LifetimeDef>, Scope<'a>),
|
||||
EarlyScope(subst::ParamSpace, &'a Vec<hir::LifetimeDef>, Scope<'a>),
|
||||
/// LateScope(['a, 'b, ...], s) extends s with late-bound
|
||||
/// lifetimes introduced by the declaration binder_id.
|
||||
LateScope(&'a Vec<ast::LifetimeDef>, Scope<'a>),
|
||||
LateScope(&'a Vec<hir::LifetimeDef>, Scope<'a>),
|
||||
/// lifetimes introduced by items within a code block are scoped
|
||||
/// to that block.
|
||||
BlockScope(region::DestructionScopeData, Scope<'a>),
|
||||
@ -92,7 +93,7 @@ type Scope<'a> = &'a ScopeChain<'a>;
|
||||
|
||||
static ROOT_SCOPE: ScopeChain<'static> = RootScope;
|
||||
|
||||
pub fn krate(sess: &Session, krate: &ast::Crate, def_map: &DefMap) -> NamedRegionMap {
|
||||
pub fn krate(sess: &Session, krate: &hir::Crate, def_map: &DefMap) -> NamedRegionMap {
|
||||
let mut named_region_map = NodeMap();
|
||||
visit::walk_crate(&mut LifetimeContext {
|
||||
sess: sess,
|
||||
@ -107,7 +108,7 @@ pub fn krate(sess: &Session, krate: &ast::Crate, def_map: &DefMap) -> NamedRegio
|
||||
}
|
||||
|
||||
impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
// Items save/restore the set of labels. This way inner items
|
||||
// can freely reuse names, be they loop labels or lifetimes.
|
||||
let saved = replace(&mut self.labels_in_fn, vec![]);
|
||||
@ -115,26 +116,25 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
// Items always introduce a new root scope
|
||||
self.with(RootScope, |_, this| {
|
||||
match item.node {
|
||||
ast::ItemFn(..) => {
|
||||
hir::ItemFn(..) => {
|
||||
// Fn lifetimes get added in visit_fn below:
|
||||
visit::walk_item(this, item);
|
||||
}
|
||||
ast::ItemExternCrate(_) |
|
||||
ast::ItemUse(_) |
|
||||
ast::ItemMod(..) |
|
||||
ast::ItemMac(..) |
|
||||
ast::ItemDefaultImpl(..) |
|
||||
ast::ItemForeignMod(..) |
|
||||
ast::ItemStatic(..) |
|
||||
ast::ItemConst(..) => {
|
||||
hir::ItemExternCrate(_) |
|
||||
hir::ItemUse(_) |
|
||||
hir::ItemMod(..) |
|
||||
hir::ItemDefaultImpl(..) |
|
||||
hir::ItemForeignMod(..) |
|
||||
hir::ItemStatic(..) |
|
||||
hir::ItemConst(..) => {
|
||||
// These sorts of items have no lifetime parameters at all.
|
||||
visit::walk_item(this, item);
|
||||
}
|
||||
ast::ItemTy(_, ref generics) |
|
||||
ast::ItemEnum(_, ref generics) |
|
||||
ast::ItemStruct(_, ref generics) |
|
||||
ast::ItemTrait(_, ref generics, _, _) |
|
||||
ast::ItemImpl(_, _, ref generics, _, _, _) => {
|
||||
hir::ItemTy(_, ref generics) |
|
||||
hir::ItemEnum(_, ref generics) |
|
||||
hir::ItemStruct(_, ref generics) |
|
||||
hir::ItemTrait(_, ref generics, _, _) |
|
||||
hir::ItemImpl(_, _, ref generics, _, _, _) => {
|
||||
// These kinds of items have only early bound lifetime parameters.
|
||||
let lifetimes = &generics.lifetimes;
|
||||
let early_scope = EarlyScope(subst::TypeSpace, lifetimes, &ROOT_SCOPE);
|
||||
@ -150,7 +150,7 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
replace(&mut self.labels_in_fn, saved);
|
||||
}
|
||||
|
||||
fn visit_foreign_item(&mut self, item: &ast::ForeignItem) {
|
||||
fn visit_foreign_item(&mut self, item: &hir::ForeignItem) {
|
||||
// Items save/restore the set of labels. This way inner items
|
||||
// can freely reuse names, be they loop labels or lifetimes.
|
||||
let saved = replace(&mut self.labels_in_fn, vec![]);
|
||||
@ -158,12 +158,12 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
// Items always introduce a new root scope
|
||||
self.with(RootScope, |_, this| {
|
||||
match item.node {
|
||||
ast::ForeignItemFn(_, ref generics) => {
|
||||
hir::ForeignItemFn(_, ref generics) => {
|
||||
this.visit_early_late(subst::FnSpace, generics, |this| {
|
||||
visit::walk_foreign_item(this, item);
|
||||
})
|
||||
}
|
||||
ast::ForeignItemStatic(..) => {
|
||||
hir::ForeignItemStatic(..) => {
|
||||
visit::walk_foreign_item(this, item);
|
||||
}
|
||||
}
|
||||
@ -173,8 +173,8 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
replace(&mut self.labels_in_fn, saved);
|
||||
}
|
||||
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v ast::FnDecl,
|
||||
b: &'v ast::Block, s: Span, _: ast::NodeId) {
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v hir::FnDecl,
|
||||
b: &'v hir::Block, s: Span, _: ast::NodeId) {
|
||||
match fk {
|
||||
FnKind::ItemFn(_, generics, _, _, _, _) => {
|
||||
self.visit_early_late(subst::FnSpace, generics, |this| {
|
||||
@ -192,9 +192,9 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_ty(&mut self, ty: &ast::Ty) {
|
||||
fn visit_ty(&mut self, ty: &hir::Ty) {
|
||||
match ty.node {
|
||||
ast::TyBareFn(ref c) => {
|
||||
hir::TyBareFn(ref c) => {
|
||||
visit::walk_lifetime_decls_helper(self, &c.lifetimes);
|
||||
self.with(LateScope(&c.lifetimes, self.scope), |old_scope, this| {
|
||||
// a bare fn has no bounds, so everything
|
||||
@ -203,7 +203,7 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
visit::walk_ty(this, ty);
|
||||
});
|
||||
}
|
||||
ast::TyPath(None, ref path) => {
|
||||
hir::TyPath(None, ref path) => {
|
||||
// if this path references a trait, then this will resolve to
|
||||
// a trait ref, which introduces a binding scope.
|
||||
match self.def_map.borrow().get(&ty.id).map(|d| (d.base_def, d.depth)) {
|
||||
@ -223,12 +223,12 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, trait_item: &ast::TraitItem) {
|
||||
fn visit_trait_item(&mut self, trait_item: &hir::TraitItem) {
|
||||
// We reset the labels on every trait item, so that different
|
||||
// methods in an impl can reuse label names.
|
||||
let saved = replace(&mut self.labels_in_fn, vec![]);
|
||||
|
||||
if let ast::MethodTraitItem(ref sig, None) = trait_item.node {
|
||||
if let hir::MethodTraitItem(ref sig, None) = trait_item.node {
|
||||
self.visit_early_late(
|
||||
subst::FnSpace, &sig.generics,
|
||||
|this| visit::walk_trait_item(this, trait_item))
|
||||
@ -239,13 +239,13 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
replace(&mut self.labels_in_fn, saved);
|
||||
}
|
||||
|
||||
fn visit_block(&mut self, b: &ast::Block) {
|
||||
fn visit_block(&mut self, b: &hir::Block) {
|
||||
self.with(BlockScope(region::DestructionScopeData::new(b.id),
|
||||
self.scope),
|
||||
|_, this| visit::walk_block(this, b));
|
||||
}
|
||||
|
||||
fn visit_lifetime_ref(&mut self, lifetime_ref: &ast::Lifetime) {
|
||||
fn visit_lifetime_ref(&mut self, lifetime_ref: &hir::Lifetime) {
|
||||
if lifetime_ref.name == special_idents::static_lifetime.name {
|
||||
self.insert_lifetime(lifetime_ref, DefStaticRegion);
|
||||
return;
|
||||
@ -253,7 +253,7 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
self.resolve_lifetime_ref(lifetime_ref);
|
||||
}
|
||||
|
||||
fn visit_generics(&mut self, generics: &ast::Generics) {
|
||||
fn visit_generics(&mut self, generics: &hir::Generics) {
|
||||
for ty_param in generics.ty_params.iter() {
|
||||
visit::walk_ty_param_bounds_helper(self, &ty_param.bounds);
|
||||
match ty_param.default {
|
||||
@ -263,7 +263,7 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
}
|
||||
for predicate in &generics.where_clause.predicates {
|
||||
match predicate {
|
||||
&ast::WherePredicate::BoundPredicate(ast::WhereBoundPredicate{ ref bounded_ty,
|
||||
&hir::WherePredicate::BoundPredicate(hir::WhereBoundPredicate{ ref bounded_ty,
|
||||
ref bounds,
|
||||
ref bound_lifetimes,
|
||||
.. }) => {
|
||||
@ -282,7 +282,7 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
visit::walk_ty_param_bounds_helper(self, bounds);
|
||||
}
|
||||
}
|
||||
&ast::WherePredicate::RegionPredicate(ast::WhereRegionPredicate{ref lifetime,
|
||||
&hir::WherePredicate::RegionPredicate(hir::WhereRegionPredicate{ref lifetime,
|
||||
ref bounds,
|
||||
.. }) => {
|
||||
|
||||
@ -291,7 +291,7 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
self.visit_lifetime_ref(bound);
|
||||
}
|
||||
}
|
||||
&ast::WherePredicate::EqPredicate(ast::WhereEqPredicate{ id,
|
||||
&hir::WherePredicate::EqPredicate(hir::WhereEqPredicate{ id,
|
||||
ref path,
|
||||
ref ty,
|
||||
.. }) => {
|
||||
@ -303,8 +303,8 @@ impl<'a, 'v> Visitor<'v> for LifetimeContext<'a> {
|
||||
}
|
||||
|
||||
fn visit_poly_trait_ref(&mut self,
|
||||
trait_ref: &ast::PolyTraitRef,
|
||||
_modifier: &ast::TraitBoundModifier) {
|
||||
trait_ref: &hir::PolyTraitRef,
|
||||
_modifier: &hir::TraitBoundModifier) {
|
||||
debug!("visit_poly_trait_ref trait_ref={:?}", trait_ref);
|
||||
|
||||
if !self.trait_ref_hack || !trait_ref.bound_lifetimes.is_empty() {
|
||||
@ -337,10 +337,10 @@ fn original_label(span: Span) -> Original {
|
||||
fn shadower_label(span: Span) -> Shadower {
|
||||
Shadower { kind: ShadowKind::Label, span: span }
|
||||
}
|
||||
fn original_lifetime(l: &ast::Lifetime) -> Original {
|
||||
fn original_lifetime(l: &hir::Lifetime) -> Original {
|
||||
Original { kind: ShadowKind::Lifetime, span: l.span }
|
||||
}
|
||||
fn shadower_lifetime(l: &ast::Lifetime) -> Shadower {
|
||||
fn shadower_lifetime(l: &hir::Lifetime) -> Shadower {
|
||||
Shadower { kind: ShadowKind::Lifetime, span: l.span }
|
||||
}
|
||||
|
||||
@ -376,7 +376,7 @@ fn signal_shadowing_problem(
|
||||
|
||||
// Adds all labels in `b` to `ctxt.labels_in_fn`, signalling a warning
|
||||
// if one of the label shadows a lifetime or another label.
|
||||
fn extract_labels<'v, 'a>(ctxt: &mut LifetimeContext<'a>, b: &'v ast::Block) {
|
||||
fn extract_labels<'v, 'a>(ctxt: &mut LifetimeContext<'a>, b: &'v hir::Block) {
|
||||
|
||||
struct GatherLabels<'a> {
|
||||
sess: &'a Session,
|
||||
@ -393,11 +393,11 @@ fn extract_labels<'v, 'a>(ctxt: &mut LifetimeContext<'a>, b: &'v ast::Block) {
|
||||
return;
|
||||
|
||||
impl<'v, 'a> Visitor<'v> for GatherLabels<'a> {
|
||||
fn visit_expr(&mut self, ex: &'v ast::Expr) {
|
||||
fn visit_expr(&mut self, ex: &'v hir::Expr) {
|
||||
// do not recurse into closures defined in the block
|
||||
// since they are treated as separate fns from the POV of
|
||||
// labels_in_fn
|
||||
if let ast::ExprClosure(..) = ex.node {
|
||||
if let hir::ExprClosure(..) = ex.node {
|
||||
return
|
||||
}
|
||||
if let Some(label) = expression_label(ex) {
|
||||
@ -421,17 +421,15 @@ fn extract_labels<'v, 'a>(ctxt: &mut LifetimeContext<'a>, b: &'v ast::Block) {
|
||||
visit::walk_expr(self, ex)
|
||||
}
|
||||
|
||||
fn visit_item(&mut self, _: &ast::Item) {
|
||||
fn visit_item(&mut self, _: &hir::Item) {
|
||||
// do not recurse into items defined in the block
|
||||
}
|
||||
}
|
||||
|
||||
fn expression_label(ex: &ast::Expr) -> Option<ast::Ident> {
|
||||
fn expression_label(ex: &hir::Expr) -> Option<ast::Ident> {
|
||||
match ex.node {
|
||||
ast::ExprWhile(_, _, Some(label)) |
|
||||
ast::ExprWhileLet(_, _, _, Some(label)) |
|
||||
ast::ExprForLoop(_, _, _, Some(label)) |
|
||||
ast::ExprLoop(_, Some(label)) => Some(label),
|
||||
hir::ExprWhile(_, _, Some(label)) |
|
||||
hir::ExprLoop(_, Some(label)) => Some(label),
|
||||
_ => None,
|
||||
}
|
||||
}
|
||||
@ -471,8 +469,8 @@ impl<'a> LifetimeContext<'a> {
|
||||
// the function body itself.
|
||||
fn walk_fn<'b>(&mut self,
|
||||
fk: FnKind,
|
||||
fd: &ast::FnDecl,
|
||||
fb: &'b ast::Block,
|
||||
fd: &hir::FnDecl,
|
||||
fb: &'b hir::Block,
|
||||
_span: Span) {
|
||||
match fk {
|
||||
FnKind::ItemFn(_, generics, _, _, _, _) => {
|
||||
@ -533,7 +531,7 @@ impl<'a> LifetimeContext<'a> {
|
||||
/// ordering is not important there.
|
||||
fn visit_early_late<F>(&mut self,
|
||||
early_space: subst::ParamSpace,
|
||||
generics: &ast::Generics,
|
||||
generics: &hir::Generics,
|
||||
walk: F) where
|
||||
F: FnOnce(&mut LifetimeContext),
|
||||
{
|
||||
@ -553,7 +551,7 @@ impl<'a> LifetimeContext<'a> {
|
||||
});
|
||||
}
|
||||
|
||||
fn resolve_lifetime_ref(&mut self, lifetime_ref: &ast::Lifetime) {
|
||||
fn resolve_lifetime_ref(&mut self, lifetime_ref: &hir::Lifetime) {
|
||||
// Walk up the scope chain, tracking the number of fn scopes
|
||||
// that we pass through, until we find a lifetime with the
|
||||
// given name or we run out of scopes. If we encounter a code
|
||||
@ -610,7 +608,7 @@ impl<'a> LifetimeContext<'a> {
|
||||
|
||||
fn resolve_free_lifetime_ref(&mut self,
|
||||
scope_data: region::DestructionScopeData,
|
||||
lifetime_ref: &ast::Lifetime,
|
||||
lifetime_ref: &hir::Lifetime,
|
||||
scope: Scope) {
|
||||
debug!("resolve_free_lifetime_ref \
|
||||
scope_data: {:?} lifetime_ref: {:?} scope: {:?}",
|
||||
@ -660,13 +658,13 @@ impl<'a> LifetimeContext<'a> {
|
||||
|
||||
}
|
||||
|
||||
fn unresolved_lifetime_ref(&self, lifetime_ref: &ast::Lifetime) {
|
||||
fn unresolved_lifetime_ref(&self, lifetime_ref: &hir::Lifetime) {
|
||||
span_err!(self.sess, lifetime_ref.span, E0261,
|
||||
"use of undeclared lifetime name `{}`",
|
||||
lifetime_ref.name);
|
||||
}
|
||||
|
||||
fn check_lifetime_defs(&mut self, old_scope: Scope, lifetimes: &Vec<ast::LifetimeDef>) {
|
||||
fn check_lifetime_defs(&mut self, old_scope: Scope, lifetimes: &Vec<hir::LifetimeDef>) {
|
||||
for i in 0..lifetimes.len() {
|
||||
let lifetime_i = &lifetimes[i];
|
||||
|
||||
@ -701,7 +699,7 @@ impl<'a> LifetimeContext<'a> {
|
||||
|
||||
fn check_lifetime_def_for_shadowing(&self,
|
||||
mut old_scope: Scope,
|
||||
lifetime: &ast::Lifetime)
|
||||
lifetime: &hir::Lifetime)
|
||||
{
|
||||
for &(label, label_span) in &self.labels_in_fn {
|
||||
// FIXME (#24278): non-hygienic comparison
|
||||
@ -742,7 +740,7 @@ impl<'a> LifetimeContext<'a> {
|
||||
}
|
||||
|
||||
fn insert_lifetime(&mut self,
|
||||
lifetime_ref: &ast::Lifetime,
|
||||
lifetime_ref: &hir::Lifetime,
|
||||
def: DefRegion) {
|
||||
if lifetime_ref.id == ast::DUMMY_NODE_ID {
|
||||
self.sess.span_bug(lifetime_ref.span,
|
||||
@ -758,9 +756,9 @@ impl<'a> LifetimeContext<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn search_lifetimes<'a>(lifetimes: &'a Vec<ast::LifetimeDef>,
|
||||
lifetime_ref: &ast::Lifetime)
|
||||
-> Option<(u32, &'a ast::Lifetime)> {
|
||||
fn search_lifetimes<'a>(lifetimes: &'a Vec<hir::LifetimeDef>,
|
||||
lifetime_ref: &hir::Lifetime)
|
||||
-> Option<(u32, &'a hir::Lifetime)> {
|
||||
for (i, lifetime_decl) in lifetimes.iter().enumerate() {
|
||||
if lifetime_decl.lifetime.name == lifetime_ref.name {
|
||||
return Some((i as u32, &lifetime_decl.lifetime));
|
||||
@ -771,7 +769,7 @@ fn search_lifetimes<'a>(lifetimes: &'a Vec<ast::LifetimeDef>,
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
|
||||
pub fn early_bound_lifetimes<'a>(generics: &'a ast::Generics) -> Vec<ast::LifetimeDef> {
|
||||
pub fn early_bound_lifetimes<'a>(generics: &'a hir::Generics) -> Vec<hir::LifetimeDef> {
|
||||
let referenced_idents = early_bound_lifetime_names(generics);
|
||||
if referenced_idents.is_empty() {
|
||||
return Vec::new();
|
||||
@ -785,7 +783,7 @@ pub fn early_bound_lifetimes<'a>(generics: &'a ast::Generics) -> Vec<ast::Lifeti
|
||||
|
||||
/// Given a set of generic declarations, returns a list of names containing all early bound
|
||||
/// lifetime names for those generics. (In fact, this list may also contain other names.)
|
||||
fn early_bound_lifetime_names(generics: &ast::Generics) -> Vec<ast::Name> {
|
||||
fn early_bound_lifetime_names(generics: &hir::Generics) -> Vec<ast::Name> {
|
||||
// Create two lists, dividing the lifetimes into early/late bound.
|
||||
// Initially, all of them are considered late, but we will move
|
||||
// things from late into early as we go if we find references to
|
||||
@ -805,13 +803,13 @@ fn early_bound_lifetime_names(generics: &ast::Generics) -> Vec<ast::Name> {
|
||||
}
|
||||
for predicate in &generics.where_clause.predicates {
|
||||
match predicate {
|
||||
&ast::WherePredicate::BoundPredicate(ast::WhereBoundPredicate{ref bounds,
|
||||
&hir::WherePredicate::BoundPredicate(hir::WhereBoundPredicate{ref bounds,
|
||||
ref bounded_ty,
|
||||
..}) => {
|
||||
collector.visit_ty(&**bounded_ty);
|
||||
visit::walk_ty_param_bounds_helper(&mut collector, bounds);
|
||||
}
|
||||
&ast::WherePredicate::RegionPredicate(ast::WhereRegionPredicate{ref lifetime,
|
||||
&hir::WherePredicate::RegionPredicate(hir::WhereRegionPredicate{ref lifetime,
|
||||
ref bounds,
|
||||
..}) => {
|
||||
collector.visit_lifetime_ref(lifetime);
|
||||
@ -820,7 +818,7 @@ fn early_bound_lifetime_names(generics: &ast::Generics) -> Vec<ast::Name> {
|
||||
collector.visit_lifetime_ref(bound);
|
||||
}
|
||||
}
|
||||
&ast::WherePredicate::EqPredicate(_) => unimplemented!()
|
||||
&hir::WherePredicate::EqPredicate(_) => unimplemented!()
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -845,7 +843,7 @@ fn early_bound_lifetime_names(generics: &ast::Generics) -> Vec<ast::Name> {
|
||||
}
|
||||
|
||||
impl<'a, 'v> Visitor<'v> for FreeLifetimeCollector<'a> {
|
||||
fn visit_lifetime_ref(&mut self, lifetime_ref: &ast::Lifetime) {
|
||||
fn visit_lifetime_ref(&mut self, lifetime_ref: &hir::Lifetime) {
|
||||
shuffle(self.early_bound, self.late_bound,
|
||||
lifetime_ref.name);
|
||||
}
|
||||
|
@ -20,15 +20,16 @@ use middle::privacy::PublicItems;
|
||||
use metadata::csearch;
|
||||
use syntax::parse::token::InternedString;
|
||||
use syntax::codemap::{Span, DUMMY_SP};
|
||||
use syntax::{attr, visit};
|
||||
use syntax::ast;
|
||||
use syntax::ast::{Attribute, Block, Crate, FnDecl, NodeId, Variant};
|
||||
use syntax::ast::{Item, Generics, StructField};
|
||||
use syntax::attr::{Stability, AttrMetaMethods};
|
||||
use syntax::visit::{FnKind, Visitor};
|
||||
use syntax::ast::NodeId;
|
||||
use syntax::feature_gate::emit_feature_err;
|
||||
use util::nodemap::{DefIdMap, FnvHashSet, FnvHashMap};
|
||||
|
||||
use rustc_front::hir;
|
||||
use rustc_front::hir::{FnDecl, Attribute, Block, Crate, Item, Generics, StructField, Variant};
|
||||
use rustc_front::attr::{self, Stability, AttrMetaMethods};
|
||||
use rustc_front::visit::{self, FnKind, Visitor};
|
||||
|
||||
use std::mem::replace;
|
||||
use std::cmp::Ordering;
|
||||
|
||||
@ -166,21 +167,21 @@ impl<'a, 'tcx, 'v> Visitor<'v> for Annotator<'a, 'tcx> {
|
||||
// stability of the trait. This is WRONG, but expedient to get
|
||||
// libstd stabilized for the 1.0 release.
|
||||
let use_parent = match i.node {
|
||||
ast::ItemImpl(_, _, _, Some(_), _, _) => false,
|
||||
hir::ItemImpl(_, _, _, Some(_), _, _) => false,
|
||||
_ => true,
|
||||
};
|
||||
|
||||
// In case of a `pub use <mod>;`, we should not error since the stability
|
||||
// is inherited from the module itself
|
||||
let required = match i.node {
|
||||
ast::ItemUse(_) => i.vis != ast::Public,
|
||||
hir::ItemUse(_) => i.vis != hir::Public,
|
||||
_ => true
|
||||
};
|
||||
|
||||
self.annotate(i.id, use_parent, &i.attrs, i.span,
|
||||
|v| visit::walk_item(v, i), required);
|
||||
|
||||
if let ast::ItemStruct(ref sd, _) = i.node {
|
||||
if let hir::ItemStruct(ref sd, _) = i.node {
|
||||
sd.ctor_id.map(|id| {
|
||||
self.annotate(id, true, &i.attrs, i.span, |_| {}, true)
|
||||
});
|
||||
@ -193,12 +194,12 @@ impl<'a, 'tcx, 'v> Visitor<'v> for Annotator<'a, 'tcx> {
|
||||
// a stability attribute, so we don't recurse.
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, ti: &ast::TraitItem) {
|
||||
fn visit_trait_item(&mut self, ti: &hir::TraitItem) {
|
||||
self.annotate(ti.id, true, &ti.attrs, ti.span,
|
||||
|v| visit::walk_trait_item(v, ti), true);
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, ii: &ast::ImplItem) {
|
||||
fn visit_impl_item(&mut self, ii: &hir::ImplItem) {
|
||||
self.annotate(ii.id, true, &ii.attrs, ii.span,
|
||||
|v| visit::walk_impl_item(v, ii), true);
|
||||
}
|
||||
@ -213,7 +214,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for Annotator<'a, 'tcx> {
|
||||
|v| visit::walk_struct_field(v, s), true);
|
||||
}
|
||||
|
||||
fn visit_foreign_item(&mut self, i: &ast::ForeignItem) {
|
||||
fn visit_foreign_item(&mut self, i: &hir::ForeignItem) {
|
||||
self.annotate(i.id, true, &i.attrs, i.span, |_| {}, true);
|
||||
}
|
||||
}
|
||||
@ -236,7 +237,7 @@ impl<'tcx> Index<'tcx> {
|
||||
for attr in &krate.attrs {
|
||||
if &attr.name()[..] == "staged_api" {
|
||||
match attr.node.value.node {
|
||||
ast::MetaWord(_) => {
|
||||
hir::MetaWord(_) => {
|
||||
attr::mark_used(attr);
|
||||
is_staged_api = true;
|
||||
}
|
||||
@ -335,7 +336,7 @@ impl<'a, 'tcx> Checker<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'v, 'tcx> Visitor<'v> for Checker<'a, 'tcx> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
// When compiling with --test we don't enforce stability on the
|
||||
// compiler-generated test module, demarcated with `DUMMY_SP` plus the
|
||||
// name `__test`
|
||||
@ -346,19 +347,19 @@ impl<'a, 'v, 'tcx> Visitor<'v> for Checker<'a, 'tcx> {
|
||||
visit::walk_item(self, item);
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, ex: &ast::Expr) {
|
||||
fn visit_expr(&mut self, ex: &hir::Expr) {
|
||||
check_expr(self.tcx, ex,
|
||||
&mut |id, sp, stab| self.check(id, sp, stab));
|
||||
visit::walk_expr(self, ex);
|
||||
}
|
||||
|
||||
fn visit_path(&mut self, path: &ast::Path, id: ast::NodeId) {
|
||||
fn visit_path(&mut self, path: &hir::Path, id: ast::NodeId) {
|
||||
check_path(self.tcx, path, id,
|
||||
&mut |id, sp, stab| self.check(id, sp, stab));
|
||||
visit::walk_path(self, path)
|
||||
}
|
||||
|
||||
fn visit_pat(&mut self, pat: &ast::Pat) {
|
||||
fn visit_pat(&mut self, pat: &hir::Pat) {
|
||||
check_pat(self.tcx, pat,
|
||||
&mut |id, sp, stab| self.check(id, sp, stab));
|
||||
visit::walk_pat(self, pat)
|
||||
@ -366,10 +367,10 @@ impl<'a, 'v, 'tcx> Visitor<'v> for Checker<'a, 'tcx> {
|
||||
}
|
||||
|
||||
/// Helper for discovering nodes to check for stability
|
||||
pub fn check_item(tcx: &ty::ctxt, item: &ast::Item, warn_about_defns: bool,
|
||||
pub fn check_item(tcx: &ty::ctxt, item: &hir::Item, warn_about_defns: bool,
|
||||
cb: &mut FnMut(DefId, Span, &Option<&Stability>)) {
|
||||
match item.node {
|
||||
ast::ItemExternCrate(_) => {
|
||||
hir::ItemExternCrate(_) => {
|
||||
// compiler-generated `extern crate` items have a dummy span.
|
||||
if item.span == DUMMY_SP { return }
|
||||
|
||||
@ -384,7 +385,7 @@ pub fn check_item(tcx: &ty::ctxt, item: &ast::Item, warn_about_defns: bool,
|
||||
// For implementations of traits, check the stability of each item
|
||||
// individually as it's possible to have a stable trait with unstable
|
||||
// items.
|
||||
ast::ItemImpl(_, _, _, Some(ref t), _, ref impl_items) => {
|
||||
hir::ItemImpl(_, _, _, Some(ref t), _, ref impl_items) => {
|
||||
let trait_did = tcx.def_map.borrow().get(&t.ref_id).unwrap().def_id();
|
||||
let trait_items = tcx.trait_items(trait_did);
|
||||
|
||||
@ -403,16 +404,16 @@ pub fn check_item(tcx: &ty::ctxt, item: &ast::Item, warn_about_defns: bool,
|
||||
}
|
||||
|
||||
/// Helper for discovering nodes to check for stability
|
||||
pub fn check_expr(tcx: &ty::ctxt, e: &ast::Expr,
|
||||
pub fn check_expr(tcx: &ty::ctxt, e: &hir::Expr,
|
||||
cb: &mut FnMut(DefId, Span, &Option<&Stability>)) {
|
||||
let span;
|
||||
let id = match e.node {
|
||||
ast::ExprMethodCall(i, _, _) => {
|
||||
hir::ExprMethodCall(i, _, _) => {
|
||||
span = i.span;
|
||||
let method_call = ty::MethodCall::expr(e.id);
|
||||
tcx.tables.borrow().method_map[&method_call].def_id
|
||||
}
|
||||
ast::ExprField(ref base_e, ref field) => {
|
||||
hir::ExprField(ref base_e, ref field) => {
|
||||
span = field.span;
|
||||
match tcx.expr_ty_adjusted(base_e).sty {
|
||||
ty::TyStruct(def, _) => def.struct_variant().field_named(field.node.name).did,
|
||||
@ -420,7 +421,7 @@ pub fn check_expr(tcx: &ty::ctxt, e: &ast::Expr,
|
||||
"stability::check_expr: named field access on non-struct")
|
||||
}
|
||||
}
|
||||
ast::ExprTupField(ref base_e, ref field) => {
|
||||
hir::ExprTupField(ref base_e, ref field) => {
|
||||
span = field.span;
|
||||
match tcx.expr_ty_adjusted(base_e).sty {
|
||||
ty::TyStruct(def, _) => def.struct_variant().fields[field.node].did,
|
||||
@ -430,7 +431,7 @@ pub fn check_expr(tcx: &ty::ctxt, e: &ast::Expr,
|
||||
something other than a tuple or struct")
|
||||
}
|
||||
}
|
||||
ast::ExprStruct(_, ref expr_fields, _) => {
|
||||
hir::ExprStruct(_, ref expr_fields, _) => {
|
||||
let type_ = tcx.expr_ty(e);
|
||||
match type_.sty {
|
||||
ty::TyStruct(def, _) => {
|
||||
@ -464,7 +465,7 @@ pub fn check_expr(tcx: &ty::ctxt, e: &ast::Expr,
|
||||
maybe_do_stability_check(tcx, id, span, cb);
|
||||
}
|
||||
|
||||
pub fn check_path(tcx: &ty::ctxt, path: &ast::Path, id: ast::NodeId,
|
||||
pub fn check_path(tcx: &ty::ctxt, path: &hir::Path, id: ast::NodeId,
|
||||
cb: &mut FnMut(DefId, Span, &Option<&Stability>)) {
|
||||
match tcx.def_map.borrow().get(&id).map(|d| d.full_def()) {
|
||||
Some(def::DefPrimTy(..)) => {}
|
||||
@ -476,7 +477,7 @@ pub fn check_path(tcx: &ty::ctxt, path: &ast::Path, id: ast::NodeId,
|
||||
|
||||
}
|
||||
|
||||
pub fn check_pat(tcx: &ty::ctxt, pat: &ast::Pat,
|
||||
pub fn check_pat(tcx: &ty::ctxt, pat: &hir::Pat,
|
||||
cb: &mut FnMut(DefId, Span, &Option<&Stability>)) {
|
||||
debug!("check_pat(pat = {:?})", pat);
|
||||
if is_internal(tcx, pat.span) { return; }
|
||||
@ -487,18 +488,18 @@ pub fn check_pat(tcx: &ty::ctxt, pat: &ast::Pat,
|
||||
};
|
||||
match pat.node {
|
||||
// Foo(a, b, c)
|
||||
ast::PatEnum(_, Some(ref pat_fields)) => {
|
||||
hir::PatEnum(_, Some(ref pat_fields)) => {
|
||||
for (field, struct_field) in pat_fields.iter().zip(&v.fields) {
|
||||
// a .. pattern is fine, but anything positional is
|
||||
// not.
|
||||
if let ast::PatWild(ast::PatWildMulti) = field.node {
|
||||
if let hir::PatWild(hir::PatWildMulti) = field.node {
|
||||
continue
|
||||
}
|
||||
maybe_do_stability_check(tcx, struct_field.did, field.span, cb)
|
||||
}
|
||||
}
|
||||
// Foo { a, b, c }
|
||||
ast::PatStruct(_, ref pat_fields, _) => {
|
||||
hir::PatStruct(_, ref pat_fields, _) => {
|
||||
for field in pat_fields {
|
||||
let did = v.field_named(field.node.ident.name).did;
|
||||
maybe_do_stability_check(tcx, did, field.span, cb);
|
||||
|
@ -31,7 +31,7 @@ use middle::ty_fold::TypeFoldable;
|
||||
use std::collections::HashMap;
|
||||
use std::fmt;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::attr::{AttributeMethods, AttrMetaMethods};
|
||||
use rustc_front::attr::{AttributeMethods, AttrMetaMethods};
|
||||
|
||||
pub fn report_fulfillment_errors<'a, 'tcx>(infcx: &InferCtxt<'a, 'tcx>,
|
||||
errors: &Vec<FulfillmentError<'tcx>>) {
|
||||
|
@ -51,7 +51,8 @@ use middle::wf;
|
||||
use std::cell::RefCell;
|
||||
use std::fmt;
|
||||
use std::rc::Rc;
|
||||
use syntax::{abi, ast};
|
||||
use syntax::abi;
|
||||
use rustc_front::hir;
|
||||
use util::common::ErrorReported;
|
||||
use util::nodemap::FnvHashMap;
|
||||
|
||||
@ -793,7 +794,7 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
||||
match candidate {
|
||||
ImplCandidate(def_id) => {
|
||||
match self.tcx().trait_impl_polarity(def_id) {
|
||||
Some(ast::ImplPolarity::Negative) => return Err(Unimplemented),
|
||||
Some(hir::ImplPolarity::Negative) => return Err(Unimplemented),
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
@ -1217,7 +1218,7 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
||||
|
||||
// provide an impl, but only for suitable `fn` pointers
|
||||
ty::TyBareFn(_, &ty::BareFnTy {
|
||||
unsafety: ast::Unsafety::Normal,
|
||||
unsafety: hir::Unsafety::Normal,
|
||||
abi: abi::Rust,
|
||||
sig: ty::Binder(ty::FnSig {
|
||||
inputs: _,
|
||||
@ -1676,10 +1677,10 @@ impl<'cx, 'tcx> SelectionContext<'cx, 'tcx> {
|
||||
ty::BoundCopy => {
|
||||
match mutbl {
|
||||
// &mut T is affine and hence never `Copy`
|
||||
ast::MutMutable => Err(Unimplemented),
|
||||
hir::MutMutable => Err(Unimplemented),
|
||||
|
||||
// &T is always copyable
|
||||
ast::MutImmutable => ok_if(Vec::new()),
|
||||
hir::MutImmutable => ok_if(Vec::new()),
|
||||
}
|
||||
}
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -42,7 +42,7 @@ use middle::traits;
|
||||
use std::fmt;
|
||||
use std::rc::Rc;
|
||||
use syntax::abi;
|
||||
use syntax::ast;
|
||||
use rustc_front::hir;
|
||||
use syntax::owned_slice::OwnedSlice;
|
||||
use util::nodemap::{FnvHashMap, FnvHashSet};
|
||||
|
||||
@ -165,7 +165,7 @@ macro_rules! CopyImpls {
|
||||
}
|
||||
}
|
||||
|
||||
CopyImpls! { (), ast::Unsafety, abi::Abi }
|
||||
CopyImpls! { (), hir::Unsafety, abi::Abi }
|
||||
|
||||
impl<'tcx, T:TypeFoldable<'tcx>, U:TypeFoldable<'tcx>> TypeFoldable<'tcx> for (T, U) {
|
||||
fn fold_with<F:TypeFolder<'tcx>>(&self, folder: &mut F) -> (T, U) {
|
||||
|
@ -19,7 +19,7 @@ use middle::ty::{self, HasTypeFlags, Ty, TypeError};
|
||||
use middle::ty_fold::TypeFoldable;
|
||||
use std::rc::Rc;
|
||||
use syntax::abi;
|
||||
use syntax::ast;
|
||||
use rustc_front::hir as ast;
|
||||
|
||||
pub type RelateResult<'tcx, T> = Result<T, ty::TypeError<'tcx>>;
|
||||
|
||||
|
@ -15,11 +15,11 @@ use session::Session;
|
||||
use metadata::csearch;
|
||||
use middle::lang_items;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::parse::token::InternedString;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::visit;
|
||||
use rustc_front::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::hir;
|
||||
|
||||
use std::collections::HashSet;
|
||||
|
||||
@ -33,7 +33,7 @@ struct Context<'a> {
|
||||
|
||||
/// Checks the crate for usage of weak lang items, returning a vector of all the
|
||||
/// language items required by this crate, but not defined yet.
|
||||
pub fn check_crate(krate: &ast::Crate,
|
||||
pub fn check_crate(krate: &hir::Crate,
|
||||
sess: &Session,
|
||||
items: &mut lang_items::LanguageItems) {
|
||||
// These are never called by user code, they're generated by the compiler.
|
||||
@ -54,7 +54,7 @@ pub fn check_crate(krate: &ast::Crate,
|
||||
verify(sess, items);
|
||||
}
|
||||
|
||||
pub fn link_name(attrs: &[ast::Attribute]) -> Option<InternedString> {
|
||||
pub fn link_name(attrs: &[hir::Attribute]) -> Option<InternedString> {
|
||||
lang_items::extract(attrs).and_then(|name| {
|
||||
$(if &name[..] == stringify!($name) {
|
||||
Some(InternedString::new(stringify!($sym)))
|
||||
@ -108,7 +108,7 @@ impl<'a> Context<'a> {
|
||||
}
|
||||
|
||||
impl<'a, 'v> Visitor<'v> for Context<'a> {
|
||||
fn visit_foreign_item(&mut self, i: &ast::ForeignItem) {
|
||||
fn visit_foreign_item(&mut self, i: &hir::ForeignItem) {
|
||||
match lang_items::extract(&i.attrs) {
|
||||
None => {}
|
||||
Some(lang_item) => self.register(&lang_item, i.span),
|
||||
|
@ -11,19 +11,20 @@
|
||||
//! Used by `rustc` when compiling a plugin crate.
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::attr;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::diagnostic;
|
||||
use syntax::visit;
|
||||
use syntax::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::visit::Visitor;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::attr;
|
||||
|
||||
struct RegistrarFinder {
|
||||
registrars: Vec<(ast::NodeId, Span)> ,
|
||||
}
|
||||
|
||||
impl<'v> Visitor<'v> for RegistrarFinder {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
if let ast::ItemFn(..) = item.node {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
if let hir::ItemFn(..) = item.node {
|
||||
if attr::contains_name(&item.attrs,
|
||||
"plugin_registrar") {
|
||||
self.registrars.push((item.id, item.span));
|
||||
@ -36,7 +37,8 @@ impl<'v> Visitor<'v> for RegistrarFinder {
|
||||
|
||||
/// Find the function marked with `#[plugin_registrar]`, if any.
|
||||
pub fn find_plugin_registrar(diagnostic: &diagnostic::SpanHandler,
|
||||
krate: &ast::Crate) -> Option<ast::NodeId> {
|
||||
krate: &hir::Crate)
|
||||
-> Option<ast::NodeId> {
|
||||
let mut finder = RegistrarFinder { registrars: Vec::new() };
|
||||
visit::walk_crate(&mut finder, krate);
|
||||
|
||||
|
@ -26,9 +26,10 @@ use lint;
|
||||
use metadata::cstore;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::ast::{IntTy, UintTy};
|
||||
use rustc_front::hir::{IntTy, UintTy};
|
||||
use syntax::attr;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use rustc_front::hir;
|
||||
use syntax::diagnostic::{ColorConfig, Auto, Always, Never, SpanHandler};
|
||||
use syntax::parse;
|
||||
use syntax::parse::token::InternedString;
|
||||
@ -664,8 +665,8 @@ pub fn build_target_config(opts: &Options, sp: &SpanHandler) -> Config {
|
||||
};
|
||||
|
||||
let (int_type, uint_type) = match &target.target_pointer_width[..] {
|
||||
"32" => (ast::TyI32, ast::TyU32),
|
||||
"64" => (ast::TyI64, ast::TyU64),
|
||||
"32" => (hir::TyI32, hir::TyU32),
|
||||
"64" => (hir::TyI64, hir::TyU64),
|
||||
w => sp.handler().fatal(&format!("target specification was invalid: unrecognized \
|
||||
target-pointer-width {}", w))
|
||||
};
|
||||
@ -824,15 +825,16 @@ pub fn rustc_optgroups() -> Vec<RustcOptGroup> {
|
||||
opt::flagopt_u("", "pretty",
|
||||
"Pretty-print the input instead of compiling;
|
||||
valid types are: `normal` (un-annotated source),
|
||||
`expanded` (crates expanded),
|
||||
`typed` (crates expanded, with type annotations), or
|
||||
`expanded` (crates expanded), or
|
||||
`expanded,identified` (fully parenthesized, AST nodes with IDs).",
|
||||
"TYPE"),
|
||||
opt::flagopt_u("", "unpretty",
|
||||
"Present the input source, unstable (and less-pretty) variants;
|
||||
valid types are any of the types for `--pretty`, as well as:
|
||||
`flowgraph=<nodeid>` (graphviz formatted flowgraph for node), or
|
||||
`everybody_loops` (all function bodies replaced with `loop {}`).",
|
||||
`flowgraph=<nodeid>` (graphviz formatted flowgraph for node),
|
||||
`everybody_loops` (all function bodies replaced with `loop {}`),
|
||||
`hir` (the HIR), `hir,identified`, or
|
||||
`hir,typed` (HIR with types for each node).",
|
||||
"TYPE"),
|
||||
opt::opt_u("", "show-span", "Show spans for compiler debugging", "expr|pat|ty"),
|
||||
]);
|
||||
|
@ -20,9 +20,9 @@ use std::iter::repeat;
|
||||
use std::path::Path;
|
||||
use std::time::Duration;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::visit;
|
||||
use syntax::visit::Visitor;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::visit::Visitor;
|
||||
|
||||
// The name of the associated type for `Fn` return types
|
||||
pub const FN_OUTPUT_NAME: &'static str = "Output";
|
||||
@ -152,18 +152,18 @@ pub fn indenter() -> Indenter {
|
||||
Indenter { _cannot_construct_outside_of_this_module: () }
|
||||
}
|
||||
|
||||
struct LoopQueryVisitor<P> where P: FnMut(&ast::Expr_) -> bool {
|
||||
struct LoopQueryVisitor<P> where P: FnMut(&hir::Expr_) -> bool {
|
||||
p: P,
|
||||
flag: bool,
|
||||
}
|
||||
|
||||
impl<'v, P> Visitor<'v> for LoopQueryVisitor<P> where P: FnMut(&ast::Expr_) -> bool {
|
||||
fn visit_expr(&mut self, e: &ast::Expr) {
|
||||
impl<'v, P> Visitor<'v> for LoopQueryVisitor<P> where P: FnMut(&hir::Expr_) -> bool {
|
||||
fn visit_expr(&mut self, e: &hir::Expr) {
|
||||
self.flag |= (self.p)(&e.node);
|
||||
match e.node {
|
||||
// Skip inner loops, since a break in the inner loop isn't a
|
||||
// break inside the outer loop
|
||||
ast::ExprLoop(..) | ast::ExprWhile(..) => {}
|
||||
hir::ExprLoop(..) | hir::ExprWhile(..) => {}
|
||||
_ => visit::walk_expr(self, e)
|
||||
}
|
||||
}
|
||||
@ -171,7 +171,7 @@ impl<'v, P> Visitor<'v> for LoopQueryVisitor<P> where P: FnMut(&ast::Expr_) -> b
|
||||
|
||||
// Takes a predicate p, returns true iff p is true for any subexpressions
|
||||
// of b -- skipping any inner loops (loop, while, loop_body)
|
||||
pub fn loop_query<P>(b: &ast::Block, p: P) -> bool where P: FnMut(&ast::Expr_) -> bool {
|
||||
pub fn loop_query<P>(b: &hir::Block, p: P) -> bool where P: FnMut(&hir::Expr_) -> bool {
|
||||
let mut v = LoopQueryVisitor {
|
||||
p: p,
|
||||
flag: false,
|
||||
@ -180,13 +180,13 @@ pub fn loop_query<P>(b: &ast::Block, p: P) -> bool where P: FnMut(&ast::Expr_) -
|
||||
return v.flag;
|
||||
}
|
||||
|
||||
struct BlockQueryVisitor<P> where P: FnMut(&ast::Expr) -> bool {
|
||||
struct BlockQueryVisitor<P> where P: FnMut(&hir::Expr) -> bool {
|
||||
p: P,
|
||||
flag: bool,
|
||||
}
|
||||
|
||||
impl<'v, P> Visitor<'v> for BlockQueryVisitor<P> where P: FnMut(&ast::Expr) -> bool {
|
||||
fn visit_expr(&mut self, e: &ast::Expr) {
|
||||
impl<'v, P> Visitor<'v> for BlockQueryVisitor<P> where P: FnMut(&hir::Expr) -> bool {
|
||||
fn visit_expr(&mut self, e: &hir::Expr) {
|
||||
self.flag |= (self.p)(e);
|
||||
visit::walk_expr(self, e)
|
||||
}
|
||||
@ -194,7 +194,7 @@ impl<'v, P> Visitor<'v> for BlockQueryVisitor<P> where P: FnMut(&ast::Expr) -> b
|
||||
|
||||
// Takes a predicate p, returns true iff p is true for any subexpressions
|
||||
// of b -- skipping any inner loops (loop, while, loop_body)
|
||||
pub fn block_query<P>(b: &ast::Block, p: P) -> bool where P: FnMut(&ast::Expr) -> bool {
|
||||
pub fn block_query<P>(b: &hir::Block, p: P) -> bool where P: FnMut(&hir::Expr) -> bool {
|
||||
let mut v = BlockQueryVisitor {
|
||||
p: p,
|
||||
flag: false,
|
||||
|
@ -26,7 +26,8 @@ use middle::ty_fold::{self, TypeFoldable};
|
||||
use std::fmt;
|
||||
use syntax::abi;
|
||||
use syntax::parse::token;
|
||||
use syntax::{ast, ast_util};
|
||||
use syntax::ast::DUMMY_NODE_ID;
|
||||
use rustc_front::hir as ast;
|
||||
|
||||
pub fn verbose() -> bool {
|
||||
ty::tls::with(|tcx| tcx.sess.verbose())
|
||||
@ -230,7 +231,7 @@ fn in_binder<'tcx, T, U>(f: &mut fmt::Formatter,
|
||||
ty::BrEnv => {
|
||||
let name = token::intern("'r");
|
||||
let _ = write!(f, "{}", name);
|
||||
ty::BrNamed(DefId::local(ast::DUMMY_NODE_ID), name)
|
||||
ty::BrNamed(DefId::local(DUMMY_NODE_ID), name)
|
||||
}
|
||||
})
|
||||
}).0;
|
||||
@ -623,14 +624,55 @@ impl<'tcx> fmt::Display for ty::TraitRef<'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn int_ty_to_string(t: ast::IntTy, val: Option<i64>) -> String {
|
||||
let s = match t {
|
||||
ast::TyIs => "isize",
|
||||
ast::TyI8 => "i8",
|
||||
ast::TyI16 => "i16",
|
||||
ast::TyI32 => "i32",
|
||||
ast::TyI64 => "i64"
|
||||
};
|
||||
|
||||
match val {
|
||||
// cast to a u64 so we can correctly print INT64_MIN. All integral types
|
||||
// are parsed as u64, so we wouldn't want to print an extra negative
|
||||
// sign.
|
||||
Some(n) => format!("{}{}", n as u64, s),
|
||||
None => s.to_string()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn uint_ty_to_string(t: ast::UintTy, val: Option<u64>) -> String {
|
||||
let s = match t {
|
||||
ast::TyUs => "usize",
|
||||
ast::TyU8 => "u8",
|
||||
ast::TyU16 => "u16",
|
||||
ast::TyU32 => "u32",
|
||||
ast::TyU64 => "u64"
|
||||
};
|
||||
|
||||
match val {
|
||||
Some(n) => format!("{}{}", n, s),
|
||||
None => s.to_string()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
pub fn float_ty_to_string(t: ast::FloatTy) -> String {
|
||||
match t {
|
||||
ast::TyF32 => "f32".to_string(),
|
||||
ast::TyF64 => "f64".to_string(),
|
||||
}
|
||||
}
|
||||
|
||||
impl<'tcx> fmt::Display for ty::TypeVariants<'tcx> {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
match *self {
|
||||
TyBool => write!(f, "bool"),
|
||||
TyChar => write!(f, "char"),
|
||||
TyInt(t) => write!(f, "{}", ast_util::int_ty_to_string(t, None)),
|
||||
TyUint(t) => write!(f, "{}", ast_util::uint_ty_to_string(t, None)),
|
||||
TyFloat(t) => write!(f, "{}", ast_util::float_ty_to_string(t)),
|
||||
TyInt(t) => write!(f, "{}", int_ty_to_string(t, None)),
|
||||
TyUint(t) => write!(f, "{}", uint_ty_to_string(t, None)),
|
||||
TyFloat(t) => write!(f, "{}", float_ty_to_string(t)),
|
||||
TyBox(typ) => write!(f, "Box<{}>", typ),
|
||||
TyRawPtr(ref tm) => {
|
||||
write!(f, "*{} {}", match tm.mutbl {
|
||||
|
@ -48,6 +48,7 @@ extern crate syntax;
|
||||
extern crate libc;
|
||||
extern crate serialize;
|
||||
extern crate rustc_llvm;
|
||||
extern crate rustc_front;
|
||||
#[macro_use] extern crate log;
|
||||
|
||||
pub mod abi;
|
||||
|
@ -48,8 +48,8 @@
|
||||
|
||||
use std::fmt;
|
||||
use std::hash::{Hash, SipHasher, Hasher};
|
||||
use syntax::ast;
|
||||
use syntax::visit;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::visit;
|
||||
|
||||
#[derive(Clone, PartialEq, Debug)]
|
||||
pub struct Svh {
|
||||
@ -66,7 +66,7 @@ impl Svh {
|
||||
&self.hash
|
||||
}
|
||||
|
||||
pub fn calculate(metadata: &Vec<String>, krate: &ast::Crate) -> Svh {
|
||||
pub fn calculate(metadata: &Vec<String>, krate: &hir::Crate) -> Svh {
|
||||
// FIXME (#14132): This is better than it used to be, but it still not
|
||||
// ideal. We now attempt to hash only the relevant portions of the
|
||||
// Crate AST as well as the top-level crate attributes. (However,
|
||||
@ -131,13 +131,13 @@ mod svh_visitor {
|
||||
pub use self::SawExprComponent::*;
|
||||
pub use self::SawStmtComponent::*;
|
||||
use self::SawAbiComponent::*;
|
||||
use syntax::ast;
|
||||
use syntax::ast::*;
|
||||
use syntax::ast::{self, NodeId, Ident};
|
||||
use syntax::codemap::Span;
|
||||
use syntax::parse::token;
|
||||
use syntax::print::pprust;
|
||||
use syntax::visit;
|
||||
use syntax::visit::{Visitor, FnKind};
|
||||
use rustc_front::visit;
|
||||
use rustc_front::visit::{Visitor, FnKind};
|
||||
use rustc_front::hir::*;
|
||||
use rustc_front::hir;
|
||||
|
||||
use std::hash::{Hash, SipHasher};
|
||||
|
||||
@ -230,9 +230,9 @@ mod svh_visitor {
|
||||
SawExprCall,
|
||||
SawExprMethodCall,
|
||||
SawExprTup,
|
||||
SawExprBinary(ast::BinOp_),
|
||||
SawExprUnary(ast::UnOp),
|
||||
SawExprLit(ast::Lit_),
|
||||
SawExprBinary(hir::BinOp_),
|
||||
SawExprUnary(hir::UnOp),
|
||||
SawExprLit(hir::Lit_),
|
||||
SawExprCast,
|
||||
SawExprIf,
|
||||
SawExprWhile,
|
||||
@ -240,13 +240,13 @@ mod svh_visitor {
|
||||
SawExprClosure,
|
||||
SawExprBlock,
|
||||
SawExprAssign,
|
||||
SawExprAssignOp(ast::BinOp_),
|
||||
SawExprAssignOp(hir::BinOp_),
|
||||
SawExprIndex,
|
||||
SawExprRange,
|
||||
SawExprPath(Option<usize>),
|
||||
SawExprAddrOf(ast::Mutability),
|
||||
SawExprAddrOf(hir::Mutability),
|
||||
SawExprRet,
|
||||
SawExprInlineAsm(&'a ast::InlineAsm),
|
||||
SawExprInlineAsm(&'a hir::InlineAsm),
|
||||
SawExprStruct,
|
||||
SawExprRepeat,
|
||||
SawExprParen,
|
||||
@ -284,12 +284,6 @@ mod svh_visitor {
|
||||
ExprStruct(..) => SawExprStruct,
|
||||
ExprRepeat(..) => SawExprRepeat,
|
||||
ExprParen(..) => SawExprParen,
|
||||
|
||||
// just syntactic artifacts, expanded away by time of SVH.
|
||||
ExprForLoop(..) => unreachable!(),
|
||||
ExprIfLet(..) => unreachable!(),
|
||||
ExprWhileLet(..) => unreachable!(),
|
||||
ExprMac(..) => unreachable!(),
|
||||
}
|
||||
}
|
||||
|
||||
@ -306,51 +300,10 @@ mod svh_visitor {
|
||||
StmtDecl(..) => SawStmtDecl,
|
||||
StmtExpr(..) => SawStmtExpr,
|
||||
StmtSemi(..) => SawStmtSemi,
|
||||
StmtMac(..) => unreachable!(),
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a, 'v> Visitor<'v> for StrictVersionHashVisitor<'a> {
|
||||
|
||||
fn visit_mac(&mut self, mac: &Mac) {
|
||||
// macro invocations, namely macro_rules definitions,
|
||||
// *can* appear as items, even in the expanded crate AST.
|
||||
|
||||
if ¯o_name(mac)[..] == "macro_rules" {
|
||||
// Pretty-printing definition to a string strips out
|
||||
// surface artifacts (currently), such as the span
|
||||
// information, yielding a content-based hash.
|
||||
|
||||
// FIXME (#14132): building temporary string is
|
||||
// expensive; a direct content-based hash on token
|
||||
// trees might be faster. Implementing this is far
|
||||
// easier in short term.
|
||||
let macro_defn_as_string = pprust::to_string(|pp_state| {
|
||||
pp_state.print_mac(mac, token::Paren)
|
||||
});
|
||||
macro_defn_as_string.hash(self.st);
|
||||
} else {
|
||||
// It is not possible to observe any kind of macro
|
||||
// invocation at this stage except `macro_rules!`.
|
||||
panic!("reached macro somehow: {}",
|
||||
pprust::to_string(|pp_state| {
|
||||
pp_state.print_mac(mac, token::Paren)
|
||||
}));
|
||||
}
|
||||
|
||||
visit::walk_mac(self, mac);
|
||||
|
||||
fn macro_name(mac: &Mac) -> token::InternedString {
|
||||
match &mac.node {
|
||||
&MacInvocTT(ref path, ref _tts, ref _stx_ctxt) => {
|
||||
let s = &path.segments;
|
||||
assert_eq!(s.len(), 1);
|
||||
s[0].identifier.name.as_str()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_struct_def(&mut self, s: &StructDef, ident: Ident,
|
||||
g: &Generics, _: NodeId) {
|
||||
SawStructDef(ident.name.as_str()).hash(self.st);
|
||||
|
@ -27,6 +27,7 @@ use rustc::middle::region;
|
||||
use rustc::middle::ty;
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use rustc_front::hir;
|
||||
|
||||
use std::rc::Rc;
|
||||
|
||||
@ -104,12 +105,12 @@ impl<'a, 'tcx> euv::Delegate<'tcx> for CheckLoanCtxt<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn matched_pat(&mut self,
|
||||
_matched_pat: &ast::Pat,
|
||||
_matched_pat: &hir::Pat,
|
||||
_cmt: mc::cmt,
|
||||
_mode: euv::MatchMode) { }
|
||||
|
||||
fn consume_pat(&mut self,
|
||||
consume_pat: &ast::Pat,
|
||||
consume_pat: &hir::Pat,
|
||||
cmt: mc::cmt<'tcx>,
|
||||
mode: euv::ConsumeMode) {
|
||||
debug!("consume_pat(consume_pat={:?}, cmt={:?}, mode={:?})",
|
||||
@ -194,8 +195,8 @@ pub fn check_loans<'a, 'b, 'c, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>,
|
||||
move_data: &move_data::FlowedMoveData<'c, 'tcx>,
|
||||
all_loans: &[Loan<'tcx>],
|
||||
fn_id: ast::NodeId,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block) {
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block) {
|
||||
debug!("check_loans(body id={})", body.id);
|
||||
|
||||
let param_env = ty::ParameterEnvironment::for_item(bccx.tcx, fn_id);
|
||||
|
@ -27,8 +27,8 @@ use rustc::middle::mem_categorization as mc;
|
||||
use std::mem;
|
||||
use std::rc::Rc;
|
||||
use syntax::ast;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use syntax::codemap::Span;
|
||||
use rustc_front::attr::AttrMetaMethods;
|
||||
|
||||
#[derive(PartialEq, Eq, PartialOrd, Ord)]
|
||||
enum Fragment {
|
||||
|
@ -22,6 +22,7 @@ use rustc::middle::ty;
|
||||
use std::rc::Rc;
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use rustc_front::hir;
|
||||
|
||||
struct GatherMoveInfo<'tcx> {
|
||||
id: ast::NodeId,
|
||||
@ -62,7 +63,7 @@ pub fn gather_move_from_expr<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>,
|
||||
pub fn gather_match_variant<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>,
|
||||
move_data: &MoveData<'tcx>,
|
||||
_move_error_collector: &MoveErrorCollector<'tcx>,
|
||||
move_pat: &ast::Pat,
|
||||
move_pat: &hir::Pat,
|
||||
cmt: mc::cmt<'tcx>,
|
||||
mode: euv::MatchMode) {
|
||||
let tcx = bccx.tcx;
|
||||
@ -93,10 +94,10 @@ pub fn gather_match_variant<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>,
|
||||
pub fn gather_move_from_pat<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>,
|
||||
move_data: &MoveData<'tcx>,
|
||||
move_error_collector: &MoveErrorCollector<'tcx>,
|
||||
move_pat: &ast::Pat,
|
||||
move_pat: &hir::Pat,
|
||||
cmt: mc::cmt<'tcx>) {
|
||||
let pat_span_path_opt = match move_pat.node {
|
||||
ast::PatIdent(_, ref path1, _) => {
|
||||
hir::PatIdent(_, ref path1, _) => {
|
||||
Some(MoveSpanAndPath{span: move_pat.span,
|
||||
ident: path1.node})
|
||||
},
|
||||
|
@ -26,9 +26,11 @@ use rustc::middle::ty;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::ast::{Expr, FnDecl, Block, NodeId, Pat};
|
||||
use syntax::ast::NodeId;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::hir::{Expr, FnDecl, Block, Pat};
|
||||
use rustc_front::visit;
|
||||
use rustc_front::visit::Visitor;
|
||||
|
||||
mod lifetime;
|
||||
mod restrictions;
|
||||
@ -37,8 +39,8 @@ mod move_error;
|
||||
|
||||
pub fn gather_loans_in_fn<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>,
|
||||
fn_id: NodeId,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block)
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block)
|
||||
-> (Vec<Loan<'tcx>>,
|
||||
move_data::MoveData<'tcx>) {
|
||||
let mut glcx = GatherLoanCtxt {
|
||||
@ -91,7 +93,7 @@ impl<'a, 'tcx> euv::Delegate<'tcx> for GatherLoanCtxt<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn matched_pat(&mut self,
|
||||
matched_pat: &ast::Pat,
|
||||
matched_pat: &hir::Pat,
|
||||
cmt: mc::cmt<'tcx>,
|
||||
mode: euv::MatchMode) {
|
||||
debug!("matched_pat(matched_pat={:?}, cmt={:?}, mode={:?})",
|
||||
@ -107,7 +109,7 @@ impl<'a, 'tcx> euv::Delegate<'tcx> for GatherLoanCtxt<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn consume_pat(&mut self,
|
||||
consume_pat: &ast::Pat,
|
||||
consume_pat: &hir::Pat,
|
||||
cmt: mc::cmt<'tcx>,
|
||||
mode: euv::ConsumeMode) {
|
||||
debug!("consume_pat(consume_pat={:?}, cmt={:?}, mode={:?})",
|
||||
@ -527,7 +529,7 @@ struct StaticInitializerCtxt<'a, 'tcx: 'a> {
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for StaticInitializerCtxt<'a, 'tcx> {
|
||||
fn visit_expr(&mut self, ex: &Expr) {
|
||||
if let ast::ExprAddrOf(mutbl, ref base) = ex.node {
|
||||
if let hir::ExprAddrOf(mutbl, ref base) = ex.node {
|
||||
let infcx = infer::new_infer_ctxt(self.bccx.tcx, &self.bccx.tcx.tables, None, false);
|
||||
let mc = mc::MemCategorizationContext::new(&infcx);
|
||||
let base_cmt = mc.cat_expr(&**base).unwrap();
|
||||
@ -544,7 +546,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for StaticInitializerCtxt<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn gather_loans_in_static_initializer(bccx: &mut BorrowckCtxt, expr: &ast::Expr) {
|
||||
pub fn gather_loans_in_static_initializer(bccx: &mut BorrowckCtxt, expr: &hir::Expr) {
|
||||
|
||||
debug!("gather_loans_in_static_initializer(expr={:?})", expr);
|
||||
|
||||
|
@ -15,7 +15,8 @@ use rustc::middle::ty;
|
||||
use std::cell::RefCell;
|
||||
use syntax::ast;
|
||||
use syntax::codemap;
|
||||
use syntax::print::pprust;
|
||||
use rustc_front::print::pprust;
|
||||
use rustc_front::hir;
|
||||
|
||||
pub struct MoveErrorCollector<'tcx> {
|
||||
errors: RefCell<Vec<MoveError<'tcx>>>
|
||||
@ -125,7 +126,7 @@ fn report_cannot_move_out_of<'a, 'tcx>(bccx: &BorrowckCtxt<'a, 'tcx>,
|
||||
|
||||
mc::cat_interior(ref b, mc::InteriorElement(Kind::Index, _)) => {
|
||||
let expr = bccx.tcx.map.expect_expr(move_from.id);
|
||||
if let ast::ExprIndex(..) = expr.node {
|
||||
if let hir::ExprIndex(..) = expr.node {
|
||||
bccx.span_err(move_from.span,
|
||||
&format!("cannot move out of type `{}`, \
|
||||
a non-copy fixed-size array",
|
||||
|
@ -20,8 +20,8 @@ pub use self::MovedValueUseKind::*;
|
||||
|
||||
use self::InteriorKind::*;
|
||||
|
||||
use rustc::ast_map;
|
||||
use rustc::ast_map::blocks::{FnLikeNode, FnParts};
|
||||
use rustc::front::map as hir_map;
|
||||
use rustc::front::map::blocks::{FnLikeNode, FnParts};
|
||||
use rustc::middle::cfg;
|
||||
use rustc::middle::dataflow::DataFlowContext;
|
||||
use rustc::middle::dataflow::BitwiseOperator;
|
||||
@ -37,12 +37,14 @@ use rustc::middle::ty::{self, Ty};
|
||||
use std::fmt;
|
||||
use std::mem;
|
||||
use std::rc::Rc;
|
||||
use syntax::ast;
|
||||
use syntax::ast_util;
|
||||
use syntax::ast::{self, NodeId};
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit;
|
||||
use syntax::visit::{Visitor, FnKind};
|
||||
use syntax::ast::{FnDecl, Block, NodeId};
|
||||
|
||||
use rustc_front::hir;
|
||||
use rustc_front::hir::{FnDecl, Block};
|
||||
use rustc_front::visit;
|
||||
use rustc_front::visit::{Visitor, FnKind};
|
||||
use rustc_front::util as hir_util;
|
||||
|
||||
pub mod check_loans;
|
||||
|
||||
@ -74,19 +76,19 @@ impl<'a, 'tcx, 'v> Visitor<'v> for BorrowckCtxt<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
borrowck_item(self, item);
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, ti: &ast::TraitItem) {
|
||||
if let ast::ConstTraitItem(_, Some(ref expr)) = ti.node {
|
||||
fn visit_trait_item(&mut self, ti: &hir::TraitItem) {
|
||||
if let hir::ConstTraitItem(_, Some(ref expr)) = ti.node {
|
||||
gather_loans::gather_loans_in_static_initializer(self, &*expr);
|
||||
}
|
||||
visit::walk_trait_item(self, ti);
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, ii: &ast::ImplItem) {
|
||||
if let ast::ConstImplItem(_, ref expr) = ii.node {
|
||||
fn visit_impl_item(&mut self, ii: &hir::ImplItem) {
|
||||
if let hir::ConstImplItem(_, ref expr) = ii.node {
|
||||
gather_loans::gather_loans_in_static_initializer(self, &*expr);
|
||||
}
|
||||
visit::walk_impl_item(self, ii);
|
||||
@ -126,14 +128,14 @@ pub fn check_crate(tcx: &ty::ctxt) {
|
||||
}
|
||||
}
|
||||
|
||||
fn borrowck_item(this: &mut BorrowckCtxt, item: &ast::Item) {
|
||||
fn borrowck_item(this: &mut BorrowckCtxt, item: &hir::Item) {
|
||||
// Gather loans for items. Note that we don't need
|
||||
// to check loans for single expressions. The check
|
||||
// loan step is intended for things that have a data
|
||||
// flow dependent conditions.
|
||||
match item.node {
|
||||
ast::ItemStatic(_, _, ref ex) |
|
||||
ast::ItemConst(_, ref ex) => {
|
||||
hir::ItemStatic(_, _, ref ex) |
|
||||
hir::ItemConst(_, ref ex) => {
|
||||
gather_loans::gather_loans_in_static_initializer(this, &**ex);
|
||||
}
|
||||
_ => { }
|
||||
@ -151,8 +153,8 @@ pub struct AnalysisData<'a, 'tcx: 'a> {
|
||||
|
||||
fn borrowck_fn(this: &mut BorrowckCtxt,
|
||||
fk: FnKind,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block,
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block,
|
||||
sp: Span,
|
||||
id: ast::NodeId) {
|
||||
debug!("borrowck_fn(id={})", id);
|
||||
@ -183,16 +185,16 @@ fn borrowck_fn(this: &mut BorrowckCtxt,
|
||||
|
||||
fn build_borrowck_dataflow_data<'a, 'tcx>(this: &mut BorrowckCtxt<'a, 'tcx>,
|
||||
fk: FnKind,
|
||||
decl: &ast::FnDecl,
|
||||
decl: &hir::FnDecl,
|
||||
cfg: &cfg::CFG,
|
||||
body: &ast::Block,
|
||||
body: &hir::Block,
|
||||
sp: Span,
|
||||
id: ast::NodeId)
|
||||
-> AnalysisData<'a, 'tcx>
|
||||
{
|
||||
// Check the body of fn items.
|
||||
let tcx = this.tcx;
|
||||
let id_range = ast_util::compute_id_range_for_fn_body(fk, decl, body, sp, id);
|
||||
let id_range = hir_util::compute_id_range_for_fn_body(fk, decl, body, sp, id);
|
||||
let (all_loans, move_data) =
|
||||
gather_loans::gather_loans_in_fn(this, id, decl, body);
|
||||
|
||||
@ -398,8 +400,8 @@ pub enum LoanPathElem {
|
||||
pub fn closure_to_block(closure_id: ast::NodeId,
|
||||
tcx: &ty::ctxt) -> ast::NodeId {
|
||||
match tcx.map.get(closure_id) {
|
||||
ast_map::NodeExpr(expr) => match expr.node {
|
||||
ast::ExprClosure(_, _, ref block) => {
|
||||
hir_map::NodeExpr(expr) => match expr.node {
|
||||
hir::ExprClosure(_, _, ref block) => {
|
||||
block.id
|
||||
}
|
||||
_ => {
|
||||
@ -667,7 +669,7 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> {
|
||||
let (expr_ty, expr_span) = match self.tcx
|
||||
.map
|
||||
.find(the_move.id) {
|
||||
Some(ast_map::NodeExpr(expr)) => {
|
||||
Some(hir_map::NodeExpr(expr)) => {
|
||||
(self.tcx.expr_ty_adjusted(&*expr), expr.span)
|
||||
}
|
||||
r => {
|
||||
@ -729,7 +731,7 @@ impl<'a, 'tcx> BorrowckCtxt<'a, 'tcx> {
|
||||
let (expr_ty, expr_span) = match self.tcx
|
||||
.map
|
||||
.find(the_move.id) {
|
||||
Some(ast_map::NodeExpr(expr)) => {
|
||||
Some(hir_map::NodeExpr(expr)) => {
|
||||
(self.tcx.expr_ty_adjusted(&*expr), expr.span)
|
||||
}
|
||||
r => {
|
||||
@ -1138,7 +1140,7 @@ fn statement_scope_span(tcx: &ty::ctxt, region: ty::Region) -> Option<Span> {
|
||||
match region {
|
||||
ty::ReScope(scope) => {
|
||||
match tcx.map.find(scope.node_id(&tcx.region_maps)) {
|
||||
Some(ast_map::NodeStmt(stmt)) => Some(stmt.span),
|
||||
Some(hir_map::NodeStmt(stmt)) => Some(stmt.span),
|
||||
_ => None
|
||||
}
|
||||
}
|
||||
|
@ -29,6 +29,7 @@ use std::usize;
|
||||
use syntax::ast;
|
||||
use syntax::ast_util;
|
||||
use syntax::codemap::Span;
|
||||
use rustc_front::hir;
|
||||
|
||||
#[path="fragments.rs"]
|
||||
pub mod fragments;
|
||||
@ -601,8 +602,8 @@ impl<'a, 'tcx> FlowedMoveData<'a, 'tcx> {
|
||||
tcx: &'a ty::ctxt<'tcx>,
|
||||
cfg: &cfg::CFG,
|
||||
id_range: ast_util::IdRange,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block)
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block)
|
||||
-> FlowedMoveData<'a, 'tcx> {
|
||||
let mut dfcx_moves =
|
||||
DataFlowContext::new(tcx,
|
||||
|
@ -34,6 +34,7 @@
|
||||
// refers to the borrowck-specific graphviz adapter traits.
|
||||
extern crate graphviz as dot;
|
||||
extern crate rustc;
|
||||
extern crate rustc_front;
|
||||
|
||||
pub use borrowck::check_crate;
|
||||
pub use borrowck::build_borrowck_dataflow_data_for_fn;
|
||||
|
@ -8,10 +8,11 @@
|
||||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
use rustc::front;
|
||||
use rustc::front::map as hir_map;
|
||||
use rustc::session::Session;
|
||||
use rustc::session::config::{self, Input, OutputFilenames};
|
||||
use rustc::session::search_paths::PathKind;
|
||||
use rustc::ast_map;
|
||||
use rustc::lint;
|
||||
use rustc::metadata;
|
||||
use rustc::metadata::creader::LocalCrateReader;
|
||||
@ -28,6 +29,8 @@ use rustc_trans::back::write;
|
||||
use rustc_trans::trans;
|
||||
use rustc_typeck as typeck;
|
||||
use rustc_privacy;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::lowering::lower_crate;
|
||||
use super::Compilation;
|
||||
|
||||
use serialize::json;
|
||||
@ -41,6 +44,7 @@ use syntax::ast;
|
||||
use syntax::attr;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use syntax::diagnostics;
|
||||
use syntax::fold::Folder;
|
||||
use syntax::parse;
|
||||
use syntax::parse::token;
|
||||
use syntax;
|
||||
@ -104,9 +108,13 @@ pub fn compile_input(sess: Session,
|
||||
&expanded_crate,
|
||||
&id[..]));
|
||||
|
||||
let mut forest = ast_map::Forest::new(expanded_crate);
|
||||
let expanded_crate = assign_node_ids(&sess, expanded_crate);
|
||||
// Lower ast -> hir.
|
||||
let mut hir_forest = time(sess.time_passes(),
|
||||
"lowering ast -> hir",
|
||||
|| hir_map::Forest::new(lower_crate(&expanded_crate)));
|
||||
let arenas = ty::CtxtArenas::new();
|
||||
let ast_map = assign_node_ids_and_map(&sess, &mut forest);
|
||||
let ast_map = make_map(&sess, &mut hir_forest);
|
||||
|
||||
write_out_deps(&sess, input, &outputs, &id[..]);
|
||||
|
||||
@ -116,11 +124,14 @@ pub fn compile_input(sess: Session,
|
||||
&sess,
|
||||
outdir,
|
||||
&ast_map,
|
||||
&expanded_crate,
|
||||
&ast_map.krate(),
|
||||
&id[..]));
|
||||
|
||||
|
||||
phase_3_run_analysis_passes(sess,
|
||||
ast_map,
|
||||
&expanded_crate,
|
||||
&arenas,
|
||||
id,
|
||||
control.make_glob_map,
|
||||
@ -130,6 +141,7 @@ pub fn compile_input(sess: Session,
|
||||
let state = CompileState::state_after_analysis(input,
|
||||
&tcx.sess,
|
||||
outdir,
|
||||
&expanded_crate,
|
||||
tcx.map.krate(),
|
||||
&analysis,
|
||||
tcx);
|
||||
@ -254,7 +266,8 @@ pub struct CompileState<'a, 'ast: 'a, 'tcx: 'a> {
|
||||
pub output_filenames: Option<&'a OutputFilenames>,
|
||||
pub out_dir: Option<&'a Path>,
|
||||
pub expanded_crate: Option<&'a ast::Crate>,
|
||||
pub ast_map: Option<&'a ast_map::Map<'ast>>,
|
||||
pub hir_crate: Option<&'a hir::Crate>,
|
||||
pub ast_map: Option<&'a hir_map::Map<'ast>>,
|
||||
pub analysis: Option<&'a ty::CrateAnalysis>,
|
||||
pub tcx: Option<&'a ty::ctxt<'tcx>>,
|
||||
pub trans: Option<&'a trans::CrateTranslation>,
|
||||
@ -274,6 +287,7 @@ impl<'a, 'ast, 'tcx> CompileState<'a, 'ast, 'tcx> {
|
||||
crate_name: None,
|
||||
output_filenames: None,
|
||||
expanded_crate: None,
|
||||
hir_crate: None,
|
||||
ast_map: None,
|
||||
analysis: None,
|
||||
tcx: None,
|
||||
@ -308,14 +322,16 @@ impl<'a, 'ast, 'tcx> CompileState<'a, 'ast, 'tcx> {
|
||||
fn state_after_write_deps(input: &'a Input,
|
||||
session: &'a Session,
|
||||
out_dir: &'a Option<PathBuf>,
|
||||
ast_map: &'a ast_map::Map<'ast>,
|
||||
expanded_crate: &'a ast::Crate,
|
||||
ast_map: &'a hir_map::Map<'ast>,
|
||||
krate: &'a ast::Crate,
|
||||
hir_crate: &'a hir::Crate,
|
||||
crate_name: &'a str)
|
||||
-> CompileState<'a, 'ast, 'tcx> {
|
||||
CompileState {
|
||||
crate_name: Some(crate_name),
|
||||
ast_map: Some(ast_map),
|
||||
expanded_crate: Some(expanded_crate),
|
||||
krate: Some(krate),
|
||||
hir_crate: Some(hir_crate),
|
||||
.. CompileState::empty(input, session, out_dir)
|
||||
}
|
||||
}
|
||||
@ -323,14 +339,16 @@ impl<'a, 'ast, 'tcx> CompileState<'a, 'ast, 'tcx> {
|
||||
fn state_after_analysis(input: &'a Input,
|
||||
session: &'a Session,
|
||||
out_dir: &'a Option<PathBuf>,
|
||||
expanded_crate: &'a ast::Crate,
|
||||
krate: &'a ast::Crate,
|
||||
hir_crate: &'a hir::Crate,
|
||||
analysis: &'a ty::CrateAnalysis,
|
||||
tcx: &'a ty::ctxt<'tcx>)
|
||||
-> CompileState<'a, 'ast, 'tcx> {
|
||||
CompileState {
|
||||
analysis: Some(analysis),
|
||||
tcx: Some(tcx),
|
||||
expanded_crate: Some(expanded_crate),
|
||||
krate: Some(krate),
|
||||
hir_crate: Some(hir_crate),
|
||||
.. CompileState::empty(input, session, out_dir)
|
||||
}
|
||||
}
|
||||
@ -582,27 +600,38 @@ pub fn phase_2_configure_and_expand(sess: &Session,
|
||||
Some(krate)
|
||||
}
|
||||
|
||||
pub fn assign_node_ids_and_map<'ast>(sess: &Session,
|
||||
forest: &'ast mut ast_map::Forest)
|
||||
-> ast_map::Map<'ast> {
|
||||
pub fn assign_node_ids(sess: &Session,
|
||||
krate: ast::Crate) -> ast::Crate {
|
||||
struct NodeIdAssigner<'a> {
|
||||
sess: &'a Session
|
||||
}
|
||||
|
||||
impl<'a> ast_map::FoldOps for NodeIdAssigner<'a> {
|
||||
fn new_id(&self, old_id: ast::NodeId) -> ast::NodeId {
|
||||
impl<'a> Folder for NodeIdAssigner<'a> {
|
||||
fn new_id(&mut self, old_id: ast::NodeId) -> ast::NodeId {
|
||||
assert_eq!(old_id, ast::DUMMY_NODE_ID);
|
||||
self.sess.next_node_id()
|
||||
}
|
||||
}
|
||||
|
||||
let map = time(sess.time_passes(), "assigning node ids and indexing ast", move ||
|
||||
ast_map::map_crate(forest, NodeIdAssigner { sess: sess }));
|
||||
let krate = time(sess.time_passes(),
|
||||
"assigning node ids",
|
||||
|| NodeIdAssigner { sess: sess }.fold_crate(krate));
|
||||
|
||||
if sess.opts.debugging_opts.ast_json {
|
||||
println!("{}", json::as_json(map.krate()));
|
||||
println!("{}", json::as_json(&krate));
|
||||
}
|
||||
|
||||
krate
|
||||
}
|
||||
|
||||
pub fn make_map<'ast>(sess: &Session,
|
||||
forest: &'ast mut front::map::Forest)
|
||||
-> front::map::Map<'ast> {
|
||||
// Construct the 'ast'-map
|
||||
let map = time(sess.time_passes(),
|
||||
"indexing hir",
|
||||
move || front::map::map_crate(forest));
|
||||
|
||||
map
|
||||
}
|
||||
|
||||
@ -610,14 +639,15 @@ pub fn assign_node_ids_and_map<'ast>(sess: &Session,
|
||||
/// miscellaneous analysis passes on the crate. Return various
|
||||
/// structures carrying the results of the analysis.
|
||||
pub fn phase_3_run_analysis_passes<'tcx, F, R>(sess: Session,
|
||||
ast_map: ast_map::Map<'tcx>,
|
||||
ast_map: front::map::Map<'tcx>,
|
||||
ast_crate: &ast::Crate,
|
||||
arenas: &'tcx ty::CtxtArenas<'tcx>,
|
||||
name: String,
|
||||
make_glob_map: resolve::MakeGlobMap,
|
||||
f: F)
|
||||
-> (Session, R)
|
||||
where F: for<'a> FnOnce(&'a ty::ctxt<'tcx>,
|
||||
ty::CrateAnalysis) -> R
|
||||
ty::CrateAnalysis) -> R
|
||||
{
|
||||
let time_passes = sess.time_passes();
|
||||
let krate = ast_map.krate();
|
||||
@ -731,7 +761,7 @@ pub fn phase_3_run_analysis_passes<'tcx, F, R>(sess: Session,
|
||||
&tcx.sess, lib_features_used));
|
||||
|
||||
time(time_passes, "lint checking", ||
|
||||
lint::check_crate(tcx, &exported_items));
|
||||
lint::check_crate(tcx, ast_crate, &exported_items));
|
||||
|
||||
// The above three passes generate errors w/o aborting
|
||||
tcx.sess.abort_if_errors();
|
||||
|
@ -42,6 +42,7 @@ extern crate libc;
|
||||
extern crate rustc;
|
||||
extern crate rustc_back;
|
||||
extern crate rustc_borrowck;
|
||||
extern crate rustc_front;
|
||||
extern crate rustc_lint;
|
||||
extern crate rustc_privacy;
|
||||
extern crate rustc_resolve;
|
||||
@ -389,6 +390,7 @@ impl<'a> CompilerCalls<'a> for RustcDefaultCalls {
|
||||
time(state.session.time_passes(),
|
||||
"save analysis",
|
||||
|| save::process_crate(state.tcx.unwrap(),
|
||||
state.krate.unwrap(),
|
||||
state.analysis.unwrap(),
|
||||
state.out_dir));
|
||||
};
|
||||
|
@ -19,7 +19,6 @@ use rustc_trans::back::link;
|
||||
|
||||
use driver;
|
||||
|
||||
use rustc::ast_map::{self, blocks, NodePrinter};
|
||||
use rustc::middle::ty;
|
||||
use rustc::middle::cfg;
|
||||
use rustc::middle::cfg::graphviz::LabelledCFG;
|
||||
@ -44,18 +43,23 @@ use std::option;
|
||||
use std::path::PathBuf;
|
||||
use std::str::FromStr;
|
||||
|
||||
use rustc::front::map as hir_map;
|
||||
use rustc::front::map::{blocks, NodePrinter};
|
||||
use rustc_front::hir;
|
||||
use rustc_front::lowering::lower_crate;
|
||||
use rustc_front::print::pprust as pprust_hir;
|
||||
|
||||
#[derive(Copy, Clone, PartialEq, Debug)]
|
||||
pub enum PpSourceMode {
|
||||
PpmNormal,
|
||||
PpmEveryBodyLoops,
|
||||
PpmExpanded,
|
||||
PpmTyped,
|
||||
PpmIdentified,
|
||||
PpmExpandedIdentified,
|
||||
PpmExpandedHygiene,
|
||||
PpmTyped,
|
||||
}
|
||||
|
||||
|
||||
#[derive(Copy, Clone, PartialEq, Debug)]
|
||||
pub enum PpFlowGraphMode {
|
||||
Default,
|
||||
@ -68,6 +72,7 @@ pub enum PpFlowGraphMode {
|
||||
#[derive(Copy, Clone, PartialEq, Debug)]
|
||||
pub enum PpMode {
|
||||
PpmSource(PpSourceMode),
|
||||
PpmHir(PpSourceMode),
|
||||
PpmFlowGraph(PpFlowGraphMode),
|
||||
}
|
||||
|
||||
@ -79,25 +84,27 @@ pub fn parse_pretty(sess: &Session,
|
||||
let opt_second = split.next();
|
||||
let first = match (first, extended) {
|
||||
("normal", _) => PpmSource(PpmNormal),
|
||||
("identified", _) => PpmSource(PpmIdentified),
|
||||
("everybody_loops", true) => PpmSource(PpmEveryBodyLoops),
|
||||
("expanded", _) => PpmSource(PpmExpanded),
|
||||
("typed", _) => PpmSource(PpmTyped),
|
||||
("expanded,identified", _) => PpmSource(PpmExpandedIdentified),
|
||||
("expanded,hygiene", _) => PpmSource(PpmExpandedHygiene),
|
||||
("identified", _) => PpmSource(PpmIdentified),
|
||||
("hir", true) => PpmHir(PpmNormal),
|
||||
("hir,identified", true) => PpmHir(PpmExpandedIdentified),
|
||||
("hir,typed", true) => PpmHir(PpmTyped),
|
||||
("flowgraph", true) => PpmFlowGraph(PpFlowGraphMode::Default),
|
||||
("flowgraph,unlabelled", true) => PpmFlowGraph(PpFlowGraphMode::UnlabelledEdges),
|
||||
_ => {
|
||||
if extended {
|
||||
sess.fatal(&format!(
|
||||
"argument to `unpretty` must be one of `normal`, \
|
||||
`expanded`, `flowgraph[,unlabelled]=<nodeid>`, `typed`, `identified`, \
|
||||
`expanded,identified`, or `everybody_loops`; got {}", name));
|
||||
`expanded`, `flowgraph[,unlabelled]=<nodeid>`, `identified`, \
|
||||
`expanded,identified`, `everybody_loops`, `hir`, \
|
||||
`hir,identified`, or `hir,typed`; got {}", name));
|
||||
} else {
|
||||
sess.fatal(&format!(
|
||||
"argument to `pretty` must be one of `normal`, \
|
||||
`expanded`, `typed`, `identified`, \
|
||||
or `expanded,identified`; got {}", name));
|
||||
"argument to `pretty` must be one of `normal`, `expanded`, \
|
||||
`identified`, or `expanded,identified`; got {}", name));
|
||||
}
|
||||
}
|
||||
};
|
||||
@ -124,9 +131,7 @@ impl PpSourceMode {
|
||||
/// Constructs a `PrinterSupport` object and passes it to `f`.
|
||||
fn call_with_pp_support<'tcx, A, B, F>(&self,
|
||||
sess: Session,
|
||||
ast_map: Option<ast_map::Map<'tcx>>,
|
||||
arenas: &'tcx ty::CtxtArenas<'tcx>,
|
||||
id: String,
|
||||
ast_map: Option<hir_map::Map<'tcx>>,
|
||||
payload: B,
|
||||
f: F) -> A where
|
||||
F: FnOnce(&PrinterSupport, B) -> A,
|
||||
@ -145,18 +150,45 @@ impl PpSourceMode {
|
||||
let annotation = HygieneAnnotation { sess: sess, ast_map: ast_map };
|
||||
f(&annotation, payload)
|
||||
}
|
||||
_ => panic!("Should use call_with_pp_support_hir"),
|
||||
}
|
||||
}
|
||||
fn call_with_pp_support_hir<'tcx, A, B, F>(&self,
|
||||
sess: Session,
|
||||
ast_map: &hir_map::Map<'tcx>,
|
||||
ast_crate: &ast::Crate,
|
||||
arenas: &'tcx ty::CtxtArenas<'tcx>,
|
||||
id: String,
|
||||
payload: B,
|
||||
f: F) -> A where
|
||||
F: FnOnce(&HirPrinterSupport, B, &hir::Crate) -> A,
|
||||
{
|
||||
match *self {
|
||||
PpmNormal => {
|
||||
let annotation = NoAnn { sess: sess, ast_map: Some(ast_map.clone()) };
|
||||
f(&annotation, payload, &ast_map.forest.krate)
|
||||
}
|
||||
|
||||
PpmIdentified => {
|
||||
let annotation = IdentifiedAnnotation {
|
||||
sess: sess,
|
||||
ast_map: Some(ast_map.clone())
|
||||
};
|
||||
f(&annotation, payload, &ast_map.forest.krate)
|
||||
}
|
||||
PpmTyped => {
|
||||
let ast_map = ast_map.expect("--pretty=typed missing ast_map");
|
||||
driver::phase_3_run_analysis_passes(sess,
|
||||
ast_map,
|
||||
ast_map.clone(),
|
||||
ast_crate,
|
||||
arenas,
|
||||
id,
|
||||
resolve::MakeGlobMap::No,
|
||||
|tcx, _| {
|
||||
let annotation = TypedAnnotation { tcx: tcx };
|
||||
f(&annotation, payload)
|
||||
f(&annotation, payload, &ast_map.forest.krate)
|
||||
}).1
|
||||
}
|
||||
_ => panic!("Should use call_with_pp_support"),
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -167,8 +199,8 @@ trait PrinterSupport<'ast>: pprust::PpAnn {
|
||||
fn sess<'a>(&'a self) -> &'a Session;
|
||||
|
||||
/// Provides a uniform interface for re-extracting a reference to an
|
||||
/// `ast_map::Map` from a value that now owns it.
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a ast_map::Map<'ast>>;
|
||||
/// `hir_map::Map` from a value that now owns it.
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a hir_map::Map<'ast>>;
|
||||
|
||||
/// Produces the pretty-print annotation object.
|
||||
///
|
||||
@ -177,32 +209,59 @@ trait PrinterSupport<'ast>: pprust::PpAnn {
|
||||
fn pp_ann<'a>(&'a self) -> &'a pprust::PpAnn;
|
||||
}
|
||||
|
||||
trait HirPrinterSupport<'ast>: pprust_hir::PpAnn {
|
||||
/// Provides a uniform interface for re-extracting a reference to a
|
||||
/// `Session` from a value that now owns it.
|
||||
fn sess<'a>(&'a self) -> &'a Session;
|
||||
|
||||
/// Provides a uniform interface for re-extracting a reference to an
|
||||
/// `hir_map::Map` from a value that now owns it.
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a hir_map::Map<'ast>>;
|
||||
|
||||
/// Produces the pretty-print annotation object.
|
||||
///
|
||||
/// (Rust does not yet support upcasting from a trait object to
|
||||
/// an object for one of its super-traits.)
|
||||
fn pp_ann<'a>(&'a self) -> &'a pprust_hir::PpAnn;
|
||||
}
|
||||
|
||||
struct NoAnn<'ast> {
|
||||
sess: Session,
|
||||
ast_map: Option<ast_map::Map<'ast>>
|
||||
ast_map: Option<hir_map::Map<'ast>>
|
||||
}
|
||||
|
||||
impl<'ast> PrinterSupport<'ast> for NoAnn<'ast> {
|
||||
fn sess<'a>(&'a self) -> &'a Session { &self.sess }
|
||||
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a ast_map::Map<'ast>> {
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a hir_map::Map<'ast>> {
|
||||
self.ast_map.as_ref()
|
||||
}
|
||||
|
||||
fn pp_ann<'a>(&'a self) -> &'a pprust::PpAnn { self }
|
||||
}
|
||||
|
||||
impl<'ast> HirPrinterSupport<'ast> for NoAnn<'ast> {
|
||||
fn sess<'a>(&'a self) -> &'a Session { &self.sess }
|
||||
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a hir_map::Map<'ast>> {
|
||||
self.ast_map.as_ref()
|
||||
}
|
||||
|
||||
fn pp_ann<'a>(&'a self) -> &'a pprust_hir::PpAnn { self }
|
||||
}
|
||||
|
||||
impl<'ast> pprust::PpAnn for NoAnn<'ast> {}
|
||||
impl<'ast> pprust_hir::PpAnn for NoAnn<'ast> {}
|
||||
|
||||
struct IdentifiedAnnotation<'ast> {
|
||||
sess: Session,
|
||||
ast_map: Option<ast_map::Map<'ast>>,
|
||||
ast_map: Option<hir_map::Map<'ast>>,
|
||||
}
|
||||
|
||||
impl<'ast> PrinterSupport<'ast> for IdentifiedAnnotation<'ast> {
|
||||
fn sess<'a>(&'a self) -> &'a Session { &self.sess }
|
||||
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a ast_map::Map<'ast>> {
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a hir_map::Map<'ast>> {
|
||||
self.ast_map.as_ref()
|
||||
}
|
||||
|
||||
@ -249,15 +308,65 @@ impl<'ast> pprust::PpAnn for IdentifiedAnnotation<'ast> {
|
||||
}
|
||||
}
|
||||
|
||||
impl<'ast> HirPrinterSupport<'ast> for IdentifiedAnnotation<'ast> {
|
||||
fn sess<'a>(&'a self) -> &'a Session { &self.sess }
|
||||
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a hir_map::Map<'ast>> {
|
||||
self.ast_map.as_ref()
|
||||
}
|
||||
|
||||
fn pp_ann<'a>(&'a self) -> &'a pprust_hir::PpAnn { self }
|
||||
}
|
||||
|
||||
impl<'ast> pprust_hir::PpAnn for IdentifiedAnnotation<'ast> {
|
||||
fn pre(&self,
|
||||
s: &mut pprust_hir::State,
|
||||
node: pprust_hir::AnnNode) -> io::Result<()> {
|
||||
match node {
|
||||
pprust_hir::NodeExpr(_) => s.popen(),
|
||||
_ => Ok(())
|
||||
}
|
||||
}
|
||||
fn post(&self,
|
||||
s: &mut pprust_hir::State,
|
||||
node: pprust_hir::AnnNode) -> io::Result<()> {
|
||||
match node {
|
||||
pprust_hir::NodeIdent(_) | pprust_hir::NodeName(_) => Ok(()),
|
||||
|
||||
pprust_hir::NodeItem(item) => {
|
||||
try!(pp::space(&mut s.s));
|
||||
s.synth_comment(item.id.to_string())
|
||||
}
|
||||
pprust_hir::NodeSubItem(id) => {
|
||||
try!(pp::space(&mut s.s));
|
||||
s.synth_comment(id.to_string())
|
||||
}
|
||||
pprust_hir::NodeBlock(blk) => {
|
||||
try!(pp::space(&mut s.s));
|
||||
s.synth_comment(format!("block {}", blk.id))
|
||||
}
|
||||
pprust_hir::NodeExpr(expr) => {
|
||||
try!(pp::space(&mut s.s));
|
||||
try!(s.synth_comment(expr.id.to_string()));
|
||||
s.pclose()
|
||||
}
|
||||
pprust_hir::NodePat(pat) => {
|
||||
try!(pp::space(&mut s.s));
|
||||
s.synth_comment(format!("pat {}", pat.id))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct HygieneAnnotation<'ast> {
|
||||
sess: Session,
|
||||
ast_map: Option<ast_map::Map<'ast>>,
|
||||
ast_map: Option<hir_map::Map<'ast>>,
|
||||
}
|
||||
|
||||
impl<'ast> PrinterSupport<'ast> for HygieneAnnotation<'ast> {
|
||||
fn sess<'a>(&'a self) -> &'a Session { &self.sess }
|
||||
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a ast_map::Map<'ast>> {
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a hir_map::Map<'ast>> {
|
||||
self.ast_map.as_ref()
|
||||
}
|
||||
|
||||
@ -289,30 +398,30 @@ struct TypedAnnotation<'a, 'tcx: 'a> {
|
||||
tcx: &'a ty::ctxt<'tcx>,
|
||||
}
|
||||
|
||||
impl<'b, 'tcx> PrinterSupport<'tcx> for TypedAnnotation<'b, 'tcx> {
|
||||
impl<'b, 'tcx> HirPrinterSupport<'tcx> for TypedAnnotation<'b, 'tcx> {
|
||||
fn sess<'a>(&'a self) -> &'a Session { &self.tcx.sess }
|
||||
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a ast_map::Map<'tcx>> {
|
||||
fn ast_map<'a>(&'a self) -> Option<&'a hir_map::Map<'tcx>> {
|
||||
Some(&self.tcx.map)
|
||||
}
|
||||
|
||||
fn pp_ann<'a>(&'a self) -> &'a pprust::PpAnn { self }
|
||||
fn pp_ann<'a>(&'a self) -> &'a pprust_hir::PpAnn { self }
|
||||
}
|
||||
|
||||
impl<'a, 'tcx> pprust::PpAnn for TypedAnnotation<'a, 'tcx> {
|
||||
impl<'a, 'tcx> pprust_hir::PpAnn for TypedAnnotation<'a, 'tcx> {
|
||||
fn pre(&self,
|
||||
s: &mut pprust::State,
|
||||
node: pprust::AnnNode) -> io::Result<()> {
|
||||
s: &mut pprust_hir::State,
|
||||
node: pprust_hir::AnnNode) -> io::Result<()> {
|
||||
match node {
|
||||
pprust::NodeExpr(_) => s.popen(),
|
||||
pprust_hir::NodeExpr(_) => s.popen(),
|
||||
_ => Ok(())
|
||||
}
|
||||
}
|
||||
fn post(&self,
|
||||
s: &mut pprust::State,
|
||||
node: pprust::AnnNode) -> io::Result<()> {
|
||||
s: &mut pprust_hir::State,
|
||||
node: pprust_hir::AnnNode) -> io::Result<()> {
|
||||
match node {
|
||||
pprust::NodeExpr(expr) => {
|
||||
pprust_hir::NodeExpr(expr) => {
|
||||
try!(pp::space(&mut s.s));
|
||||
try!(pp::word(&mut s.s, "as"));
|
||||
try!(pp::space(&mut s.s));
|
||||
@ -360,7 +469,7 @@ impl FromStr for UserIdentifiedItem {
|
||||
|
||||
enum NodesMatchingUII<'a, 'ast: 'a> {
|
||||
NodesMatchingDirect(option::IntoIter<ast::NodeId>),
|
||||
NodesMatchingSuffix(ast_map::NodesMatchingSuffix<'a, 'ast>),
|
||||
NodesMatchingSuffix(hir_map::NodesMatchingSuffix<'a, 'ast>),
|
||||
}
|
||||
|
||||
impl<'a, 'ast> Iterator for NodesMatchingUII<'a, 'ast> {
|
||||
@ -382,7 +491,7 @@ impl UserIdentifiedItem {
|
||||
}
|
||||
}
|
||||
|
||||
fn all_matching_node_ids<'a, 'ast>(&'a self, map: &'a ast_map::Map<'ast>)
|
||||
fn all_matching_node_ids<'a, 'ast>(&'a self, map: &'a hir_map::Map<'ast>)
|
||||
-> NodesMatchingUII<'a, 'ast> {
|
||||
match *self {
|
||||
ItemViaNode(node_id) =>
|
||||
@ -392,7 +501,7 @@ impl UserIdentifiedItem {
|
||||
}
|
||||
}
|
||||
|
||||
fn to_one_node_id(self, user_option: &str, sess: &Session, map: &ast_map::Map) -> ast::NodeId {
|
||||
fn to_one_node_id(self, user_option: &str, sess: &Session, map: &hir_map::Map) -> ast::NodeId {
|
||||
let fail_because = |is_wrong_because| -> ast::NodeId {
|
||||
let message =
|
||||
format!("{} needs NodeId (int) or unique \
|
||||
@ -430,8 +539,9 @@ fn needs_ast_map(ppm: &PpMode, opt_uii: &Option<UserIdentifiedItem>) -> bool {
|
||||
PpmSource(PpmExpanded) |
|
||||
PpmSource(PpmExpandedIdentified) |
|
||||
PpmSource(PpmExpandedHygiene) |
|
||||
PpmSource(PpmTyped) |
|
||||
PpmFlowGraph(_) => true
|
||||
PpmHir(_) |
|
||||
PpmFlowGraph(_) => true,
|
||||
PpmSource(PpmTyped) => panic!("invalid state"),
|
||||
}
|
||||
}
|
||||
|
||||
@ -444,8 +554,9 @@ fn needs_expansion(ppm: &PpMode) -> bool {
|
||||
PpmSource(PpmExpanded) |
|
||||
PpmSource(PpmExpandedIdentified) |
|
||||
PpmSource(PpmExpandedHygiene) |
|
||||
PpmSource(PpmTyped) |
|
||||
PpmFlowGraph(_) => true
|
||||
PpmHir(_) |
|
||||
PpmFlowGraph(_) => true,
|
||||
PpmSource(PpmTyped) => panic!("invalid state"),
|
||||
}
|
||||
}
|
||||
|
||||
@ -552,20 +663,22 @@ pub fn pretty_print_input(sess: Session,
|
||||
let krate = if compute_ast_map {
|
||||
match driver::phase_2_configure_and_expand(&sess, krate, &id[..], None) {
|
||||
None => return,
|
||||
Some(k) => k
|
||||
Some(k) => driver::assign_node_ids(&sess, k)
|
||||
}
|
||||
} else {
|
||||
krate
|
||||
};
|
||||
|
||||
let mut forest = ast_map::Forest::new(krate);
|
||||
// There is some twisted, god-forsaken tangle of lifetimes here which makes
|
||||
// the ordering of stuff super-finicky.
|
||||
let mut hir_forest;
|
||||
let arenas = ty::CtxtArenas::new();
|
||||
|
||||
let (krate, ast_map) = if compute_ast_map {
|
||||
let map = driver::assign_node_ids_and_map(&sess, &mut forest);
|
||||
(map.krate(), Some(map))
|
||||
let ast_map = if compute_ast_map {
|
||||
hir_forest = hir_map::Forest::new(lower_crate(&krate));
|
||||
let map = driver::make_map(&sess, &mut hir_forest);
|
||||
Some(map)
|
||||
} else {
|
||||
(forest.krate(), None)
|
||||
None
|
||||
};
|
||||
|
||||
let src_name = driver::source_name(input);
|
||||
@ -580,15 +693,16 @@ pub fn pretty_print_input(sess: Session,
|
||||
let mut out = Vec::new();
|
||||
|
||||
match (ppm, opt_uii) {
|
||||
(PpmSource(s), None) => {
|
||||
(PpmSource(s), _) => {
|
||||
// Silently ignores an identified node.
|
||||
let out: &mut Write = &mut out;
|
||||
s.call_with_pp_support(
|
||||
sess, ast_map, &arenas, id, box out, |annotation, out| {
|
||||
sess, ast_map, box out, |annotation, out| {
|
||||
debug!("pretty printing source code {:?}", s);
|
||||
let sess = annotation.sess();
|
||||
pprust::print_crate(sess.codemap(),
|
||||
sess.diagnostic(),
|
||||
krate,
|
||||
&krate,
|
||||
src_name.to_string(),
|
||||
&mut rdr,
|
||||
out,
|
||||
@ -597,31 +711,52 @@ pub fn pretty_print_input(sess: Session,
|
||||
})
|
||||
}
|
||||
|
||||
(PpmSource(s), Some(uii)) => {
|
||||
(PpmHir(s), None) => {
|
||||
let out: &mut Write = &mut out;
|
||||
s.call_with_pp_support(
|
||||
sess, ast_map, &arenas, id, (out,uii), |annotation, (out,uii)| {
|
||||
s.call_with_pp_support_hir(
|
||||
sess, &ast_map.unwrap(), &krate, &arenas, id, box out, |annotation, out, krate| {
|
||||
debug!("pretty printing source code {:?}", s);
|
||||
let sess = annotation.sess();
|
||||
let ast_map = annotation.ast_map()
|
||||
.expect("--pretty missing ast_map");
|
||||
let mut pp_state =
|
||||
pprust::State::new_from_input(sess.codemap(),
|
||||
pprust_hir::print_crate(sess.codemap(),
|
||||
sess.diagnostic(),
|
||||
krate,
|
||||
src_name.to_string(),
|
||||
&mut rdr,
|
||||
out,
|
||||
annotation.pp_ann(),
|
||||
is_expanded)
|
||||
})
|
||||
}
|
||||
|
||||
(PpmHir(s), Some(uii)) => {
|
||||
let out: &mut Write = &mut out;
|
||||
s.call_with_pp_support_hir(sess,
|
||||
&ast_map.unwrap(),
|
||||
&krate,
|
||||
&arenas,
|
||||
id,
|
||||
(out,uii),
|
||||
|annotation, (out,uii), _| {
|
||||
debug!("pretty printing source code {:?}", s);
|
||||
let sess = annotation.sess();
|
||||
let ast_map = annotation.ast_map().expect("--pretty missing ast_map");
|
||||
let mut pp_state =
|
||||
pprust_hir::State::new_from_input(sess.codemap(),
|
||||
sess.diagnostic(),
|
||||
src_name.to_string(),
|
||||
&mut rdr,
|
||||
box out,
|
||||
annotation.pp_ann(),
|
||||
is_expanded);
|
||||
for node_id in uii.all_matching_node_ids(ast_map) {
|
||||
let node = ast_map.get(node_id);
|
||||
try!(pp_state.print_node(&node));
|
||||
try!(pp::space(&mut pp_state.s));
|
||||
try!(pp_state.synth_comment(ast_map.path_to_string(node_id)));
|
||||
try!(pp::hardbreak(&mut pp_state.s));
|
||||
}
|
||||
pp::eof(&mut pp_state.s)
|
||||
})
|
||||
true);
|
||||
for node_id in uii.all_matching_node_ids(ast_map) {
|
||||
let node = ast_map.get(node_id);
|
||||
try!(pp_state.print_node(&node));
|
||||
try!(pp::space(&mut pp_state.s));
|
||||
try!(pp_state.synth_comment(ast_map.path_to_string(node_id)));
|
||||
try!(pp::hardbreak(&mut pp_state.s));
|
||||
}
|
||||
pp::eof(&mut pp_state.s)
|
||||
})
|
||||
}
|
||||
|
||||
(PpmFlowGraph(mode), opt_uii) => {
|
||||
@ -646,6 +781,7 @@ pub fn pretty_print_input(sess: Session,
|
||||
let variants = gather_flowgraph_variants(&sess);
|
||||
driver::phase_3_run_analysis_passes(sess,
|
||||
ast_map,
|
||||
&krate,
|
||||
&arenas,
|
||||
id,
|
||||
resolve::MakeGlobMap::No,
|
||||
|
@ -29,7 +29,7 @@ use rustc_typeck::middle::infer;
|
||||
use rustc_typeck::middle::infer::lub::Lub;
|
||||
use rustc_typeck::middle::infer::glb::Glb;
|
||||
use rustc_typeck::middle::infer::sub::Sub;
|
||||
use rustc::ast_map;
|
||||
use rustc::front::map as hir_map;
|
||||
use rustc::session::{self,config};
|
||||
use syntax::{abi, ast};
|
||||
use syntax::codemap;
|
||||
@ -38,6 +38,9 @@ use syntax::diagnostic::{Level, RenderSpan, Bug, Fatal, Error, Warning, Note, He
|
||||
use syntax::parse::token;
|
||||
use syntax::feature_gate::UnstableFeatures;
|
||||
|
||||
use rustc_front::lowering::lower_crate;
|
||||
use rustc_front::hir;
|
||||
|
||||
struct Env<'a, 'tcx: 'a> {
|
||||
infcx: &'a infer::InferCtxt<'a, 'tcx>,
|
||||
}
|
||||
@ -120,9 +123,10 @@ fn test_env<F>(source_string: &str,
|
||||
let krate = driver::phase_2_configure_and_expand(&sess, krate, "test", None)
|
||||
.expect("phase 2 aborted");
|
||||
|
||||
let mut forest = ast_map::Forest::new(krate);
|
||||
let krate = driver::assign_node_ids(&sess, krate);
|
||||
let mut hir_forest = hir_map::Forest::new(lower_crate(&krate));
|
||||
let arenas = ty::CtxtArenas::new();
|
||||
let ast_map = driver::assign_node_ids_and_map(&sess, &mut forest);
|
||||
let ast_map = driver::make_map(&sess, &mut hir_forest);
|
||||
let krate = ast_map.krate();
|
||||
|
||||
// run just enough stuff to build a tcx:
|
||||
@ -185,7 +189,7 @@ impl<'a, 'tcx> Env<'a, 'tcx> {
|
||||
};
|
||||
|
||||
fn search_mod(this: &Env,
|
||||
m: &ast::Mod,
|
||||
m: &hir::Mod,
|
||||
idx: usize,
|
||||
names: &[String])
|
||||
-> Option<ast::NodeId> {
|
||||
@ -199,7 +203,7 @@ impl<'a, 'tcx> Env<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn search(this: &Env,
|
||||
it: &ast::Item,
|
||||
it: &hir::Item,
|
||||
idx: usize,
|
||||
names: &[String])
|
||||
-> Option<ast::NodeId> {
|
||||
@ -208,19 +212,19 @@ impl<'a, 'tcx> Env<'a, 'tcx> {
|
||||
}
|
||||
|
||||
return match it.node {
|
||||
ast::ItemUse(..) | ast::ItemExternCrate(..) |
|
||||
ast::ItemConst(..) | ast::ItemStatic(..) | ast::ItemFn(..) |
|
||||
ast::ItemForeignMod(..) | ast::ItemTy(..) => {
|
||||
hir::ItemUse(..) | hir::ItemExternCrate(..) |
|
||||
hir::ItemConst(..) | hir::ItemStatic(..) | hir::ItemFn(..) |
|
||||
hir::ItemForeignMod(..) | hir::ItemTy(..) => {
|
||||
None
|
||||
}
|
||||
|
||||
ast::ItemEnum(..) | ast::ItemStruct(..) |
|
||||
ast::ItemTrait(..) | ast::ItemImpl(..) |
|
||||
ast::ItemMac(..) | ast::ItemDefaultImpl(..) => {
|
||||
hir::ItemEnum(..) | hir::ItemStruct(..) |
|
||||
hir::ItemTrait(..) | hir::ItemImpl(..) |
|
||||
hir::ItemDefaultImpl(..) => {
|
||||
None
|
||||
}
|
||||
|
||||
ast::ItemMod(ref m) => {
|
||||
hir::ItemMod(ref m) => {
|
||||
search_mod(this, m, idx, names)
|
||||
}
|
||||
};
|
||||
@ -260,7 +264,7 @@ impl<'a, 'tcx> Env<'a, 'tcx> {
|
||||
let input_args = input_tys.iter().cloned().collect();
|
||||
self.infcx.tcx.mk_fn(None,
|
||||
self.infcx.tcx.mk_bare_fn(ty::BareFnTy {
|
||||
unsafety: ast::Unsafety::Normal,
|
||||
unsafety: hir::Unsafety::Normal,
|
||||
abi: abi::Rust,
|
||||
sig: ty::Binder(ty::FnSig {
|
||||
inputs: input_args,
|
||||
|
628
src/librustc_front/attr.rs
Normal file
628
src/librustc_front/attr.rs
Normal file
@ -0,0 +1,628 @@
|
||||
// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
|
||||
// file at the top-level directory of this distribution and at
|
||||
// http://rust-lang.org/COPYRIGHT.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
// Functions dealing with attributes and meta items
|
||||
|
||||
pub use self::StabilityLevel::*;
|
||||
pub use self::ReprAttr::*;
|
||||
pub use self::IntType::*;
|
||||
|
||||
use hir;
|
||||
use hir::{AttrId, Attribute, Attribute_, MetaItem, MetaWord, MetaNameValue, MetaList};
|
||||
use lowering::{lower_attr_style, unlower_attribute};
|
||||
use syntax::codemap::{Span, Spanned, spanned, dummy_spanned};
|
||||
use syntax::codemap::BytePos;
|
||||
use syntax::diagnostic::SpanHandler;
|
||||
use syntax::attr as syntax_attr;
|
||||
use syntax::parse::lexer::comments::{doc_comment_style, strip_doc_comment_decoration};
|
||||
use syntax::parse::token::{InternedString, intern_and_get_ident};
|
||||
use syntax::parse::token;
|
||||
use syntax::ptr::P;
|
||||
|
||||
use std::cell::Cell;
|
||||
use std::collections::HashSet;
|
||||
use std::fmt;
|
||||
|
||||
pub fn mark_used(attr: &Attribute) {
|
||||
syntax_attr::mark_used(&unlower_attribute(attr))
|
||||
}
|
||||
|
||||
pub trait AttrMetaMethods {
|
||||
fn check_name(&self, name: &str) -> bool {
|
||||
name == &self.name()[..]
|
||||
}
|
||||
|
||||
/// Retrieve the name of the meta item, e.g. `foo` in `#[foo]`,
|
||||
/// `#[foo="bar"]` and `#[foo(bar)]`
|
||||
fn name(&self) -> InternedString;
|
||||
|
||||
/// Gets the string value if self is a MetaNameValue variant
|
||||
/// containing a string, otherwise None.
|
||||
fn value_str(&self) -> Option<InternedString>;
|
||||
/// Gets a list of inner meta items from a list MetaItem type.
|
||||
fn meta_item_list<'a>(&'a self) -> Option<&'a [P<MetaItem>]>;
|
||||
|
||||
fn span(&self) -> Span;
|
||||
}
|
||||
|
||||
impl AttrMetaMethods for Attribute {
|
||||
fn check_name(&self, name: &str) -> bool {
|
||||
let matches = name == &self.name()[..];
|
||||
if matches {
|
||||
syntax_attr::mark_used(&unlower_attribute(self));
|
||||
}
|
||||
matches
|
||||
}
|
||||
fn name(&self) -> InternedString { self.meta().name() }
|
||||
fn value_str(&self) -> Option<InternedString> {
|
||||
self.meta().value_str()
|
||||
}
|
||||
fn meta_item_list<'a>(&'a self) -> Option<&'a [P<MetaItem>]> {
|
||||
self.node.value.meta_item_list()
|
||||
}
|
||||
fn span(&self) -> Span { self.meta().span }
|
||||
}
|
||||
|
||||
impl AttrMetaMethods for MetaItem {
|
||||
fn name(&self) -> InternedString {
|
||||
match self.node {
|
||||
MetaWord(ref n) => (*n).clone(),
|
||||
MetaNameValue(ref n, _) => (*n).clone(),
|
||||
MetaList(ref n, _) => (*n).clone(),
|
||||
}
|
||||
}
|
||||
|
||||
fn value_str(&self) -> Option<InternedString> {
|
||||
match self.node {
|
||||
MetaNameValue(_, ref v) => {
|
||||
match v.node {
|
||||
hir::LitStr(ref s, _) => Some((*s).clone()),
|
||||
_ => None,
|
||||
}
|
||||
},
|
||||
_ => None
|
||||
}
|
||||
}
|
||||
|
||||
fn meta_item_list<'a>(&'a self) -> Option<&'a [P<MetaItem>]> {
|
||||
match self.node {
|
||||
MetaList(_, ref l) => Some(&l[..]),
|
||||
_ => None
|
||||
}
|
||||
}
|
||||
fn span(&self) -> Span { self.span }
|
||||
}
|
||||
|
||||
// Annoying, but required to get test_cfg to work
|
||||
impl AttrMetaMethods for P<MetaItem> {
|
||||
fn name(&self) -> InternedString { (**self).name() }
|
||||
fn value_str(&self) -> Option<InternedString> { (**self).value_str() }
|
||||
fn meta_item_list<'a>(&'a self) -> Option<&'a [P<MetaItem>]> {
|
||||
(**self).meta_item_list()
|
||||
}
|
||||
fn span(&self) -> Span { (**self).span() }
|
||||
}
|
||||
|
||||
|
||||
pub trait AttributeMethods {
|
||||
fn meta<'a>(&'a self) -> &'a MetaItem;
|
||||
fn with_desugared_doc<T, F>(&self, f: F) -> T where
|
||||
F: FnOnce(&Attribute) -> T;
|
||||
}
|
||||
|
||||
impl AttributeMethods for Attribute {
|
||||
/// Extract the MetaItem from inside this Attribute.
|
||||
fn meta<'a>(&'a self) -> &'a MetaItem {
|
||||
&*self.node.value
|
||||
}
|
||||
|
||||
/// Convert self to a normal #[doc="foo"] comment, if it is a
|
||||
/// comment like `///` or `/** */`. (Returns self unchanged for
|
||||
/// non-sugared doc attributes.)
|
||||
fn with_desugared_doc<T, F>(&self, f: F) -> T where
|
||||
F: FnOnce(&Attribute) -> T,
|
||||
{
|
||||
if self.node.is_sugared_doc {
|
||||
let comment = self.value_str().unwrap();
|
||||
let meta = mk_name_value_item_str(
|
||||
InternedString::new("doc"),
|
||||
token::intern_and_get_ident(&strip_doc_comment_decoration(
|
||||
&comment)));
|
||||
if self.node.style == hir::AttrOuter {
|
||||
f(&mk_attr_outer(self.node.id, meta))
|
||||
} else {
|
||||
f(&mk_attr_inner(self.node.id, meta))
|
||||
}
|
||||
} else {
|
||||
f(self)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Constructors */
|
||||
|
||||
pub fn mk_name_value_item_str(name: InternedString, value: InternedString)
|
||||
-> P<MetaItem> {
|
||||
let value_lit = dummy_spanned(hir::LitStr(value, hir::CookedStr));
|
||||
mk_name_value_item(name, value_lit)
|
||||
}
|
||||
|
||||
pub fn mk_name_value_item(name: InternedString, value: hir::Lit)
|
||||
-> P<MetaItem> {
|
||||
P(dummy_spanned(MetaNameValue(name, value)))
|
||||
}
|
||||
|
||||
pub fn mk_list_item(name: InternedString, items: Vec<P<MetaItem>>) -> P<MetaItem> {
|
||||
P(dummy_spanned(MetaList(name, items)))
|
||||
}
|
||||
|
||||
pub fn mk_word_item(name: InternedString) -> P<MetaItem> {
|
||||
P(dummy_spanned(MetaWord(name)))
|
||||
}
|
||||
|
||||
thread_local! { static NEXT_ATTR_ID: Cell<usize> = Cell::new(0) }
|
||||
|
||||
pub fn mk_attr_id() -> AttrId {
|
||||
let id = NEXT_ATTR_ID.with(|slot| {
|
||||
let r = slot.get();
|
||||
slot.set(r + 1);
|
||||
r
|
||||
});
|
||||
AttrId(id)
|
||||
}
|
||||
|
||||
/// Returns an inner attribute with the given value.
|
||||
pub fn mk_attr_inner(id: AttrId, item: P<MetaItem>) -> Attribute {
|
||||
dummy_spanned(Attribute_ {
|
||||
id: id,
|
||||
style: hir::AttrInner,
|
||||
value: item,
|
||||
is_sugared_doc: false,
|
||||
})
|
||||
}
|
||||
|
||||
/// Returns an outer attribute with the given value.
|
||||
pub fn mk_attr_outer(id: AttrId, item: P<MetaItem>) -> Attribute {
|
||||
dummy_spanned(Attribute_ {
|
||||
id: id,
|
||||
style: hir::AttrOuter,
|
||||
value: item,
|
||||
is_sugared_doc: false,
|
||||
})
|
||||
}
|
||||
|
||||
pub fn mk_sugared_doc_attr(id: AttrId, text: InternedString, lo: BytePos,
|
||||
hi: BytePos)
|
||||
-> Attribute {
|
||||
let style = lower_attr_style(doc_comment_style(&text));
|
||||
let lit = spanned(lo, hi, hir::LitStr(text, hir::CookedStr));
|
||||
let attr = Attribute_ {
|
||||
id: id,
|
||||
style: style,
|
||||
value: P(spanned(lo, hi, MetaNameValue(InternedString::new("doc"),
|
||||
lit))),
|
||||
is_sugared_doc: true
|
||||
};
|
||||
spanned(lo, hi, attr)
|
||||
}
|
||||
|
||||
/* Searching */
|
||||
/// Check if `needle` occurs in `haystack` by a structural
|
||||
/// comparison. This is slightly subtle, and relies on ignoring the
|
||||
/// span included in the `==` comparison a plain MetaItem.
|
||||
pub fn contains(haystack: &[P<MetaItem>], needle: &MetaItem) -> bool {
|
||||
debug!("attr::contains (name={})", needle.name());
|
||||
haystack.iter().any(|item| {
|
||||
debug!(" testing: {}", item.name());
|
||||
item.node == needle.node
|
||||
})
|
||||
}
|
||||
|
||||
pub fn contains_name<AM: AttrMetaMethods>(metas: &[AM], name: &str) -> bool {
|
||||
debug!("attr::contains_name (name={})", name);
|
||||
metas.iter().any(|item| {
|
||||
debug!(" testing: {}", item.name());
|
||||
item.check_name(name)
|
||||
})
|
||||
}
|
||||
|
||||
pub fn first_attr_value_str_by_name(attrs: &[Attribute], name: &str)
|
||||
-> Option<InternedString> {
|
||||
attrs.iter()
|
||||
.find(|at| at.check_name(name))
|
||||
.and_then(|at| at.value_str())
|
||||
}
|
||||
|
||||
pub fn last_meta_item_value_str_by_name(items: &[P<MetaItem>], name: &str)
|
||||
-> Option<InternedString> {
|
||||
items.iter()
|
||||
.rev()
|
||||
.find(|mi| mi.check_name(name))
|
||||
.and_then(|i| i.value_str())
|
||||
}
|
||||
|
||||
/* Higher-level applications */
|
||||
|
||||
pub fn sort_meta_items(items: Vec<P<MetaItem>>) -> Vec<P<MetaItem>> {
|
||||
// This is sort of stupid here, but we need to sort by
|
||||
// human-readable strings.
|
||||
let mut v = items.into_iter()
|
||||
.map(|mi| (mi.name(), mi))
|
||||
.collect::<Vec<(InternedString, P<MetaItem>)>>();
|
||||
|
||||
v.sort_by(|&(ref a, _), &(ref b, _)| a.cmp(b));
|
||||
|
||||
// There doesn't seem to be a more optimal way to do this
|
||||
v.into_iter().map(|(_, m)| m.map(|Spanned {node, span}| {
|
||||
Spanned {
|
||||
node: match node {
|
||||
MetaList(n, mis) => MetaList(n, sort_meta_items(mis)),
|
||||
_ => node
|
||||
},
|
||||
span: span
|
||||
}
|
||||
})).collect()
|
||||
}
|
||||
|
||||
pub fn find_crate_name(attrs: &[Attribute]) -> Option<InternedString> {
|
||||
first_attr_value_str_by_name(attrs, "crate_name")
|
||||
}
|
||||
|
||||
/// Find the value of #[export_name=*] attribute and check its validity.
|
||||
pub fn find_export_name_attr(diag: &SpanHandler, attrs: &[Attribute]) -> Option<InternedString> {
|
||||
attrs.iter().fold(None, |ia,attr| {
|
||||
if attr.check_name("export_name") {
|
||||
if let s@Some(_) = attr.value_str() {
|
||||
s
|
||||
} else {
|
||||
diag.span_err(attr.span, "export_name attribute has invalid format");
|
||||
diag.handler.help("use #[export_name=\"*\"]");
|
||||
None
|
||||
}
|
||||
} else {
|
||||
ia
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone, PartialEq)]
|
||||
pub enum InlineAttr {
|
||||
None,
|
||||
Hint,
|
||||
Always,
|
||||
Never,
|
||||
}
|
||||
|
||||
/// Determine what `#[inline]` attribute is present in `attrs`, if any.
|
||||
pub fn find_inline_attr(diagnostic: Option<&SpanHandler>, attrs: &[Attribute]) -> InlineAttr {
|
||||
// FIXME (#2809)---validate the usage of #[inline] and #[inline]
|
||||
attrs.iter().fold(InlineAttr::None, |ia,attr| {
|
||||
match attr.node.value.node {
|
||||
MetaWord(ref n) if *n == "inline" => {
|
||||
syntax_attr::mark_used(&unlower_attribute(attr));
|
||||
InlineAttr::Hint
|
||||
}
|
||||
MetaList(ref n, ref items) if *n == "inline" => {
|
||||
syntax_attr::mark_used(&unlower_attribute(attr));
|
||||
if items.len() != 1 {
|
||||
diagnostic.map(|d|{ d.span_err(attr.span, "expected one argument"); });
|
||||
InlineAttr::None
|
||||
} else if contains_name(&items[..], "always") {
|
||||
InlineAttr::Always
|
||||
} else if contains_name(&items[..], "never") {
|
||||
InlineAttr::Never
|
||||
} else {
|
||||
diagnostic.map(|d|{ d.span_err((*items[0]).span, "invalid argument"); });
|
||||
InlineAttr::None
|
||||
}
|
||||
}
|
||||
_ => ia
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
/// True if `#[inline]` or `#[inline(always)]` is present in `attrs`.
|
||||
pub fn requests_inline(attrs: &[Attribute]) -> bool {
|
||||
match find_inline_attr(None, attrs) {
|
||||
InlineAttr::Hint | InlineAttr::Always => true,
|
||||
InlineAttr::None | InlineAttr::Never => false,
|
||||
}
|
||||
}
|
||||
|
||||
/// Represents the #[deprecated] and friends attributes.
|
||||
#[derive(RustcEncodable, RustcDecodable, Clone, Debug, PartialEq, Eq, Hash)]
|
||||
pub struct Stability {
|
||||
pub level: StabilityLevel,
|
||||
pub feature: InternedString,
|
||||
pub since: Option<InternedString>,
|
||||
pub deprecated_since: Option<InternedString>,
|
||||
// The reason for the current stability level. If deprecated, the
|
||||
// reason for deprecation.
|
||||
pub reason: Option<InternedString>,
|
||||
// The relevant rust-lang issue
|
||||
pub issue: Option<u32>
|
||||
}
|
||||
|
||||
/// The available stability levels.
|
||||
#[derive(RustcEncodable, RustcDecodable, PartialEq, PartialOrd, Clone, Debug, Copy, Eq, Hash)]
|
||||
pub enum StabilityLevel {
|
||||
Unstable,
|
||||
Stable,
|
||||
}
|
||||
|
||||
impl fmt::Display for StabilityLevel {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
fmt::Debug::fmt(self, f)
|
||||
}
|
||||
}
|
||||
|
||||
fn find_stability_generic<'a,
|
||||
AM: AttrMetaMethods,
|
||||
I: Iterator<Item=&'a AM>>
|
||||
(diagnostic: &SpanHandler, attrs: I, item_sp: Span)
|
||||
-> (Option<Stability>, Vec<&'a AM>) {
|
||||
|
||||
let mut stab: Option<Stability> = None;
|
||||
let mut deprecated: Option<(Option<InternedString>, Option<InternedString>)> = None;
|
||||
let mut used_attrs: Vec<&'a AM> = vec![];
|
||||
|
||||
'outer: for attr in attrs {
|
||||
let tag = attr.name();
|
||||
let tag = &tag[..];
|
||||
if tag != "deprecated" && tag != "unstable" && tag != "stable" {
|
||||
continue // not a stability level
|
||||
}
|
||||
|
||||
used_attrs.push(attr);
|
||||
|
||||
let (feature, since, reason, issue) = match attr.meta_item_list() {
|
||||
Some(metas) => {
|
||||
let mut feature = None;
|
||||
let mut since = None;
|
||||
let mut reason = None;
|
||||
let mut issue = None;
|
||||
for meta in metas {
|
||||
match &*meta.name() {
|
||||
"feature" => {
|
||||
match meta.value_str() {
|
||||
Some(v) => feature = Some(v),
|
||||
None => {
|
||||
diagnostic.span_err(meta.span, "incorrect meta item");
|
||||
continue 'outer;
|
||||
}
|
||||
}
|
||||
}
|
||||
"since" => {
|
||||
match meta.value_str() {
|
||||
Some(v) => since = Some(v),
|
||||
None => {
|
||||
diagnostic.span_err(meta.span, "incorrect meta item");
|
||||
continue 'outer;
|
||||
}
|
||||
}
|
||||
}
|
||||
"reason" => {
|
||||
match meta.value_str() {
|
||||
Some(v) => reason = Some(v),
|
||||
None => {
|
||||
diagnostic.span_err(meta.span, "incorrect meta item");
|
||||
continue 'outer;
|
||||
}
|
||||
}
|
||||
}
|
||||
"issue" => {
|
||||
match meta.value_str().and_then(|s| s.parse().ok()) {
|
||||
Some(v) => issue = Some(v),
|
||||
None => {
|
||||
diagnostic.span_err(meta.span, "incorrect meta item");
|
||||
continue 'outer;
|
||||
}
|
||||
}
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
(feature, since, reason, issue)
|
||||
}
|
||||
None => {
|
||||
diagnostic.span_err(attr.span(), "incorrect stability attribute type");
|
||||
continue
|
||||
}
|
||||
};
|
||||
|
||||
// Deprecated tags don't require feature names
|
||||
if feature == None && tag != "deprecated" {
|
||||
diagnostic.span_err(attr.span(), "missing 'feature'");
|
||||
}
|
||||
|
||||
// Unstable tags don't require a version
|
||||
if since == None && tag != "unstable" {
|
||||
diagnostic.span_err(attr.span(), "missing 'since'");
|
||||
}
|
||||
|
||||
if tag == "unstable" || tag == "stable" {
|
||||
if stab.is_some() {
|
||||
diagnostic.span_err(item_sp, "multiple stability levels");
|
||||
}
|
||||
|
||||
let level = match tag {
|
||||
"unstable" => Unstable,
|
||||
"stable" => Stable,
|
||||
_ => unreachable!()
|
||||
};
|
||||
|
||||
stab = Some(Stability {
|
||||
level: level,
|
||||
feature: feature.unwrap_or(intern_and_get_ident("bogus")),
|
||||
since: since,
|
||||
deprecated_since: None,
|
||||
reason: reason,
|
||||
issue: issue,
|
||||
});
|
||||
} else { // "deprecated"
|
||||
if deprecated.is_some() {
|
||||
diagnostic.span_err(item_sp, "multiple deprecated attributes");
|
||||
}
|
||||
|
||||
deprecated = Some((since, reason));
|
||||
}
|
||||
}
|
||||
|
||||
// Merge the deprecation info into the stability info
|
||||
if deprecated.is_some() {
|
||||
match stab {
|
||||
Some(ref mut s) => {
|
||||
let (since, reason) = deprecated.unwrap();
|
||||
s.deprecated_since = since;
|
||||
s.reason = reason;
|
||||
}
|
||||
None => {
|
||||
diagnostic.span_err(item_sp, "deprecated attribute must be paired with \
|
||||
either stable or unstable attribute");
|
||||
}
|
||||
}
|
||||
} else if stab.as_ref().map_or(false, |s| s.level == Unstable && s.issue.is_none()) {
|
||||
// non-deprecated unstable items need to point to issues.
|
||||
diagnostic.span_err(item_sp,
|
||||
"non-deprecated unstable items need to point \
|
||||
to an issue with `issue = \"NNN\"`");
|
||||
}
|
||||
|
||||
(stab, used_attrs)
|
||||
}
|
||||
|
||||
/// Find the first stability attribute. `None` if none exists.
|
||||
pub fn find_stability(diagnostic: &SpanHandler, attrs: &[Attribute],
|
||||
item_sp: Span) -> Option<Stability> {
|
||||
let (s, used) = find_stability_generic(diagnostic, attrs.iter(), item_sp);
|
||||
for used in used { syntax_attr::mark_used(&unlower_attribute(used)) }
|
||||
return s;
|
||||
}
|
||||
|
||||
pub fn require_unique_names(diagnostic: &SpanHandler, metas: &[P<MetaItem>]) {
|
||||
let mut set = HashSet::new();
|
||||
for meta in metas {
|
||||
let name = meta.name();
|
||||
|
||||
if !set.insert(name.clone()) {
|
||||
panic!(diagnostic.span_fatal(meta.span,
|
||||
&format!("duplicate meta item `{}`", name)));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Parse #[repr(...)] forms.
|
||||
///
|
||||
/// Valid repr contents: any of the primitive integral type names (see
|
||||
/// `int_type_of_word`, below) to specify enum discriminant type; `C`, to use
|
||||
/// the same discriminant size that the corresponding C enum would or C
|
||||
/// structure layout, and `packed` to remove padding.
|
||||
pub fn find_repr_attrs(diagnostic: &SpanHandler, attr: &Attribute) -> Vec<ReprAttr> {
|
||||
let mut acc = Vec::new();
|
||||
match attr.node.value.node {
|
||||
hir::MetaList(ref s, ref items) if *s == "repr" => {
|
||||
syntax_attr::mark_used(&unlower_attribute(attr));
|
||||
for item in items {
|
||||
match item.node {
|
||||
hir::MetaWord(ref word) => {
|
||||
let hint = match &word[..] {
|
||||
// Can't use "extern" because it's not a lexical identifier.
|
||||
"C" => Some(ReprExtern),
|
||||
"packed" => Some(ReprPacked),
|
||||
"simd" => Some(ReprSimd),
|
||||
_ => match int_type_of_word(&word) {
|
||||
Some(ity) => Some(ReprInt(item.span, ity)),
|
||||
None => {
|
||||
// Not a word we recognize
|
||||
diagnostic.span_err(item.span,
|
||||
"unrecognized representation hint");
|
||||
None
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
match hint {
|
||||
Some(h) => acc.push(h),
|
||||
None => { }
|
||||
}
|
||||
}
|
||||
// Not a word:
|
||||
_ => diagnostic.span_err(item.span, "unrecognized enum representation hint")
|
||||
}
|
||||
}
|
||||
}
|
||||
// Not a "repr" hint: ignore.
|
||||
_ => { }
|
||||
}
|
||||
acc
|
||||
}
|
||||
|
||||
fn int_type_of_word(s: &str) -> Option<IntType> {
|
||||
match s {
|
||||
"i8" => Some(SignedInt(hir::TyI8)),
|
||||
"u8" => Some(UnsignedInt(hir::TyU8)),
|
||||
"i16" => Some(SignedInt(hir::TyI16)),
|
||||
"u16" => Some(UnsignedInt(hir::TyU16)),
|
||||
"i32" => Some(SignedInt(hir::TyI32)),
|
||||
"u32" => Some(UnsignedInt(hir::TyU32)),
|
||||
"i64" => Some(SignedInt(hir::TyI64)),
|
||||
"u64" => Some(UnsignedInt(hir::TyU64)),
|
||||
"isize" => Some(SignedInt(hir::TyIs)),
|
||||
"usize" => Some(UnsignedInt(hir::TyUs)),
|
||||
_ => None
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(PartialEq, Debug, RustcEncodable, RustcDecodable, Copy, Clone)]
|
||||
pub enum ReprAttr {
|
||||
ReprAny,
|
||||
ReprInt(Span, IntType),
|
||||
ReprExtern,
|
||||
ReprPacked,
|
||||
ReprSimd,
|
||||
}
|
||||
|
||||
impl ReprAttr {
|
||||
pub fn is_ffi_safe(&self) -> bool {
|
||||
match *self {
|
||||
ReprAny => false,
|
||||
ReprInt(_sp, ity) => ity.is_ffi_safe(),
|
||||
ReprExtern => true,
|
||||
ReprPacked => false,
|
||||
ReprSimd => true,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Eq, Hash, PartialEq, Debug, RustcEncodable, RustcDecodable, Copy, Clone)]
|
||||
pub enum IntType {
|
||||
SignedInt(hir::IntTy),
|
||||
UnsignedInt(hir::UintTy)
|
||||
}
|
||||
|
||||
impl IntType {
|
||||
#[inline]
|
||||
pub fn is_signed(self) -> bool {
|
||||
match self {
|
||||
SignedInt(..) => true,
|
||||
UnsignedInt(..) => false
|
||||
}
|
||||
}
|
||||
fn is_ffi_safe(self) -> bool {
|
||||
match self {
|
||||
SignedInt(hir::TyI8) | UnsignedInt(hir::TyU8) |
|
||||
SignedInt(hir::TyI16) | UnsignedInt(hir::TyU16) |
|
||||
SignedInt(hir::TyI32) | UnsignedInt(hir::TyU32) |
|
||||
SignedInt(hir::TyI64) | UnsignedInt(hir::TyU64) => true,
|
||||
SignedInt(hir::TyIs) | UnsignedInt(hir::TyUs) => false
|
||||
}
|
||||
}
|
||||
}
|
1192
src/librustc_front/fold.rs
Normal file
1192
src/librustc_front/fold.rs
Normal file
File diff suppressed because it is too large
Load Diff
1533
src/librustc_front/hir.rs
Normal file
1533
src/librustc_front/hir.rs
Normal file
File diff suppressed because it is too large
Load Diff
58
src/librustc_front/lib.rs
Normal file
58
src/librustc_front/lib.rs
Normal file
@ -0,0 +1,58 @@
|
||||
// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
|
||||
// file at the top-level directory of this distribution and at
|
||||
// http://rust-lang.org/COPYRIGHT.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
//! The Rust compiler.
|
||||
//!
|
||||
//! # Note
|
||||
//!
|
||||
//! This API is completely unstable and subject to change.
|
||||
|
||||
// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
|
||||
#![cfg_attr(stage0, feature(custom_attribute))]
|
||||
#![crate_name = "rustc_front"]
|
||||
#![unstable(feature = "rustc_private", issue = "27812")]
|
||||
#![staged_api]
|
||||
#![crate_type = "dylib"]
|
||||
#![crate_type = "rlib"]
|
||||
#![doc(html_logo_url = "http://www.rust-lang.org/logos/rust-logo-128x128-blk-v2.png",
|
||||
html_favicon_url = "https://doc.rust-lang.org/favicon.ico",
|
||||
html_root_url = "http://doc.rust-lang.org/nightly/")]
|
||||
|
||||
#![feature(associated_consts)]
|
||||
#![feature(box_patterns)]
|
||||
#![feature(box_syntax)]
|
||||
#![feature(const_fn)]
|
||||
#![feature(quote)]
|
||||
#![feature(rustc_diagnostic_macros)]
|
||||
#![feature(rustc_private)]
|
||||
#![feature(slice_patterns)]
|
||||
#![feature(staged_api)]
|
||||
#![feature(str_char)]
|
||||
#![feature(filling_drop)]
|
||||
#![feature(str_escape)]
|
||||
#![cfg_attr(test, feature(test))]
|
||||
|
||||
extern crate serialize;
|
||||
#[macro_use] extern crate log;
|
||||
#[macro_use] extern crate syntax;
|
||||
#[macro_use] #[no_link] extern crate rustc_bitflags;
|
||||
|
||||
extern crate serialize as rustc_serialize; // used by deriving
|
||||
|
||||
pub mod hir;
|
||||
pub mod lowering;
|
||||
pub mod fold;
|
||||
pub mod visit;
|
||||
pub mod attr;
|
||||
pub mod util;
|
||||
|
||||
pub mod print {
|
||||
pub mod pprust;
|
||||
}
|
1133
src/librustc_front/lowering.rs
Normal file
1133
src/librustc_front/lowering.rs
Normal file
File diff suppressed because it is too large
Load Diff
686
src/librustc_front/print/pp.rs
Normal file
686
src/librustc_front/print/pp.rs
Normal file
@ -0,0 +1,686 @@
|
||||
// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
|
||||
// file at the top-level directory of this distribution and at
|
||||
// http://rust-lang.org/COPYRIGHT.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
//! This pretty-printer is a direct reimplementation of Philip Karlton's
|
||||
//! Mesa pretty-printer, as described in appendix A of
|
||||
//!
|
||||
//! STAN-CS-79-770: "Pretty Printing", by Derek C. Oppen.
|
||||
//! Stanford Department of Computer Science, 1979.
|
||||
//!
|
||||
//! The algorithm's aim is to break a stream into as few lines as possible
|
||||
//! while respecting the indentation-consistency requirements of the enclosing
|
||||
//! block, and avoiding breaking at silly places on block boundaries, for
|
||||
//! example, between "x" and ")" in "x)".
|
||||
//!
|
||||
//! I am implementing this algorithm because it comes with 20 pages of
|
||||
//! documentation explaining its theory, and because it addresses the set of
|
||||
//! concerns I've seen other pretty-printers fall down on. Weirdly. Even though
|
||||
//! it's 32 years old. What can I say?
|
||||
//!
|
||||
//! Despite some redundancies and quirks in the way it's implemented in that
|
||||
//! paper, I've opted to keep the implementation here as similar as I can,
|
||||
//! changing only what was blatantly wrong, a typo, or sufficiently
|
||||
//! non-idiomatic rust that it really stuck out.
|
||||
//!
|
||||
//! In particular you'll see a certain amount of churn related to INTEGER vs.
|
||||
//! CARDINAL in the Mesa implementation. Mesa apparently interconverts the two
|
||||
//! somewhat readily? In any case, I've used usize for indices-in-buffers and
|
||||
//! ints for character-sizes-and-indentation-offsets. This respects the need
|
||||
//! for ints to "go negative" while carrying a pending-calculation balance, and
|
||||
//! helps differentiate all the numbers flying around internally (slightly).
|
||||
//!
|
||||
//! I also inverted the indentation arithmetic used in the print stack, since
|
||||
//! the Mesa implementation (somewhat randomly) stores the offset on the print
|
||||
//! stack in terms of margin-col rather than col itself. I store col.
|
||||
//!
|
||||
//! I also implemented a small change in the String token, in that I store an
|
||||
//! explicit length for the string. For most tokens this is just the length of
|
||||
//! the accompanying string. But it's necessary to permit it to differ, for
|
||||
//! encoding things that are supposed to "go on their own line" -- certain
|
||||
//! classes of comment and blank-line -- where relying on adjacent
|
||||
//! hardbreak-like Break tokens with long blankness indication doesn't actually
|
||||
//! work. To see why, consider when there is a "thing that should be on its own
|
||||
//! line" between two long blocks, say functions. If you put a hardbreak after
|
||||
//! each function (or before each) and the breaking algorithm decides to break
|
||||
//! there anyways (because the functions themselves are long) you wind up with
|
||||
//! extra blank lines. If you don't put hardbreaks you can wind up with the
|
||||
//! "thing which should be on its own line" not getting its own line in the
|
||||
//! rare case of "really small functions" or such. This re-occurs with comments
|
||||
//! and explicit blank lines. So in those cases we use a string with a payload
|
||||
//! we want isolated to a line and an explicit length that's huge, surrounded
|
||||
//! by two zero-length breaks. The algorithm will try its best to fit it on a
|
||||
//! line (which it can't) and so naturally place the content on its own line to
|
||||
//! avoid combining it with other lines and making matters even worse.
|
||||
|
||||
use std::io;
|
||||
use std::string;
|
||||
|
||||
#[derive(Clone, Copy, PartialEq)]
|
||||
pub enum Breaks {
|
||||
Consistent,
|
||||
Inconsistent,
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy)]
|
||||
pub struct BreakToken {
|
||||
offset: isize,
|
||||
blank_space: isize
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy)]
|
||||
pub struct BeginToken {
|
||||
offset: isize,
|
||||
breaks: Breaks
|
||||
}
|
||||
|
||||
#[derive(Clone)]
|
||||
pub enum Token {
|
||||
String(String, isize),
|
||||
Break(BreakToken),
|
||||
Begin(BeginToken),
|
||||
End,
|
||||
Eof,
|
||||
}
|
||||
|
||||
impl Token {
|
||||
pub fn is_eof(&self) -> bool {
|
||||
match *self {
|
||||
Token::Eof => true,
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn is_hardbreak_tok(&self) -> bool {
|
||||
match *self {
|
||||
Token::Break(BreakToken {
|
||||
offset: 0,
|
||||
blank_space: bs
|
||||
}) if bs == SIZE_INFINITY =>
|
||||
true,
|
||||
_ =>
|
||||
false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn tok_str(token: &Token) -> String {
|
||||
match *token {
|
||||
Token::String(ref s, len) => format!("STR({},{})", s, len),
|
||||
Token::Break(_) => "BREAK".to_string(),
|
||||
Token::Begin(_) => "BEGIN".to_string(),
|
||||
Token::End => "END".to_string(),
|
||||
Token::Eof => "EOF".to_string()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn buf_str(toks: &[Token],
|
||||
szs: &[isize],
|
||||
left: usize,
|
||||
right: usize,
|
||||
lim: usize)
|
||||
-> String {
|
||||
let n = toks.len();
|
||||
assert_eq!(n, szs.len());
|
||||
let mut i = left;
|
||||
let mut l = lim;
|
||||
let mut s = string::String::from("[");
|
||||
while i != right && l != 0 {
|
||||
l -= 1;
|
||||
if i != left {
|
||||
s.push_str(", ");
|
||||
}
|
||||
s.push_str(&format!("{}={}",
|
||||
szs[i],
|
||||
tok_str(&toks[i])));
|
||||
i += 1;
|
||||
i %= n;
|
||||
}
|
||||
s.push(']');
|
||||
s
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub enum PrintStackBreak {
|
||||
Fits,
|
||||
Broken(Breaks),
|
||||
}
|
||||
|
||||
#[derive(Copy, Clone)]
|
||||
pub struct PrintStackElem {
|
||||
offset: isize,
|
||||
pbreak: PrintStackBreak
|
||||
}
|
||||
|
||||
const SIZE_INFINITY: isize = 0xffff;
|
||||
|
||||
pub fn mk_printer<'a>(out: Box<io::Write+'a>, linewidth: usize) -> Printer<'a> {
|
||||
// Yes 3, it makes the ring buffers big enough to never
|
||||
// fall behind.
|
||||
let n: usize = 3 * linewidth;
|
||||
debug!("mk_printer {}", linewidth);
|
||||
let token = vec![Token::Eof; n];
|
||||
let size = vec![0_isize; n];
|
||||
let scan_stack = vec![0_usize; n];
|
||||
Printer {
|
||||
out: out,
|
||||
buf_len: n,
|
||||
margin: linewidth as isize,
|
||||
space: linewidth as isize,
|
||||
left: 0,
|
||||
right: 0,
|
||||
token: token,
|
||||
size: size,
|
||||
left_total: 0,
|
||||
right_total: 0,
|
||||
scan_stack: scan_stack,
|
||||
scan_stack_empty: true,
|
||||
top: 0,
|
||||
bottom: 0,
|
||||
print_stack: Vec::new(),
|
||||
pending_indentation: 0
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// In case you do not have the paper, here is an explanation of what's going
|
||||
/// on.
|
||||
///
|
||||
/// There is a stream of input tokens flowing through this printer.
|
||||
///
|
||||
/// The printer buffers up to 3N tokens inside itself, where N is linewidth.
|
||||
/// Yes, linewidth is chars and tokens are multi-char, but in the worst
|
||||
/// case every token worth buffering is 1 char long, so it's ok.
|
||||
///
|
||||
/// Tokens are String, Break, and Begin/End to delimit blocks.
|
||||
///
|
||||
/// Begin tokens can carry an offset, saying "how far to indent when you break
|
||||
/// inside here", as well as a flag indicating "consistent" or "inconsistent"
|
||||
/// breaking. Consistent breaking means that after the first break, no attempt
|
||||
/// will be made to flow subsequent breaks together onto lines. Inconsistent
|
||||
/// is the opposite. Inconsistent breaking example would be, say:
|
||||
///
|
||||
/// foo(hello, there, good, friends)
|
||||
///
|
||||
/// breaking inconsistently to become
|
||||
///
|
||||
/// foo(hello, there
|
||||
/// good, friends);
|
||||
///
|
||||
/// whereas a consistent breaking would yield:
|
||||
///
|
||||
/// foo(hello,
|
||||
/// there
|
||||
/// good,
|
||||
/// friends);
|
||||
///
|
||||
/// That is, in the consistent-break blocks we value vertical alignment
|
||||
/// more than the ability to cram stuff onto a line. But in all cases if it
|
||||
/// can make a block a one-liner, it'll do so.
|
||||
///
|
||||
/// Carrying on with high-level logic:
|
||||
///
|
||||
/// The buffered tokens go through a ring-buffer, 'tokens'. The 'left' and
|
||||
/// 'right' indices denote the active portion of the ring buffer as well as
|
||||
/// describing hypothetical points-in-the-infinite-stream at most 3N tokens
|
||||
/// apart (i.e. "not wrapped to ring-buffer boundaries"). The paper will switch
|
||||
/// between using 'left' and 'right' terms to denote the wrapped-to-ring-buffer
|
||||
/// and point-in-infinite-stream senses freely.
|
||||
///
|
||||
/// There is a parallel ring buffer, 'size', that holds the calculated size of
|
||||
/// each token. Why calculated? Because for Begin/End pairs, the "size"
|
||||
/// includes everything between the pair. That is, the "size" of Begin is
|
||||
/// actually the sum of the sizes of everything between Begin and the paired
|
||||
/// End that follows. Since that is arbitrarily far in the future, 'size' is
|
||||
/// being rewritten regularly while the printer runs; in fact most of the
|
||||
/// machinery is here to work out 'size' entries on the fly (and give up when
|
||||
/// they're so obviously over-long that "infinity" is a good enough
|
||||
/// approximation for purposes of line breaking).
|
||||
///
|
||||
/// The "input side" of the printer is managed as an abstract process called
|
||||
/// SCAN, which uses 'scan_stack', 'scan_stack_empty', 'top' and 'bottom', to
|
||||
/// manage calculating 'size'. SCAN is, in other words, the process of
|
||||
/// calculating 'size' entries.
|
||||
///
|
||||
/// The "output side" of the printer is managed by an abstract process called
|
||||
/// PRINT, which uses 'print_stack', 'margin' and 'space' to figure out what to
|
||||
/// do with each token/size pair it consumes as it goes. It's trying to consume
|
||||
/// the entire buffered window, but can't output anything until the size is >=
|
||||
/// 0 (sizes are set to negative while they're pending calculation).
|
||||
///
|
||||
/// So SCAN takes input and buffers tokens and pending calculations, while
|
||||
/// PRINT gobbles up completed calculations and tokens from the buffer. The
|
||||
/// theory is that the two can never get more than 3N tokens apart, because
|
||||
/// once there's "obviously" too much data to fit on a line, in a size
|
||||
/// calculation, SCAN will write "infinity" to the size and let PRINT consume
|
||||
/// it.
|
||||
///
|
||||
/// In this implementation (following the paper, again) the SCAN process is
|
||||
/// the method called 'pretty_print', and the 'PRINT' process is the method
|
||||
/// called 'print'.
|
||||
pub struct Printer<'a> {
|
||||
pub out: Box<io::Write+'a>,
|
||||
buf_len: usize,
|
||||
/// Width of lines we're constrained to
|
||||
margin: isize,
|
||||
/// Number of spaces left on line
|
||||
space: isize,
|
||||
/// Index of left side of input stream
|
||||
left: usize,
|
||||
/// Index of right side of input stream
|
||||
right: usize,
|
||||
/// Ring-buffer stream goes through
|
||||
token: Vec<Token> ,
|
||||
/// Ring-buffer of calculated sizes
|
||||
size: Vec<isize> ,
|
||||
/// Running size of stream "...left"
|
||||
left_total: isize,
|
||||
/// Running size of stream "...right"
|
||||
right_total: isize,
|
||||
/// Pseudo-stack, really a ring too. Holds the
|
||||
/// primary-ring-buffers index of the Begin that started the
|
||||
/// current block, possibly with the most recent Break after that
|
||||
/// Begin (if there is any) on top of it. Stuff is flushed off the
|
||||
/// bottom as it becomes irrelevant due to the primary ring-buffer
|
||||
/// advancing.
|
||||
scan_stack: Vec<usize> ,
|
||||
/// Top==bottom disambiguator
|
||||
scan_stack_empty: bool,
|
||||
/// Index of top of scan_stack
|
||||
top: usize,
|
||||
/// Index of bottom of scan_stack
|
||||
bottom: usize,
|
||||
/// Stack of blocks-in-progress being flushed by print
|
||||
print_stack: Vec<PrintStackElem> ,
|
||||
/// Buffered indentation to avoid writing trailing whitespace
|
||||
pending_indentation: isize,
|
||||
}
|
||||
|
||||
impl<'a> Printer<'a> {
|
||||
pub fn last_token(&mut self) -> Token {
|
||||
self.token[self.right].clone()
|
||||
}
|
||||
// be very careful with this!
|
||||
pub fn replace_last_token(&mut self, t: Token) {
|
||||
self.token[self.right] = t;
|
||||
}
|
||||
pub fn pretty_print(&mut self, token: Token) -> io::Result<()> {
|
||||
debug!("pp Vec<{},{}>", self.left, self.right);
|
||||
match token {
|
||||
Token::Eof => {
|
||||
if !self.scan_stack_empty {
|
||||
self.check_stack(0);
|
||||
try!(self.advance_left());
|
||||
}
|
||||
self.indent(0);
|
||||
Ok(())
|
||||
}
|
||||
Token::Begin(b) => {
|
||||
if self.scan_stack_empty {
|
||||
self.left_total = 1;
|
||||
self.right_total = 1;
|
||||
self.left = 0;
|
||||
self.right = 0;
|
||||
} else { self.advance_right(); }
|
||||
debug!("pp Begin({})/buffer Vec<{},{}>",
|
||||
b.offset, self.left, self.right);
|
||||
self.token[self.right] = token;
|
||||
self.size[self.right] = -self.right_total;
|
||||
let right = self.right;
|
||||
self.scan_push(right);
|
||||
Ok(())
|
||||
}
|
||||
Token::End => {
|
||||
if self.scan_stack_empty {
|
||||
debug!("pp End/print Vec<{},{}>", self.left, self.right);
|
||||
self.print(token, 0)
|
||||
} else {
|
||||
debug!("pp End/buffer Vec<{},{}>", self.left, self.right);
|
||||
self.advance_right();
|
||||
self.token[self.right] = token;
|
||||
self.size[self.right] = -1;
|
||||
let right = self.right;
|
||||
self.scan_push(right);
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
Token::Break(b) => {
|
||||
if self.scan_stack_empty {
|
||||
self.left_total = 1;
|
||||
self.right_total = 1;
|
||||
self.left = 0;
|
||||
self.right = 0;
|
||||
} else { self.advance_right(); }
|
||||
debug!("pp Break({})/buffer Vec<{},{}>",
|
||||
b.offset, self.left, self.right);
|
||||
self.check_stack(0);
|
||||
let right = self.right;
|
||||
self.scan_push(right);
|
||||
self.token[self.right] = token;
|
||||
self.size[self.right] = -self.right_total;
|
||||
self.right_total += b.blank_space;
|
||||
Ok(())
|
||||
}
|
||||
Token::String(s, len) => {
|
||||
if self.scan_stack_empty {
|
||||
debug!("pp String('{}')/print Vec<{},{}>",
|
||||
s, self.left, self.right);
|
||||
self.print(Token::String(s, len), len)
|
||||
} else {
|
||||
debug!("pp String('{}')/buffer Vec<{},{}>",
|
||||
s, self.left, self.right);
|
||||
self.advance_right();
|
||||
self.token[self.right] = Token::String(s, len);
|
||||
self.size[self.right] = len;
|
||||
self.right_total += len;
|
||||
self.check_stream()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
pub fn check_stream(&mut self) -> io::Result<()> {
|
||||
debug!("check_stream Vec<{}, {}> with left_total={}, right_total={}",
|
||||
self.left, self.right, self.left_total, self.right_total);
|
||||
if self.right_total - self.left_total > self.space {
|
||||
debug!("scan window is {}, longer than space on line ({})",
|
||||
self.right_total - self.left_total, self.space);
|
||||
if !self.scan_stack_empty {
|
||||
if self.left == self.scan_stack[self.bottom] {
|
||||
debug!("setting {} to infinity and popping", self.left);
|
||||
let scanned = self.scan_pop_bottom();
|
||||
self.size[scanned] = SIZE_INFINITY;
|
||||
}
|
||||
}
|
||||
try!(self.advance_left());
|
||||
if self.left != self.right {
|
||||
try!(self.check_stream());
|
||||
}
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
pub fn scan_push(&mut self, x: usize) {
|
||||
debug!("scan_push {}", x);
|
||||
if self.scan_stack_empty {
|
||||
self.scan_stack_empty = false;
|
||||
} else {
|
||||
self.top += 1;
|
||||
self.top %= self.buf_len;
|
||||
assert!((self.top != self.bottom));
|
||||
}
|
||||
self.scan_stack[self.top] = x;
|
||||
}
|
||||
pub fn scan_pop(&mut self) -> usize {
|
||||
assert!((!self.scan_stack_empty));
|
||||
let x = self.scan_stack[self.top];
|
||||
if self.top == self.bottom {
|
||||
self.scan_stack_empty = true;
|
||||
} else {
|
||||
self.top += self.buf_len - 1; self.top %= self.buf_len;
|
||||
}
|
||||
return x;
|
||||
}
|
||||
pub fn scan_top(&mut self) -> usize {
|
||||
assert!((!self.scan_stack_empty));
|
||||
return self.scan_stack[self.top];
|
||||
}
|
||||
pub fn scan_pop_bottom(&mut self) -> usize {
|
||||
assert!((!self.scan_stack_empty));
|
||||
let x = self.scan_stack[self.bottom];
|
||||
if self.top == self.bottom {
|
||||
self.scan_stack_empty = true;
|
||||
} else {
|
||||
self.bottom += 1; self.bottom %= self.buf_len;
|
||||
}
|
||||
return x;
|
||||
}
|
||||
pub fn advance_right(&mut self) {
|
||||
self.right += 1;
|
||||
self.right %= self.buf_len;
|
||||
assert!((self.right != self.left));
|
||||
}
|
||||
pub fn advance_left(&mut self) -> io::Result<()> {
|
||||
debug!("advance_left Vec<{},{}>, sizeof({})={}", self.left, self.right,
|
||||
self.left, self.size[self.left]);
|
||||
|
||||
let mut left_size = self.size[self.left];
|
||||
|
||||
while left_size >= 0 {
|
||||
let left = self.token[self.left].clone();
|
||||
|
||||
let len = match left {
|
||||
Token::Break(b) => b.blank_space,
|
||||
Token::String(_, len) => {
|
||||
assert_eq!(len, left_size);
|
||||
len
|
||||
}
|
||||
_ => 0
|
||||
};
|
||||
|
||||
try!(self.print(left, left_size));
|
||||
|
||||
self.left_total += len;
|
||||
|
||||
if self.left == self.right {
|
||||
break;
|
||||
}
|
||||
|
||||
self.left += 1;
|
||||
self.left %= self.buf_len;
|
||||
|
||||
left_size = self.size[self.left];
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
pub fn check_stack(&mut self, k: isize) {
|
||||
if !self.scan_stack_empty {
|
||||
let x = self.scan_top();
|
||||
match self.token[x] {
|
||||
Token::Begin(_) => {
|
||||
if k > 0 {
|
||||
let popped = self.scan_pop();
|
||||
self.size[popped] = self.size[x] + self.right_total;
|
||||
self.check_stack(k - 1);
|
||||
}
|
||||
}
|
||||
Token::End => {
|
||||
// paper says + not =, but that makes no sense.
|
||||
let popped = self.scan_pop();
|
||||
self.size[popped] = 1;
|
||||
self.check_stack(k + 1);
|
||||
}
|
||||
_ => {
|
||||
let popped = self.scan_pop();
|
||||
self.size[popped] = self.size[x] + self.right_total;
|
||||
if k > 0 {
|
||||
self.check_stack(k);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
pub fn print_newline(&mut self, amount: isize) -> io::Result<()> {
|
||||
debug!("NEWLINE {}", amount);
|
||||
let ret = write!(self.out, "\n");
|
||||
self.pending_indentation = 0;
|
||||
self.indent(amount);
|
||||
return ret;
|
||||
}
|
||||
pub fn indent(&mut self, amount: isize) {
|
||||
debug!("INDENT {}", amount);
|
||||
self.pending_indentation += amount;
|
||||
}
|
||||
pub fn get_top(&mut self) -> PrintStackElem {
|
||||
let print_stack = &mut self.print_stack;
|
||||
let n = print_stack.len();
|
||||
if n != 0 {
|
||||
(*print_stack)[n - 1]
|
||||
} else {
|
||||
PrintStackElem {
|
||||
offset: 0,
|
||||
pbreak: PrintStackBreak::Broken(Breaks::Inconsistent)
|
||||
}
|
||||
}
|
||||
}
|
||||
pub fn print_str(&mut self, s: &str) -> io::Result<()> {
|
||||
while self.pending_indentation > 0 {
|
||||
try!(write!(self.out, " "));
|
||||
self.pending_indentation -= 1;
|
||||
}
|
||||
write!(self.out, "{}", s)
|
||||
}
|
||||
pub fn print(&mut self, token: Token, l: isize) -> io::Result<()> {
|
||||
debug!("print {} {} (remaining line space={})", tok_str(&token), l,
|
||||
self.space);
|
||||
debug!("{}", buf_str(&self.token,
|
||||
&self.size,
|
||||
self.left,
|
||||
self.right,
|
||||
6));
|
||||
match token {
|
||||
Token::Begin(b) => {
|
||||
if l > self.space {
|
||||
let col = self.margin - self.space + b.offset;
|
||||
debug!("print Begin -> push broken block at col {}", col);
|
||||
self.print_stack.push(PrintStackElem {
|
||||
offset: col,
|
||||
pbreak: PrintStackBreak::Broken(b.breaks)
|
||||
});
|
||||
} else {
|
||||
debug!("print Begin -> push fitting block");
|
||||
self.print_stack.push(PrintStackElem {
|
||||
offset: 0,
|
||||
pbreak: PrintStackBreak::Fits
|
||||
});
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
Token::End => {
|
||||
debug!("print End -> pop End");
|
||||
let print_stack = &mut self.print_stack;
|
||||
assert!((!print_stack.is_empty()));
|
||||
print_stack.pop().unwrap();
|
||||
Ok(())
|
||||
}
|
||||
Token::Break(b) => {
|
||||
let top = self.get_top();
|
||||
match top.pbreak {
|
||||
PrintStackBreak::Fits => {
|
||||
debug!("print Break({}) in fitting block", b.blank_space);
|
||||
self.space -= b.blank_space;
|
||||
self.indent(b.blank_space);
|
||||
Ok(())
|
||||
}
|
||||
PrintStackBreak::Broken(Breaks::Consistent) => {
|
||||
debug!("print Break({}+{}) in consistent block",
|
||||
top.offset, b.offset);
|
||||
let ret = self.print_newline(top.offset + b.offset);
|
||||
self.space = self.margin - (top.offset + b.offset);
|
||||
ret
|
||||
}
|
||||
PrintStackBreak::Broken(Breaks::Inconsistent) => {
|
||||
if l > self.space {
|
||||
debug!("print Break({}+{}) w/ newline in inconsistent",
|
||||
top.offset, b.offset);
|
||||
let ret = self.print_newline(top.offset + b.offset);
|
||||
self.space = self.margin - (top.offset + b.offset);
|
||||
ret
|
||||
} else {
|
||||
debug!("print Break({}) w/o newline in inconsistent",
|
||||
b.blank_space);
|
||||
self.indent(b.blank_space);
|
||||
self.space -= b.blank_space;
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Token::String(s, len) => {
|
||||
debug!("print String({})", s);
|
||||
assert_eq!(l, len);
|
||||
// assert!(l <= space);
|
||||
self.space -= len;
|
||||
self.print_str(&s[..])
|
||||
}
|
||||
Token::Eof => {
|
||||
// Eof should never get here.
|
||||
panic!();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Convenience functions to talk to the printer.
|
||||
//
|
||||
// "raw box"
|
||||
pub fn rbox(p: &mut Printer, indent: usize, b: Breaks) -> io::Result<()> {
|
||||
p.pretty_print(Token::Begin(BeginToken {
|
||||
offset: indent as isize,
|
||||
breaks: b
|
||||
}))
|
||||
}
|
||||
|
||||
pub fn ibox(p: &mut Printer, indent: usize) -> io::Result<()> {
|
||||
rbox(p, indent, Breaks::Inconsistent)
|
||||
}
|
||||
|
||||
pub fn cbox(p: &mut Printer, indent: usize) -> io::Result<()> {
|
||||
rbox(p, indent, Breaks::Consistent)
|
||||
}
|
||||
|
||||
pub fn break_offset(p: &mut Printer, n: usize, off: isize) -> io::Result<()> {
|
||||
p.pretty_print(Token::Break(BreakToken {
|
||||
offset: off,
|
||||
blank_space: n as isize
|
||||
}))
|
||||
}
|
||||
|
||||
pub fn end(p: &mut Printer) -> io::Result<()> {
|
||||
p.pretty_print(Token::End)
|
||||
}
|
||||
|
||||
pub fn eof(p: &mut Printer) -> io::Result<()> {
|
||||
p.pretty_print(Token::Eof)
|
||||
}
|
||||
|
||||
pub fn word(p: &mut Printer, wrd: &str) -> io::Result<()> {
|
||||
p.pretty_print(Token::String(/* bad */ wrd.to_string(), wrd.len() as isize))
|
||||
}
|
||||
|
||||
pub fn huge_word(p: &mut Printer, wrd: &str) -> io::Result<()> {
|
||||
p.pretty_print(Token::String(/* bad */ wrd.to_string(), SIZE_INFINITY))
|
||||
}
|
||||
|
||||
pub fn zero_word(p: &mut Printer, wrd: &str) -> io::Result<()> {
|
||||
p.pretty_print(Token::String(/* bad */ wrd.to_string(), 0))
|
||||
}
|
||||
|
||||
pub fn spaces(p: &mut Printer, n: usize) -> io::Result<()> {
|
||||
break_offset(p, n, 0)
|
||||
}
|
||||
|
||||
pub fn zerobreak(p: &mut Printer) -> io::Result<()> {
|
||||
spaces(p, 0)
|
||||
}
|
||||
|
||||
pub fn space(p: &mut Printer) -> io::Result<()> {
|
||||
spaces(p, 1)
|
||||
}
|
||||
|
||||
pub fn hardbreak(p: &mut Printer) -> io::Result<()> {
|
||||
spaces(p, SIZE_INFINITY as usize)
|
||||
}
|
||||
|
||||
pub fn hardbreak_tok_offset(off: isize) -> Token {
|
||||
Token::Break(BreakToken {offset: off, blank_space: SIZE_INFINITY})
|
||||
}
|
||||
|
||||
pub fn hardbreak_tok() -> Token {
|
||||
hardbreak_tok_offset(0)
|
||||
}
|
2760
src/librustc_front/print/pprust.rs
Normal file
2760
src/librustc_front/print/pprust.rs
Normal file
File diff suppressed because it is too large
Load Diff
427
src/librustc_front/util.rs
Normal file
427
src/librustc_front/util.rs
Normal file
@ -0,0 +1,427 @@
|
||||
// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
|
||||
// file at the top-level directory of this distribution and at
|
||||
// http://rust-lang.org/COPYRIGHT.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
use hir;
|
||||
use hir::*;
|
||||
use visit::{self, Visitor, FnKind};
|
||||
use syntax::ast_util;
|
||||
use syntax::ast::{Ident, NodeId, DUMMY_NODE_ID};
|
||||
use syntax::codemap::Span;
|
||||
use syntax::ptr::P;
|
||||
use syntax::owned_slice::OwnedSlice;
|
||||
|
||||
pub fn walk_pat<F>(pat: &Pat, mut it: F) -> bool where F: FnMut(&Pat) -> bool {
|
||||
// FIXME(#19596) this is a workaround, but there should be a better way
|
||||
fn walk_pat_<G>(pat: &Pat, it: &mut G) -> bool where G: FnMut(&Pat) -> bool {
|
||||
if !(*it)(pat) {
|
||||
return false;
|
||||
}
|
||||
|
||||
match pat.node {
|
||||
PatIdent(_, _, Some(ref p)) => walk_pat_(&**p, it),
|
||||
PatStruct(_, ref fields, _) => {
|
||||
fields.iter().all(|field| walk_pat_(&*field.node.pat, it))
|
||||
}
|
||||
PatEnum(_, Some(ref s)) | PatTup(ref s) => {
|
||||
s.iter().all(|p| walk_pat_(&**p, it))
|
||||
}
|
||||
PatBox(ref s) | PatRegion(ref s, _) => {
|
||||
walk_pat_(&**s, it)
|
||||
}
|
||||
PatVec(ref before, ref slice, ref after) => {
|
||||
before.iter().all(|p| walk_pat_(&**p, it)) &&
|
||||
slice.iter().all(|p| walk_pat_(&**p, it)) &&
|
||||
after.iter().all(|p| walk_pat_(&**p, it))
|
||||
}
|
||||
PatWild(_) | PatLit(_) | PatRange(_, _) | PatIdent(_, _, _) |
|
||||
PatEnum(_, _) | PatQPath(_, _) => {
|
||||
true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
walk_pat_(pat, &mut it)
|
||||
}
|
||||
|
||||
pub fn binop_to_string(op: BinOp_) -> &'static str {
|
||||
match op {
|
||||
BiAdd => "+",
|
||||
BiSub => "-",
|
||||
BiMul => "*",
|
||||
BiDiv => "/",
|
||||
BiRem => "%",
|
||||
BiAnd => "&&",
|
||||
BiOr => "||",
|
||||
BiBitXor => "^",
|
||||
BiBitAnd => "&",
|
||||
BiBitOr => "|",
|
||||
BiShl => "<<",
|
||||
BiShr => ">>",
|
||||
BiEq => "==",
|
||||
BiLt => "<",
|
||||
BiLe => "<=",
|
||||
BiNe => "!=",
|
||||
BiGe => ">=",
|
||||
BiGt => ">"
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns true if the given struct def is tuple-like; i.e. that its fields
|
||||
/// are unnamed.
|
||||
pub fn struct_def_is_tuple_like(struct_def: &hir::StructDef) -> bool {
|
||||
struct_def.ctor_id.is_some()
|
||||
}
|
||||
|
||||
pub fn stmt_id(s: &Stmt) -> NodeId {
|
||||
match s.node {
|
||||
StmtDecl(_, id) => id,
|
||||
StmtExpr(_, id) => id,
|
||||
StmtSemi(_, id) => id,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn lazy_binop(b: BinOp_) -> bool {
|
||||
match b {
|
||||
BiAnd => true,
|
||||
BiOr => true,
|
||||
_ => false
|
||||
}
|
||||
}
|
||||
|
||||
pub fn is_shift_binop(b: BinOp_) -> bool {
|
||||
match b {
|
||||
BiShl => true,
|
||||
BiShr => true,
|
||||
_ => false
|
||||
}
|
||||
}
|
||||
|
||||
pub fn is_comparison_binop(b: BinOp_) -> bool {
|
||||
match b {
|
||||
BiEq | BiLt | BiLe | BiNe | BiGt | BiGe =>
|
||||
true,
|
||||
BiAnd | BiOr | BiAdd | BiSub | BiMul | BiDiv | BiRem |
|
||||
BiBitXor | BiBitAnd | BiBitOr | BiShl | BiShr =>
|
||||
false,
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns `true` if the binary operator takes its arguments by value
|
||||
pub fn is_by_value_binop(b: BinOp_) -> bool {
|
||||
!is_comparison_binop(b)
|
||||
}
|
||||
|
||||
/// Returns `true` if the unary operator takes its argument by value
|
||||
pub fn is_by_value_unop(u: UnOp) -> bool {
|
||||
match u {
|
||||
UnNeg | UnNot => true,
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn unop_to_string(op: UnOp) -> &'static str {
|
||||
match op {
|
||||
UnUniq => "box() ",
|
||||
UnDeref => "*",
|
||||
UnNot => "!",
|
||||
UnNeg => "-",
|
||||
}
|
||||
}
|
||||
|
||||
pub struct IdVisitor<'a, O:'a> {
|
||||
pub operation: &'a mut O,
|
||||
pub pass_through_items: bool,
|
||||
pub visited_outermost: bool,
|
||||
}
|
||||
|
||||
impl<'a, O: ast_util::IdVisitingOperation> IdVisitor<'a, O> {
|
||||
fn visit_generics_helper(&mut self, generics: &Generics) {
|
||||
for type_parameter in generics.ty_params.iter() {
|
||||
self.operation.visit_id(type_parameter.id)
|
||||
}
|
||||
for lifetime in &generics.lifetimes {
|
||||
self.operation.visit_id(lifetime.lifetime.id)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a, 'v, O: ast_util::IdVisitingOperation> Visitor<'v> for IdVisitor<'a, O> {
|
||||
fn visit_mod(&mut self,
|
||||
module: &Mod,
|
||||
_: Span,
|
||||
node_id: NodeId) {
|
||||
self.operation.visit_id(node_id);
|
||||
visit::walk_mod(self, module)
|
||||
}
|
||||
|
||||
fn visit_foreign_item(&mut self, foreign_item: &ForeignItem) {
|
||||
self.operation.visit_id(foreign_item.id);
|
||||
visit::walk_foreign_item(self, foreign_item)
|
||||
}
|
||||
|
||||
fn visit_item(&mut self, item: &Item) {
|
||||
if !self.pass_through_items {
|
||||
if self.visited_outermost {
|
||||
return
|
||||
} else {
|
||||
self.visited_outermost = true
|
||||
}
|
||||
}
|
||||
|
||||
self.operation.visit_id(item.id);
|
||||
match item.node {
|
||||
ItemUse(ref view_path) => {
|
||||
match view_path.node {
|
||||
ViewPathSimple(_, _) |
|
||||
ViewPathGlob(_) => {}
|
||||
ViewPathList(_, ref paths) => {
|
||||
for path in paths {
|
||||
self.operation.visit_id(path.node.id())
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
ItemEnum(ref enum_definition, _) => {
|
||||
for variant in &enum_definition.variants {
|
||||
self.operation.visit_id(variant.node.id)
|
||||
}
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
|
||||
visit::walk_item(self, item);
|
||||
|
||||
self.visited_outermost = false
|
||||
}
|
||||
|
||||
fn visit_local(&mut self, local: &Local) {
|
||||
self.operation.visit_id(local.id);
|
||||
visit::walk_local(self, local)
|
||||
}
|
||||
|
||||
fn visit_block(&mut self, block: &Block) {
|
||||
self.operation.visit_id(block.id);
|
||||
visit::walk_block(self, block)
|
||||
}
|
||||
|
||||
fn visit_stmt(&mut self, statement: &Stmt) {
|
||||
self.operation.visit_id(stmt_id(statement));
|
||||
visit::walk_stmt(self, statement)
|
||||
}
|
||||
|
||||
fn visit_pat(&mut self, pattern: &Pat) {
|
||||
self.operation.visit_id(pattern.id);
|
||||
visit::walk_pat(self, pattern)
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, expression: &Expr) {
|
||||
self.operation.visit_id(expression.id);
|
||||
visit::walk_expr(self, expression)
|
||||
}
|
||||
|
||||
fn visit_ty(&mut self, typ: &Ty) {
|
||||
self.operation.visit_id(typ.id);
|
||||
visit::walk_ty(self, typ)
|
||||
}
|
||||
|
||||
fn visit_generics(&mut self, generics: &Generics) {
|
||||
self.visit_generics_helper(generics);
|
||||
visit::walk_generics(self, generics)
|
||||
}
|
||||
|
||||
fn visit_fn(&mut self,
|
||||
function_kind: FnKind<'v>,
|
||||
function_declaration: &'v FnDecl,
|
||||
block: &'v Block,
|
||||
span: Span,
|
||||
node_id: NodeId) {
|
||||
if !self.pass_through_items {
|
||||
match function_kind {
|
||||
FnKind::Method(..) if self.visited_outermost => return,
|
||||
FnKind::Method(..) => self.visited_outermost = true,
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
||||
self.operation.visit_id(node_id);
|
||||
|
||||
match function_kind {
|
||||
FnKind::ItemFn(_, generics, _, _, _, _) => {
|
||||
self.visit_generics_helper(generics)
|
||||
}
|
||||
FnKind::Method(_, sig, _) => {
|
||||
self.visit_generics_helper(&sig.generics)
|
||||
}
|
||||
FnKind::Closure => {}
|
||||
}
|
||||
|
||||
for argument in &function_declaration.inputs {
|
||||
self.operation.visit_id(argument.id)
|
||||
}
|
||||
|
||||
visit::walk_fn(self,
|
||||
function_kind,
|
||||
function_declaration,
|
||||
block,
|
||||
span);
|
||||
|
||||
if !self.pass_through_items {
|
||||
if let FnKind::Method(..) = function_kind {
|
||||
self.visited_outermost = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_struct_field(&mut self, struct_field: &StructField) {
|
||||
self.operation.visit_id(struct_field.node.id);
|
||||
visit::walk_struct_field(self, struct_field)
|
||||
}
|
||||
|
||||
fn visit_struct_def(&mut self,
|
||||
struct_def: &StructDef,
|
||||
_: Ident,
|
||||
_: &hir::Generics,
|
||||
id: NodeId) {
|
||||
self.operation.visit_id(id);
|
||||
struct_def.ctor_id.map(|ctor_id| self.operation.visit_id(ctor_id));
|
||||
visit::walk_struct_def(self, struct_def);
|
||||
}
|
||||
|
||||
fn visit_trait_item(&mut self, ti: &hir::TraitItem) {
|
||||
self.operation.visit_id(ti.id);
|
||||
visit::walk_trait_item(self, ti);
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, ii: &hir::ImplItem) {
|
||||
self.operation.visit_id(ii.id);
|
||||
visit::walk_impl_item(self, ii);
|
||||
}
|
||||
|
||||
fn visit_lifetime_ref(&mut self, lifetime: &Lifetime) {
|
||||
self.operation.visit_id(lifetime.id);
|
||||
}
|
||||
|
||||
fn visit_lifetime_def(&mut self, def: &LifetimeDef) {
|
||||
self.visit_lifetime_ref(&def.lifetime);
|
||||
}
|
||||
|
||||
fn visit_trait_ref(&mut self, trait_ref: &TraitRef) {
|
||||
self.operation.visit_id(trait_ref.ref_id);
|
||||
visit::walk_trait_ref(self, trait_ref);
|
||||
}
|
||||
}
|
||||
|
||||
/// Computes the id range for a single fn body, ignoring nested items.
|
||||
pub fn compute_id_range_for_fn_body(fk: FnKind,
|
||||
decl: &FnDecl,
|
||||
body: &Block,
|
||||
sp: Span,
|
||||
id: NodeId)
|
||||
-> ast_util::IdRange
|
||||
{
|
||||
let mut visitor = ast_util::IdRangeComputingVisitor {
|
||||
result: ast_util::IdRange::max()
|
||||
};
|
||||
let mut id_visitor = IdVisitor {
|
||||
operation: &mut visitor,
|
||||
pass_through_items: false,
|
||||
visited_outermost: false,
|
||||
};
|
||||
id_visitor.visit_fn(fk, decl, body, sp, id);
|
||||
id_visitor.operation.result
|
||||
}
|
||||
|
||||
/// Returns true if this literal is a string and false otherwise.
|
||||
pub fn lit_is_str(lit: &Lit) -> bool {
|
||||
match lit.node {
|
||||
LitStr(..) => true,
|
||||
_ => false,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn is_path(e: P<Expr>) -> bool {
|
||||
match e.node { ExprPath(..) => true, _ => false }
|
||||
}
|
||||
|
||||
/// Get a string representation of a signed int type, with its value.
|
||||
/// We want to avoid "45int" and "-3int" in favor of "45" and "-3"
|
||||
pub fn int_ty_to_string(t: IntTy, val: Option<i64>) -> String {
|
||||
let s = match t {
|
||||
TyIs => "isize",
|
||||
TyI8 => "i8",
|
||||
TyI16 => "i16",
|
||||
TyI32 => "i32",
|
||||
TyI64 => "i64"
|
||||
};
|
||||
|
||||
match val {
|
||||
// cast to a u64 so we can correctly print INT64_MIN. All integral types
|
||||
// are parsed as u64, so we wouldn't want to print an extra negative
|
||||
// sign.
|
||||
Some(n) => format!("{}{}", n as u64, s),
|
||||
None => s.to_string()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Get a string representation of an unsigned int type, with its value.
|
||||
/// We want to avoid "42u" in favor of "42us". "42uint" is right out.
|
||||
pub fn uint_ty_to_string(t: UintTy, val: Option<u64>) -> String {
|
||||
let s = match t {
|
||||
TyUs => "usize",
|
||||
TyU8 => "u8",
|
||||
TyU16 => "u16",
|
||||
TyU32 => "u32",
|
||||
TyU64 => "u64"
|
||||
};
|
||||
|
||||
match val {
|
||||
Some(n) => format!("{}{}", n, s),
|
||||
None => s.to_string()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn float_ty_to_string(t: FloatTy) -> String {
|
||||
match t {
|
||||
TyF32 => "f32".to_string(),
|
||||
TyF64 => "f64".to_string(),
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
pub fn empty_generics() -> Generics {
|
||||
Generics {
|
||||
lifetimes: Vec::new(),
|
||||
ty_params: OwnedSlice::empty(),
|
||||
where_clause: WhereClause {
|
||||
id: DUMMY_NODE_ID,
|
||||
predicates: Vec::new(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// convert a span and an identifier to the corresponding
|
||||
// 1-segment path
|
||||
pub fn ident_to_path(s: Span, identifier: Ident) -> Path {
|
||||
hir::Path {
|
||||
span: s,
|
||||
global: false,
|
||||
segments: vec!(
|
||||
hir::PathSegment {
|
||||
identifier: identifier,
|
||||
parameters: hir::AngleBracketedParameters(hir::AngleBracketedParameterData {
|
||||
lifetimes: Vec::new(),
|
||||
types: OwnedSlice::empty(),
|
||||
bindings: OwnedSlice::empty(),
|
||||
})
|
||||
}
|
||||
),
|
||||
}
|
||||
}
|
841
src/librustc_front/visit.rs
Normal file
841
src/librustc_front/visit.rs
Normal file
@ -0,0 +1,841 @@
|
||||
// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
|
||||
// file at the top-level directory of this distribution and at
|
||||
// http://rust-lang.org/COPYRIGHT.
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
|
||||
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
|
||||
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
|
||||
// option. This file may not be copied, modified, or distributed
|
||||
// except according to those terms.
|
||||
|
||||
//! HIR walker. Each overridden visit method has full control over what
|
||||
//! happens with its node, it can do its own traversal of the node's children,
|
||||
//! call `visit::walk_*` to apply the default traversal algorithm, or prevent
|
||||
//! deeper traversal by doing nothing.
|
||||
//!
|
||||
//! Note: it is an important invariant that the default visitor walks the body
|
||||
//! of a function in "execution order" (more concretely, reverse post-order
|
||||
//! with respect to the CFG implied by the AST), meaning that if AST node A may
|
||||
//! execute before AST node B, then A is visited first. The borrow checker in
|
||||
//! particular relies on this property.
|
||||
//!
|
||||
//! Note: walking an AST before macro expansion is probably a bad idea. For
|
||||
//! instance, a walker looking for item names in a module will miss all of
|
||||
//! those that are created by the expansion of a macro.
|
||||
|
||||
use syntax::abi::Abi;
|
||||
use syntax::ast::{Ident, NodeId, CRATE_NODE_ID, Name};
|
||||
use hir::*;
|
||||
use hir;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::ptr::P;
|
||||
use syntax::owned_slice::OwnedSlice;
|
||||
|
||||
#[derive(Copy, Clone, PartialEq, Eq)]
|
||||
pub enum FnKind<'a> {
|
||||
/// fn foo() or extern "Abi" fn foo()
|
||||
ItemFn(Ident, &'a Generics, Unsafety, Constness, Abi, Visibility),
|
||||
|
||||
/// fn foo(&self)
|
||||
Method(Ident, &'a MethodSig, Option<Visibility>),
|
||||
|
||||
/// |x, y| ...
|
||||
/// proc(x, y) ...
|
||||
Closure,
|
||||
}
|
||||
|
||||
/// Each method of the Visitor trait is a hook to be potentially
|
||||
/// overridden. Each method's default implementation recursively visits
|
||||
/// the substructure of the input via the corresponding `walk` method;
|
||||
/// e.g. the `visit_mod` method by default calls `visit::walk_mod`.
|
||||
///
|
||||
/// If you want to ensure that your code handles every variant
|
||||
/// explicitly, you need to override each method. (And you also need
|
||||
/// to monitor future changes to `Visitor` in case a new method with a
|
||||
/// new default implementation gets introduced.)
|
||||
pub trait Visitor<'v> : Sized {
|
||||
fn visit_name(&mut self, _span: Span, _name: Name) {
|
||||
// Nothing to do.
|
||||
}
|
||||
fn visit_ident(&mut self, span: Span, ident: Ident) {
|
||||
self.visit_name(span, ident.name);
|
||||
}
|
||||
fn visit_mod(&mut self, m: &'v Mod, _s: Span, _n: NodeId) { walk_mod(self, m) }
|
||||
fn visit_foreign_item(&mut self, i: &'v ForeignItem) { walk_foreign_item(self, i) }
|
||||
fn visit_item(&mut self, i: &'v Item) { walk_item(self, i) }
|
||||
fn visit_local(&mut self, l: &'v Local) { walk_local(self, l) }
|
||||
fn visit_block(&mut self, b: &'v Block) { walk_block(self, b) }
|
||||
fn visit_stmt(&mut self, s: &'v Stmt) { walk_stmt(self, s) }
|
||||
fn visit_arm(&mut self, a: &'v Arm) { walk_arm(self, a) }
|
||||
fn visit_pat(&mut self, p: &'v Pat) { walk_pat(self, p) }
|
||||
fn visit_decl(&mut self, d: &'v Decl) { walk_decl(self, d) }
|
||||
fn visit_expr(&mut self, ex: &'v Expr) { walk_expr(self, ex) }
|
||||
fn visit_expr_post(&mut self, _ex: &'v Expr) { }
|
||||
fn visit_ty(&mut self, t: &'v Ty) { walk_ty(self, t) }
|
||||
fn visit_generics(&mut self, g: &'v Generics) { walk_generics(self, g) }
|
||||
fn visit_fn(&mut self, fk: FnKind<'v>, fd: &'v FnDecl, b: &'v Block, s: Span, _: NodeId) {
|
||||
walk_fn(self, fk, fd, b, s)
|
||||
}
|
||||
fn visit_trait_item(&mut self, ti: &'v TraitItem) { walk_trait_item(self, ti) }
|
||||
fn visit_impl_item(&mut self, ii: &'v ImplItem) { walk_impl_item(self, ii) }
|
||||
fn visit_trait_ref(&mut self, t: &'v TraitRef) { walk_trait_ref(self, t) }
|
||||
fn visit_ty_param_bound(&mut self, bounds: &'v TyParamBound) {
|
||||
walk_ty_param_bound(self, bounds)
|
||||
}
|
||||
fn visit_poly_trait_ref(&mut self, t: &'v PolyTraitRef, m: &'v TraitBoundModifier) {
|
||||
walk_poly_trait_ref(self, t, m)
|
||||
}
|
||||
fn visit_struct_def(&mut self, s: &'v StructDef, _: Ident, _: &'v Generics, _: NodeId) {
|
||||
walk_struct_def(self, s)
|
||||
}
|
||||
fn visit_struct_field(&mut self, s: &'v StructField) { walk_struct_field(self, s) }
|
||||
fn visit_enum_def(&mut self, enum_definition: &'v EnumDef,
|
||||
generics: &'v Generics) {
|
||||
walk_enum_def(self, enum_definition, generics)
|
||||
}
|
||||
|
||||
fn visit_variant(&mut self, v: &'v Variant, g: &'v Generics) { walk_variant(self, v, g) }
|
||||
|
||||
/// Visits an optional reference to a lifetime. The `span` is the span of some surrounding
|
||||
/// reference should opt_lifetime be None.
|
||||
fn visit_opt_lifetime_ref(&mut self,
|
||||
_span: Span,
|
||||
opt_lifetime: &'v Option<Lifetime>) {
|
||||
match *opt_lifetime {
|
||||
Some(ref l) => self.visit_lifetime_ref(l),
|
||||
None => ()
|
||||
}
|
||||
}
|
||||
fn visit_lifetime_bound(&mut self, lifetime: &'v Lifetime) {
|
||||
walk_lifetime_bound(self, lifetime)
|
||||
}
|
||||
fn visit_lifetime_ref(&mut self, lifetime: &'v Lifetime) {
|
||||
walk_lifetime_ref(self, lifetime)
|
||||
}
|
||||
fn visit_lifetime_def(&mut self, lifetime: &'v LifetimeDef) {
|
||||
walk_lifetime_def(self, lifetime)
|
||||
}
|
||||
fn visit_explicit_self(&mut self, es: &'v ExplicitSelf) {
|
||||
walk_explicit_self(self, es)
|
||||
}
|
||||
fn visit_path(&mut self, path: &'v Path, _id: NodeId) {
|
||||
walk_path(self, path)
|
||||
}
|
||||
fn visit_path_segment(&mut self, path_span: Span, path_segment: &'v PathSegment) {
|
||||
walk_path_segment(self, path_span, path_segment)
|
||||
}
|
||||
fn visit_path_parameters(&mut self, path_span: Span, path_parameters: &'v PathParameters) {
|
||||
walk_path_parameters(self, path_span, path_parameters)
|
||||
}
|
||||
fn visit_assoc_type_binding(&mut self, type_binding: &'v TypeBinding) {
|
||||
walk_assoc_type_binding(self, type_binding)
|
||||
}
|
||||
fn visit_attribute(&mut self, _attr: &'v Attribute) {}
|
||||
}
|
||||
|
||||
pub fn walk_crate<'v, V: Visitor<'v>>(visitor: &mut V, krate: &'v Crate) {
|
||||
visitor.visit_mod(&krate.module, krate.span, CRATE_NODE_ID);
|
||||
for attr in &krate.attrs {
|
||||
visitor.visit_attribute(attr);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_mod<'v, V: Visitor<'v>>(visitor: &mut V, module: &'v Mod) {
|
||||
for item in &module.items {
|
||||
visitor.visit_item(&**item)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_local<'v, V: Visitor<'v>>(visitor: &mut V, local: &'v Local) {
|
||||
visitor.visit_pat(&*local.pat);
|
||||
walk_ty_opt(visitor, &local.ty);
|
||||
walk_expr_opt(visitor, &local.init);
|
||||
}
|
||||
|
||||
pub fn walk_lifetime_def<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
lifetime_def: &'v LifetimeDef) {
|
||||
visitor.visit_name(lifetime_def.lifetime.span, lifetime_def.lifetime.name);
|
||||
for bound in &lifetime_def.bounds {
|
||||
visitor.visit_lifetime_bound(bound);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_lifetime_bound<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
lifetime_ref: &'v Lifetime) {
|
||||
visitor.visit_lifetime_ref(lifetime_ref)
|
||||
}
|
||||
|
||||
pub fn walk_lifetime_ref<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
lifetime_ref: &'v Lifetime) {
|
||||
visitor.visit_name(lifetime_ref.span, lifetime_ref.name)
|
||||
}
|
||||
|
||||
pub fn walk_explicit_self<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
explicit_self: &'v ExplicitSelf) {
|
||||
match explicit_self.node {
|
||||
SelfStatic | SelfValue(_) => {},
|
||||
SelfRegion(ref lifetime, _, _) => {
|
||||
visitor.visit_opt_lifetime_ref(explicit_self.span, lifetime)
|
||||
}
|
||||
SelfExplicit(ref typ, _) => visitor.visit_ty(&**typ),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_poly_trait_ref<'v, V>(visitor: &mut V,
|
||||
trait_ref: &'v PolyTraitRef,
|
||||
_modifier: &'v TraitBoundModifier)
|
||||
where V: Visitor<'v>
|
||||
{
|
||||
walk_lifetime_decls_helper(visitor, &trait_ref.bound_lifetimes);
|
||||
visitor.visit_trait_ref(&trait_ref.trait_ref);
|
||||
}
|
||||
|
||||
pub fn walk_trait_ref<'v,V>(visitor: &mut V,
|
||||
trait_ref: &'v TraitRef)
|
||||
where V: Visitor<'v>
|
||||
{
|
||||
visitor.visit_path(&trait_ref.path, trait_ref.ref_id)
|
||||
}
|
||||
|
||||
pub fn walk_item<'v, V: Visitor<'v>>(visitor: &mut V, item: &'v Item) {
|
||||
visitor.visit_ident(item.span, item.ident);
|
||||
match item.node {
|
||||
ItemExternCrate(..) => {}
|
||||
ItemUse(ref vp) => {
|
||||
match vp.node {
|
||||
ViewPathSimple(ident, ref path) => {
|
||||
visitor.visit_ident(vp.span, ident);
|
||||
visitor.visit_path(path, item.id);
|
||||
}
|
||||
ViewPathGlob(ref path) => {
|
||||
visitor.visit_path(path, item.id);
|
||||
}
|
||||
ViewPathList(ref prefix, ref list) => {
|
||||
for id in list {
|
||||
match id.node {
|
||||
PathListIdent { name, .. } => {
|
||||
visitor.visit_ident(id.span, name);
|
||||
}
|
||||
PathListMod { .. } => ()
|
||||
}
|
||||
}
|
||||
|
||||
// Note that the `prefix` here is not a complete
|
||||
// path, so we don't use `visit_path`.
|
||||
walk_path(visitor, prefix);
|
||||
}
|
||||
}
|
||||
}
|
||||
ItemStatic(ref typ, _, ref expr) |
|
||||
ItemConst(ref typ, ref expr) => {
|
||||
visitor.visit_ty(&**typ);
|
||||
visitor.visit_expr(&**expr);
|
||||
}
|
||||
ItemFn(ref declaration, unsafety, constness, abi, ref generics, ref body) => {
|
||||
visitor.visit_fn(FnKind::ItemFn(item.ident, generics, unsafety,
|
||||
constness, abi, item.vis),
|
||||
&**declaration,
|
||||
&**body,
|
||||
item.span,
|
||||
item.id)
|
||||
}
|
||||
ItemMod(ref module) => {
|
||||
visitor.visit_mod(module, item.span, item.id)
|
||||
}
|
||||
ItemForeignMod(ref foreign_module) => {
|
||||
for foreign_item in &foreign_module.items {
|
||||
visitor.visit_foreign_item(&**foreign_item)
|
||||
}
|
||||
}
|
||||
ItemTy(ref typ, ref type_parameters) => {
|
||||
visitor.visit_ty(&**typ);
|
||||
visitor.visit_generics(type_parameters)
|
||||
}
|
||||
ItemEnum(ref enum_definition, ref type_parameters) => {
|
||||
visitor.visit_generics(type_parameters);
|
||||
visitor.visit_enum_def(enum_definition, type_parameters)
|
||||
}
|
||||
ItemDefaultImpl(_, ref trait_ref) => {
|
||||
visitor.visit_trait_ref(trait_ref)
|
||||
}
|
||||
ItemImpl(_, _,
|
||||
ref type_parameters,
|
||||
ref trait_reference,
|
||||
ref typ,
|
||||
ref impl_items) => {
|
||||
visitor.visit_generics(type_parameters);
|
||||
match *trait_reference {
|
||||
Some(ref trait_reference) => visitor.visit_trait_ref(trait_reference),
|
||||
None => ()
|
||||
}
|
||||
visitor.visit_ty(&**typ);
|
||||
for impl_item in impl_items {
|
||||
visitor.visit_impl_item(impl_item);
|
||||
}
|
||||
}
|
||||
ItemStruct(ref struct_definition, ref generics) => {
|
||||
visitor.visit_generics(generics);
|
||||
visitor.visit_struct_def(&**struct_definition,
|
||||
item.ident,
|
||||
generics,
|
||||
item.id)
|
||||
}
|
||||
ItemTrait(_, ref generics, ref bounds, ref methods) => {
|
||||
visitor.visit_generics(generics);
|
||||
walk_ty_param_bounds_helper(visitor, bounds);
|
||||
for method in methods {
|
||||
visitor.visit_trait_item(method)
|
||||
}
|
||||
}
|
||||
}
|
||||
for attr in &item.attrs {
|
||||
visitor.visit_attribute(attr);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_enum_def<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
enum_definition: &'v EnumDef,
|
||||
generics: &'v Generics) {
|
||||
for variant in &enum_definition.variants {
|
||||
visitor.visit_variant(&**variant, generics);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_variant<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
variant: &'v Variant,
|
||||
generics: &'v Generics) {
|
||||
visitor.visit_ident(variant.span, variant.node.name);
|
||||
|
||||
match variant.node.kind {
|
||||
TupleVariantKind(ref variant_arguments) => {
|
||||
for variant_argument in variant_arguments {
|
||||
visitor.visit_ty(&*variant_argument.ty)
|
||||
}
|
||||
}
|
||||
StructVariantKind(ref struct_definition) => {
|
||||
visitor.visit_struct_def(&**struct_definition,
|
||||
variant.node.name,
|
||||
generics,
|
||||
variant.node.id)
|
||||
}
|
||||
}
|
||||
match variant.node.disr_expr {
|
||||
Some(ref expr) => visitor.visit_expr(&**expr),
|
||||
None => ()
|
||||
}
|
||||
for attr in &variant.node.attrs {
|
||||
visitor.visit_attribute(attr);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn skip_ty<'v, V: Visitor<'v>>(_: &mut V, _: &'v Ty) {
|
||||
// Empty!
|
||||
}
|
||||
|
||||
pub fn walk_ty_opt<'v, V: Visitor<'v>>(visitor: &mut V, optional_type: &'v Option<P<Ty>>) {
|
||||
match *optional_type {
|
||||
Some(ref ty) => visitor.visit_ty(&**ty),
|
||||
None => ()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_ty<'v, V: Visitor<'v>>(visitor: &mut V, typ: &'v Ty) {
|
||||
match typ.node {
|
||||
TyVec(ref ty) | TyParen(ref ty) => {
|
||||
visitor.visit_ty(&**ty)
|
||||
}
|
||||
TyPtr(ref mutable_type) => {
|
||||
visitor.visit_ty(&*mutable_type.ty)
|
||||
}
|
||||
TyRptr(ref lifetime, ref mutable_type) => {
|
||||
visitor.visit_opt_lifetime_ref(typ.span, lifetime);
|
||||
visitor.visit_ty(&*mutable_type.ty)
|
||||
}
|
||||
TyTup(ref tuple_element_types) => {
|
||||
for tuple_element_type in tuple_element_types {
|
||||
visitor.visit_ty(&**tuple_element_type)
|
||||
}
|
||||
}
|
||||
TyBareFn(ref function_declaration) => {
|
||||
for argument in &function_declaration.decl.inputs {
|
||||
visitor.visit_ty(&*argument.ty)
|
||||
}
|
||||
walk_fn_ret_ty(visitor, &function_declaration.decl.output);
|
||||
walk_lifetime_decls_helper(visitor, &function_declaration.lifetimes);
|
||||
}
|
||||
TyPath(ref maybe_qself, ref path) => {
|
||||
if let Some(ref qself) = *maybe_qself {
|
||||
visitor.visit_ty(&qself.ty);
|
||||
}
|
||||
visitor.visit_path(path, typ.id);
|
||||
}
|
||||
TyObjectSum(ref ty, ref bounds) => {
|
||||
visitor.visit_ty(&**ty);
|
||||
walk_ty_param_bounds_helper(visitor, bounds);
|
||||
}
|
||||
TyFixedLengthVec(ref ty, ref expression) => {
|
||||
visitor.visit_ty(&**ty);
|
||||
visitor.visit_expr(&**expression)
|
||||
}
|
||||
TyPolyTraitRef(ref bounds) => {
|
||||
walk_ty_param_bounds_helper(visitor, bounds)
|
||||
}
|
||||
TyTypeof(ref expression) => {
|
||||
visitor.visit_expr(&**expression)
|
||||
}
|
||||
TyInfer => {}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_lifetime_decls_helper<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
lifetimes: &'v Vec<LifetimeDef>) {
|
||||
for l in lifetimes {
|
||||
visitor.visit_lifetime_def(l);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_path<'v, V: Visitor<'v>>(visitor: &mut V, path: &'v Path) {
|
||||
for segment in &path.segments {
|
||||
visitor.visit_path_segment(path.span, segment);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_path_segment<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
path_span: Span,
|
||||
segment: &'v PathSegment) {
|
||||
visitor.visit_ident(path_span, segment.identifier);
|
||||
visitor.visit_path_parameters(path_span, &segment.parameters);
|
||||
}
|
||||
|
||||
pub fn walk_path_parameters<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
_path_span: Span,
|
||||
path_parameters: &'v PathParameters) {
|
||||
match *path_parameters {
|
||||
hir::AngleBracketedParameters(ref data) => {
|
||||
for typ in data.types.iter() {
|
||||
visitor.visit_ty(&**typ);
|
||||
}
|
||||
for lifetime in &data.lifetimes {
|
||||
visitor.visit_lifetime_ref(lifetime);
|
||||
}
|
||||
for binding in data.bindings.iter() {
|
||||
visitor.visit_assoc_type_binding(&**binding);
|
||||
}
|
||||
}
|
||||
hir::ParenthesizedParameters(ref data) => {
|
||||
for typ in &data.inputs {
|
||||
visitor.visit_ty(&**typ);
|
||||
}
|
||||
if let Some(ref typ) = data.output {
|
||||
visitor.visit_ty(&**typ);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_assoc_type_binding<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
type_binding: &'v TypeBinding) {
|
||||
visitor.visit_ident(type_binding.span, type_binding.ident);
|
||||
visitor.visit_ty(&*type_binding.ty);
|
||||
}
|
||||
|
||||
pub fn walk_pat<'v, V: Visitor<'v>>(visitor: &mut V, pattern: &'v Pat) {
|
||||
match pattern.node {
|
||||
PatEnum(ref path, ref children) => {
|
||||
visitor.visit_path(path, pattern.id);
|
||||
if let Some(ref children) = *children {
|
||||
for child in children {
|
||||
visitor.visit_pat(&*child)
|
||||
}
|
||||
}
|
||||
}
|
||||
PatQPath(ref qself, ref path) => {
|
||||
visitor.visit_ty(&qself.ty);
|
||||
visitor.visit_path(path, pattern.id)
|
||||
}
|
||||
PatStruct(ref path, ref fields, _) => {
|
||||
visitor.visit_path(path, pattern.id);
|
||||
for field in fields {
|
||||
visitor.visit_pat(&*field.node.pat)
|
||||
}
|
||||
}
|
||||
PatTup(ref tuple_elements) => {
|
||||
for tuple_element in tuple_elements {
|
||||
visitor.visit_pat(&**tuple_element)
|
||||
}
|
||||
}
|
||||
PatBox(ref subpattern) |
|
||||
PatRegion(ref subpattern, _) => {
|
||||
visitor.visit_pat(&**subpattern)
|
||||
}
|
||||
PatIdent(_, ref pth1, ref optional_subpattern) => {
|
||||
visitor.visit_ident(pth1.span, pth1.node);
|
||||
match *optional_subpattern {
|
||||
None => {}
|
||||
Some(ref subpattern) => visitor.visit_pat(&**subpattern),
|
||||
}
|
||||
}
|
||||
PatLit(ref expression) => visitor.visit_expr(&**expression),
|
||||
PatRange(ref lower_bound, ref upper_bound) => {
|
||||
visitor.visit_expr(&**lower_bound);
|
||||
visitor.visit_expr(&**upper_bound)
|
||||
}
|
||||
PatWild(_) => (),
|
||||
PatVec(ref prepattern, ref slice_pattern, ref postpatterns) => {
|
||||
for prepattern in prepattern {
|
||||
visitor.visit_pat(&**prepattern)
|
||||
}
|
||||
if let Some(ref slice_pattern) = *slice_pattern {
|
||||
visitor.visit_pat(&**slice_pattern)
|
||||
}
|
||||
for postpattern in postpatterns {
|
||||
visitor.visit_pat(&**postpattern)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_foreign_item<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
foreign_item: &'v ForeignItem) {
|
||||
visitor.visit_ident(foreign_item.span, foreign_item.ident);
|
||||
|
||||
match foreign_item.node {
|
||||
ForeignItemFn(ref function_declaration, ref generics) => {
|
||||
walk_fn_decl(visitor, &**function_declaration);
|
||||
visitor.visit_generics(generics)
|
||||
}
|
||||
ForeignItemStatic(ref typ, _) => visitor.visit_ty(&**typ),
|
||||
}
|
||||
|
||||
for attr in &foreign_item.attrs {
|
||||
visitor.visit_attribute(attr);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_ty_param_bounds_helper<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
bounds: &'v OwnedSlice<TyParamBound>) {
|
||||
for bound in bounds.iter() {
|
||||
visitor.visit_ty_param_bound(bound)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_ty_param_bound<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
bound: &'v TyParamBound) {
|
||||
match *bound {
|
||||
TraitTyParamBound(ref typ, ref modifier) => {
|
||||
visitor.visit_poly_trait_ref(typ, modifier);
|
||||
}
|
||||
RegionTyParamBound(ref lifetime) => {
|
||||
visitor.visit_lifetime_bound(lifetime);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_generics<'v, V: Visitor<'v>>(visitor: &mut V, generics: &'v Generics) {
|
||||
for param in generics.ty_params.iter() {
|
||||
visitor.visit_ident(param.span, param.ident);
|
||||
walk_ty_param_bounds_helper(visitor, ¶m.bounds);
|
||||
walk_ty_opt(visitor, ¶m.default);
|
||||
}
|
||||
walk_lifetime_decls_helper(visitor, &generics.lifetimes);
|
||||
for predicate in &generics.where_clause.predicates {
|
||||
match predicate {
|
||||
&hir::WherePredicate::BoundPredicate(hir::WhereBoundPredicate{ref bounded_ty,
|
||||
ref bounds,
|
||||
..}) => {
|
||||
visitor.visit_ty(&**bounded_ty);
|
||||
walk_ty_param_bounds_helper(visitor, bounds);
|
||||
}
|
||||
&hir::WherePredicate::RegionPredicate(hir::WhereRegionPredicate{ref lifetime,
|
||||
ref bounds,
|
||||
..}) => {
|
||||
visitor.visit_lifetime_ref(lifetime);
|
||||
|
||||
for bound in bounds {
|
||||
visitor.visit_lifetime_ref(bound);
|
||||
}
|
||||
}
|
||||
&hir::WherePredicate::EqPredicate(hir::WhereEqPredicate{id,
|
||||
ref path,
|
||||
ref ty,
|
||||
..}) => {
|
||||
visitor.visit_path(path, id);
|
||||
visitor.visit_ty(&**ty);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_fn_ret_ty<'v, V: Visitor<'v>>(visitor: &mut V, ret_ty: &'v FunctionRetTy) {
|
||||
if let Return(ref output_ty) = *ret_ty {
|
||||
visitor.visit_ty(&**output_ty)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_fn_decl<'v, V: Visitor<'v>>(visitor: &mut V, function_declaration: &'v FnDecl) {
|
||||
for argument in &function_declaration.inputs {
|
||||
visitor.visit_pat(&*argument.pat);
|
||||
visitor.visit_ty(&*argument.ty)
|
||||
}
|
||||
walk_fn_ret_ty(visitor, &function_declaration.output)
|
||||
}
|
||||
|
||||
pub fn walk_fn<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
function_kind: FnKind<'v>,
|
||||
function_declaration: &'v FnDecl,
|
||||
function_body: &'v Block,
|
||||
_span: Span) {
|
||||
walk_fn_decl(visitor, function_declaration);
|
||||
|
||||
match function_kind {
|
||||
FnKind::ItemFn(_, generics, _, _, _, _) => {
|
||||
visitor.visit_generics(generics);
|
||||
}
|
||||
FnKind::Method(_, sig, _) => {
|
||||
visitor.visit_generics(&sig.generics);
|
||||
visitor.visit_explicit_self(&sig.explicit_self);
|
||||
}
|
||||
FnKind::Closure(..) => {}
|
||||
}
|
||||
|
||||
visitor.visit_block(function_body)
|
||||
}
|
||||
|
||||
pub fn walk_trait_item<'v, V: Visitor<'v>>(visitor: &mut V, trait_item: &'v TraitItem) {
|
||||
visitor.visit_ident(trait_item.span, trait_item.ident);
|
||||
for attr in &trait_item.attrs {
|
||||
visitor.visit_attribute(attr);
|
||||
}
|
||||
match trait_item.node {
|
||||
ConstTraitItem(ref ty, ref default) => {
|
||||
visitor.visit_ty(ty);
|
||||
if let Some(ref expr) = *default {
|
||||
visitor.visit_expr(expr);
|
||||
}
|
||||
}
|
||||
MethodTraitItem(ref sig, None) => {
|
||||
visitor.visit_explicit_self(&sig.explicit_self);
|
||||
visitor.visit_generics(&sig.generics);
|
||||
walk_fn_decl(visitor, &sig.decl);
|
||||
}
|
||||
MethodTraitItem(ref sig, Some(ref body)) => {
|
||||
visitor.visit_fn(FnKind::Method(trait_item.ident, sig, None), &sig.decl,
|
||||
body, trait_item.span, trait_item.id);
|
||||
}
|
||||
TypeTraitItem(ref bounds, ref default) => {
|
||||
walk_ty_param_bounds_helper(visitor, bounds);
|
||||
walk_ty_opt(visitor, default);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_impl_item<'v, V: Visitor<'v>>(visitor: &mut V, impl_item: &'v ImplItem) {
|
||||
visitor.visit_ident(impl_item.span, impl_item.ident);
|
||||
for attr in &impl_item.attrs {
|
||||
visitor.visit_attribute(attr);
|
||||
}
|
||||
match impl_item.node {
|
||||
ConstImplItem(ref ty, ref expr) => {
|
||||
visitor.visit_ty(ty);
|
||||
visitor.visit_expr(expr);
|
||||
}
|
||||
MethodImplItem(ref sig, ref body) => {
|
||||
visitor.visit_fn(FnKind::Method(impl_item.ident, sig, Some(impl_item.vis)), &sig.decl,
|
||||
body, impl_item.span, impl_item.id);
|
||||
}
|
||||
TypeImplItem(ref ty) => {
|
||||
visitor.visit_ty(ty);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_struct_def<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
struct_definition: &'v StructDef) {
|
||||
for field in &struct_definition.fields {
|
||||
visitor.visit_struct_field(field)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_struct_field<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
struct_field: &'v StructField) {
|
||||
if let NamedField(name, _) = struct_field.node.kind {
|
||||
visitor.visit_ident(struct_field.span, name);
|
||||
}
|
||||
|
||||
visitor.visit_ty(&*struct_field.node.ty);
|
||||
|
||||
for attr in &struct_field.node.attrs {
|
||||
visitor.visit_attribute(attr);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_block<'v, V: Visitor<'v>>(visitor: &mut V, block: &'v Block) {
|
||||
for statement in &block.stmts {
|
||||
visitor.visit_stmt(&**statement)
|
||||
}
|
||||
walk_expr_opt(visitor, &block.expr)
|
||||
}
|
||||
|
||||
pub fn walk_stmt<'v, V: Visitor<'v>>(visitor: &mut V, statement: &'v Stmt) {
|
||||
match statement.node {
|
||||
StmtDecl(ref declaration, _) => visitor.visit_decl(&**declaration),
|
||||
StmtExpr(ref expression, _) | StmtSemi(ref expression, _) => {
|
||||
visitor.visit_expr(&**expression)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_decl<'v, V: Visitor<'v>>(visitor: &mut V, declaration: &'v Decl) {
|
||||
match declaration.node {
|
||||
DeclLocal(ref local) => visitor.visit_local(&**local),
|
||||
DeclItem(ref item) => visitor.visit_item(&**item),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_expr_opt<'v, V: Visitor<'v>>(visitor: &mut V,
|
||||
optional_expression: &'v Option<P<Expr>>) {
|
||||
match *optional_expression {
|
||||
None => {}
|
||||
Some(ref expression) => visitor.visit_expr(&**expression),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_exprs<'v, V: Visitor<'v>>(visitor: &mut V, expressions: &'v [P<Expr>]) {
|
||||
for expression in expressions {
|
||||
visitor.visit_expr(&**expression)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn walk_expr<'v, V: Visitor<'v>>(visitor: &mut V, expression: &'v Expr) {
|
||||
match expression.node {
|
||||
ExprBox(ref place, ref subexpression) => {
|
||||
place.as_ref().map(|e|visitor.visit_expr(&**e));
|
||||
visitor.visit_expr(&**subexpression)
|
||||
}
|
||||
ExprVec(ref subexpressions) => {
|
||||
walk_exprs(visitor, subexpressions)
|
||||
}
|
||||
ExprRepeat(ref element, ref count) => {
|
||||
visitor.visit_expr(&**element);
|
||||
visitor.visit_expr(&**count)
|
||||
}
|
||||
ExprStruct(ref path, ref fields, ref optional_base) => {
|
||||
visitor.visit_path(path, expression.id);
|
||||
for field in fields {
|
||||
visitor.visit_expr(&*field.expr)
|
||||
}
|
||||
walk_expr_opt(visitor, optional_base)
|
||||
}
|
||||
ExprTup(ref subexpressions) => {
|
||||
for subexpression in subexpressions {
|
||||
visitor.visit_expr(&**subexpression)
|
||||
}
|
||||
}
|
||||
ExprCall(ref callee_expression, ref arguments) => {
|
||||
for argument in arguments {
|
||||
visitor.visit_expr(&**argument)
|
||||
}
|
||||
visitor.visit_expr(&**callee_expression)
|
||||
}
|
||||
ExprMethodCall(_, ref types, ref arguments) => {
|
||||
walk_exprs(visitor, arguments);
|
||||
for typ in types {
|
||||
visitor.visit_ty(&**typ)
|
||||
}
|
||||
}
|
||||
ExprBinary(_, ref left_expression, ref right_expression) => {
|
||||
visitor.visit_expr(&**left_expression);
|
||||
visitor.visit_expr(&**right_expression)
|
||||
}
|
||||
ExprAddrOf(_, ref subexpression) | ExprUnary(_, ref subexpression) => {
|
||||
visitor.visit_expr(&**subexpression)
|
||||
}
|
||||
ExprLit(_) => {}
|
||||
ExprCast(ref subexpression, ref typ) => {
|
||||
visitor.visit_expr(&**subexpression);
|
||||
visitor.visit_ty(&**typ)
|
||||
}
|
||||
ExprIf(ref head_expression, ref if_block, ref optional_else) => {
|
||||
visitor.visit_expr(&**head_expression);
|
||||
visitor.visit_block(&**if_block);
|
||||
walk_expr_opt(visitor, optional_else)
|
||||
}
|
||||
ExprWhile(ref subexpression, ref block, _) => {
|
||||
visitor.visit_expr(&**subexpression);
|
||||
visitor.visit_block(&**block)
|
||||
}
|
||||
ExprLoop(ref block, _) => visitor.visit_block(&**block),
|
||||
ExprMatch(ref subexpression, ref arms, _) => {
|
||||
visitor.visit_expr(&**subexpression);
|
||||
for arm in arms {
|
||||
visitor.visit_arm(arm)
|
||||
}
|
||||
}
|
||||
ExprClosure(_, ref function_declaration, ref body) => {
|
||||
visitor.visit_fn(FnKind::Closure,
|
||||
&**function_declaration,
|
||||
&**body,
|
||||
expression.span,
|
||||
expression.id)
|
||||
}
|
||||
ExprBlock(ref block) => visitor.visit_block(&**block),
|
||||
ExprAssign(ref left_hand_expression, ref right_hand_expression) => {
|
||||
visitor.visit_expr(&**right_hand_expression);
|
||||
visitor.visit_expr(&**left_hand_expression)
|
||||
}
|
||||
ExprAssignOp(_, ref left_expression, ref right_expression) => {
|
||||
visitor.visit_expr(&**right_expression);
|
||||
visitor.visit_expr(&**left_expression)
|
||||
}
|
||||
ExprField(ref subexpression, _) => {
|
||||
visitor.visit_expr(&**subexpression);
|
||||
}
|
||||
ExprTupField(ref subexpression, _) => {
|
||||
visitor.visit_expr(&**subexpression);
|
||||
}
|
||||
ExprIndex(ref main_expression, ref index_expression) => {
|
||||
visitor.visit_expr(&**main_expression);
|
||||
visitor.visit_expr(&**index_expression)
|
||||
}
|
||||
ExprRange(ref start, ref end) => {
|
||||
walk_expr_opt(visitor, start);
|
||||
walk_expr_opt(visitor, end)
|
||||
}
|
||||
ExprPath(ref maybe_qself, ref path) => {
|
||||
if let Some(ref qself) = *maybe_qself {
|
||||
visitor.visit_ty(&qself.ty);
|
||||
}
|
||||
visitor.visit_path(path, expression.id)
|
||||
}
|
||||
ExprBreak(_) | ExprAgain(_) => {}
|
||||
ExprRet(ref optional_expression) => {
|
||||
walk_expr_opt(visitor, optional_expression)
|
||||
}
|
||||
ExprParen(ref subexpression) => {
|
||||
visitor.visit_expr(&**subexpression)
|
||||
}
|
||||
ExprInlineAsm(ref ia) => {
|
||||
for input in &ia.inputs {
|
||||
let (_, ref input) = *input;
|
||||
visitor.visit_expr(&**input)
|
||||
}
|
||||
for output in &ia.outputs {
|
||||
let (_, ref output, _) = *output;
|
||||
visitor.visit_expr(&**output)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
visitor.visit_expr_post(expression)
|
||||
}
|
||||
|
||||
pub fn walk_arm<'v, V: Visitor<'v>>(visitor: &mut V, arm: &'v Arm) {
|
||||
for pattern in &arm.pats {
|
||||
visitor.visit_pat(&**pattern)
|
||||
}
|
||||
walk_expr_opt(visitor, &arm.guard);
|
||||
visitor.visit_expr(&*arm.body);
|
||||
for attr in &arm.attrs {
|
||||
visitor.visit_attribute(attr);
|
||||
}
|
||||
}
|
@ -35,7 +35,7 @@ use middle::subst::Substs;
|
||||
use middle::ty::{self, Ty};
|
||||
use middle::const_eval::{eval_const_expr_partial, ConstVal};
|
||||
use middle::const_eval::EvalHint::ExprTypeChecked;
|
||||
use rustc::ast_map;
|
||||
use rustc::front::map as hir_map;
|
||||
use util::nodemap::{FnvHashMap, FnvHashSet, NodeSet};
|
||||
use lint::{Level, Context, LintPass, LintArray, Lint};
|
||||
|
||||
@ -53,6 +53,14 @@ use syntax::ast::{TyIs, TyUs, TyI8, TyU8, TyI16, TyU16, TyI32, TyU32, TyI64, TyU
|
||||
use syntax::ptr::P;
|
||||
use syntax::visit::{self, FnKind, Visitor};
|
||||
|
||||
use rustc_front::lowering::{lower_expr, lower_block, lower_item, lower_path, lower_pat,
|
||||
lower_trait_ref};
|
||||
use rustc_front::hir;
|
||||
use rustc_front::attr as front_attr;
|
||||
use rustc_front::attr::AttrMetaMethods as FrontAttrMetaMethods;
|
||||
use rustc_front::visit::Visitor as HirVisitor;
|
||||
use rustc_front::visit as hir_visit;
|
||||
|
||||
// hardwired lints from librustc
|
||||
pub use lint::builtin::*;
|
||||
|
||||
@ -129,7 +137,7 @@ impl LintPass for TypeLimits {
|
||||
check_unsigned_negation_feature(cx, e.span);
|
||||
},
|
||||
ast::LitInt(_, ast::UnsuffixedIntLit(_)) => {
|
||||
if let ty::TyUint(_) = cx.tcx.expr_ty(e).sty {
|
||||
if let ty::TyUint(_) = cx.tcx.node_id_to_type(e.id).sty {
|
||||
check_unsigned_negation_feature(cx, e.span);
|
||||
}
|
||||
},
|
||||
@ -137,7 +145,7 @@ impl LintPass for TypeLimits {
|
||||
}
|
||||
},
|
||||
_ => {
|
||||
let t = cx.tcx.expr_ty(&**expr);
|
||||
let t = cx.tcx.node_id_to_type(expr.id);
|
||||
match t.sty {
|
||||
ty::TyUint(_) => {
|
||||
check_unsigned_negation_feature(cx, e.span);
|
||||
@ -161,7 +169,7 @@ impl LintPass for TypeLimits {
|
||||
}
|
||||
|
||||
if is_shift_binop(binop.node) {
|
||||
let opt_ty_bits = match cx.tcx.expr_ty(&**l).sty {
|
||||
let opt_ty_bits = match cx.tcx.node_id_to_type(l.id).sty {
|
||||
ty::TyInt(t) => Some(int_ty_bits(t, cx.sess().target.int_type)),
|
||||
ty::TyUint(t) => Some(uint_ty_bits(t, cx.sess().target.uint_type)),
|
||||
_ => None
|
||||
@ -172,7 +180,8 @@ impl LintPass for TypeLimits {
|
||||
if let ast::LitInt(shift, _) = lit.node { shift >= bits }
|
||||
else { false }
|
||||
} else {
|
||||
match eval_const_expr_partial(cx.tcx, &**r, ExprTypeChecked) {
|
||||
let r = lower_expr(r);
|
||||
match eval_const_expr_partial(cx.tcx, &r, ExprTypeChecked) {
|
||||
Ok(ConstVal::Int(shift)) => { shift as u64 >= bits },
|
||||
Ok(ConstVal::Uint(shift)) => { shift >= bits },
|
||||
_ => { false }
|
||||
@ -186,12 +195,12 @@ impl LintPass for TypeLimits {
|
||||
}
|
||||
},
|
||||
ast::ExprLit(ref lit) => {
|
||||
match cx.tcx.expr_ty(e).sty {
|
||||
match cx.tcx.node_id_to_type(e.id).sty {
|
||||
ty::TyInt(t) => {
|
||||
match lit.node {
|
||||
ast::LitInt(v, ast::SignedIntLit(_, ast::Plus)) |
|
||||
ast::LitInt(v, ast::UnsuffixedIntLit(ast::Plus)) => {
|
||||
let int_type = if let ast::TyIs = t {
|
||||
let int_type = if let hir::TyIs = t {
|
||||
cx.sess().target.int_type
|
||||
} else {
|
||||
t
|
||||
@ -212,7 +221,7 @@ impl LintPass for TypeLimits {
|
||||
};
|
||||
},
|
||||
ty::TyUint(t) => {
|
||||
let uint_type = if let ast::TyUs = t {
|
||||
let uint_type = if let hir::TyUs = t {
|
||||
cx.sess().target.uint_type
|
||||
} else {
|
||||
t
|
||||
@ -275,50 +284,50 @@ impl LintPass for TypeLimits {
|
||||
|
||||
// for isize & usize, be conservative with the warnings, so that the
|
||||
// warnings are consistent between 32- and 64-bit platforms
|
||||
fn int_ty_range(int_ty: ast::IntTy) -> (i64, i64) {
|
||||
fn int_ty_range(int_ty: hir::IntTy) -> (i64, i64) {
|
||||
match int_ty {
|
||||
ast::TyIs => (i64::MIN, i64::MAX),
|
||||
ast::TyI8 => (i8::MIN as i64, i8::MAX as i64),
|
||||
ast::TyI16 => (i16::MIN as i64, i16::MAX as i64),
|
||||
ast::TyI32 => (i32::MIN as i64, i32::MAX as i64),
|
||||
ast::TyI64 => (i64::MIN, i64::MAX)
|
||||
hir::TyIs => (i64::MIN, i64::MAX),
|
||||
hir::TyI8 => (i8::MIN as i64, i8::MAX as i64),
|
||||
hir::TyI16 => (i16::MIN as i64, i16::MAX as i64),
|
||||
hir::TyI32 => (i32::MIN as i64, i32::MAX as i64),
|
||||
hir::TyI64 => (i64::MIN, i64::MAX)
|
||||
}
|
||||
}
|
||||
|
||||
fn uint_ty_range(uint_ty: ast::UintTy) -> (u64, u64) {
|
||||
fn uint_ty_range(uint_ty: hir::UintTy) -> (u64, u64) {
|
||||
match uint_ty {
|
||||
ast::TyUs => (u64::MIN, u64::MAX),
|
||||
ast::TyU8 => (u8::MIN as u64, u8::MAX as u64),
|
||||
ast::TyU16 => (u16::MIN as u64, u16::MAX as u64),
|
||||
ast::TyU32 => (u32::MIN as u64, u32::MAX as u64),
|
||||
ast::TyU64 => (u64::MIN, u64::MAX)
|
||||
hir::TyUs => (u64::MIN, u64::MAX),
|
||||
hir::TyU8 => (u8::MIN as u64, u8::MAX as u64),
|
||||
hir::TyU16 => (u16::MIN as u64, u16::MAX as u64),
|
||||
hir::TyU32 => (u32::MIN as u64, u32::MAX as u64),
|
||||
hir::TyU64 => (u64::MIN, u64::MAX)
|
||||
}
|
||||
}
|
||||
|
||||
fn float_ty_range(float_ty: ast::FloatTy) -> (f64, f64) {
|
||||
fn float_ty_range(float_ty: hir::FloatTy) -> (f64, f64) {
|
||||
match float_ty {
|
||||
ast::TyF32 => (f32::MIN as f64, f32::MAX as f64),
|
||||
ast::TyF64 => (f64::MIN, f64::MAX)
|
||||
hir::TyF32 => (f32::MIN as f64, f32::MAX as f64),
|
||||
hir::TyF64 => (f64::MIN, f64::MAX)
|
||||
}
|
||||
}
|
||||
|
||||
fn int_ty_bits(int_ty: ast::IntTy, target_int_ty: ast::IntTy) -> u64 {
|
||||
fn int_ty_bits(int_ty: hir::IntTy, target_int_ty: hir::IntTy) -> u64 {
|
||||
match int_ty {
|
||||
ast::TyIs => int_ty_bits(target_int_ty, target_int_ty),
|
||||
ast::TyI8 => i8::BITS as u64,
|
||||
ast::TyI16 => i16::BITS as u64,
|
||||
ast::TyI32 => i32::BITS as u64,
|
||||
ast::TyI64 => i64::BITS as u64
|
||||
hir::TyIs => int_ty_bits(target_int_ty, target_int_ty),
|
||||
hir::TyI8 => i8::BITS as u64,
|
||||
hir::TyI16 => i16::BITS as u64,
|
||||
hir::TyI32 => i32::BITS as u64,
|
||||
hir::TyI64 => i64::BITS as u64
|
||||
}
|
||||
}
|
||||
|
||||
fn uint_ty_bits(uint_ty: ast::UintTy, target_uint_ty: ast::UintTy) -> u64 {
|
||||
fn uint_ty_bits(uint_ty: hir::UintTy, target_uint_ty: hir::UintTy) -> u64 {
|
||||
match uint_ty {
|
||||
ast::TyUs => uint_ty_bits(target_uint_ty, target_uint_ty),
|
||||
ast::TyU8 => u8::BITS as u64,
|
||||
ast::TyU16 => u16::BITS as u64,
|
||||
ast::TyU32 => u32::BITS as u64,
|
||||
ast::TyU64 => u64::BITS as u64
|
||||
hir::TyUs => uint_ty_bits(target_uint_ty, target_uint_ty),
|
||||
hir::TyU8 => u8::BITS as u64,
|
||||
hir::TyU16 => u16::BITS as u64,
|
||||
hir::TyU32 => u32::BITS as u64,
|
||||
hir::TyU64 => u64::BITS as u64
|
||||
}
|
||||
}
|
||||
|
||||
@ -336,7 +345,7 @@ impl LintPass for TypeLimits {
|
||||
} else {
|
||||
binop
|
||||
};
|
||||
match tcx.expr_ty(expr).sty {
|
||||
match tcx.node_id_to_type(expr.id).sty {
|
||||
ty::TyInt(int_ty) => {
|
||||
let (min, max) = int_ty_range(int_ty);
|
||||
let lit_val: i64 = match lit.node {
|
||||
@ -466,7 +475,7 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> {
|
||||
|
||||
match ty.sty {
|
||||
ty::TyStruct(def, substs) => {
|
||||
if !cx.lookup_repr_hints(def.did).contains(&attr::ReprExtern) {
|
||||
if !cx.lookup_repr_hints(def.did).contains(&front_attr::ReprExtern) {
|
||||
return FfiUnsafe(
|
||||
"found struct without foreign-function-safe \
|
||||
representation annotation in foreign module, \
|
||||
@ -550,11 +559,11 @@ impl<'a, 'tcx> ImproperCTypesVisitor<'a, 'tcx> {
|
||||
FfiSafe
|
||||
}
|
||||
|
||||
ty::TyInt(ast::TyIs) => {
|
||||
ty::TyInt(hir::TyIs) => {
|
||||
FfiUnsafe("found Rust type `isize` in foreign module, while \
|
||||
`libc::c_int` or `libc::c_long` should be used")
|
||||
}
|
||||
ty::TyUint(ast::TyUs) => {
|
||||
ty::TyUint(hir::TyUs) => {
|
||||
FfiUnsafe("found Rust type `usize` in foreign module, while \
|
||||
`libc::c_uint` or `libc::c_ulong` should be used")
|
||||
}
|
||||
@ -784,7 +793,7 @@ impl LintPass for BoxPointers {
|
||||
}
|
||||
|
||||
fn check_expr(&mut self, cx: &Context, e: &ast::Expr) {
|
||||
let ty = cx.tcx.expr_ty(e);
|
||||
let ty = cx.tcx.node_id_to_type(e.id);
|
||||
self.check_heap_type(cx, e.span, ty);
|
||||
}
|
||||
}
|
||||
@ -799,17 +808,17 @@ struct RawPtrDeriveVisitor<'a, 'tcx: 'a> {
|
||||
cx: &'a Context<'a, 'tcx>
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for RawPtrDeriveVisitor<'a, 'tcx> {
|
||||
fn visit_ty(&mut self, ty: &ast::Ty) {
|
||||
impl<'a, 'tcx, 'v> HirVisitor<'v> for RawPtrDeriveVisitor<'a, 'tcx> {
|
||||
fn visit_ty(&mut self, ty: &hir::Ty) {
|
||||
const MSG: &'static str = "use of `#[derive]` with a raw pointer";
|
||||
if let ast::TyPtr(..) = ty.node {
|
||||
if let hir::TyPtr(..) = ty.node {
|
||||
self.cx.span_lint(RAW_POINTER_DERIVE, ty.span, MSG);
|
||||
}
|
||||
visit::walk_ty(self, ty);
|
||||
hir_visit::walk_ty(self, ty);
|
||||
}
|
||||
// explicit override to a no-op to reduce code bloat
|
||||
fn visit_expr(&mut self, _: &ast::Expr) {}
|
||||
fn visit_block(&mut self, _: &ast::Block) {}
|
||||
fn visit_expr(&mut self, _: &hir::Expr) {}
|
||||
fn visit_block(&mut self, _: &hir::Block) {}
|
||||
}
|
||||
|
||||
pub struct RawPointerDerive {
|
||||
@ -833,8 +842,9 @@ impl LintPass for RawPointerDerive {
|
||||
if !attr::contains_name(&item.attrs, "automatically_derived") {
|
||||
return;
|
||||
}
|
||||
let item = lower_item(item);
|
||||
let did = match item.node {
|
||||
ast::ItemImpl(_, _, _, ref t_ref_opt, _, _) => {
|
||||
hir::ItemImpl(_, _, _, ref t_ref_opt, _, _) => {
|
||||
// Deriving the Copy trait does not cause a warning
|
||||
if let &Some(ref trait_ref) = t_ref_opt {
|
||||
let def_id = cx.tcx.trait_ref_to_def_id(trait_ref);
|
||||
@ -855,16 +865,16 @@ impl LintPass for RawPointerDerive {
|
||||
return;
|
||||
}
|
||||
let item = match cx.tcx.map.find(did.node) {
|
||||
Some(ast_map::NodeItem(item)) => item,
|
||||
Some(hir_map::NodeItem(item)) => item,
|
||||
_ => return,
|
||||
};
|
||||
if !self.checked_raw_pointers.insert(item.id) {
|
||||
return;
|
||||
}
|
||||
match item.node {
|
||||
ast::ItemStruct(..) | ast::ItemEnum(..) => {
|
||||
hir::ItemStruct(..) | hir::ItemEnum(..) => {
|
||||
let mut visitor = RawPtrDeriveVisitor { cx: cx };
|
||||
visit::walk_item(&mut visitor, &*item);
|
||||
hir_visit::walk_item(&mut visitor, &item);
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
@ -989,14 +999,15 @@ impl LintPass for UnusedResults {
|
||||
return;
|
||||
}
|
||||
|
||||
let t = cx.tcx.expr_ty(expr);
|
||||
let expr = lower_expr(expr);
|
||||
let t = cx.tcx.expr_ty(&expr);
|
||||
let warned = match t.sty {
|
||||
ty::TyTuple(ref tys) if tys.is_empty() => return,
|
||||
ty::TyBool => return,
|
||||
ty::TyStruct(def, _) |
|
||||
ty::TyEnum(def, _) => {
|
||||
if def.did.is_local() {
|
||||
if let ast_map::NodeItem(it) = cx.tcx.map.get(def.did.node) {
|
||||
if let hir_map::NodeItem(it) = cx.tcx.map.get(def.did.node) {
|
||||
check_must_use(cx, &it.attrs, s.span)
|
||||
} else {
|
||||
false
|
||||
@ -1012,7 +1023,7 @@ impl LintPass for UnusedResults {
|
||||
cx.span_lint(UNUSED_RESULTS, s.span, "unused result");
|
||||
}
|
||||
|
||||
fn check_must_use(cx: &Context, attrs: &[ast::Attribute], sp: Span) -> bool {
|
||||
fn check_must_use(cx: &Context, attrs: &[hir::Attribute], sp: Span) -> bool {
|
||||
for attr in attrs {
|
||||
if attr.check_name("must_use") {
|
||||
let mut msg = "unused result which must be used".to_string();
|
||||
@ -1642,9 +1653,9 @@ impl UnusedMut {
|
||||
|
||||
let mut mutables = FnvHashMap();
|
||||
for p in pats {
|
||||
pat_util::pat_bindings(&cx.tcx.def_map, &**p, |mode, id, _, path1| {
|
||||
pat_util::pat_bindings(&cx.tcx.def_map, &lower_pat(p), |mode, id, _, path1| {
|
||||
let ident = path1.node;
|
||||
if let ast::BindByValue(ast::MutMutable) = mode {
|
||||
if let hir::BindByValue(hir::MutMutable) = mode {
|
||||
if !ident.name.as_str().starts_with("_") {
|
||||
match mutables.entry(ident.name.usize()) {
|
||||
Vacant(entry) => { entry.insert(vec![id]); },
|
||||
@ -1718,11 +1729,11 @@ impl LintPass for UnusedAllocation {
|
||||
if let Some(adjustment) = cx.tcx.tables.borrow().adjustments.get(&e.id) {
|
||||
if let ty::AdjustDerefRef(ty::AutoDerefRef { ref autoref, .. }) = *adjustment {
|
||||
match autoref {
|
||||
&Some(ty::AutoPtr(_, ast::MutImmutable)) => {
|
||||
&Some(ty::AutoPtr(_, hir::MutImmutable)) => {
|
||||
cx.span_lint(UNUSED_ALLOCATION, e.span,
|
||||
"unnecessary allocation, use & instead");
|
||||
}
|
||||
&Some(ty::AutoPtr(_, ast::MutMutable)) => {
|
||||
&Some(ty::AutoPtr(_, hir::MutMutable)) => {
|
||||
cx.span_lint(UNUSED_ALLOCATION, e.span,
|
||||
"unnecessary allocation, use &mut instead");
|
||||
}
|
||||
@ -1862,9 +1873,9 @@ impl LintPass for MissingDoc {
|
||||
ast::ItemImpl(_, _, _, Some(ref trait_ref), _, ref impl_items) => {
|
||||
// If the trait is private, add the impl items to private_traits so they don't get
|
||||
// reported for missing docs.
|
||||
let real_trait = cx.tcx.trait_ref_to_def_id(trait_ref);
|
||||
let real_trait = cx.tcx.trait_ref_to_def_id(&lower_trait_ref(trait_ref));
|
||||
match cx.tcx.map.find(real_trait.node) {
|
||||
Some(ast_map::NodeItem(item)) => if item.vis == ast::Visibility::Inherited {
|
||||
Some(hir_map::NodeItem(item)) => if item.vis == hir::Visibility::Inherited {
|
||||
for itm in impl_items {
|
||||
self.private_traits.insert(itm.id);
|
||||
}
|
||||
@ -2087,29 +2098,51 @@ impl Stability {
|
||||
}
|
||||
}
|
||||
|
||||
fn hir_to_ast_stability(stab: &front_attr::Stability) -> attr::Stability {
|
||||
attr::Stability {
|
||||
level: match stab.level {
|
||||
front_attr::Unstable => attr::Unstable,
|
||||
front_attr::Stable => attr::Stable,
|
||||
},
|
||||
feature: stab.feature.clone(),
|
||||
since: stab.since.clone(),
|
||||
deprecated_since: stab.deprecated_since.clone(),
|
||||
reason: stab.reason.clone(),
|
||||
issue: stab.issue,
|
||||
}
|
||||
}
|
||||
|
||||
impl LintPass for Stability {
|
||||
fn get_lints(&self) -> LintArray {
|
||||
lint_array!(DEPRECATED)
|
||||
}
|
||||
|
||||
fn check_item(&mut self, cx: &Context, item: &ast::Item) {
|
||||
stability::check_item(cx.tcx, item, false,
|
||||
&mut |id, sp, stab| self.lint(cx, id, sp, stab));
|
||||
stability::check_item(cx.tcx, &lower_item(item), false,
|
||||
&mut |id, sp, stab|
|
||||
self.lint(cx, id, sp,
|
||||
&stab.map(|s| hir_to_ast_stability(s)).as_ref()));
|
||||
}
|
||||
|
||||
fn check_expr(&mut self, cx: &Context, e: &ast::Expr) {
|
||||
stability::check_expr(cx.tcx, e,
|
||||
&mut |id, sp, stab| self.lint(cx, id, sp, stab));
|
||||
stability::check_expr(cx.tcx, &lower_expr(e),
|
||||
&mut |id, sp, stab|
|
||||
self.lint(cx, id, sp,
|
||||
&stab.map(|s| hir_to_ast_stability(s)).as_ref()));
|
||||
}
|
||||
|
||||
fn check_path(&mut self, cx: &Context, path: &ast::Path, id: ast::NodeId) {
|
||||
stability::check_path(cx.tcx, path, id,
|
||||
&mut |id, sp, stab| self.lint(cx, id, sp, stab));
|
||||
stability::check_path(cx.tcx, &lower_path(path), id,
|
||||
&mut |id, sp, stab|
|
||||
self.lint(cx, id, sp,
|
||||
&stab.map(|s| hir_to_ast_stability(s)).as_ref()));
|
||||
}
|
||||
|
||||
fn check_pat(&mut self, cx: &Context, pat: &ast::Pat) {
|
||||
stability::check_pat(cx.tcx, pat,
|
||||
&mut |id, sp, stab| self.lint(cx, id, sp, stab))
|
||||
stability::check_pat(cx.tcx, &lower_pat(pat),
|
||||
&mut |id, sp, stab|
|
||||
self.lint(cx, id, sp,
|
||||
&stab.map(|s| hir_to_ast_stability(s)).as_ref()));
|
||||
}
|
||||
}
|
||||
|
||||
@ -2168,7 +2201,7 @@ impl LintPass for UnconditionalRecursion {
|
||||
// to have behaviour like the above, rather than
|
||||
// e.g. accidentally recurring after an assert.
|
||||
|
||||
let cfg = cfg::CFG::new(cx.tcx, blk);
|
||||
let cfg = cfg::CFG::new(cx.tcx, &lower_block(blk));
|
||||
|
||||
let mut work_queue = vec![cfg.entry];
|
||||
let mut reached_exit_without_self_call = false;
|
||||
@ -2248,7 +2281,7 @@ impl LintPass for UnconditionalRecursion {
|
||||
fn_id: ast::NodeId,
|
||||
id: ast::NodeId) -> bool {
|
||||
match tcx.map.get(id) {
|
||||
ast_map::NodeExpr(&ast::Expr { node: ast::ExprCall(ref callee, _), .. }) => {
|
||||
hir_map::NodeExpr(&hir::Expr { node: hir::ExprCall(ref callee, _), .. }) => {
|
||||
tcx.def_map.borrow().get(&callee.id)
|
||||
.map_or(false, |def| def.def_id() == DefId::local(fn_id))
|
||||
}
|
||||
@ -2283,7 +2316,7 @@ impl LintPass for UnconditionalRecursion {
|
||||
|
||||
// Check for calls to methods via explicit paths (e.g. `T::method()`).
|
||||
match tcx.map.get(id) {
|
||||
ast_map::NodeExpr(&ast::Expr { node: ast::ExprCall(ref callee, _), .. }) => {
|
||||
hir_map::NodeExpr(&hir::Expr { node: hir::ExprCall(ref callee, _), .. }) => {
|
||||
match tcx.def_map.borrow().get(&callee.id).map(|d| d.full_def()) {
|
||||
Some(def::DefMethod(def_id)) => {
|
||||
let no_substs = &ty::ItemSubsts::empty();
|
||||
@ -2479,12 +2512,13 @@ impl LintPass for MutableTransmutes {
|
||||
|
||||
fn check_expr(&mut self, cx: &Context, expr: &ast::Expr) {
|
||||
use syntax::abi::RustIntrinsic;
|
||||
|
||||
let msg = "mutating transmuted &mut T from &T may cause undefined behavior,\
|
||||
consider instead using an UnsafeCell";
|
||||
match get_transmute_from_to(cx, expr) {
|
||||
Some((&ty::TyRef(_, from_mt), &ty::TyRef(_, to_mt))) => {
|
||||
if to_mt.mutbl == ast::Mutability::MutMutable
|
||||
&& from_mt.mutbl == ast::Mutability::MutImmutable {
|
||||
if to_mt.mutbl == hir::Mutability::MutMutable
|
||||
&& from_mt.mutbl == hir::Mutability::MutImmutable {
|
||||
cx.span_lint(MUTABLE_TRANSMUTES, expr.span, msg);
|
||||
}
|
||||
}
|
||||
@ -2497,7 +2531,7 @@ impl LintPass for MutableTransmutes {
|
||||
ast::ExprPath(..) => (),
|
||||
_ => return None
|
||||
}
|
||||
if let def::DefFn(did, _) = cx.tcx.resolve_expr(expr) {
|
||||
if let def::DefFn(did, _) = cx.tcx.resolve_expr(&lower_expr(expr)) {
|
||||
if !def_id_is_transmute(cx, did) {
|
||||
return None;
|
||||
}
|
||||
@ -2584,7 +2618,7 @@ impl LintPass for DropWithReprExtern {
|
||||
ty::TyStruct(self_type_def, _) => {
|
||||
let self_type_did = self_type_def.did;
|
||||
let hints = ctx.tcx.lookup_repr_hints(self_type_did);
|
||||
if hints.iter().any(|attr| *attr == attr::ReprExtern) &&
|
||||
if hints.iter().any(|attr| *attr == front_attr::ReprExtern) &&
|
||||
self_type_def.dtor_kind().has_drop_flag() {
|
||||
let drop_impl_span = ctx.tcx.map.def_id_span(drop_impl_did,
|
||||
codemap::DUMMY_SP);
|
||||
|
@ -47,6 +47,7 @@ extern crate syntax;
|
||||
extern crate rustc;
|
||||
#[macro_use]
|
||||
extern crate log;
|
||||
extern crate rustc_front;
|
||||
|
||||
pub use rustc::lint as lint;
|
||||
pub use rustc::metadata as metadata;
|
||||
|
@ -27,13 +27,16 @@
|
||||
#[macro_use] extern crate syntax;
|
||||
|
||||
extern crate rustc;
|
||||
extern crate rustc_front;
|
||||
|
||||
use self::PrivacyResult::*;
|
||||
use self::FieldName::*;
|
||||
|
||||
use std::mem::replace;
|
||||
|
||||
use rustc::ast_map;
|
||||
use rustc_front::hir;
|
||||
use rustc_front::visit::{self, Visitor};
|
||||
|
||||
use rustc::middle::def;
|
||||
use rustc::middle::def_id::DefId;
|
||||
use rustc::middle::privacy::ImportUse::*;
|
||||
@ -42,10 +45,10 @@ use rustc::middle::privacy::PrivateDep::*;
|
||||
use rustc::middle::privacy::{ExternalExports, ExportedItems, PublicItems};
|
||||
use rustc::middle::ty::{self, Ty};
|
||||
use rustc::util::nodemap::{NodeMap, NodeSet};
|
||||
use rustc::front::map as ast_map;
|
||||
|
||||
use syntax::ast;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::visit::{self, Visitor};
|
||||
|
||||
type Context<'a, 'tcx> = (&'a ty::MethodMap<'tcx>, &'a def::ExportMap);
|
||||
|
||||
@ -64,15 +67,15 @@ struct ParentVisitor {
|
||||
}
|
||||
|
||||
impl<'v> Visitor<'v> for ParentVisitor {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
self.parents.insert(item.id, self.curparent);
|
||||
|
||||
let prev = self.curparent;
|
||||
match item.node {
|
||||
ast::ItemMod(..) => { self.curparent = item.id; }
|
||||
hir::ItemMod(..) => { self.curparent = item.id; }
|
||||
// Enum variants are parented to the enum definition itself because
|
||||
// they inherit privacy
|
||||
ast::ItemEnum(ref def, _) => {
|
||||
hir::ItemEnum(ref def, _) => {
|
||||
for variant in &def.variants {
|
||||
// The parent is considered the enclosing enum because the
|
||||
// enum will dictate the privacy visibility of this variant
|
||||
@ -86,7 +89,7 @@ impl<'v> Visitor<'v> for ParentVisitor {
|
||||
// method to the root. In this case, if the trait is private, then
|
||||
// parent all the methods to the trait to indicate that they're
|
||||
// private.
|
||||
ast::ItemTrait(_, _, _, ref trait_items) if item.vis != ast::Public => {
|
||||
hir::ItemTrait(_, _, _, ref trait_items) if item.vis != hir::Public => {
|
||||
for trait_item in trait_items {
|
||||
self.parents.insert(trait_item.id, item.id);
|
||||
}
|
||||
@ -98,13 +101,13 @@ impl<'v> Visitor<'v> for ParentVisitor {
|
||||
self.curparent = prev;
|
||||
}
|
||||
|
||||
fn visit_foreign_item(&mut self, a: &ast::ForeignItem) {
|
||||
fn visit_foreign_item(&mut self, a: &hir::ForeignItem) {
|
||||
self.parents.insert(a.id, self.curparent);
|
||||
visit::walk_foreign_item(self, a);
|
||||
}
|
||||
|
||||
fn visit_fn(&mut self, a: visit::FnKind<'v>, b: &'v ast::FnDecl,
|
||||
c: &'v ast::Block, d: Span, id: ast::NodeId) {
|
||||
fn visit_fn(&mut self, a: visit::FnKind<'v>, b: &'v hir::FnDecl,
|
||||
c: &'v hir::Block, d: Span, id: ast::NodeId) {
|
||||
// We already took care of some trait methods above, otherwise things
|
||||
// like impl methods and pub trait methods are parented to the
|
||||
// containing module, not the containing trait.
|
||||
@ -114,7 +117,7 @@ impl<'v> Visitor<'v> for ParentVisitor {
|
||||
visit::walk_fn(self, a, b, c, d);
|
||||
}
|
||||
|
||||
fn visit_impl_item(&mut self, ii: &'v ast::ImplItem) {
|
||||
fn visit_impl_item(&mut self, ii: &'v hir::ImplItem) {
|
||||
// visit_fn handles methods, but associated consts have to be handled
|
||||
// here.
|
||||
if !self.parents.contains_key(&ii.id) {
|
||||
@ -123,8 +126,8 @@ impl<'v> Visitor<'v> for ParentVisitor {
|
||||
visit::walk_impl_item(self, ii);
|
||||
}
|
||||
|
||||
fn visit_struct_def(&mut self, s: &ast::StructDef, _: ast::Ident,
|
||||
_: &'v ast::Generics, n: ast::NodeId) {
|
||||
fn visit_struct_def(&mut self, s: &hir::StructDef, _: ast::Ident,
|
||||
_: &'v hir::Generics, n: ast::NodeId) {
|
||||
// Struct constructors are parented to their struct definitions because
|
||||
// they essentially are the struct definitions.
|
||||
match s.ctor_id {
|
||||
@ -193,9 +196,9 @@ impl<'a, 'tcx> EmbargoVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
let orig_all_pub = self.prev_public;
|
||||
self.prev_public = orig_all_pub && item.vis == ast::Public;
|
||||
self.prev_public = orig_all_pub && item.vis == hir::Public;
|
||||
if self.prev_public {
|
||||
self.public_items.insert(item.id);
|
||||
}
|
||||
@ -204,11 +207,11 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
match item.node {
|
||||
// impls/extern blocks do not break the "public chain" because they
|
||||
// cannot have visibility qualifiers on them anyway
|
||||
ast::ItemImpl(..) | ast::ItemDefaultImpl(..) | ast::ItemForeignMod(..) => {}
|
||||
hir::ItemImpl(..) | hir::ItemDefaultImpl(..) | hir::ItemForeignMod(..) => {}
|
||||
|
||||
// Traits are a little special in that even if they themselves are
|
||||
// not public they may still be exported.
|
||||
ast::ItemTrait(..) => {
|
||||
hir::ItemTrait(..) => {
|
||||
self.prev_exported = self.exported_trait(item.id);
|
||||
}
|
||||
|
||||
@ -216,7 +219,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
// `pub` is explicitly listed.
|
||||
_ => {
|
||||
self.prev_exported =
|
||||
(orig_all_exported && item.vis == ast::Public) ||
|
||||
(orig_all_exported && item.vis == hir::Public) ||
|
||||
self.reexports.contains(&item.id);
|
||||
}
|
||||
}
|
||||
@ -227,7 +230,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
match item.node {
|
||||
// Enum variants inherit from their parent, so if the enum is
|
||||
// public all variants are public unless they're explicitly priv
|
||||
ast::ItemEnum(ref def, _) if public_first => {
|
||||
hir::ItemEnum(ref def, _) if public_first => {
|
||||
for variant in &def.variants {
|
||||
self.exported_items.insert(variant.node.id);
|
||||
self.public_items.insert(variant.node.id);
|
||||
@ -253,9 +256,9 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
// undefined symbols at linkage time if this case is not handled.
|
||||
//
|
||||
// * Private trait impls for private types can be completely ignored
|
||||
ast::ItemImpl(_, _, _, _, ref ty, ref impl_items) => {
|
||||
hir::ItemImpl(_, _, _, _, ref ty, ref impl_items) => {
|
||||
let public_ty = match ty.node {
|
||||
ast::TyPath(..) => {
|
||||
hir::TyPath(..) => {
|
||||
match self.tcx.def_map.borrow().get(&ty.id).unwrap().full_def() {
|
||||
def::DefPrimTy(..) => true,
|
||||
def => {
|
||||
@ -276,23 +279,22 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
if public_ty || public_trait {
|
||||
for impl_item in impl_items {
|
||||
match impl_item.node {
|
||||
ast::ConstImplItem(..) => {
|
||||
if (public_ty && impl_item.vis == ast::Public)
|
||||
hir::ConstImplItem(..) => {
|
||||
if (public_ty && impl_item.vis == hir::Public)
|
||||
|| tr.is_some() {
|
||||
self.exported_items.insert(impl_item.id);
|
||||
}
|
||||
}
|
||||
ast::MethodImplItem(ref sig, _) => {
|
||||
hir::MethodImplItem(ref sig, _) => {
|
||||
let meth_public = match sig.explicit_self.node {
|
||||
ast::SelfStatic => public_ty,
|
||||
hir::SelfStatic => public_ty,
|
||||
_ => true,
|
||||
} && impl_item.vis == ast::Public;
|
||||
} && impl_item.vis == hir::Public;
|
||||
if meth_public || tr.is_some() {
|
||||
self.exported_items.insert(impl_item.id);
|
||||
}
|
||||
}
|
||||
ast::TypeImplItem(_) |
|
||||
ast::MacImplItem(_) => {}
|
||||
hir::TypeImplItem(_) => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -300,7 +302,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
|
||||
// Default methods on traits are all public so long as the trait
|
||||
// is public
|
||||
ast::ItemTrait(_, _, _, ref trait_items) if public_first => {
|
||||
hir::ItemTrait(_, _, _, ref trait_items) if public_first => {
|
||||
for trait_item in trait_items {
|
||||
debug!("trait item {}", trait_item.id);
|
||||
self.exported_items.insert(trait_item.id);
|
||||
@ -308,7 +310,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
// Struct constructors are public if the struct is all public.
|
||||
ast::ItemStruct(ref def, _) if public_first => {
|
||||
hir::ItemStruct(ref def, _) if public_first => {
|
||||
match def.ctor_id {
|
||||
Some(id) => { self.exported_items.insert(id); }
|
||||
None => {}
|
||||
@ -316,16 +318,16 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
// fields can be public or private, so lets check
|
||||
for field in &def.fields {
|
||||
let vis = match field.node.kind {
|
||||
ast::NamedField(_, vis) | ast::UnnamedField(vis) => vis
|
||||
hir::NamedField(_, vis) | hir::UnnamedField(vis) => vis
|
||||
};
|
||||
if vis == ast::Public {
|
||||
if vis == hir::Public {
|
||||
self.public_items.insert(field.node.id);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ast::ItemTy(ref ty, _) if public_first => {
|
||||
if let ast::TyPath(..) = ty.node {
|
||||
hir::ItemTy(ref ty, _) if public_first => {
|
||||
if let hir::TyPath(..) = ty.node {
|
||||
match self.tcx.def_map.borrow().get(&ty.id).unwrap().full_def() {
|
||||
def::DefPrimTy(..) | def::DefTyParam(..) => {},
|
||||
def => {
|
||||
@ -347,13 +349,13 @@ impl<'a, 'tcx, 'v> Visitor<'v> for EmbargoVisitor<'a, 'tcx> {
|
||||
self.prev_public = orig_all_pub;
|
||||
}
|
||||
|
||||
fn visit_foreign_item(&mut self, a: &ast::ForeignItem) {
|
||||
if (self.prev_exported && a.vis == ast::Public) || self.reexports.contains(&a.id) {
|
||||
fn visit_foreign_item(&mut self, a: &hir::ForeignItem) {
|
||||
if (self.prev_exported && a.vis == hir::Public) || self.reexports.contains(&a.id) {
|
||||
self.exported_items.insert(a.id);
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_mod(&mut self, m: &ast::Mod, _sp: Span, id: ast::NodeId) {
|
||||
fn visit_mod(&mut self, m: &hir::Mod, _sp: Span, id: ast::NodeId) {
|
||||
// This code is here instead of in visit_item so that the
|
||||
// crate module gets processed as well.
|
||||
if self.prev_exported {
|
||||
@ -426,7 +428,7 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
debug!("privacy - found inherent \
|
||||
associated constant {:?}",
|
||||
ac.vis);
|
||||
if ac.vis == ast::Public {
|
||||
if ac.vis == hir::Public {
|
||||
Allowable
|
||||
} else {
|
||||
ExternallyDenied
|
||||
@ -453,7 +455,7 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
None => {
|
||||
debug!("privacy - found a method {:?}",
|
||||
meth.vis);
|
||||
if meth.vis == ast::Public {
|
||||
if meth.vis == hir::Public {
|
||||
Allowable
|
||||
} else {
|
||||
ExternallyDenied
|
||||
@ -478,7 +480,7 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
None => {
|
||||
debug!("privacy - found a typedef {:?}",
|
||||
typedef.vis);
|
||||
if typedef.vis == ast::Public {
|
||||
if typedef.vis == hir::Public {
|
||||
Allowable
|
||||
} else {
|
||||
ExternallyDenied
|
||||
@ -527,20 +529,19 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
// where the method was defined?
|
||||
Some(ast_map::NodeImplItem(ii)) => {
|
||||
match ii.node {
|
||||
ast::ConstImplItem(..) |
|
||||
ast::MethodImplItem(..) => {
|
||||
hir::ConstImplItem(..) |
|
||||
hir::MethodImplItem(..) => {
|
||||
let imp = self.tcx.map
|
||||
.get_parent_did(closest_private_id);
|
||||
match self.tcx.impl_trait_ref(imp) {
|
||||
Some(..) => return Allowable,
|
||||
_ if ii.vis == ast::Public => {
|
||||
_ if ii.vis == hir::Public => {
|
||||
return Allowable
|
||||
}
|
||||
_ => ii.vis
|
||||
}
|
||||
}
|
||||
ast::TypeImplItem(_) |
|
||||
ast::MacImplItem(_) => return Allowable,
|
||||
hir::TypeImplItem(_) => return Allowable,
|
||||
}
|
||||
}
|
||||
Some(ast_map::NodeTraitItem(_)) => {
|
||||
@ -554,11 +555,11 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
self.tcx.map.get_foreign_vis(closest_private_id)
|
||||
}
|
||||
Some(ast_map::NodeVariant(..)) => {
|
||||
ast::Public // need to move up a level (to the enum)
|
||||
hir::Public // need to move up a level (to the enum)
|
||||
}
|
||||
_ => ast::Public,
|
||||
_ => hir::Public,
|
||||
};
|
||||
if vis != ast::Public { break }
|
||||
if vis != hir::Public { break }
|
||||
// if we've reached the root, then everything was allowable and this
|
||||
// access is public.
|
||||
if closest_private_id == ast::CRATE_NODE_ID { return Allowable }
|
||||
@ -654,9 +655,9 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
// invoked, and the struct/enum itself is private. Crawl
|
||||
// back up the chains to find the relevant struct/enum that
|
||||
// was private.
|
||||
ast::ItemImpl(_, _, _, _, ref ty, _) => {
|
||||
hir::ItemImpl(_, _, _, _, ref ty, _) => {
|
||||
match ty.node {
|
||||
ast::TyPath(..) => {}
|
||||
hir::TyPath(..) => {}
|
||||
_ => return Some((err_span, err_msg, None)),
|
||||
};
|
||||
let def = self.tcx.def_map.borrow().get(&ty.id).unwrap().full_def();
|
||||
@ -674,10 +675,10 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
Some(..) | None => return Some((err_span, err_msg, None)),
|
||||
};
|
||||
let desc = match item.node {
|
||||
ast::ItemMod(..) => "module",
|
||||
ast::ItemTrait(..) => "trait",
|
||||
ast::ItemStruct(..) => "struct",
|
||||
ast::ItemEnum(..) => "enum",
|
||||
hir::ItemMod(..) => "module",
|
||||
hir::ItemTrait(..) => "trait",
|
||||
hir::ItemStruct(..) => "struct",
|
||||
hir::ItemEnum(..) => "enum",
|
||||
_ => return Some((err_span, err_msg, None))
|
||||
};
|
||||
let msg = format!("{} `{}` is private", desc, item.ident);
|
||||
@ -697,7 +698,7 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
}
|
||||
UnnamedField(idx) => &v.fields[idx]
|
||||
};
|
||||
if field.vis == ast::Public ||
|
||||
if field.vis == hir::Public ||
|
||||
(field.did.is_local() && self.private_accessible(field.did.node)) {
|
||||
return
|
||||
}
|
||||
@ -854,16 +855,16 @@ impl<'a, 'tcx> PrivacyVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
if let ast::ItemUse(ref vpath) = item.node {
|
||||
if let ast::ViewPathList(ref prefix, ref list) = vpath.node {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
if let hir::ItemUse(ref vpath) = item.node {
|
||||
if let hir::ViewPathList(ref prefix, ref list) = vpath.node {
|
||||
for pid in list {
|
||||
match pid.node {
|
||||
ast::PathListIdent { id, name, .. } => {
|
||||
hir::PathListIdent { id, name, .. } => {
|
||||
debug!("privacy - ident item {}", id);
|
||||
self.check_path(pid.span, id, name.name);
|
||||
}
|
||||
ast::PathListMod { id, .. } => {
|
||||
hir::PathListMod { id, .. } => {
|
||||
debug!("privacy - mod item {}", id);
|
||||
let name = prefix.segments.last().unwrap().identifier.name;
|
||||
self.check_path(pid.span, id, name);
|
||||
@ -877,9 +878,9 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
self.curitem = orig_curitem;
|
||||
}
|
||||
|
||||
fn visit_expr(&mut self, expr: &ast::Expr) {
|
||||
fn visit_expr(&mut self, expr: &hir::Expr) {
|
||||
match expr.node {
|
||||
ast::ExprField(ref base, ident) => {
|
||||
hir::ExprField(ref base, ident) => {
|
||||
if let ty::TyStruct(def, _) = self.tcx.expr_ty_adjusted(&**base).sty {
|
||||
self.check_field(expr.span,
|
||||
def,
|
||||
@ -887,7 +888,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
NamedField(ident.node.name));
|
||||
}
|
||||
}
|
||||
ast::ExprTupField(ref base, idx) => {
|
||||
hir::ExprTupField(ref base, idx) => {
|
||||
if let ty::TyStruct(def, _) = self.tcx.expr_ty_adjusted(&**base).sty {
|
||||
self.check_field(expr.span,
|
||||
def,
|
||||
@ -895,13 +896,13 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
UnnamedField(idx.node));
|
||||
}
|
||||
}
|
||||
ast::ExprMethodCall(ident, _, _) => {
|
||||
hir::ExprMethodCall(ident, _, _) => {
|
||||
let method_call = ty::MethodCall::expr(expr.id);
|
||||
let method = self.tcx.tables.borrow().method_map[&method_call];
|
||||
debug!("(privacy checking) checking impl method");
|
||||
self.check_method(expr.span, method.def_id, ident.node.name);
|
||||
}
|
||||
ast::ExprStruct(..) => {
|
||||
hir::ExprStruct(..) => {
|
||||
let adt = self.tcx.expr_ty(expr).ty_adt_def().unwrap();
|
||||
let variant = adt.variant_of_def(self.tcx.resolve_expr(expr));
|
||||
// RFC 736: ensure all unmentioned fields are visible.
|
||||
@ -911,7 +912,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
self.check_field(expr.span, adt, variant, NamedField(field.name));
|
||||
}
|
||||
}
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
|
||||
if let def::DefStruct(_) = self.tcx.resolve_expr(expr) {
|
||||
let expr_ty = self.tcx.expr_ty(expr);
|
||||
@ -922,10 +923,11 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
_ => expr_ty
|
||||
}.ty_adt_def().unwrap();
|
||||
let any_priv = def.struct_variant().fields.iter().any(|f| {
|
||||
f.vis != ast::Public && (
|
||||
f.vis != hir::Public && (
|
||||
!f.did.is_local() ||
|
||||
!self.private_accessible(f.did.node))
|
||||
});
|
||||
|
||||
if any_priv {
|
||||
self.tcx.sess.span_err(expr.span,
|
||||
"cannot invoke tuple struct constructor \
|
||||
@ -939,7 +941,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
visit::walk_expr(self, expr);
|
||||
}
|
||||
|
||||
fn visit_pat(&mut self, pattern: &ast::Pat) {
|
||||
fn visit_pat(&mut self, pattern: &hir::Pat) {
|
||||
// Foreign functions do not have their patterns mapped in the def_map,
|
||||
// and there's nothing really relevant there anyway, so don't bother
|
||||
// checking privacy. If you can name the type then you can pass it to an
|
||||
@ -947,7 +949,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
if self.in_foreign { return }
|
||||
|
||||
match pattern.node {
|
||||
ast::PatStruct(_, ref fields, _) => {
|
||||
hir::PatStruct(_, ref fields, _) => {
|
||||
let adt = self.tcx.pat_ty(pattern).ty_adt_def().unwrap();
|
||||
let def = self.tcx.def_map.borrow().get(&pattern.id).unwrap().full_def();
|
||||
let variant = adt.variant_of_def(def);
|
||||
@ -959,11 +961,11 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
|
||||
// Patterns which bind no fields are allowable (the path is check
|
||||
// elsewhere).
|
||||
ast::PatEnum(_, Some(ref fields)) => {
|
||||
hir::PatEnum(_, Some(ref fields)) => {
|
||||
match self.tcx.pat_ty(pattern).sty {
|
||||
ty::TyStruct(def, _) => {
|
||||
for (i, field) in fields.iter().enumerate() {
|
||||
if let ast::PatWild(..) = field.node {
|
||||
if let hir::PatWild(..) = field.node {
|
||||
continue
|
||||
}
|
||||
self.check_field(field.span,
|
||||
@ -985,13 +987,13 @@ impl<'a, 'tcx, 'v> Visitor<'v> for PrivacyVisitor<'a, 'tcx> {
|
||||
visit::walk_pat(self, pattern);
|
||||
}
|
||||
|
||||
fn visit_foreign_item(&mut self, fi: &ast::ForeignItem) {
|
||||
fn visit_foreign_item(&mut self, fi: &hir::ForeignItem) {
|
||||
self.in_foreign = true;
|
||||
visit::walk_foreign_item(self, fi);
|
||||
self.in_foreign = false;
|
||||
}
|
||||
|
||||
fn visit_path(&mut self, path: &ast::Path, id: ast::NodeId) {
|
||||
fn visit_path(&mut self, path: &hir::Path, id: ast::NodeId) {
|
||||
self.check_path(path.span, id, path.segments.last().unwrap().identifier.name);
|
||||
visit::walk_path(self, path);
|
||||
}
|
||||
@ -1007,7 +1009,7 @@ struct SanePrivacyVisitor<'a, 'tcx: 'a> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for SanePrivacyVisitor<'a, 'tcx> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
if self.in_fn {
|
||||
self.check_all_inherited(item);
|
||||
} else {
|
||||
@ -1016,15 +1018,15 @@ impl<'a, 'tcx, 'v> Visitor<'v> for SanePrivacyVisitor<'a, 'tcx> {
|
||||
|
||||
let in_fn = self.in_fn;
|
||||
let orig_in_fn = replace(&mut self.in_fn, match item.node {
|
||||
ast::ItemMod(..) => false, // modules turn privacy back on
|
||||
hir::ItemMod(..) => false, // modules turn privacy back on
|
||||
_ => in_fn, // otherwise we inherit
|
||||
});
|
||||
visit::walk_item(self, item);
|
||||
self.in_fn = orig_in_fn;
|
||||
}
|
||||
|
||||
fn visit_fn(&mut self, fk: visit::FnKind<'v>, fd: &'v ast::FnDecl,
|
||||
b: &'v ast::Block, s: Span, _: ast::NodeId) {
|
||||
fn visit_fn(&mut self, fk: visit::FnKind<'v>, fd: &'v hir::FnDecl,
|
||||
b: &'v hir::Block, s: Span, _: ast::NodeId) {
|
||||
// This catches both functions and methods
|
||||
let orig_in_fn = replace(&mut self.in_fn, true);
|
||||
visit::walk_fn(self, fk, fd, b, s);
|
||||
@ -1037,10 +1039,10 @@ impl<'a, 'tcx> SanePrivacyVisitor<'a, 'tcx> {
|
||||
/// ensures that there are no extraneous qualifiers that don't actually do
|
||||
/// anything. In theory these qualifiers wouldn't parse, but that may happen
|
||||
/// later on down the road...
|
||||
fn check_sane_privacy(&self, item: &ast::Item) {
|
||||
fn check_sane_privacy(&self, item: &hir::Item) {
|
||||
let tcx = self.tcx;
|
||||
let check_inherited = |sp: Span, vis: ast::Visibility, note: &str| {
|
||||
if vis != ast::Inherited {
|
||||
let check_inherited = |sp: Span, vis: hir::Visibility, note: &str| {
|
||||
if vis != hir::Inherited {
|
||||
tcx.sess.span_err(sp, "unnecessary visibility qualifier");
|
||||
if !note.is_empty() {
|
||||
tcx.sess.span_note(sp, note);
|
||||
@ -1050,7 +1052,7 @@ impl<'a, 'tcx> SanePrivacyVisitor<'a, 'tcx> {
|
||||
match item.node {
|
||||
// implementations of traits don't need visibility qualifiers because
|
||||
// that's controlled by having the trait in scope.
|
||||
ast::ItemImpl(_, _, _, Some(..), _, ref impl_items) => {
|
||||
hir::ItemImpl(_, _, _, Some(..), _, ref impl_items) => {
|
||||
check_inherited(item.span, item.vis,
|
||||
"visibility qualifiers have no effect on trait \
|
||||
impls");
|
||||
@ -1059,84 +1061,83 @@ impl<'a, 'tcx> SanePrivacyVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ast::ItemImpl(..) => {
|
||||
hir::ItemImpl(..) => {
|
||||
check_inherited(item.span, item.vis,
|
||||
"place qualifiers on individual methods instead");
|
||||
}
|
||||
ast::ItemForeignMod(..) => {
|
||||
hir::ItemForeignMod(..) => {
|
||||
check_inherited(item.span, item.vis,
|
||||
"place qualifiers on individual functions \
|
||||
instead");
|
||||
}
|
||||
|
||||
ast::ItemEnum(ref def, _) => {
|
||||
hir::ItemEnum(ref def, _) => {
|
||||
for v in &def.variants {
|
||||
match v.node.vis {
|
||||
ast::Public => {
|
||||
if item.vis == ast::Public {
|
||||
hir::Public => {
|
||||
if item.vis == hir::Public {
|
||||
tcx.sess.span_err(v.span, "unnecessary `pub` \
|
||||
visibility");
|
||||
}
|
||||
}
|
||||
ast::Inherited => {}
|
||||
hir::Inherited => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ast::ItemTrait(..) | ast::ItemDefaultImpl(..) |
|
||||
ast::ItemConst(..) | ast::ItemStatic(..) | ast::ItemStruct(..) |
|
||||
ast::ItemFn(..) | ast::ItemMod(..) | ast::ItemTy(..) |
|
||||
ast::ItemExternCrate(_) | ast::ItemUse(_) | ast::ItemMac(..) => {}
|
||||
hir::ItemTrait(..) | hir::ItemDefaultImpl(..) |
|
||||
hir::ItemConst(..) | hir::ItemStatic(..) | hir::ItemStruct(..) |
|
||||
hir::ItemFn(..) | hir::ItemMod(..) | hir::ItemTy(..) |
|
||||
hir::ItemExternCrate(_) | hir::ItemUse(_) => {}
|
||||
}
|
||||
}
|
||||
|
||||
/// When inside of something like a function or a method, visibility has no
|
||||
/// control over anything so this forbids any mention of any visibility
|
||||
fn check_all_inherited(&self, item: &ast::Item) {
|
||||
fn check_all_inherited(&self, item: &hir::Item) {
|
||||
let tcx = self.tcx;
|
||||
fn check_inherited(tcx: &ty::ctxt, sp: Span, vis: ast::Visibility) {
|
||||
if vis != ast::Inherited {
|
||||
fn check_inherited(tcx: &ty::ctxt, sp: Span, vis: hir::Visibility) {
|
||||
if vis != hir::Inherited {
|
||||
tcx.sess.span_err(sp, "visibility has no effect inside functions");
|
||||
}
|
||||
}
|
||||
let check_struct = |def: &ast::StructDef| {
|
||||
let check_struct = |def: &hir::StructDef| {
|
||||
for f in &def.fields {
|
||||
match f.node.kind {
|
||||
ast::NamedField(_, p) => check_inherited(tcx, f.span, p),
|
||||
ast::UnnamedField(..) => {}
|
||||
hir::NamedField(_, p) => check_inherited(tcx, f.span, p),
|
||||
hir::UnnamedField(..) => {}
|
||||
}
|
||||
}
|
||||
};
|
||||
check_inherited(tcx, item.span, item.vis);
|
||||
match item.node {
|
||||
ast::ItemImpl(_, _, _, _, _, ref impl_items) => {
|
||||
hir::ItemImpl(_, _, _, _, _, ref impl_items) => {
|
||||
for impl_item in impl_items {
|
||||
match impl_item.node {
|
||||
ast::MethodImplItem(..) => {
|
||||
hir::MethodImplItem(..) => {
|
||||
check_inherited(tcx, impl_item.span, impl_item.vis);
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::ItemForeignMod(ref fm) => {
|
||||
hir::ItemForeignMod(ref fm) => {
|
||||
for i in &fm.items {
|
||||
check_inherited(tcx, i.span, i.vis);
|
||||
}
|
||||
}
|
||||
ast::ItemEnum(ref def, _) => {
|
||||
hir::ItemEnum(ref def, _) => {
|
||||
for v in &def.variants {
|
||||
check_inherited(tcx, v.span, v.node.vis);
|
||||
}
|
||||
}
|
||||
|
||||
ast::ItemStruct(ref def, _) => check_struct(&**def),
|
||||
hir::ItemStruct(ref def, _) => check_struct(&**def),
|
||||
|
||||
ast::ItemExternCrate(_) | ast::ItemUse(_) |
|
||||
ast::ItemTrait(..) | ast::ItemDefaultImpl(..) |
|
||||
ast::ItemStatic(..) | ast::ItemConst(..) |
|
||||
ast::ItemFn(..) | ast::ItemMod(..) | ast::ItemTy(..) |
|
||||
ast::ItemMac(..) => {}
|
||||
hir::ItemExternCrate(_) | hir::ItemUse(_) |
|
||||
hir::ItemTrait(..) | hir::ItemDefaultImpl(..) |
|
||||
hir::ItemStatic(..) | hir::ItemConst(..) |
|
||||
hir::ItemFn(..) | hir::ItemMod(..) | hir::ItemTy(..) => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1175,7 +1176,7 @@ impl<'a, 'tcx> VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
// .. and it corresponds to a private type in the AST (this returns
|
||||
// None for type parameters)
|
||||
match self.tcx.map.find(did.node) {
|
||||
Some(ast_map::NodeItem(ref item)) => item.vis != ast::Public,
|
||||
Some(ast_map::NodeItem(ref item)) => item.vis != hir::Public,
|
||||
Some(_) | None => false,
|
||||
}
|
||||
}
|
||||
@ -1187,8 +1188,8 @@ impl<'a, 'tcx> VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
}
|
||||
|
||||
fn check_ty_param_bound(&self,
|
||||
ty_param_bound: &ast::TyParamBound) {
|
||||
if let ast::TraitTyParamBound(ref trait_ref, _) = *ty_param_bound {
|
||||
ty_param_bound: &hir::TyParamBound) {
|
||||
if let hir::TraitTyParamBound(ref trait_ref, _) = *ty_param_bound {
|
||||
if !self.tcx.sess.features.borrow().visible_private_types &&
|
||||
self.path_is_private_type(trait_ref.trait_ref.ref_id) {
|
||||
let span = trait_ref.trait_ref.path.span;
|
||||
@ -1198,14 +1199,14 @@ impl<'a, 'tcx> VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn item_is_public(&self, id: &ast::NodeId, vis: ast::Visibility) -> bool {
|
||||
self.exported_items.contains(id) || vis == ast::Public
|
||||
fn item_is_public(&self, id: &ast::NodeId, vis: hir::Visibility) -> bool {
|
||||
self.exported_items.contains(id) || vis == hir::Public
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a, 'b, 'tcx, 'v> Visitor<'v> for CheckTypeForPrivatenessVisitor<'a, 'b, 'tcx> {
|
||||
fn visit_ty(&mut self, ty: &ast::Ty) {
|
||||
if let ast::TyPath(..) = ty.node {
|
||||
fn visit_ty(&mut self, ty: &hir::Ty) {
|
||||
if let hir::TyPath(..) = ty.node {
|
||||
if self.inner.path_is_private_type(ty.id) {
|
||||
self.contains_private = true;
|
||||
// found what we're looking for so let's stop
|
||||
@ -1220,21 +1221,21 @@ impl<'a, 'b, 'tcx, 'v> Visitor<'v> for CheckTypeForPrivatenessVisitor<'a, 'b, 't
|
||||
}
|
||||
|
||||
// don't want to recurse into [, .. expr]
|
||||
fn visit_expr(&mut self, _: &ast::Expr) {}
|
||||
fn visit_expr(&mut self, _: &hir::Expr) {}
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
match item.node {
|
||||
// contents of a private mod can be reexported, so we need
|
||||
// to check internals.
|
||||
ast::ItemMod(_) => {}
|
||||
hir::ItemMod(_) => {}
|
||||
|
||||
// An `extern {}` doesn't introduce a new privacy
|
||||
// namespace (the contents have their own privacies).
|
||||
ast::ItemForeignMod(_) => {}
|
||||
hir::ItemForeignMod(_) => {}
|
||||
|
||||
ast::ItemTrait(_, _, ref bounds, _) => {
|
||||
hir::ItemTrait(_, _, ref bounds, _) => {
|
||||
if !self.trait_is_public(item.id) {
|
||||
return
|
||||
}
|
||||
@ -1249,7 +1250,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
// (i.e. we could just return here to not check them at
|
||||
// all, or some worse estimation of whether an impl is
|
||||
// publicly visible).
|
||||
ast::ItemImpl(_, _, ref g, ref trait_ref, ref self_, ref impl_items) => {
|
||||
hir::ItemImpl(_, _, ref g, ref trait_ref, ref self_, ref impl_items) => {
|
||||
// `impl [... for] Private` is never visible.
|
||||
let self_contains_private;
|
||||
// impl [... for] Public<...>, but not `impl [... for]
|
||||
@ -1293,12 +1294,11 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
impl_items.iter()
|
||||
.any(|impl_item| {
|
||||
match impl_item.node {
|
||||
ast::ConstImplItem(..) |
|
||||
ast::MethodImplItem(..) => {
|
||||
hir::ConstImplItem(..) |
|
||||
hir::MethodImplItem(..) => {
|
||||
self.exported_items.contains(&impl_item.id)
|
||||
}
|
||||
ast::TypeImplItem(_) |
|
||||
ast::MacImplItem(_) => false,
|
||||
hir::TypeImplItem(_) => false,
|
||||
}
|
||||
});
|
||||
|
||||
@ -1317,13 +1317,13 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
// don't erroneously report errors for private
|
||||
// types in private items.
|
||||
match impl_item.node {
|
||||
ast::ConstImplItem(..) |
|
||||
ast::MethodImplItem(..)
|
||||
hir::ConstImplItem(..) |
|
||||
hir::MethodImplItem(..)
|
||||
if self.item_is_public(&impl_item.id, impl_item.vis) =>
|
||||
{
|
||||
visit::walk_impl_item(self, impl_item)
|
||||
}
|
||||
ast::TypeImplItem(..) => {
|
||||
hir::TypeImplItem(..) => {
|
||||
visit::walk_impl_item(self, impl_item)
|
||||
}
|
||||
_ => {}
|
||||
@ -1348,7 +1348,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
|
||||
// Those in 3. are warned with this call.
|
||||
for impl_item in impl_items {
|
||||
if let ast::TypeImplItem(ref ty) = impl_item.node {
|
||||
if let hir::TypeImplItem(ref ty) = impl_item.node {
|
||||
self.visit_ty(ty);
|
||||
}
|
||||
}
|
||||
@ -1360,14 +1360,14 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
let mut found_pub_static = false;
|
||||
for impl_item in impl_items {
|
||||
match impl_item.node {
|
||||
ast::ConstImplItem(..) => {
|
||||
hir::ConstImplItem(..) => {
|
||||
if self.item_is_public(&impl_item.id, impl_item.vis) {
|
||||
found_pub_static = true;
|
||||
visit::walk_impl_item(self, impl_item);
|
||||
}
|
||||
}
|
||||
ast::MethodImplItem(ref sig, _) => {
|
||||
if sig.explicit_self.node == ast::SelfStatic &&
|
||||
hir::MethodImplItem(ref sig, _) => {
|
||||
if sig.explicit_self.node == hir::SelfStatic &&
|
||||
self.item_is_public(&impl_item.id, impl_item.vis) {
|
||||
found_pub_static = true;
|
||||
visit::walk_impl_item(self, impl_item);
|
||||
@ -1385,7 +1385,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
|
||||
// `type ... = ...;` can contain private types, because
|
||||
// we're introducing a new name.
|
||||
ast::ItemTy(..) => return,
|
||||
hir::ItemTy(..) => return,
|
||||
|
||||
// not at all public, so we don't care
|
||||
_ if !self.item_is_public(&item.id, item.vis) => {
|
||||
@ -1403,7 +1403,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
visit::walk_item(self, item);
|
||||
}
|
||||
|
||||
fn visit_generics(&mut self, generics: &ast::Generics) {
|
||||
fn visit_generics(&mut self, generics: &hir::Generics) {
|
||||
for ty_param in generics.ty_params.iter() {
|
||||
for bound in ty_param.bounds.iter() {
|
||||
self.check_ty_param_bound(bound)
|
||||
@ -1411,28 +1411,28 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
}
|
||||
for predicate in &generics.where_clause.predicates {
|
||||
match predicate {
|
||||
&ast::WherePredicate::BoundPredicate(ref bound_pred) => {
|
||||
&hir::WherePredicate::BoundPredicate(ref bound_pred) => {
|
||||
for bound in bound_pred.bounds.iter() {
|
||||
self.check_ty_param_bound(bound)
|
||||
}
|
||||
}
|
||||
&ast::WherePredicate::RegionPredicate(_) => {}
|
||||
&ast::WherePredicate::EqPredicate(ref eq_pred) => {
|
||||
&hir::WherePredicate::RegionPredicate(_) => {}
|
||||
&hir::WherePredicate::EqPredicate(ref eq_pred) => {
|
||||
self.visit_ty(&*eq_pred.ty);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_foreign_item(&mut self, item: &ast::ForeignItem) {
|
||||
fn visit_foreign_item(&mut self, item: &hir::ForeignItem) {
|
||||
if self.exported_items.contains(&item.id) {
|
||||
visit::walk_foreign_item(self, item)
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_ty(&mut self, t: &ast::Ty) {
|
||||
fn visit_ty(&mut self, t: &hir::Ty) {
|
||||
debug!("VisiblePrivateTypesVisitor checking ty {:?}", t);
|
||||
if let ast::TyPath(_, ref p) = t.node {
|
||||
if let hir::TyPath(_, ref p) = t.node {
|
||||
if !self.tcx.sess.features.borrow().visible_private_types &&
|
||||
self.path_is_private_type(t.id) {
|
||||
self.tcx.sess.span_err(p.span, "private type in exported type signature");
|
||||
@ -1441,7 +1441,7 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
visit::walk_ty(self, t)
|
||||
}
|
||||
|
||||
fn visit_variant(&mut self, v: &ast::Variant, g: &ast::Generics) {
|
||||
fn visit_variant(&mut self, v: &hir::Variant, g: &hir::Generics) {
|
||||
if self.exported_items.contains(&v.node.id) {
|
||||
self.in_variant = true;
|
||||
visit::walk_variant(self, v, g);
|
||||
@ -1449,9 +1449,9 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
fn visit_struct_field(&mut self, s: &ast::StructField) {
|
||||
fn visit_struct_field(&mut self, s: &hir::StructField) {
|
||||
match s.node.kind {
|
||||
ast::NamedField(_, vis) if vis == ast::Public || self.in_variant => {
|
||||
hir::NamedField(_, vis) if vis == hir::Public || self.in_variant => {
|
||||
visit::walk_struct_field(self, s);
|
||||
}
|
||||
_ => {}
|
||||
@ -1463,8 +1463,8 @@ impl<'a, 'tcx, 'v> Visitor<'v> for VisiblePrivateTypesVisitor<'a, 'tcx> {
|
||||
// expression/block context can't possibly contain exported things.
|
||||
// (Making them no-ops stops us from traversing the whole AST without
|
||||
// having to be super careful about our `walk_...` calls above.)
|
||||
fn visit_block(&mut self, _: &ast::Block) {}
|
||||
fn visit_expr(&mut self, _: &ast::Expr) {}
|
||||
fn visit_block(&mut self, _: &hir::Block) {}
|
||||
fn visit_expr(&mut self, _: &hir::Expr) {}
|
||||
}
|
||||
|
||||
pub fn check_crate(tcx: &ty::ctxt,
|
||||
|
@ -36,25 +36,25 @@ use rustc::metadata::decoder::{DefLike, DlDef, DlField, DlImpl};
|
||||
use rustc::middle::def::*;
|
||||
use rustc::middle::def_id::DefId;
|
||||
|
||||
use syntax::ast::{Block, Crate};
|
||||
use syntax::ast::{DeclItem};
|
||||
use syntax::ast::{ForeignItem, ForeignItemFn, ForeignItemStatic};
|
||||
use syntax::ast::{Item, ItemConst, ItemEnum, ItemExternCrate, ItemFn};
|
||||
use syntax::ast::{ItemForeignMod, ItemImpl, ItemMac, ItemMod, ItemStatic, ItemDefaultImpl};
|
||||
use syntax::ast::{ItemStruct, ItemTrait, ItemTy, ItemUse};
|
||||
use syntax::ast::{Name, NamedField, NodeId};
|
||||
use syntax::ast::{PathListIdent, PathListMod, Public};
|
||||
use syntax::ast::StmtDecl;
|
||||
use syntax::ast::StructVariantKind;
|
||||
use syntax::ast::TupleVariantKind;
|
||||
use syntax::ast::UnnamedField;
|
||||
use syntax::ast::{Variant, ViewPathGlob, ViewPathList, ViewPathSimple};
|
||||
use syntax::ast::Visibility;
|
||||
use syntax::ast;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use syntax::ast::{Name, NodeId};
|
||||
use syntax::parse::token::special_idents;
|
||||
use syntax::codemap::{Span, DUMMY_SP};
|
||||
use syntax::visit::{self, Visitor};
|
||||
|
||||
use rustc_front::hir;
|
||||
use rustc_front::hir::{Block, Crate, DeclItem};
|
||||
use rustc_front::hir::{ForeignItem, ForeignItemFn, ForeignItemStatic};
|
||||
use rustc_front::hir::{Item, ItemConst, ItemEnum, ItemExternCrate, ItemFn};
|
||||
use rustc_front::hir::{ItemForeignMod, ItemImpl, ItemMod, ItemStatic, ItemDefaultImpl};
|
||||
use rustc_front::hir::{ItemStruct, ItemTrait, ItemTy, ItemUse};
|
||||
use rustc_front::hir::{NamedField, PathListIdent, PathListMod, Public};
|
||||
use rustc_front::hir::StmtDecl;
|
||||
use rustc_front::hir::StructVariantKind;
|
||||
use rustc_front::hir::TupleVariantKind;
|
||||
use rustc_front::hir::UnnamedField;
|
||||
use rustc_front::hir::{Variant, ViewPathGlob, ViewPathList, ViewPathSimple};
|
||||
use rustc_front::hir::Visibility;
|
||||
use rustc_front::attr::AttrMetaMethods;
|
||||
use rustc_front::visit::{self, Visitor};
|
||||
|
||||
use std::mem::replace;
|
||||
use std::ops::{Deref, DerefMut};
|
||||
@ -107,7 +107,7 @@ impl<'a, 'b:'a, 'tcx:'b> DerefMut for GraphBuilder<'a, 'b, 'tcx> {
|
||||
|
||||
impl<'a, 'b:'a, 'tcx:'b> GraphBuilder<'a, 'b, 'tcx> {
|
||||
/// Constructs the reduced graph for the entire crate.
|
||||
fn build_reduced_graph(self, krate: &ast::Crate) {
|
||||
fn build_reduced_graph(self, krate: &hir::Crate) {
|
||||
let parent = self.graph_root.get_module();
|
||||
let mut visitor = BuildReducedGraphVisitor {
|
||||
builder: self,
|
||||
@ -265,7 +265,7 @@ impl<'a, 'b:'a, 'tcx:'b> GraphBuilder<'a, 'b, 'tcx> {
|
||||
fn build_reduced_graph_for_item(&mut self, item: &Item, parent: &Rc<Module>) -> Rc<Module> {
|
||||
let name = item.ident.name;
|
||||
let sp = item.span;
|
||||
let is_public = item.vis == ast::Public;
|
||||
let is_public = item.vis == hir::Public;
|
||||
let modifiers = if is_public {
|
||||
DefModifiers::PUBLIC
|
||||
} else {
|
||||
@ -426,7 +426,7 @@ impl<'a, 'b:'a, 'tcx:'b> GraphBuilder<'a, 'b, 'tcx> {
|
||||
// These items live in the value namespace.
|
||||
ItemStatic(_, m, _) => {
|
||||
let name_bindings = self.add_child(name, parent, ForbidDuplicateValues, sp);
|
||||
let mutbl = m == ast::MutMutable;
|
||||
let mutbl = m == hir::MutMutable;
|
||||
|
||||
name_bindings.define_value(DefStatic(DefId::local(item.id), mutbl), sp, modifiers);
|
||||
parent.clone()
|
||||
@ -545,17 +545,17 @@ impl<'a, 'b:'a, 'tcx:'b> GraphBuilder<'a, 'b, 'tcx> {
|
||||
trait_item.span);
|
||||
|
||||
match trait_item.node {
|
||||
ast::ConstTraitItem(..) => {
|
||||
hir::ConstTraitItem(..) => {
|
||||
let def = DefAssociatedConst(DefId::local(trait_item.id));
|
||||
// NB: not DefModifiers::IMPORTABLE
|
||||
name_bindings.define_value(def, trait_item.span, DefModifiers::PUBLIC);
|
||||
}
|
||||
ast::MethodTraitItem(..) => {
|
||||
hir::MethodTraitItem(..) => {
|
||||
let def = DefMethod(DefId::local(trait_item.id));
|
||||
// NB: not DefModifiers::IMPORTABLE
|
||||
name_bindings.define_value(def, trait_item.span, DefModifiers::PUBLIC);
|
||||
}
|
||||
ast::TypeTraitItem(..) => {
|
||||
hir::TypeTraitItem(..) => {
|
||||
let def = DefAssociatedTy(DefId::local(item.id),
|
||||
DefId::local(trait_item.id));
|
||||
// NB: not DefModifiers::IMPORTABLE
|
||||
@ -570,7 +570,6 @@ impl<'a, 'b:'a, 'tcx:'b> GraphBuilder<'a, 'b, 'tcx> {
|
||||
name_bindings.define_type(DefTrait(def_id), sp, modifiers);
|
||||
parent.clone()
|
||||
}
|
||||
ItemMac(..) => parent.clone()
|
||||
}
|
||||
}
|
||||
|
||||
@ -608,7 +607,7 @@ impl<'a, 'b:'a, 'tcx:'b> GraphBuilder<'a, 'b, 'tcx> {
|
||||
foreign_item: &ForeignItem,
|
||||
parent: &Rc<Module>) {
|
||||
let name = foreign_item.ident.name;
|
||||
let is_public = foreign_item.vis == ast::Public;
|
||||
let is_public = foreign_item.vis == hir::Public;
|
||||
let modifiers = if is_public {
|
||||
DefModifiers::PUBLIC
|
||||
} else {
|
||||
@ -660,7 +659,7 @@ impl<'a, 'b:'a, 'tcx:'b> GraphBuilder<'a, 'b, 'tcx> {
|
||||
debug!("(building reduced graph for \
|
||||
external crate) building external def {}, priv {:?}",
|
||||
final_ident, vis);
|
||||
let is_public = vis == ast::Public;
|
||||
let is_public = vis == hir::Public;
|
||||
let modifiers = if is_public {
|
||||
DefModifiers::PUBLIC
|
||||
} else {
|
||||
@ -1001,7 +1000,7 @@ impl<'a, 'b, 'v, 'tcx> Visitor<'v> for BuildReducedGraphVisitor<'a, 'b, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn build_reduced_graph(resolver: &mut Resolver, krate: &ast::Crate) {
|
||||
pub fn build_reduced_graph(resolver: &mut Resolver, krate: &hir::Crate) {
|
||||
GraphBuilder {
|
||||
resolver: resolver
|
||||
}.build_reduced_graph(krate);
|
||||
|
@ -25,9 +25,11 @@ use Namespace::{TypeNS, ValueNS};
|
||||
use rustc::lint;
|
||||
use rustc::middle::privacy::{DependsOn, LastImport, Used, Unused};
|
||||
use syntax::ast;
|
||||
use syntax::ast::{ViewPathGlob, ViewPathList, ViewPathSimple};
|
||||
use syntax::codemap::{Span, DUMMY_SP};
|
||||
use syntax::visit::{self, Visitor};
|
||||
|
||||
use rustc_front::hir;
|
||||
use rustc_front::hir::{ViewPathGlob, ViewPathList, ViewPathSimple};
|
||||
use rustc_front::visit::{self, Visitor};
|
||||
|
||||
struct UnusedImportCheckVisitor<'a, 'b:'a, 'tcx:'b> {
|
||||
resolver: &'a mut Resolver<'b, 'tcx>
|
||||
@ -110,18 +112,18 @@ impl<'a, 'b, 'tcx> UnusedImportCheckVisitor<'a, 'b, 'tcx> {
|
||||
}
|
||||
|
||||
impl<'a, 'b, 'v, 'tcx> Visitor<'v> for UnusedImportCheckVisitor<'a, 'b, 'tcx> {
|
||||
fn visit_item(&mut self, item: &ast::Item) {
|
||||
fn visit_item(&mut self, item: &hir::Item) {
|
||||
// Ignore is_public import statements because there's no way to be sure
|
||||
// whether they're used or not. Also ignore imports with a dummy span
|
||||
// because this means that they were generated in some fashion by the
|
||||
// compiler and we don't need to consider them.
|
||||
if item.vis == ast::Public || item.span == DUMMY_SP {
|
||||
if item.vis == hir::Public || item.span == DUMMY_SP {
|
||||
visit::walk_item(self, item);
|
||||
return;
|
||||
}
|
||||
|
||||
match item.node {
|
||||
ast::ItemExternCrate(_) => {
|
||||
hir::ItemExternCrate(_) => {
|
||||
if let Some(crate_num) = self.session.cstore.find_extern_mod_stmt_cnum(item.id) {
|
||||
if !self.used_crates.contains(&crate_num) {
|
||||
self.session.add_lint(lint::builtin::UNUSED_EXTERN_CRATES,
|
||||
@ -131,7 +133,7 @@ impl<'a, 'b, 'v, 'tcx> Visitor<'v> for UnusedImportCheckVisitor<'a, 'b, 'tcx> {
|
||||
}
|
||||
}
|
||||
},
|
||||
ast::ItemUse(ref p) => {
|
||||
hir::ItemUse(ref p) => {
|
||||
match p.node {
|
||||
ViewPathSimple(_, _) => {
|
||||
self.finalize_import(item.id, p.span)
|
||||
@ -161,7 +163,7 @@ impl<'a, 'b, 'v, 'tcx> Visitor<'v> for UnusedImportCheckVisitor<'a, 'b, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn check_crate(resolver: &mut Resolver, krate: &ast::Crate) {
|
||||
pub fn check_crate(resolver: &mut Resolver, krate: &hir::Crate) {
|
||||
let mut visitor = UnusedImportCheckVisitor { resolver: resolver };
|
||||
visit::walk_crate(&mut visitor, krate);
|
||||
}
|
||||
|
@ -30,6 +30,7 @@
|
||||
#[macro_use] extern crate log;
|
||||
#[macro_use] extern crate syntax;
|
||||
#[macro_use] #[no_link] extern crate rustc_bitflags;
|
||||
extern crate rustc_front;
|
||||
|
||||
extern crate rustc;
|
||||
|
||||
@ -50,7 +51,7 @@ use self::ParentLink::*;
|
||||
use self::ModuleKind::*;
|
||||
use self::FallbackChecks::*;
|
||||
|
||||
use rustc::ast_map;
|
||||
use rustc::front::map as hir_map;
|
||||
use rustc::session::Session;
|
||||
use rustc::lint;
|
||||
use rustc::metadata::csearch;
|
||||
@ -64,31 +65,34 @@ use rustc::middle::ty::{Freevar, FreevarMap, TraitMap, GlobMap};
|
||||
use rustc::util::nodemap::{NodeMap, NodeSet, DefIdSet, FnvHashMap};
|
||||
use rustc::util::lev_distance::lev_distance;
|
||||
|
||||
use syntax::ast::{Arm, BindByRef, BindByValue, BindingMode, Block};
|
||||
use syntax::ast::{ConstImplItem, Crate, CrateNum};
|
||||
use syntax::ast::{Expr, ExprAgain, ExprBreak, ExprField};
|
||||
use syntax::ast::{ExprLoop, ExprWhile, ExprMethodCall};
|
||||
use syntax::ast::{ExprPath, ExprStruct, FnDecl};
|
||||
use syntax::ast::{ForeignItemFn, ForeignItemStatic, Generics};
|
||||
use syntax::ast::{Ident, ImplItem, Item, ItemConst, ItemEnum, ItemExternCrate};
|
||||
use syntax::ast::{ItemFn, ItemForeignMod, ItemImpl, ItemMac, ItemMod, ItemStatic, ItemDefaultImpl};
|
||||
use syntax::ast::{ItemStruct, ItemTrait, ItemTy, ItemUse};
|
||||
use syntax::ast::{Local, MethodImplItem, Name, NodeId};
|
||||
use syntax::ast::{Pat, PatEnum, PatIdent, PatLit, PatQPath};
|
||||
use syntax::ast::{PatRange, PatStruct, Path, PrimTy};
|
||||
use syntax::ast::{TraitRef, Ty, TyBool, TyChar, TyF32};
|
||||
use syntax::ast::{TyF64, TyFloat, TyIs, TyI8, TyI16, TyI32, TyI64, TyInt};
|
||||
use syntax::ast::{TyPath, TyPtr};
|
||||
use syntax::ast::{TyRptr, TyStr, TyUs, TyU8, TyU16, TyU32, TyU64, TyUint};
|
||||
use syntax::ast::TypeImplItem;
|
||||
use syntax::ast;
|
||||
use syntax::ast_util::{walk_pat};
|
||||
use syntax::ast::{Ident, Name, NodeId, CrateNum};
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use syntax::ext::mtwt;
|
||||
use syntax::parse::token::{self, special_names, special_idents};
|
||||
use syntax::ptr::P;
|
||||
use syntax::codemap::{self, Span, Pos};
|
||||
use syntax::visit::{self, FnKind, Visitor};
|
||||
|
||||
use rustc_front::visit::{self, FnKind, Visitor};
|
||||
use rustc_front::hir;
|
||||
use rustc_front::hir::{Arm, BindByRef, BindByValue, BindingMode, Block};
|
||||
use rustc_front::hir::{ConstImplItem, Crate};
|
||||
use rustc_front::hir::{Expr, ExprAgain, ExprBreak, ExprField};
|
||||
use rustc_front::hir::{ExprLoop, ExprWhile, ExprMethodCall};
|
||||
use rustc_front::hir::{ExprPath, ExprStruct, FnDecl};
|
||||
use rustc_front::hir::{ForeignItemFn, ForeignItemStatic, Generics};
|
||||
use rustc_front::hir::{ImplItem, Item, ItemConst, ItemEnum, ItemExternCrate};
|
||||
use rustc_front::hir::{ItemFn, ItemForeignMod, ItemImpl, ItemMod, ItemStatic, ItemDefaultImpl};
|
||||
use rustc_front::hir::{ItemStruct, ItemTrait, ItemTy, ItemUse};
|
||||
use rustc_front::hir::{Local, MethodImplItem};
|
||||
use rustc_front::hir::{Pat, PatEnum, PatIdent, PatLit, PatQPath};
|
||||
use rustc_front::hir::{PatRange, PatStruct, Path, PrimTy};
|
||||
use rustc_front::hir::{TraitRef, Ty, TyBool, TyChar, TyF32};
|
||||
use rustc_front::hir::{TyF64, TyFloat, TyIs, TyI8, TyI16, TyI32, TyI64, TyInt};
|
||||
use rustc_front::hir::{TyPath, TyPtr};
|
||||
use rustc_front::hir::{TyRptr, TyStr, TyUs, TyU8, TyU16, TyU32, TyU64, TyUint};
|
||||
use rustc_front::hir::TypeImplItem;
|
||||
use rustc_front::util::walk_pat;
|
||||
|
||||
use std::collections::{HashMap, HashSet};
|
||||
use std::collections::hash_map::Entry::{Occupied, Vacant};
|
||||
@ -457,22 +461,22 @@ enum NameDefinition {
|
||||
|
||||
impl<'a, 'v, 'tcx> Visitor<'v> for Resolver<'a, 'tcx> {
|
||||
fn visit_item(&mut self, item: &Item) {
|
||||
execute_callback!(ast_map::Node::NodeItem(item), self);
|
||||
execute_callback!(hir_map::Node::NodeItem(item), self);
|
||||
self.resolve_item(item);
|
||||
}
|
||||
fn visit_arm(&mut self, arm: &Arm) {
|
||||
self.resolve_arm(arm);
|
||||
}
|
||||
fn visit_block(&mut self, block: &Block) {
|
||||
execute_callback!(ast_map::Node::NodeBlock(block), self);
|
||||
execute_callback!(hir_map::Node::NodeBlock(block), self);
|
||||
self.resolve_block(block);
|
||||
}
|
||||
fn visit_expr(&mut self, expr: &Expr) {
|
||||
execute_callback!(ast_map::Node::NodeExpr(expr), self);
|
||||
execute_callback!(hir_map::Node::NodeExpr(expr), self);
|
||||
self.resolve_expr(expr);
|
||||
}
|
||||
fn visit_local(&mut self, local: &Local) {
|
||||
execute_callback!(ast_map::Node::NodeLocal(&*local.pat), self);
|
||||
execute_callback!(hir_map::Node::NodeLocal(&*local.pat), self);
|
||||
self.resolve_local(local);
|
||||
}
|
||||
fn visit_ty(&mut self, ty: &Ty) {
|
||||
@ -482,16 +486,16 @@ impl<'a, 'v, 'tcx> Visitor<'v> for Resolver<'a, 'tcx> {
|
||||
self.resolve_generics(generics);
|
||||
}
|
||||
fn visit_poly_trait_ref(&mut self,
|
||||
tref: &ast::PolyTraitRef,
|
||||
m: &ast::TraitBoundModifier) {
|
||||
tref: &hir::PolyTraitRef,
|
||||
m: &hir::TraitBoundModifier) {
|
||||
match self.resolve_trait_reference(tref.trait_ref.ref_id, &tref.trait_ref.path, 0) {
|
||||
Ok(def) => self.record_def(tref.trait_ref.ref_id, def),
|
||||
Err(_) => { /* error already reported */ }
|
||||
}
|
||||
visit::walk_poly_trait_ref(self, tref, m);
|
||||
}
|
||||
fn visit_variant(&mut self, variant: &ast::Variant, generics: &Generics) {
|
||||
execute_callback!(ast_map::Node::NodeVariant(variant), self);
|
||||
fn visit_variant(&mut self, variant: &hir::Variant, generics: &Generics) {
|
||||
execute_callback!(hir_map::Node::NodeVariant(variant), self);
|
||||
if let Some(ref dis_expr) = variant.node.disr_expr {
|
||||
// resolve the discriminator expr as a constant
|
||||
self.with_constant_rib(|this| {
|
||||
@ -501,12 +505,12 @@ impl<'a, 'v, 'tcx> Visitor<'v> for Resolver<'a, 'tcx> {
|
||||
|
||||
// `visit::walk_variant` without the discriminant expression.
|
||||
match variant.node.kind {
|
||||
ast::TupleVariantKind(ref variant_arguments) => {
|
||||
hir::TupleVariantKind(ref variant_arguments) => {
|
||||
for variant_argument in variant_arguments {
|
||||
self.visit_ty(&*variant_argument.ty);
|
||||
}
|
||||
}
|
||||
ast::StructVariantKind(ref struct_definition) => {
|
||||
hir::StructVariantKind(ref struct_definition) => {
|
||||
self.visit_struct_def(&**struct_definition,
|
||||
variant.node.name,
|
||||
generics,
|
||||
@ -514,8 +518,8 @@ impl<'a, 'v, 'tcx> Visitor<'v> for Resolver<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
}
|
||||
fn visit_foreign_item(&mut self, foreign_item: &ast::ForeignItem) {
|
||||
execute_callback!(ast_map::Node::NodeForeignItem(foreign_item), self);
|
||||
fn visit_foreign_item(&mut self, foreign_item: &hir::ForeignItem) {
|
||||
execute_callback!(hir_map::Node::NodeForeignItem(foreign_item), self);
|
||||
let type_parameters = match foreign_item.node {
|
||||
ForeignItemFn(_, ref generics) => {
|
||||
HasTypeParameters(generics, FnSpace, ItemRibKind)
|
||||
@ -1113,7 +1117,7 @@ impl PrimitiveTypeTable {
|
||||
pub struct Resolver<'a, 'tcx:'a> {
|
||||
session: &'a Session,
|
||||
|
||||
ast_map: &'a ast_map::Map<'tcx>,
|
||||
ast_map: &'a hir_map::Map<'tcx>,
|
||||
|
||||
graph_root: NameBindings,
|
||||
|
||||
@ -1167,7 +1171,7 @@ pub struct Resolver<'a, 'tcx:'a> {
|
||||
used_crates: HashSet<CrateNum>,
|
||||
|
||||
// Callback function for intercepting walks
|
||||
callback: Option<Box<Fn(ast_map::Node, &mut bool) -> bool>>,
|
||||
callback: Option<Box<Fn(hir_map::Node, &mut bool) -> bool>>,
|
||||
// The intention is that the callback modifies this flag.
|
||||
// Once set, the resolver falls out of the walk, preserving the ribs.
|
||||
resolved: bool,
|
||||
@ -1182,7 +1186,7 @@ enum FallbackChecks {
|
||||
|
||||
impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
fn new(session: &'a Session,
|
||||
ast_map: &'a ast_map::Map<'tcx>,
|
||||
ast_map: &'a hir_map::Map<'tcx>,
|
||||
crate_span: Span,
|
||||
make_glob_map: MakeGlobMap) -> Resolver<'a, 'tcx> {
|
||||
let graph_root = NameBindings::new();
|
||||
@ -2094,7 +2098,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
None
|
||||
}
|
||||
|
||||
fn resolve_crate(&mut self, krate: &ast::Crate) {
|
||||
fn resolve_crate(&mut self, krate: &hir::Crate) {
|
||||
debug!("(resolving crate) starting");
|
||||
|
||||
visit::walk_crate(self, krate);
|
||||
@ -2161,7 +2165,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
|
||||
for trait_item in trait_items {
|
||||
match trait_item.node {
|
||||
ast::ConstTraitItem(_, ref default) => {
|
||||
hir::ConstTraitItem(_, ref default) => {
|
||||
// Only impose the restrictions of
|
||||
// ConstRibKind if there's an actual constant
|
||||
// expression in a provided default.
|
||||
@ -2173,7 +2177,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
visit::walk_trait_item(this, trait_item)
|
||||
}
|
||||
}
|
||||
ast::MethodTraitItem(ref sig, _) => {
|
||||
hir::MethodTraitItem(ref sig, _) => {
|
||||
let type_parameters =
|
||||
HasTypeParameters(&sig.generics,
|
||||
FnSpace,
|
||||
@ -2182,7 +2186,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
visit::walk_trait_item(this, trait_item)
|
||||
});
|
||||
}
|
||||
ast::TypeTraitItem(..) => {
|
||||
hir::TypeTraitItem(..) => {
|
||||
this.check_if_primitive_type_name(trait_item.ident.name,
|
||||
trait_item.span);
|
||||
this.with_type_parameter_rib(NoTypeParameters, |this| {
|
||||
@ -2209,7 +2213,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
|
||||
ItemUse(ref view_path) => {
|
||||
// check for imports shadowing primitive types
|
||||
if let ast::ViewPathSimple(ident, _) = view_path.node {
|
||||
if let hir::ViewPathSimple(ident, _) = view_path.node {
|
||||
match self.def_map.borrow().get(&item.id).map(|d| d.full_def()) {
|
||||
Some(DefTy(..)) | Some(DefStruct(..)) | Some(DefTrait(..)) | None => {
|
||||
self.check_if_primitive_type_name(ident.name, item.span);
|
||||
@ -2219,7 +2223,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
}
|
||||
}
|
||||
|
||||
ItemExternCrate(_) | ItemMac(..) => {
|
||||
ItemExternCrate(_) => {
|
||||
// do nothing, these are just around to be encoded
|
||||
}
|
||||
}
|
||||
@ -2363,9 +2367,9 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
}
|
||||
for predicate in &generics.where_clause.predicates {
|
||||
match predicate {
|
||||
&ast::WherePredicate::BoundPredicate(_) |
|
||||
&ast::WherePredicate::RegionPredicate(_) => {}
|
||||
&ast::WherePredicate::EqPredicate(ref eq_pred) => {
|
||||
&hir::WherePredicate::BoundPredicate(_) |
|
||||
&hir::WherePredicate::RegionPredicate(_) => {}
|
||||
&hir::WherePredicate::EqPredicate(ref eq_pred) => {
|
||||
let path_res = self.resolve_path(eq_pred.id, &eq_pred.path, 0, TypeNS, true);
|
||||
if let Some(PathResolution { base_def: DefTyParam(..), .. }) = path_res {
|
||||
self.record_def(eq_pred.id, path_res.unwrap());
|
||||
@ -2488,7 +2492,6 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
|
||||
this.visit_ty(ty);
|
||||
}
|
||||
ast::MacImplItem(_) => {}
|
||||
}
|
||||
}
|
||||
});
|
||||
@ -2618,8 +2621,8 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
// Check for imports appearing after non-item statements.
|
||||
let mut found_non_item = false;
|
||||
for statement in &block.stmts {
|
||||
if let ast::StmtDecl(ref declaration, _) = statement.node {
|
||||
if let ast::DeclItem(ref i) = declaration.node {
|
||||
if let hir::StmtDecl(ref declaration, _) = statement.node {
|
||||
if let hir::DeclItem(ref i) = declaration.node {
|
||||
match i.node {
|
||||
ItemExternCrate(_) | ItemUse(_) if found_non_item => {
|
||||
span_err!(self.session, i.span, E0154,
|
||||
@ -3039,7 +3042,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
/// Handles paths that may refer to associated items
|
||||
fn resolve_possibly_assoc_item(&mut self,
|
||||
id: NodeId,
|
||||
maybe_qself: Option<&ast::QSelf>,
|
||||
maybe_qself: Option<&hir::QSelf>,
|
||||
path: &Path,
|
||||
namespace: Namespace,
|
||||
check_ribs: bool)
|
||||
@ -3228,7 +3231,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
// resolve a "module-relative" path, e.g. a::b::c
|
||||
fn resolve_module_relative_path(&mut self,
|
||||
span: Span,
|
||||
segments: &[ast::PathSegment],
|
||||
segments: &[hir::PathSegment],
|
||||
namespace: Namespace)
|
||||
-> Option<(Def, LastPrivate)> {
|
||||
let module_path = segments.split_last().unwrap().1.iter()
|
||||
@ -3285,7 +3288,7 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
/// import resolution.
|
||||
fn resolve_crate_relative_path(&mut self,
|
||||
span: Span,
|
||||
segments: &[ast::PathSegment],
|
||||
segments: &[hir::PathSegment],
|
||||
namespace: Namespace)
|
||||
-> Option<(Def, LastPrivate)> {
|
||||
let module_path = segments.split_last().unwrap().1.iter()
|
||||
@ -3469,17 +3472,17 @@ impl<'a, 'tcx> Resolver<'a, 'tcx> {
|
||||
fn is_static_method(this: &Resolver, did: DefId) -> bool {
|
||||
if did.is_local() {
|
||||
let sig = match this.ast_map.get(did.node) {
|
||||
ast_map::NodeTraitItem(trait_item) => match trait_item.node {
|
||||
ast::MethodTraitItem(ref sig, _) => sig,
|
||||
hir_map::NodeTraitItem(trait_item) => match trait_item.node {
|
||||
hir::MethodTraitItem(ref sig, _) => sig,
|
||||
_ => return false
|
||||
},
|
||||
ast_map::NodeImplItem(impl_item) => match impl_item.node {
|
||||
ast::MethodImplItem(ref sig, _) => sig,
|
||||
hir_map::NodeImplItem(impl_item) => match impl_item.node {
|
||||
hir::MethodImplItem(ref sig, _) => sig,
|
||||
_ => return false
|
||||
},
|
||||
_ => return false
|
||||
};
|
||||
sig.explicit_self.node == ast::SelfStatic
|
||||
sig.explicit_self.node == hir::SelfStatic
|
||||
} else {
|
||||
csearch::is_static_method(&this.session.cstore, did)
|
||||
}
|
||||
@ -4024,7 +4027,7 @@ pub enum MakeGlobMap {
|
||||
|
||||
/// Entry point to crate resolution.
|
||||
pub fn resolve_crate<'a, 'tcx>(session: &'a Session,
|
||||
ast_map: &'a ast_map::Map<'tcx>,
|
||||
ast_map: &'a hir_map::Map<'tcx>,
|
||||
make_glob_map: MakeGlobMap)
|
||||
-> CrateMap {
|
||||
let krate = ast_map.krate();
|
||||
@ -4058,10 +4061,10 @@ pub fn resolve_crate<'a, 'tcx>(session: &'a Session,
|
||||
/// calls to be made with the correct scope info. The node in the
|
||||
/// callback corresponds to the current node in the walk.
|
||||
pub fn create_resolver<'a, 'tcx>(session: &'a Session,
|
||||
ast_map: &'a ast_map::Map<'tcx>,
|
||||
ast_map: &'a hir_map::Map<'tcx>,
|
||||
krate: &'a Crate,
|
||||
make_glob_map: MakeGlobMap,
|
||||
callback: Option<Box<Fn(ast_map::Node, &mut bool) -> bool>>)
|
||||
callback: Option<Box<Fn(hir_map::Node, &mut bool) -> bool>>)
|
||||
-> Resolver<'a, 'tcx> {
|
||||
let mut resolver = Resolver::new(session, ast_map, krate.span, make_glob_map);
|
||||
|
||||
|
@ -25,7 +25,7 @@ use metadata::loader::METADATA_FILENAME;
|
||||
use metadata::{encoder, cstore, filesearch, csearch, creader};
|
||||
use middle::dependency_format::Linkage;
|
||||
use middle::ty::{self, Ty};
|
||||
use rustc::ast_map::{PathElem, PathElems, PathName};
|
||||
use rustc::front::map::{PathElem, PathElems, PathName};
|
||||
use trans::{CrateContext, CrateTranslation, gensym_name};
|
||||
use util::common::time;
|
||||
use util::sha2::{Digest, Sha256};
|
||||
@ -43,9 +43,12 @@ use std::str;
|
||||
use flate;
|
||||
use serialize::hex::ToHex;
|
||||
use syntax::ast;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::parse::token;
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use rustc_front::attr::AttrMetaMethods as FrontAttrMetaMethods;
|
||||
|
||||
use rustc_front::hir;
|
||||
|
||||
// RLIB LLVM-BYTECODE OBJECT LAYOUT
|
||||
// Version 1
|
||||
@ -178,7 +181,7 @@ pub fn find_crate_name(sess: Option<&Session>,
|
||||
"rust_out".to_string()
|
||||
}
|
||||
|
||||
pub fn build_link_meta(sess: &Session, krate: &ast::Crate,
|
||||
pub fn build_link_meta(sess: &Session, krate: &hir::Crate,
|
||||
name: String) -> LinkMeta {
|
||||
let r = LinkMeta {
|
||||
crate_name: name,
|
||||
|
@ -53,6 +53,7 @@ extern crate graphviz;
|
||||
extern crate libc;
|
||||
extern crate rustc;
|
||||
extern crate rustc_back;
|
||||
extern crate rustc_front;
|
||||
extern crate rustc_llvm as llvm;
|
||||
extern crate rustc_platform_intrinsics as intrinsics;
|
||||
extern crate serialize;
|
||||
|
@ -47,6 +47,8 @@ use syntax::visit::{self, Visitor};
|
||||
use syntax::print::pprust::{path_to_string, ty_to_string};
|
||||
use syntax::ptr::P;
|
||||
|
||||
use rustc_front::lowering::lower_expr;
|
||||
|
||||
use super::span_utils::SpanUtils;
|
||||
use super::recorder::{Recorder, FmtStrs};
|
||||
|
||||
@ -1074,8 +1076,9 @@ impl<'l, 'tcx, 'v> Visitor<'v> for DumpCsvVisitor<'l, 'tcx> {
|
||||
visit::walk_expr(self, ex);
|
||||
}
|
||||
ast::ExprStruct(ref path, ref fields, ref base) => {
|
||||
let adt = self.tcx.expr_ty(ex).ty_adt_def().unwrap();
|
||||
let def = self.tcx.resolve_expr(ex);
|
||||
let hir_expr = lower_expr(ex);
|
||||
let adt = self.tcx.expr_ty(&hir_expr).ty_adt_def().unwrap();
|
||||
let def = self.tcx.resolve_expr(&hir_expr);
|
||||
self.process_struct_lit(ex,
|
||||
path,
|
||||
fields,
|
||||
@ -1106,7 +1109,8 @@ impl<'l, 'tcx, 'v> Visitor<'v> for DumpCsvVisitor<'l, 'tcx> {
|
||||
|
||||
self.visit_expr(&**sub_ex);
|
||||
|
||||
let ty = &self.tcx.expr_ty_adjusted(&**sub_ex).sty;
|
||||
let hir_node = self.tcx.map.expect_expr(sub_ex.id);
|
||||
let ty = &self.tcx.expr_ty_adjusted(&hir_node).sty;
|
||||
match *ty {
|
||||
ty::TyStruct(def, _) => {
|
||||
let sub_span = self.span.sub_span_after_token(ex.span, token::Dot);
|
||||
|
@ -16,9 +16,11 @@ use std::env;
|
||||
use std::fs::{self, File};
|
||||
use std::path::{Path, PathBuf};
|
||||
|
||||
use rustc::ast_map::NodeItem;
|
||||
use rustc_front;
|
||||
use rustc::front::map::NodeItem;
|
||||
use rustc_front::hir;
|
||||
|
||||
use syntax::{attr};
|
||||
use syntax::attr;
|
||||
use syntax::ast::{self, NodeId};
|
||||
use syntax::ast_util;
|
||||
use syntax::codemap::*;
|
||||
@ -356,9 +358,9 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
||||
Some(impl_id) => match self.tcx.map.get(impl_id.node) {
|
||||
NodeItem(item) => {
|
||||
match item.node {
|
||||
ast::ItemImpl(_, _, _, _, ref ty, _) => {
|
||||
hir::ItemImpl(_, _, _, _, ref ty, _) => {
|
||||
let mut result = String::from("<");
|
||||
result.push_str(&ty_to_string(&**ty));
|
||||
result.push_str(&rustc_front::print::pprust::ty_to_string(&**ty));
|
||||
|
||||
match self.tcx.trait_of_item(DefId::local(id)) {
|
||||
Some(def_id) => {
|
||||
@ -446,7 +448,8 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
||||
pub fn get_expr_data(&self, expr: &ast::Expr) -> Option<Data> {
|
||||
match expr.node {
|
||||
ast::ExprField(ref sub_ex, ident) => {
|
||||
let ty = &self.tcx.expr_ty_adjusted(&sub_ex).sty;
|
||||
let hir_node = self.tcx.map.expect_expr(sub_ex.id);
|
||||
let ty = &self.tcx.expr_ty_adjusted(&hir_node).sty;
|
||||
match *ty {
|
||||
ty::TyStruct(def, _) => {
|
||||
let f = def.struct_variant().field_named(ident.node.name);
|
||||
@ -465,7 +468,8 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
||||
}
|
||||
}
|
||||
ast::ExprStruct(ref path, _, _) => {
|
||||
let ty = &self.tcx.expr_ty_adjusted(expr).sty;
|
||||
let hir_node = self.tcx.map.expect_expr(expr.id);
|
||||
let ty = &self.tcx.expr_ty_adjusted(hir_node).sty;
|
||||
match *ty {
|
||||
ty::TyStruct(def, _) => {
|
||||
let sub_span = self.span_utils.span_for_last_ident(path.span);
|
||||
@ -605,7 +609,7 @@ impl<'l, 'tcx: 'l> SaveContext<'l, 'tcx> {
|
||||
}
|
||||
|
||||
let trait_item = self.tcx.map.expect_trait_item(def_id.node);
|
||||
if let ast::TraitItem_::MethodTraitItem(_, Some(_)) = trait_item.node {
|
||||
if let hir::TraitItem_::MethodTraitItem(_, Some(_)) = trait_item.node {
|
||||
true
|
||||
} else {
|
||||
false
|
||||
@ -705,9 +709,9 @@ impl<'v> Visitor<'v> for PathCollector {
|
||||
}
|
||||
|
||||
pub fn process_crate(tcx: &ty::ctxt,
|
||||
krate: &ast::Crate,
|
||||
analysis: &ty::CrateAnalysis,
|
||||
odir: Option<&Path>) {
|
||||
let krate = tcx.map.krate();
|
||||
if generated_code(krate.span) {
|
||||
return;
|
||||
}
|
||||
|
@ -224,14 +224,14 @@ use std;
|
||||
use std::cmp::Ordering;
|
||||
use std::fmt;
|
||||
use std::rc::Rc;
|
||||
use syntax::ast;
|
||||
use syntax::ast::{DUMMY_NODE_ID, NodeId};
|
||||
use rustc_front::hir;
|
||||
use syntax::ast::{self, DUMMY_NODE_ID, NodeId};
|
||||
use syntax::codemap::Span;
|
||||
use syntax::fold::Folder;
|
||||
use rustc_front::fold::Folder;
|
||||
use syntax::ptr::P;
|
||||
|
||||
#[derive(Copy, Clone, Debug)]
|
||||
struct ConstantExpr<'a>(&'a ast::Expr);
|
||||
struct ConstantExpr<'a>(&'a hir::Expr);
|
||||
|
||||
impl<'a> ConstantExpr<'a> {
|
||||
fn eq(self, other: ConstantExpr<'a>, tcx: &ty::ctxt) -> bool {
|
||||
@ -379,7 +379,7 @@ type BindingsMap<'tcx> = FnvHashMap<ast::Ident, BindingInfo<'tcx>>;
|
||||
|
||||
struct ArmData<'p, 'blk, 'tcx: 'blk> {
|
||||
bodycx: Block<'blk, 'tcx>,
|
||||
arm: &'p ast::Arm,
|
||||
arm: &'p hir::Arm,
|
||||
bindings_map: BindingsMap<'tcx>
|
||||
}
|
||||
|
||||
@ -388,7 +388,7 @@ struct ArmData<'p, 'blk, 'tcx: 'blk> {
|
||||
/// As we proceed `bound_ptrs` are filled with pointers to values to be bound,
|
||||
/// these pointers are stored in llmatch variables just before executing `data` arm.
|
||||
struct Match<'a, 'p: 'a, 'blk: 'a, 'tcx: 'blk> {
|
||||
pats: Vec<&'p ast::Pat>,
|
||||
pats: Vec<&'p hir::Pat>,
|
||||
data: &'a ArmData<'p, 'blk, 'tcx>,
|
||||
bound_ptrs: Vec<(ast::Ident, ValueRef)>,
|
||||
// Thread along renamings done by the check_match::StaticInliner, so we can
|
||||
@ -410,7 +410,7 @@ impl<'a, 'p, 'blk, 'tcx> fmt::Debug for Match<'a, 'p, 'blk, 'tcx> {
|
||||
fn has_nested_bindings(m: &[Match], col: usize) -> bool {
|
||||
for br in m {
|
||||
match br.pats[col].node {
|
||||
ast::PatIdent(_, _, Some(_)) => return true,
|
||||
hir::PatIdent(_, _, Some(_)) => return true,
|
||||
_ => ()
|
||||
}
|
||||
}
|
||||
@ -463,7 +463,7 @@ fn expand_nested_bindings<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
let mut pat = br.pats[col];
|
||||
loop {
|
||||
pat = match pat.node {
|
||||
ast::PatIdent(_, ref path, Some(ref inner)) => {
|
||||
hir::PatIdent(_, ref path, Some(ref inner)) => {
|
||||
bound_ptrs.push((path.node, val.val));
|
||||
&**inner
|
||||
},
|
||||
@ -489,7 +489,7 @@ fn enter_match<'a, 'b, 'p, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>,
|
||||
val: MatchInput,
|
||||
mut e: F)
|
||||
-> Vec<Match<'a, 'p, 'blk, 'tcx>> where
|
||||
F: FnMut(&[&'p ast::Pat]) -> Option<Vec<&'p ast::Pat>>,
|
||||
F: FnMut(&[&'p hir::Pat]) -> Option<Vec<&'p hir::Pat>>,
|
||||
{
|
||||
debug!("enter_match(bcx={}, m={:?}, col={}, val={})",
|
||||
bcx.to_str(),
|
||||
@ -503,13 +503,13 @@ fn enter_match<'a, 'b, 'p, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>,
|
||||
let this = br.pats[col];
|
||||
let mut bound_ptrs = br.bound_ptrs.clone();
|
||||
match this.node {
|
||||
ast::PatIdent(_, ref path, None) => {
|
||||
hir::PatIdent(_, ref path, None) => {
|
||||
if pat_is_binding(dm, &*this) {
|
||||
bound_ptrs.push((path.node, val.val));
|
||||
}
|
||||
}
|
||||
ast::PatVec(ref before, Some(ref slice), ref after) => {
|
||||
if let ast::PatIdent(_, ref path, None) = slice.node {
|
||||
hir::PatVec(ref before, Some(ref slice), ref after) => {
|
||||
if let hir::PatIdent(_, ref path, None) = slice.node {
|
||||
let subslice_val = bind_subslice_pat(
|
||||
bcx, this.id, val,
|
||||
before.len(), after.len());
|
||||
@ -648,10 +648,10 @@ fn get_branches<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
};
|
||||
|
||||
let opt = match cur.node {
|
||||
ast::PatLit(ref l) => {
|
||||
hir::PatLit(ref l) => {
|
||||
ConstantValue(ConstantExpr(&**l), debug_loc)
|
||||
}
|
||||
ast::PatIdent(..) | ast::PatEnum(..) | ast::PatStruct(..) => {
|
||||
hir::PatIdent(..) | hir::PatEnum(..) | hir::PatStruct(..) => {
|
||||
// This is either an enum variant or a variable binding.
|
||||
let opt_def = tcx.def_map.borrow().get(&cur.id).map(|d| d.full_def());
|
||||
match opt_def {
|
||||
@ -665,13 +665,13 @@ fn get_branches<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
_ => continue
|
||||
}
|
||||
}
|
||||
ast::PatRange(ref l1, ref l2) => {
|
||||
hir::PatRange(ref l1, ref l2) => {
|
||||
ConstantRange(ConstantExpr(&**l1), ConstantExpr(&**l2), debug_loc)
|
||||
}
|
||||
ast::PatVec(ref before, None, ref after) => {
|
||||
hir::PatVec(ref before, None, ref after) => {
|
||||
SliceLengthEqual(before.len() + after.len(), debug_loc)
|
||||
}
|
||||
ast::PatVec(ref before, Some(_), ref after) => {
|
||||
hir::PatVec(ref before, Some(_), ref after) => {
|
||||
SliceLengthGreaterOrEqual(before.len(), after.len(), debug_loc)
|
||||
}
|
||||
_ => continue
|
||||
@ -770,25 +770,25 @@ macro_rules! any_pat {
|
||||
}
|
||||
|
||||
fn any_uniq_pat(m: &[Match], col: usize) -> bool {
|
||||
any_pat!(m, col, ast::PatBox(_))
|
||||
any_pat!(m, col, hir::PatBox(_))
|
||||
}
|
||||
|
||||
fn any_region_pat(m: &[Match], col: usize) -> bool {
|
||||
any_pat!(m, col, ast::PatRegion(..))
|
||||
any_pat!(m, col, hir::PatRegion(..))
|
||||
}
|
||||
|
||||
fn any_irrefutable_adt_pat(tcx: &ty::ctxt, m: &[Match], col: usize) -> bool {
|
||||
m.iter().any(|br| {
|
||||
let pat = br.pats[col];
|
||||
match pat.node {
|
||||
ast::PatTup(_) => true,
|
||||
ast::PatStruct(..) => {
|
||||
hir::PatTup(_) => true,
|
||||
hir::PatStruct(..) => {
|
||||
match tcx.def_map.borrow().get(&pat.id).map(|d| d.full_def()) {
|
||||
Some(def::DefVariant(..)) => false,
|
||||
_ => true,
|
||||
}
|
||||
}
|
||||
ast::PatEnum(..) | ast::PatIdent(_, _, None) => {
|
||||
hir::PatEnum(..) | hir::PatIdent(_, _, None) => {
|
||||
match tcx.def_map.borrow().get(&pat.id).map(|d| d.full_def()) {
|
||||
Some(def::DefStruct(..)) => true,
|
||||
_ => false
|
||||
@ -831,9 +831,9 @@ impl FailureHandler {
|
||||
}
|
||||
|
||||
fn pick_column_to_specialize(def_map: &DefMap, m: &[Match]) -> Option<usize> {
|
||||
fn pat_score(def_map: &DefMap, pat: &ast::Pat) -> usize {
|
||||
fn pat_score(def_map: &DefMap, pat: &hir::Pat) -> usize {
|
||||
match pat.node {
|
||||
ast::PatIdent(_, _, Some(ref inner)) => pat_score(def_map, &**inner),
|
||||
hir::PatIdent(_, _, Some(ref inner)) => pat_score(def_map, &**inner),
|
||||
_ if pat_is_refutable(def_map, pat) => 1,
|
||||
_ => 0
|
||||
}
|
||||
@ -855,7 +855,7 @@ fn pick_column_to_specialize(def_map: &DefMap, m: &[Match]) -> Option<usize> {
|
||||
|
||||
let column_contains_any_nonwild_patterns = |&col: &usize| -> bool {
|
||||
m.iter().any(|row| match row.pats[col].node {
|
||||
ast::PatWild(_) => false,
|
||||
hir::PatWild(_) => false,
|
||||
_ => true
|
||||
})
|
||||
};
|
||||
@ -891,7 +891,7 @@ fn compare_values<'blk, 'tcx>(cx: Block<'blk, 'tcx>,
|
||||
|
||||
let _icx = push_ctxt("compare_values");
|
||||
if rhs_t.is_scalar() {
|
||||
let cmp = compare_scalar_types(cx, lhs, rhs, rhs_t, ast::BiEq, debug_loc);
|
||||
let cmp = compare_scalar_types(cx, lhs, rhs, rhs_t, hir::BiEq, debug_loc);
|
||||
return Result::new(cx, cmp);
|
||||
}
|
||||
|
||||
@ -905,7 +905,7 @@ fn compare_values<'blk, 'tcx>(cx: Block<'blk, 'tcx>,
|
||||
compare_str(cx, lhs_data, lhs_len, rhs_data, rhs_len, rhs_t, debug_loc)
|
||||
}
|
||||
ty::TyArray(ty, _) | ty::TySlice(ty) => match ty.sty {
|
||||
ty::TyUint(ast::TyU8) => {
|
||||
ty::TyUint(hir::TyU8) => {
|
||||
// NOTE: cast &[u8] and &[u8; N] to &str and abuse the str_eq lang item,
|
||||
// which calls memcmp().
|
||||
let pat_len = val_ty(rhs).element_type().array_length();
|
||||
@ -1027,7 +1027,7 @@ fn insert_lllocals<'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>,
|
||||
}
|
||||
|
||||
fn compile_guard<'a, 'p, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
guard_expr: &ast::Expr,
|
||||
guard_expr: &hir::Expr,
|
||||
data: &ArmData<'p, 'blk, 'tcx>,
|
||||
m: &[Match<'a, 'p, 'blk, 'tcx>],
|
||||
vals: &[MatchInput],
|
||||
@ -1324,14 +1324,14 @@ fn compile_submatch_continue<'a, 'p, 'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>,
|
||||
RangeResult(Result { val: vbegin, .. },
|
||||
Result { bcx, val: vend }) => {
|
||||
let llge = compare_scalar_types(bcx, test_val, vbegin,
|
||||
t, ast::BiGe, debug_loc);
|
||||
t, hir::BiGe, debug_loc);
|
||||
let llle = compare_scalar_types(bcx, test_val, vend,
|
||||
t, ast::BiLe, debug_loc);
|
||||
t, hir::BiLe, debug_loc);
|
||||
Result::new(bcx, And(bcx, llge, llle, DebugLoc::None))
|
||||
}
|
||||
LowerBound(Result { bcx, val }) => {
|
||||
Result::new(bcx, compare_scalar_types(bcx, test_val,
|
||||
val, t, ast::BiGe,
|
||||
val, t, hir::BiGe,
|
||||
debug_loc))
|
||||
}
|
||||
}
|
||||
@ -1415,9 +1415,9 @@ fn compile_submatch_continue<'a, 'p, 'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>,
|
||||
}
|
||||
|
||||
pub fn trans_match<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
match_expr: &ast::Expr,
|
||||
discr_expr: &ast::Expr,
|
||||
arms: &[ast::Arm],
|
||||
match_expr: &hir::Expr,
|
||||
discr_expr: &hir::Expr,
|
||||
arms: &[hir::Arm],
|
||||
dest: Dest)
|
||||
-> Block<'blk, 'tcx> {
|
||||
let _icx = push_ctxt("match::trans_match");
|
||||
@ -1425,20 +1425,20 @@ pub fn trans_match<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
}
|
||||
|
||||
/// Checks whether the binding in `discr` is assigned to anywhere in the expression `body`
|
||||
fn is_discr_reassigned(bcx: Block, discr: &ast::Expr, body: &ast::Expr) -> bool {
|
||||
fn is_discr_reassigned(bcx: Block, discr: &hir::Expr, body: &hir::Expr) -> bool {
|
||||
let (vid, field) = match discr.node {
|
||||
ast::ExprPath(..) => match bcx.def(discr.id) {
|
||||
hir::ExprPath(..) => match bcx.def(discr.id) {
|
||||
def::DefLocal(vid) | def::DefUpvar(vid, _) => (vid, None),
|
||||
_ => return false
|
||||
},
|
||||
ast::ExprField(ref base, field) => {
|
||||
hir::ExprField(ref base, field) => {
|
||||
let vid = match bcx.tcx().def_map.borrow().get(&base.id).map(|d| d.full_def()) {
|
||||
Some(def::DefLocal(vid)) | Some(def::DefUpvar(vid, _)) => vid,
|
||||
_ => return false
|
||||
};
|
||||
(vid, Some(mc::NamedField(field.node.name)))
|
||||
},
|
||||
ast::ExprTupField(ref base, field) => {
|
||||
hir::ExprTupField(ref base, field) => {
|
||||
let vid = match bcx.tcx().def_map.borrow().get(&base.id).map(|d| d.full_def()) {
|
||||
Some(def::DefLocal(vid)) | Some(def::DefUpvar(vid, _)) => vid,
|
||||
_ => return false
|
||||
@ -1473,8 +1473,8 @@ struct ReassignmentChecker {
|
||||
// for cases where the matched value is moved.
|
||||
impl<'tcx> euv::Delegate<'tcx> for ReassignmentChecker {
|
||||
fn consume(&mut self, _: ast::NodeId, _: Span, _: mc::cmt, _: euv::ConsumeMode) {}
|
||||
fn matched_pat(&mut self, _: &ast::Pat, _: mc::cmt, _: euv::MatchMode) {}
|
||||
fn consume_pat(&mut self, _: &ast::Pat, _: mc::cmt, _: euv::ConsumeMode) {}
|
||||
fn matched_pat(&mut self, _: &hir::Pat, _: mc::cmt, _: euv::MatchMode) {}
|
||||
fn consume_pat(&mut self, _: &hir::Pat, _: mc::cmt, _: euv::ConsumeMode) {}
|
||||
fn borrow(&mut self, _: ast::NodeId, _: Span, _: mc::cmt, _: ty::Region,
|
||||
_: ty::BorrowKind, _: euv::LoanCause) {}
|
||||
fn decl_without_init(&mut self, _: ast::NodeId, _: Span) {}
|
||||
@ -1498,8 +1498,8 @@ impl<'tcx> euv::Delegate<'tcx> for ReassignmentChecker {
|
||||
}
|
||||
}
|
||||
|
||||
fn create_bindings_map<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, pat: &ast::Pat,
|
||||
discr: &ast::Expr, body: &ast::Expr)
|
||||
fn create_bindings_map<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, pat: &hir::Pat,
|
||||
discr: &hir::Expr, body: &hir::Expr)
|
||||
-> BindingsMap<'tcx> {
|
||||
// Create the bindings map, which is a mapping from each binding name
|
||||
// to an alloca() that will be the value for that local variable.
|
||||
@ -1521,7 +1521,7 @@ fn create_bindings_map<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, pat: &ast::Pat,
|
||||
let trmode;
|
||||
let moves_by_default = variable_ty.moves_by_default(¶m_env, span);
|
||||
match bm {
|
||||
ast::BindByValue(_) if !moves_by_default || reassigned =>
|
||||
hir::BindByValue(_) if !moves_by_default || reassigned =>
|
||||
{
|
||||
llmatch = alloca(bcx, llvariable_ty.ptr_to(), "__llmatch");
|
||||
let llcopy = alloca(bcx, llvariable_ty, &bcx.name(name));
|
||||
@ -1531,14 +1531,14 @@ fn create_bindings_map<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, pat: &ast::Pat,
|
||||
TrByCopy(llcopy)
|
||||
};
|
||||
}
|
||||
ast::BindByValue(_) => {
|
||||
hir::BindByValue(_) => {
|
||||
// in this case, the final type of the variable will be T,
|
||||
// but during matching we need to store a *T as explained
|
||||
// above
|
||||
llmatch = alloca(bcx, llvariable_ty.ptr_to(), &bcx.name(name));
|
||||
trmode = TrByMoveRef;
|
||||
}
|
||||
ast::BindByRef(_) => {
|
||||
hir::BindByRef(_) => {
|
||||
llmatch = alloca(bcx, llvariable_ty, &bcx.name(name));
|
||||
trmode = TrByRef;
|
||||
}
|
||||
@ -1556,8 +1556,8 @@ fn create_bindings_map<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, pat: &ast::Pat,
|
||||
|
||||
fn trans_match_inner<'blk, 'tcx>(scope_cx: Block<'blk, 'tcx>,
|
||||
match_id: ast::NodeId,
|
||||
discr_expr: &ast::Expr,
|
||||
arms: &[ast::Arm],
|
||||
discr_expr: &hir::Expr,
|
||||
arms: &[hir::Arm],
|
||||
dest: Dest) -> Block<'blk, 'tcx> {
|
||||
let _icx = push_ctxt("match::trans_match_inner");
|
||||
let fcx = scope_cx.fcx;
|
||||
@ -1589,7 +1589,7 @@ fn trans_match_inner<'blk, 'tcx>(scope_cx: Block<'blk, 'tcx>,
|
||||
None
|
||||
};
|
||||
|
||||
let arm_pats: Vec<Vec<P<ast::Pat>>> = {
|
||||
let arm_pats: Vec<Vec<P<hir::Pat>>> = {
|
||||
let mut static_inliner = StaticInliner::new(scope_cx.tcx(),
|
||||
pat_renaming_map.as_mut());
|
||||
arm_datas.iter().map(|arm_data| {
|
||||
@ -1615,7 +1615,7 @@ fn trans_match_inner<'blk, 'tcx>(scope_cx: Block<'blk, 'tcx>,
|
||||
// to the default arm.
|
||||
let has_default = arms.last().map_or(false, |arm| {
|
||||
arm.pats.len() == 1
|
||||
&& arm.pats.last().unwrap().node == ast::PatWild(ast::PatWildSingle)
|
||||
&& arm.pats.last().unwrap().node == hir::PatWild(hir::PatWildSingle)
|
||||
});
|
||||
|
||||
compile_submatch(bcx, &matches[..], &[discr_datum.match_input()], &chk, has_default);
|
||||
@ -1639,7 +1639,7 @@ fn trans_match_inner<'blk, 'tcx>(scope_cx: Block<'blk, 'tcx>,
|
||||
/// Generates code for a local variable declaration like `let <pat>;` or `let <pat> =
|
||||
/// <opt_init_expr>`.
|
||||
pub fn store_local<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
local: &ast::Local)
|
||||
local: &hir::Local)
|
||||
-> Block<'blk, 'tcx> {
|
||||
let _icx = push_ctxt("match::store_local");
|
||||
let mut bcx = bcx;
|
||||
@ -1647,7 +1647,7 @@ pub fn store_local<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
let pat = &*local.pat;
|
||||
|
||||
fn create_dummy_locals<'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>,
|
||||
pat: &ast::Pat)
|
||||
pat: &hir::Pat)
|
||||
-> Block<'blk, 'tcx> {
|
||||
let _icx = push_ctxt("create_dummy_locals");
|
||||
// create dummy memory for the variables if we have no
|
||||
@ -1764,7 +1764,7 @@ fn mk_binding_alloca<'blk, 'tcx, A, F>(bcx: Block<'blk, 'tcx>,
|
||||
/// - pat: the irrefutable pattern being matched.
|
||||
/// - val: the value being matched -- must be an lvalue (by ref, with cleanup)
|
||||
pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
pat: &ast::Pat,
|
||||
pat: &hir::Pat,
|
||||
val: MatchInput,
|
||||
cleanup_scope: cleanup::ScopeId)
|
||||
-> Block<'blk, 'tcx> {
|
||||
@ -1784,7 +1784,7 @@ pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
let tcx = bcx.tcx();
|
||||
let ccx = bcx.ccx();
|
||||
match pat.node {
|
||||
ast::PatIdent(pat_binding_mode, ref path1, ref inner) => {
|
||||
hir::PatIdent(pat_binding_mode, ref path1, ref inner) => {
|
||||
if pat_is_binding(&tcx.def_map, &*pat) {
|
||||
// Allocate the stack slot where the value of this
|
||||
// binding will live and place it into the appropriate
|
||||
@ -1794,14 +1794,14 @@ pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
"_match::bind_irrefutable_pat",
|
||||
|(), bcx, Datum { val: llval, ty, kind: _ }| {
|
||||
match pat_binding_mode {
|
||||
ast::BindByValue(_) => {
|
||||
hir::BindByValue(_) => {
|
||||
// By value binding: move the value that `val`
|
||||
// points at into the binding's stack slot.
|
||||
let d = val.to_datum(ty);
|
||||
d.store_to(bcx, llval)
|
||||
}
|
||||
|
||||
ast::BindByRef(_) => {
|
||||
hir::BindByRef(_) => {
|
||||
// By ref binding: the value of the variable
|
||||
// is the pointer `val` itself or fat pointer referenced by `val`
|
||||
if type_is_fat_ptr(bcx.tcx(), ty) {
|
||||
@ -1821,7 +1821,7 @@ pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
bcx = bind_irrefutable_pat(bcx, &**inner_pat, val, cleanup_scope);
|
||||
}
|
||||
}
|
||||
ast::PatEnum(_, ref sub_pats) => {
|
||||
hir::PatEnum(_, ref sub_pats) => {
|
||||
let opt_def = bcx.tcx().def_map.borrow().get(&pat.id).map(|d| d.full_def());
|
||||
match opt_def {
|
||||
Some(def::DefVariant(enum_id, var_id, _)) => {
|
||||
@ -1866,7 +1866,7 @@ pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::PatStruct(_, ref fields, _) => {
|
||||
hir::PatStruct(_, ref fields, _) => {
|
||||
let tcx = bcx.tcx();
|
||||
let pat_ty = node_id_type(bcx, pat.id);
|
||||
let pat_repr = adt::represent_type(bcx.ccx(), pat_ty);
|
||||
@ -1885,7 +1885,7 @@ pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
cleanup_scope);
|
||||
}
|
||||
}
|
||||
ast::PatTup(ref elems) => {
|
||||
hir::PatTup(ref elems) => {
|
||||
let repr = adt::represent_node(bcx, pat.id);
|
||||
for (i, elem) in elems.iter().enumerate() {
|
||||
let fldptr = adt::trans_field_ptr(bcx, &*repr, val.val, 0, i);
|
||||
@ -1896,12 +1896,12 @@ pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
cleanup_scope);
|
||||
}
|
||||
}
|
||||
ast::PatBox(ref inner) => {
|
||||
hir::PatBox(ref inner) => {
|
||||
let llbox = Load(bcx, val.val);
|
||||
bcx = bind_irrefutable_pat(
|
||||
bcx, &**inner, MatchInput::from_val(llbox), cleanup_scope);
|
||||
}
|
||||
ast::PatRegion(ref inner, _) => {
|
||||
hir::PatRegion(ref inner, _) => {
|
||||
let loaded_val = Load(bcx, val.val);
|
||||
bcx = bind_irrefutable_pat(
|
||||
bcx,
|
||||
@ -1909,7 +1909,7 @@ pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
MatchInput::from_val(loaded_val),
|
||||
cleanup_scope);
|
||||
}
|
||||
ast::PatVec(ref before, ref slice, ref after) => {
|
||||
hir::PatVec(ref before, ref slice, ref after) => {
|
||||
let pat_ty = node_id_type(bcx, pat.id);
|
||||
let mut extracted = extract_vec_elems(bcx, pat_ty, before.len(), after.len(), val);
|
||||
match slice {
|
||||
@ -1934,11 +1934,8 @@ pub fn bind_irrefutable_pat<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
cleanup_scope)
|
||||
});
|
||||
}
|
||||
ast::PatMac(..) => {
|
||||
bcx.sess().span_bug(pat.span, "unexpanded macro");
|
||||
}
|
||||
ast::PatQPath(..) | ast::PatWild(_) | ast::PatLit(_) |
|
||||
ast::PatRange(_, _) => ()
|
||||
hir::PatQPath(..) | hir::PatWild(_) | hir::PatLit(_) |
|
||||
hir::PatRange(_, _) => ()
|
||||
}
|
||||
return bcx;
|
||||
}
|
||||
|
@ -51,8 +51,9 @@ use middle::subst;
|
||||
use middle::ty::{self, Ty};
|
||||
use middle::ty::Disr;
|
||||
use syntax::ast;
|
||||
use syntax::attr;
|
||||
use syntax::attr::IntType;
|
||||
use rustc_front::attr;
|
||||
use rustc_front::attr::IntType;
|
||||
use rustc_front::hir;
|
||||
use trans::_match;
|
||||
use trans::build::*;
|
||||
use trans::cleanup;
|
||||
@ -386,11 +387,11 @@ fn represent_type_uncached<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
let ity = if use_align {
|
||||
// Use the overall alignment
|
||||
match align {
|
||||
1 => attr::UnsignedInt(ast::TyU8),
|
||||
2 => attr::UnsignedInt(ast::TyU16),
|
||||
4 => attr::UnsignedInt(ast::TyU32),
|
||||
1 => attr::UnsignedInt(hir::TyU8),
|
||||
2 => attr::UnsignedInt(hir::TyU16),
|
||||
4 => attr::UnsignedInt(hir::TyU32),
|
||||
8 if machine::llalign_of_min(cx, Type::i64(cx)) == 8 =>
|
||||
attr::UnsignedInt(ast::TyU64),
|
||||
attr::UnsignedInt(hir::TyU64),
|
||||
_ => min_ity // use min_ity as a fallback
|
||||
}
|
||||
} else {
|
||||
@ -582,12 +583,12 @@ fn range_to_inttype(cx: &CrateContext, hint: Hint, bounds: &IntBounds) -> IntTyp
|
||||
// Lists of sizes to try. u64 is always allowed as a fallback.
|
||||
#[allow(non_upper_case_globals)]
|
||||
const choose_shortest: &'static [IntType] = &[
|
||||
attr::UnsignedInt(ast::TyU8), attr::SignedInt(ast::TyI8),
|
||||
attr::UnsignedInt(ast::TyU16), attr::SignedInt(ast::TyI16),
|
||||
attr::UnsignedInt(ast::TyU32), attr::SignedInt(ast::TyI32)];
|
||||
attr::UnsignedInt(hir::TyU8), attr::SignedInt(hir::TyI8),
|
||||
attr::UnsignedInt(hir::TyU16), attr::SignedInt(hir::TyI16),
|
||||
attr::UnsignedInt(hir::TyU32), attr::SignedInt(hir::TyI32)];
|
||||
#[allow(non_upper_case_globals)]
|
||||
const at_least_32: &'static [IntType] = &[
|
||||
attr::UnsignedInt(ast::TyU32), attr::SignedInt(ast::TyI32)];
|
||||
attr::UnsignedInt(hir::TyU32), attr::SignedInt(hir::TyI32)];
|
||||
|
||||
let attempts;
|
||||
match hint {
|
||||
@ -621,7 +622,7 @@ fn range_to_inttype(cx: &CrateContext, hint: Hint, bounds: &IntBounds) -> IntTyp
|
||||
return ity;
|
||||
}
|
||||
}
|
||||
return attr::UnsignedInt(ast::TyU64);
|
||||
return attr::UnsignedInt(hir::TyU64);
|
||||
}
|
||||
|
||||
pub fn ll_inttype(cx: &CrateContext, ity: IntType) -> Type {
|
||||
|
@ -20,7 +20,7 @@ use trans::expr;
|
||||
use trans::type_of;
|
||||
use trans::type_::Type;
|
||||
|
||||
use syntax::ast;
|
||||
use rustc_front::hir as ast;
|
||||
use std::ffi::CString;
|
||||
use libc::{c_uint, c_char};
|
||||
|
||||
|
@ -15,8 +15,8 @@ use middle::ty;
|
||||
use middle::infer;
|
||||
use session::config::NoDebugInfo;
|
||||
use syntax::abi;
|
||||
use syntax::ast;
|
||||
pub use syntax::attr::InlineAttr;
|
||||
use rustc_front::hir;
|
||||
pub use rustc_front::attr::InlineAttr;
|
||||
use trans::base;
|
||||
use trans::common;
|
||||
use trans::context::CrateContext;
|
||||
@ -91,8 +91,8 @@ pub fn set_optimize_for_size(val: ValueRef, optimize: bool) {
|
||||
|
||||
/// Composite function which sets LLVM attributes for function depending on its AST (#[attribute])
|
||||
/// attributes.
|
||||
pub fn from_fn_attrs(ccx: &CrateContext, attrs: &[ast::Attribute], llfn: ValueRef) {
|
||||
use syntax::attr::*;
|
||||
pub fn from_fn_attrs(ccx: &CrateContext, attrs: &[hir::Attribute], llfn: ValueRef) {
|
||||
use rustc_front::attr::*;
|
||||
inline(llfn, find_inline_attr(Some(ccx.sess().diagnostic()), attrs));
|
||||
|
||||
// FIXME: #11906: Omitting frame pointers breaks retrieving the value of a
|
||||
@ -262,11 +262,11 @@ pub fn from_fn_type<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>, fn_type: ty::Ty<'tcx
|
||||
// on memory dependencies rather than pointer equality
|
||||
let interior_unsafe = mt.ty.type_contents(ccx.tcx()).interior_unsafe();
|
||||
|
||||
if mt.mutbl == ast::MutMutable || !interior_unsafe {
|
||||
if mt.mutbl == hir::MutMutable || !interior_unsafe {
|
||||
attrs.arg(idx, llvm::Attribute::NoAlias);
|
||||
}
|
||||
|
||||
if mt.mutbl == ast::MutImmutable && !interior_unsafe {
|
||||
if mt.mutbl == hir::MutImmutable && !interior_unsafe {
|
||||
attrs.arg(idx, llvm::Attribute::ReadOnly);
|
||||
}
|
||||
|
||||
|
@ -43,7 +43,7 @@ use middle::weak_lang_items;
|
||||
use middle::pat_util::simple_identifier;
|
||||
use middle::subst::Substs;
|
||||
use middle::ty::{self, Ty, HasTypeFlags};
|
||||
use rustc::ast_map;
|
||||
use rustc::front::map as hir_map;
|
||||
use session::config::{self, NoDebugInfo, FullDebugInfo};
|
||||
use session::Session;
|
||||
use trans::_match;
|
||||
@ -93,13 +93,15 @@ use std::mem;
|
||||
use std::str;
|
||||
use std::{i8, i16, i32, i64};
|
||||
use syntax::abi::{Rust, RustCall, RustIntrinsic, PlatformIntrinsic, Abi};
|
||||
use syntax::attr::AttrMetaMethods;
|
||||
use syntax::attr;
|
||||
use syntax::codemap::Span;
|
||||
use syntax::parse::token::InternedString;
|
||||
use syntax::visit::Visitor;
|
||||
use syntax::visit;
|
||||
use syntax::{ast, ast_util};
|
||||
use rustc_front;
|
||||
use rustc_front::attr::AttrMetaMethods;
|
||||
use rustc_front::attr;
|
||||
use rustc_front::visit::Visitor;
|
||||
use rustc_front::visit;
|
||||
use rustc_front::hir;
|
||||
use syntax::ast;
|
||||
|
||||
thread_local! {
|
||||
static TASK_LOCAL_INSN_KEY: RefCell<Option<Vec<&'static str>>> = {
|
||||
@ -277,15 +279,15 @@ pub fn malloc_raw_dyn<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
}
|
||||
|
||||
|
||||
pub fn bin_op_to_icmp_predicate(ccx: &CrateContext, op: ast::BinOp_, signed: bool)
|
||||
pub fn bin_op_to_icmp_predicate(ccx: &CrateContext, op: hir::BinOp_, signed: bool)
|
||||
-> llvm::IntPredicate {
|
||||
match op {
|
||||
ast::BiEq => llvm::IntEQ,
|
||||
ast::BiNe => llvm::IntNE,
|
||||
ast::BiLt => if signed { llvm::IntSLT } else { llvm::IntULT },
|
||||
ast::BiLe => if signed { llvm::IntSLE } else { llvm::IntULE },
|
||||
ast::BiGt => if signed { llvm::IntSGT } else { llvm::IntUGT },
|
||||
ast::BiGe => if signed { llvm::IntSGE } else { llvm::IntUGE },
|
||||
hir::BiEq => llvm::IntEQ,
|
||||
hir::BiNe => llvm::IntNE,
|
||||
hir::BiLt => if signed { llvm::IntSLT } else { llvm::IntULT },
|
||||
hir::BiLe => if signed { llvm::IntSLE } else { llvm::IntULE },
|
||||
hir::BiGt => if signed { llvm::IntSGT } else { llvm::IntUGT },
|
||||
hir::BiGe => if signed { llvm::IntSGE } else { llvm::IntUGE },
|
||||
op => {
|
||||
ccx.sess().bug(&format!("comparison_op_to_icmp_predicate: expected \
|
||||
comparison operator, found {:?}", op));
|
||||
@ -293,15 +295,15 @@ pub fn bin_op_to_icmp_predicate(ccx: &CrateContext, op: ast::BinOp_, signed: boo
|
||||
}
|
||||
}
|
||||
|
||||
pub fn bin_op_to_fcmp_predicate(ccx: &CrateContext, op: ast::BinOp_)
|
||||
pub fn bin_op_to_fcmp_predicate(ccx: &CrateContext, op: hir::BinOp_)
|
||||
-> llvm::RealPredicate {
|
||||
match op {
|
||||
ast::BiEq => llvm::RealOEQ,
|
||||
ast::BiNe => llvm::RealUNE,
|
||||
ast::BiLt => llvm::RealOLT,
|
||||
ast::BiLe => llvm::RealOLE,
|
||||
ast::BiGt => llvm::RealOGT,
|
||||
ast::BiGe => llvm::RealOGE,
|
||||
hir::BiEq => llvm::RealOEQ,
|
||||
hir::BiNe => llvm::RealUNE,
|
||||
hir::BiLt => llvm::RealOLT,
|
||||
hir::BiLe => llvm::RealOLE,
|
||||
hir::BiGt => llvm::RealOGT,
|
||||
hir::BiGe => llvm::RealOGE,
|
||||
op => {
|
||||
ccx.sess().bug(&format!("comparison_op_to_fcmp_predicate: expected \
|
||||
comparison operator, found {:?}", op));
|
||||
@ -313,7 +315,7 @@ pub fn compare_scalar_types<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
lhs: ValueRef,
|
||||
rhs: ValueRef,
|
||||
t: Ty<'tcx>,
|
||||
op: ast::BinOp_,
|
||||
op: hir::BinOp_,
|
||||
debug_loc: DebugLoc)
|
||||
-> ValueRef {
|
||||
match t.sty {
|
||||
@ -321,8 +323,8 @@ pub fn compare_scalar_types<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
// We don't need to do actual comparisons for nil.
|
||||
// () == () holds but () < () does not.
|
||||
match op {
|
||||
ast::BiEq | ast::BiLe | ast::BiGe => return C_bool(bcx.ccx(), true),
|
||||
ast::BiNe | ast::BiLt | ast::BiGt => return C_bool(bcx.ccx(), false),
|
||||
hir::BiEq | hir::BiLe | hir::BiGe => return C_bool(bcx.ccx(), true),
|
||||
hir::BiNe | hir::BiLt | hir::BiGt => return C_bool(bcx.ccx(), false),
|
||||
// refinements would be nice
|
||||
_ => bcx.sess().bug("compare_scalar_types: must be a comparison operator")
|
||||
}
|
||||
@ -349,7 +351,7 @@ pub fn compare_simd_types<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
rhs: ValueRef,
|
||||
t: Ty<'tcx>,
|
||||
ret_ty: Type,
|
||||
op: ast::BinOp_,
|
||||
op: hir::BinOp_,
|
||||
debug_loc: DebugLoc)
|
||||
-> ValueRef {
|
||||
let signed = match t.sty {
|
||||
@ -526,7 +528,7 @@ pub fn iter_structural_ty<'blk, 'tcx, F>(cx: Block<'blk, 'tcx>,
|
||||
}
|
||||
|
||||
pub fn cast_shift_expr_rhs(cx: Block,
|
||||
op: ast::BinOp_,
|
||||
op: hir::BinOp_,
|
||||
lhs: ValueRef,
|
||||
rhs: ValueRef)
|
||||
-> ValueRef {
|
||||
@ -535,14 +537,14 @@ pub fn cast_shift_expr_rhs(cx: Block,
|
||||
|a,b| ZExt(cx, a, b))
|
||||
}
|
||||
|
||||
pub fn cast_shift_const_rhs(op: ast::BinOp_,
|
||||
pub fn cast_shift_const_rhs(op: hir::BinOp_,
|
||||
lhs: ValueRef, rhs: ValueRef) -> ValueRef {
|
||||
cast_shift_rhs(op, lhs, rhs,
|
||||
|a, b| unsafe { llvm::LLVMConstTrunc(a, b.to_ref()) },
|
||||
|a, b| unsafe { llvm::LLVMConstZExt(a, b.to_ref()) })
|
||||
}
|
||||
|
||||
fn cast_shift_rhs<F, G>(op: ast::BinOp_,
|
||||
fn cast_shift_rhs<F, G>(op: hir::BinOp_,
|
||||
lhs: ValueRef,
|
||||
rhs: ValueRef,
|
||||
trunc: F,
|
||||
@ -552,7 +554,7 @@ fn cast_shift_rhs<F, G>(op: ast::BinOp_,
|
||||
G: FnOnce(ValueRef, Type) -> ValueRef,
|
||||
{
|
||||
// Shifts may have any size int on the rhs
|
||||
if ast_util::is_shift_binop(op) {
|
||||
if rustc_front::util::is_shift_binop(op) {
|
||||
let mut rhs_llty = val_ty(rhs);
|
||||
let mut lhs_llty = val_ty(lhs);
|
||||
if rhs_llty.kind() == Vector { rhs_llty = rhs_llty.element_type() }
|
||||
@ -579,12 +581,12 @@ pub fn llty_and_min_for_signed_ty<'blk, 'tcx>(cx: Block<'blk, 'tcx>,
|
||||
ty::TyInt(t) => {
|
||||
let llty = Type::int_from_ty(cx.ccx(), t);
|
||||
let min = match t {
|
||||
ast::TyIs if llty == Type::i32(cx.ccx()) => i32::MIN as u64,
|
||||
ast::TyIs => i64::MIN as u64,
|
||||
ast::TyI8 => i8::MIN as u64,
|
||||
ast::TyI16 => i16::MIN as u64,
|
||||
ast::TyI32 => i32::MIN as u64,
|
||||
ast::TyI64 => i64::MIN as u64,
|
||||
hir::TyIs if llty == Type::i32(cx.ccx()) => i32::MIN as u64,
|
||||
hir::TyIs => i64::MIN as u64,
|
||||
hir::TyI8 => i8::MIN as u64,
|
||||
hir::TyI16 => i16::MIN as u64,
|
||||
hir::TyI32 => i32::MIN as u64,
|
||||
hir::TyI64 => i64::MIN as u64,
|
||||
};
|
||||
(llty, min)
|
||||
}
|
||||
@ -595,12 +597,12 @@ pub fn llty_and_min_for_signed_ty<'blk, 'tcx>(cx: Block<'blk, 'tcx>,
|
||||
pub fn fail_if_zero_or_overflows<'blk, 'tcx>(
|
||||
cx: Block<'blk, 'tcx>,
|
||||
call_info: NodeIdAndSpan,
|
||||
divrem: ast::BinOp,
|
||||
divrem: hir::BinOp,
|
||||
lhs: ValueRef,
|
||||
rhs: ValueRef,
|
||||
rhs_t: Ty<'tcx>)
|
||||
-> Block<'blk, 'tcx> {
|
||||
let (zero_text, overflow_text) = if divrem.node == ast::BiDiv {
|
||||
let (zero_text, overflow_text) = if divrem.node == hir::BiDiv {
|
||||
("attempted to divide by zero",
|
||||
"attempted to divide with overflow")
|
||||
} else {
|
||||
@ -871,7 +873,7 @@ pub fn to_arg_ty_ptr<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, ptr: ValueRef, ty: Ty<'
|
||||
}
|
||||
}
|
||||
|
||||
pub fn init_local<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, local: &ast::Local)
|
||||
pub fn init_local<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, local: &hir::Local)
|
||||
-> Block<'blk, 'tcx> {
|
||||
debug!("init_local(bcx={}, local.id={})", bcx.to_str(), local.id);
|
||||
let _indenter = indenter();
|
||||
@ -1086,9 +1088,9 @@ impl FindNestedReturn {
|
||||
}
|
||||
|
||||
impl<'v> Visitor<'v> for FindNestedReturn {
|
||||
fn visit_expr(&mut self, e: &ast::Expr) {
|
||||
fn visit_expr(&mut self, e: &hir::Expr) {
|
||||
match e.node {
|
||||
ast::ExprRet(..) => {
|
||||
hir::ExprRet(..) => {
|
||||
self.found = true;
|
||||
}
|
||||
_ => visit::walk_expr(self, e)
|
||||
@ -1098,40 +1100,40 @@ impl<'v> Visitor<'v> for FindNestedReturn {
|
||||
|
||||
fn build_cfg(tcx: &ty::ctxt, id: ast::NodeId) -> (ast::NodeId, Option<cfg::CFG>) {
|
||||
let blk = match tcx.map.find(id) {
|
||||
Some(ast_map::NodeItem(i)) => {
|
||||
Some(hir_map::NodeItem(i)) => {
|
||||
match i.node {
|
||||
ast::ItemFn(_, _, _, _, _, ref blk) => {
|
||||
hir::ItemFn(_, _, _, _, _, ref blk) => {
|
||||
blk
|
||||
}
|
||||
_ => tcx.sess.bug("unexpected item variant in has_nested_returns")
|
||||
}
|
||||
}
|
||||
Some(ast_map::NodeTraitItem(trait_item)) => {
|
||||
Some(hir_map::NodeTraitItem(trait_item)) => {
|
||||
match trait_item.node {
|
||||
ast::MethodTraitItem(_, Some(ref body)) => body,
|
||||
hir::MethodTraitItem(_, Some(ref body)) => body,
|
||||
_ => {
|
||||
tcx.sess.bug("unexpected variant: trait item other than a \
|
||||
provided method in has_nested_returns")
|
||||
}
|
||||
}
|
||||
}
|
||||
Some(ast_map::NodeImplItem(impl_item)) => {
|
||||
Some(hir_map::NodeImplItem(impl_item)) => {
|
||||
match impl_item.node {
|
||||
ast::MethodImplItem(_, ref body) => body,
|
||||
hir::MethodImplItem(_, ref body) => body,
|
||||
_ => {
|
||||
tcx.sess.bug("unexpected variant: non-method impl item in \
|
||||
has_nested_returns")
|
||||
}
|
||||
}
|
||||
}
|
||||
Some(ast_map::NodeExpr(e)) => {
|
||||
Some(hir_map::NodeExpr(e)) => {
|
||||
match e.node {
|
||||
ast::ExprClosure(_, _, ref blk) => blk,
|
||||
hir::ExprClosure(_, _, ref blk) => blk,
|
||||
_ => tcx.sess.bug("unexpected expr variant in has_nested_returns")
|
||||
}
|
||||
}
|
||||
Some(ast_map::NodeVariant(..)) |
|
||||
Some(ast_map::NodeStructCtor(..)) => return (ast::DUMMY_NODE_ID, None),
|
||||
Some(hir_map::NodeVariant(..)) |
|
||||
Some(hir_map::NodeStructCtor(..)) => return (ast::DUMMY_NODE_ID, None),
|
||||
|
||||
// glue, shims, etc
|
||||
None if id == ast::DUMMY_NODE_ID => return (ast::DUMMY_NODE_ID, None),
|
||||
@ -1157,8 +1159,8 @@ fn has_nested_returns(tcx: &ty::ctxt, cfg: &cfg::CFG, blk_id: ast::NodeId) -> bo
|
||||
for index in cfg.graph.depth_traverse(cfg.entry) {
|
||||
let n = cfg.graph.node_data(index);
|
||||
match tcx.map.find(n.id()) {
|
||||
Some(ast_map::NodeExpr(ex)) => {
|
||||
if let ast::ExprRet(Some(ref ret_expr)) = ex.node {
|
||||
Some(hir_map::NodeExpr(ex)) => {
|
||||
if let hir::ExprRet(Some(ref ret_expr)) = ex.node {
|
||||
let mut visitor = FindNestedReturn::new();
|
||||
visit::walk_expr(&mut visitor, &**ret_expr);
|
||||
if visitor.found {
|
||||
@ -1166,7 +1168,7 @@ fn has_nested_returns(tcx: &ty::ctxt, cfg: &cfg::CFG, blk_id: ast::NodeId) -> bo
|
||||
}
|
||||
}
|
||||
}
|
||||
Some(ast_map::NodeBlock(blk)) if blk.id == blk_id => {
|
||||
Some(hir_map::NodeBlock(blk)) if blk.id == blk_id => {
|
||||
let mut visitor = FindNestedReturn::new();
|
||||
visit::walk_expr_opt(&mut visitor, &blk.expr);
|
||||
if visitor.found {
|
||||
@ -1354,7 +1356,7 @@ pub fn arg_kind<'a, 'tcx>(cx: &FunctionContext<'a, 'tcx>, t: Ty<'tcx>)
|
||||
// create_datums_for_fn_args: creates lvalue datums for each of the
|
||||
// incoming function arguments.
|
||||
pub fn create_datums_for_fn_args<'a, 'tcx>(mut bcx: Block<'a, 'tcx>,
|
||||
args: &[ast::Arg],
|
||||
args: &[hir::Arg],
|
||||
arg_tys: &[Ty<'tcx>],
|
||||
has_tupled_arg: bool,
|
||||
arg_scope: cleanup::CustomScopeIndex)
|
||||
@ -1559,12 +1561,12 @@ pub fn build_return_block<'blk, 'tcx>(fcx: &FunctionContext<'blk, 'tcx>,
|
||||
///
|
||||
/// If the function closes over its environment a closure will be returned.
|
||||
pub fn trans_closure<'a, 'b, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block,
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block,
|
||||
llfndecl: ValueRef,
|
||||
param_substs: &'tcx Substs<'tcx>,
|
||||
fn_ast_id: ast::NodeId,
|
||||
_attributes: &[ast::Attribute],
|
||||
_attributes: &[hir::Attribute],
|
||||
output_type: ty::FnOutput<'tcx>,
|
||||
abi: Abi,
|
||||
closure_env: closure::ClosureEnv<'b>) {
|
||||
@ -1678,12 +1680,12 @@ pub fn trans_closure<'a, 'b, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
|
||||
|
||||
/// Creates an LLVM function corresponding to a source language function.
|
||||
pub fn trans_fn<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block,
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block,
|
||||
llfndecl: ValueRef,
|
||||
param_substs: &'tcx Substs<'tcx>,
|
||||
id: ast::NodeId,
|
||||
attrs: &[ast::Attribute]) {
|
||||
attrs: &[hir::Attribute]) {
|
||||
let _s = StatRecorder::new(ccx, ccx.tcx().map.path_to_string(id).to_string());
|
||||
debug!("trans_fn(param_substs={:?})", param_substs);
|
||||
let _icx = push_ctxt("trans_fn");
|
||||
@ -1860,7 +1862,7 @@ fn trans_enum_variant_or_tuple_like_struct<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx
|
||||
finish_fn(&fcx, bcx, result_ty, DebugLoc::None);
|
||||
}
|
||||
|
||||
fn enum_variant_size_lint(ccx: &CrateContext, enum_def: &ast::EnumDef, sp: Span, id: ast::NodeId) {
|
||||
fn enum_variant_size_lint(ccx: &CrateContext, enum_def: &hir::EnumDef, sp: Span, id: ast::NodeId) {
|
||||
let mut sizes = Vec::new(); // does no allocation if no pushes, thankfully
|
||||
|
||||
let print_info = ccx.sess().print_enum_sizes();
|
||||
@ -1939,7 +1941,7 @@ pub struct TransItemVisitor<'a, 'tcx: 'a> {
|
||||
}
|
||||
|
||||
impl<'a, 'tcx, 'v> Visitor<'v> for TransItemVisitor<'a, 'tcx> {
|
||||
fn visit_item(&mut self, i: &ast::Item) {
|
||||
fn visit_item(&mut self, i: &hir::Item) {
|
||||
trans_item(self.ccx, i);
|
||||
}
|
||||
}
|
||||
@ -2010,7 +2012,7 @@ pub fn update_linkage(ccx: &CrateContext,
|
||||
|
||||
if let Some(id) = id {
|
||||
let item = ccx.tcx().map.get(id);
|
||||
if let ast_map::NodeItem(i) = item {
|
||||
if let hir_map::NodeItem(i) = item {
|
||||
if let Some(name) = attr::first_attr_value_str_by_name(&i.attrs, "linkage") {
|
||||
if let Some(linkage) = llvm_linkage_by_name(&name) {
|
||||
llvm::SetLinkage(llval, linkage);
|
||||
@ -2037,7 +2039,7 @@ pub fn update_linkage(ccx: &CrateContext,
|
||||
}
|
||||
}
|
||||
|
||||
fn set_global_section(ccx: &CrateContext, llval: ValueRef, i: &ast::Item) {
|
||||
fn set_global_section(ccx: &CrateContext, llval: ValueRef, i: &hir::Item) {
|
||||
match attr::first_attr_value_str_by_name(&i.attrs,
|
||||
"link_section") {
|
||||
Some(sect) => {
|
||||
@ -2054,13 +2056,13 @@ fn set_global_section(ccx: &CrateContext, llval: ValueRef, i: &ast::Item) {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn trans_item(ccx: &CrateContext, item: &ast::Item) {
|
||||
pub fn trans_item(ccx: &CrateContext, item: &hir::Item) {
|
||||
let _icx = push_ctxt("trans_item");
|
||||
|
||||
let from_external = ccx.external_srcs().borrow().contains_key(&item.id);
|
||||
|
||||
match item.node {
|
||||
ast::ItemFn(ref decl, _, _, abi, ref generics, ref body) => {
|
||||
hir::ItemFn(ref decl, _, _, abi, ref generics, ref body) => {
|
||||
if !generics.is_type_parameterized() {
|
||||
let trans_everywhere = attr::requests_inline(&item.attrs);
|
||||
// Ignore `trans_everywhere` for cross-crate inlined items
|
||||
@ -2098,29 +2100,29 @@ pub fn trans_item(ccx: &CrateContext, item: &ast::Item) {
|
||||
let mut v = TransItemVisitor{ ccx: ccx };
|
||||
v.visit_block(&**body);
|
||||
}
|
||||
ast::ItemImpl(_, _, ref generics, _, _, ref impl_items) => {
|
||||
hir::ItemImpl(_, _, ref generics, _, _, ref impl_items) => {
|
||||
meth::trans_impl(ccx,
|
||||
item.ident,
|
||||
&impl_items[..],
|
||||
generics,
|
||||
item.id);
|
||||
}
|
||||
ast::ItemMod(ref m) => {
|
||||
hir::ItemMod(ref m) => {
|
||||
trans_mod(&ccx.rotate(), m);
|
||||
}
|
||||
ast::ItemEnum(ref enum_definition, ref gens) => {
|
||||
hir::ItemEnum(ref enum_definition, ref gens) => {
|
||||
if gens.ty_params.is_empty() {
|
||||
// sizes only make sense for non-generic types
|
||||
|
||||
enum_variant_size_lint(ccx, enum_definition, item.span, item.id);
|
||||
}
|
||||
}
|
||||
ast::ItemConst(_, ref expr) => {
|
||||
hir::ItemConst(_, ref expr) => {
|
||||
// Recurse on the expression to catch items in blocks
|
||||
let mut v = TransItemVisitor{ ccx: ccx };
|
||||
v.visit_expr(&**expr);
|
||||
}
|
||||
ast::ItemStatic(_, m, ref expr) => {
|
||||
hir::ItemStatic(_, m, ref expr) => {
|
||||
// Recurse on the expression to catch items in blocks
|
||||
let mut v = TransItemVisitor{ ccx: ccx };
|
||||
v.visit_expr(&**expr);
|
||||
@ -2129,10 +2131,10 @@ pub fn trans_item(ccx: &CrateContext, item: &ast::Item) {
|
||||
set_global_section(ccx, g, item);
|
||||
update_linkage(ccx, g, Some(item.id), OriginalTranslation);
|
||||
},
|
||||
ast::ItemForeignMod(ref foreign_mod) => {
|
||||
hir::ItemForeignMod(ref foreign_mod) => {
|
||||
foreign::trans_foreign_mod(ccx, foreign_mod);
|
||||
}
|
||||
ast::ItemTrait(..) => {
|
||||
hir::ItemTrait(..) => {
|
||||
// Inside of this trait definition, we won't be actually translating any
|
||||
// functions, but the trait still needs to be walked. Otherwise default
|
||||
// methods with items will not get translated and will cause ICE's when
|
||||
@ -2149,7 +2151,7 @@ pub fn trans_item(ccx: &CrateContext, item: &ast::Item) {
|
||||
// separate modules in the compiled program. That's because modules exist
|
||||
// only as a convenience for humans working with the code, to organize names
|
||||
// and control visibility.
|
||||
pub fn trans_mod(ccx: &CrateContext, m: &ast::Mod) {
|
||||
pub fn trans_mod(ccx: &CrateContext, m: &hir::Mod) {
|
||||
let _icx = push_ctxt("trans_mod");
|
||||
for item in &m.items {
|
||||
trans_item(ccx, &**item);
|
||||
@ -2295,7 +2297,7 @@ pub fn create_entry_wrapper(ccx: &CrateContext,
|
||||
}
|
||||
|
||||
fn exported_name<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>, id: ast::NodeId,
|
||||
ty: Ty<'tcx>, attrs: &[ast::Attribute]) -> String {
|
||||
ty: Ty<'tcx>, attrs: &[hir::Attribute]) -> String {
|
||||
match ccx.external_srcs().borrow().get(&id) {
|
||||
Some(&did) => {
|
||||
let sym = csearch::get_symbol(&ccx.sess().cstore, did);
|
||||
@ -2340,12 +2342,12 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
let item = ccx.tcx().map.get(id);
|
||||
debug!("get_item_val: id={} item={:?}", id, item);
|
||||
let val = match item {
|
||||
ast_map::NodeItem(i) => {
|
||||
hir_map::NodeItem(i) => {
|
||||
let ty = ccx.tcx().node_id_to_type(i.id);
|
||||
let sym = || exported_name(ccx, id, ty, &i.attrs);
|
||||
|
||||
let v = match i.node {
|
||||
ast::ItemStatic(..) => {
|
||||
hir::ItemStatic(..) => {
|
||||
// If this static came from an external crate, then
|
||||
// we need to get the symbol from csearch instead of
|
||||
// using the current crate's name/version
|
||||
@ -2366,7 +2368,7 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
g
|
||||
}
|
||||
|
||||
ast::ItemFn(_, _, _, abi, _, _) => {
|
||||
hir::ItemFn(_, _, _, abi, _, _) => {
|
||||
let sym = sym();
|
||||
let llfn = if abi == Rust {
|
||||
register_fn(ccx, i.span, sym, i.id, ty)
|
||||
@ -2383,10 +2385,10 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
v
|
||||
}
|
||||
|
||||
ast_map::NodeTraitItem(trait_item) => {
|
||||
hir_map::NodeTraitItem(trait_item) => {
|
||||
debug!("get_item_val(): processing a NodeTraitItem");
|
||||
match trait_item.node {
|
||||
ast::MethodTraitItem(_, Some(_)) => {
|
||||
hir::MethodTraitItem(_, Some(_)) => {
|
||||
register_method(ccx, id, &trait_item.attrs, trait_item.span)
|
||||
}
|
||||
_ => {
|
||||
@ -2397,9 +2399,9 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
}
|
||||
}
|
||||
|
||||
ast_map::NodeImplItem(impl_item) => {
|
||||
hir_map::NodeImplItem(impl_item) => {
|
||||
match impl_item.node {
|
||||
ast::MethodImplItem(..) => {
|
||||
hir::MethodImplItem(..) => {
|
||||
register_method(ccx, id, &impl_item.attrs, impl_item.span)
|
||||
}
|
||||
_ => {
|
||||
@ -2410,9 +2412,9 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
}
|
||||
}
|
||||
|
||||
ast_map::NodeForeignItem(ni) => {
|
||||
hir_map::NodeForeignItem(ni) => {
|
||||
match ni.node {
|
||||
ast::ForeignItemFn(..) => {
|
||||
hir::ForeignItemFn(..) => {
|
||||
let abi = ccx.tcx().map.get_foreign_abi(id);
|
||||
let ty = ccx.tcx().node_id_to_type(ni.id);
|
||||
let name = foreign::link_name(&*ni);
|
||||
@ -2420,17 +2422,17 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
attributes::from_fn_attrs(ccx, &ni.attrs, llfn);
|
||||
llfn
|
||||
}
|
||||
ast::ForeignItemStatic(..) => {
|
||||
hir::ForeignItemStatic(..) => {
|
||||
foreign::register_static(ccx, &*ni)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ast_map::NodeVariant(ref v) => {
|
||||
hir_map::NodeVariant(ref v) => {
|
||||
let llfn;
|
||||
let args = match v.node.kind {
|
||||
ast::TupleVariantKind(ref args) => args,
|
||||
ast::StructVariantKind(_) => {
|
||||
hir::TupleVariantKind(ref args) => args,
|
||||
hir::StructVariantKind(_) => {
|
||||
ccx.sess().bug("struct variant kind unexpected in get_item_val")
|
||||
}
|
||||
};
|
||||
@ -2444,7 +2446,7 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
&enm.attrs);
|
||||
|
||||
llfn = match enm.node {
|
||||
ast::ItemEnum(_, _) => {
|
||||
hir::ItemEnum(_, _) => {
|
||||
register_fn(ccx, (*v).span, sym, id, ty)
|
||||
}
|
||||
_ => ccx.sess().bug("NodeVariant, shouldn't happen")
|
||||
@ -2453,7 +2455,7 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
llfn
|
||||
}
|
||||
|
||||
ast_map::NodeStructCtor(struct_def) => {
|
||||
hir_map::NodeStructCtor(struct_def) => {
|
||||
// Only register the constructor if this is a tuple-like struct.
|
||||
let ctor_id = match struct_def.ctor_id {
|
||||
None => {
|
||||
@ -2495,7 +2497,7 @@ pub fn get_item_val(ccx: &CrateContext, id: ast::NodeId) -> ValueRef {
|
||||
}
|
||||
|
||||
fn register_method(ccx: &CrateContext, id: ast::NodeId,
|
||||
attrs: &[ast::Attribute], span: Span) -> ValueRef {
|
||||
attrs: &[hir::Attribute], span: Span) -> ValueRef {
|
||||
let mty = ccx.tcx().node_id_to_type(id);
|
||||
|
||||
let sym = exported_name(ccx, id, mty, &attrs);
|
||||
@ -2529,7 +2531,7 @@ pub fn crate_ctxt_to_encode_parms<'a, 'tcx>(cx: &'a SharedCrateContext<'a, 'tcx>
|
||||
}
|
||||
}
|
||||
|
||||
pub fn write_metadata(cx: &SharedCrateContext, krate: &ast::Crate,
|
||||
pub fn write_metadata(cx: &SharedCrateContext, krate: &hir::Crate,
|
||||
reachable: &NodeSet) -> Vec<u8> {
|
||||
use flate;
|
||||
|
||||
@ -2679,7 +2681,7 @@ pub fn filter_reachable_ids(ccx: &SharedCrateContext) -> NodeSet {
|
||||
// As a result, if this id is an FFI item (foreign item) then we only
|
||||
// let it through if it's included statically.
|
||||
match ccx.tcx().map.get(id) {
|
||||
ast_map::NodeForeignItem(..) => {
|
||||
hir_map::NodeForeignItem(..) => {
|
||||
ccx.sess().cstore.is_statically_included_foreign_item(id)
|
||||
}
|
||||
_ => true,
|
||||
|
@ -26,6 +26,7 @@ use middle::def;
|
||||
use middle::def_id::{DefId, LOCAL_CRATE};
|
||||
use middle::subst;
|
||||
use middle::subst::{Subst, Substs};
|
||||
use rustc::front::map as hir_map;
|
||||
use trans::adt;
|
||||
use trans::base;
|
||||
use trans::base::*;
|
||||
@ -50,7 +51,7 @@ use trans::type_::Type;
|
||||
use trans::type_of;
|
||||
use middle::ty::{self, Ty, HasTypeFlags, RegionEscape};
|
||||
use middle::ty::MethodCall;
|
||||
use rustc::ast_map;
|
||||
use rustc_front::hir;
|
||||
|
||||
use syntax::abi as synabi;
|
||||
use syntax::ast;
|
||||
@ -83,14 +84,14 @@ pub struct Callee<'blk, 'tcx: 'blk> {
|
||||
pub ty: Ty<'tcx>
|
||||
}
|
||||
|
||||
fn trans<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, expr: &ast::Expr)
|
||||
fn trans<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, expr: &hir::Expr)
|
||||
-> Callee<'blk, 'tcx> {
|
||||
let _icx = push_ctxt("trans_callee");
|
||||
debug!("callee::trans(expr={:?})", expr);
|
||||
|
||||
// pick out special kinds of expressions that can be called:
|
||||
match expr.node {
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
return trans_def(bcx, bcx.def(expr.id), expr);
|
||||
}
|
||||
_ => {}
|
||||
@ -99,7 +100,7 @@ fn trans<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, expr: &ast::Expr)
|
||||
// any other expressions are closures:
|
||||
return datum_callee(bcx, expr);
|
||||
|
||||
fn datum_callee<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, expr: &ast::Expr)
|
||||
fn datum_callee<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, expr: &hir::Expr)
|
||||
-> Callee<'blk, 'tcx> {
|
||||
let DatumBlock { bcx, datum, .. } = expr::trans(bcx, expr);
|
||||
match datum.ty.sty {
|
||||
@ -130,7 +131,7 @@ fn trans<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, expr: &ast::Expr)
|
||||
|
||||
fn trans_def<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
def: def::Def,
|
||||
ref_expr: &ast::Expr)
|
||||
ref_expr: &hir::Expr)
|
||||
-> Callee<'blk, 'tcx> {
|
||||
debug!("trans_def(def={:?}, ref_expr={:?})", def, ref_expr);
|
||||
let expr_ty = common::node_id_type(bcx, ref_expr.id);
|
||||
@ -140,7 +141,7 @@ fn trans<'blk, 'tcx>(bcx: Block<'blk, 'tcx>, expr: &ast::Expr)
|
||||
let maybe_ast_node = maybe_def_id.and_then(|def_id| bcx.tcx().map
|
||||
.find(def_id.node));
|
||||
match maybe_ast_node {
|
||||
Some(ast_map::NodeStructCtor(_)) => true,
|
||||
Some(hir_map::NodeStructCtor(_)) => true,
|
||||
_ => false
|
||||
}
|
||||
} => {
|
||||
@ -286,7 +287,7 @@ pub fn trans_fn_pointer_shim<'a, 'tcx>(
|
||||
let (opt_def_id, sig) =
|
||||
match bare_fn_ty.sty {
|
||||
ty::TyBareFn(opt_def_id,
|
||||
&ty::BareFnTy { unsafety: ast::Unsafety::Normal,
|
||||
&ty::BareFnTy { unsafety: hir::Unsafety::Normal,
|
||||
abi: synabi::Rust,
|
||||
ref sig }) => {
|
||||
(opt_def_id, sig)
|
||||
@ -301,7 +302,7 @@ pub fn trans_fn_pointer_shim<'a, 'tcx>(
|
||||
let tuple_input_ty = tcx.mk_tup(sig.inputs.to_vec());
|
||||
let tuple_fn_ty = tcx.mk_fn(opt_def_id,
|
||||
tcx.mk_bare_fn(ty::BareFnTy {
|
||||
unsafety: ast::Unsafety::Normal,
|
||||
unsafety: hir::Unsafety::Normal,
|
||||
abi: synabi::RustCall,
|
||||
sig: ty::Binder(ty::FnSig {
|
||||
inputs: vec![bare_fn_ty_maybe_ref,
|
||||
@ -471,11 +472,11 @@ pub fn trans_fn_ref_with_substs<'a, 'tcx>(
|
||||
|| "local item should be in ast map".to_string());
|
||||
|
||||
match map_node {
|
||||
ast_map::NodeVariant(v) => match v.node.kind {
|
||||
ast::TupleVariantKind(ref args) => !args.is_empty(),
|
||||
hir_map::NodeVariant(v) => match v.node.kind {
|
||||
hir::TupleVariantKind(ref args) => !args.is_empty(),
|
||||
_ => false
|
||||
},
|
||||
ast_map::NodeStructCtor(_) => true,
|
||||
hir_map::NodeStructCtor(_) => true,
|
||||
_ => false
|
||||
}
|
||||
} else {
|
||||
@ -572,8 +573,8 @@ pub fn trans_fn_ref_with_substs<'a, 'tcx>(
|
||||
// Translating calls
|
||||
|
||||
pub fn trans_call<'a, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
call_expr: &ast::Expr,
|
||||
f: &ast::Expr,
|
||||
call_expr: &hir::Expr,
|
||||
f: &hir::Expr,
|
||||
args: CallArgs<'a, 'tcx>,
|
||||
dest: expr::Dest)
|
||||
-> Block<'blk, 'tcx> {
|
||||
@ -586,8 +587,8 @@ pub fn trans_call<'a, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
}
|
||||
|
||||
pub fn trans_method_call<'a, 'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
call_expr: &ast::Expr,
|
||||
rcvr: &ast::Expr,
|
||||
call_expr: &hir::Expr,
|
||||
rcvr: &hir::Expr,
|
||||
args: CallArgs<'a, 'tcx>,
|
||||
dest: expr::Dest)
|
||||
-> Block<'blk, 'tcx> {
|
||||
@ -853,7 +854,7 @@ pub fn trans_call_inner<'a, 'blk, 'tcx, F>(bcx: Block<'blk, 'tcx>,
|
||||
pub enum CallArgs<'a, 'tcx> {
|
||||
// Supply value of arguments as a list of expressions that must be
|
||||
// translated. This is used in the common case of `foo(bar, qux)`.
|
||||
ArgExprs(&'a [P<ast::Expr>]),
|
||||
ArgExprs(&'a [P<hir::Expr>]),
|
||||
|
||||
// Supply value of arguments as a list of LLVM value refs; frequently
|
||||
// used with lang items and so forth, when the argument is an internal
|
||||
@ -868,12 +869,12 @@ pub enum CallArgs<'a, 'tcx> {
|
||||
|
||||
// Supply value of arguments as a list of expressions that must be
|
||||
// translated, for overloaded call operators.
|
||||
ArgOverloadedCall(Vec<&'a ast::Expr>),
|
||||
ArgOverloadedCall(Vec<&'a hir::Expr>),
|
||||
}
|
||||
|
||||
fn trans_args_under_call_abi<'blk, 'tcx>(
|
||||
mut bcx: Block<'blk, 'tcx>,
|
||||
arg_exprs: &[P<ast::Expr>],
|
||||
arg_exprs: &[P<hir::Expr>],
|
||||
fn_ty: Ty<'tcx>,
|
||||
llargs: &mut Vec<ValueRef>,
|
||||
arg_cleanup_scope: cleanup::ScopeId,
|
||||
@ -934,7 +935,7 @@ fn trans_args_under_call_abi<'blk, 'tcx>(
|
||||
|
||||
fn trans_overloaded_call_args<'blk, 'tcx>(
|
||||
mut bcx: Block<'blk, 'tcx>,
|
||||
arg_exprs: Vec<&ast::Expr>,
|
||||
arg_exprs: Vec<&hir::Expr>,
|
||||
fn_ty: Ty<'tcx>,
|
||||
llargs: &mut Vec<ValueRef>,
|
||||
arg_cleanup_scope: cleanup::ScopeId,
|
||||
|
@ -32,6 +32,8 @@ use session::config::FullDebugInfo;
|
||||
use syntax::abi::RustCall;
|
||||
use syntax::ast;
|
||||
|
||||
use rustc_front::hir;
|
||||
|
||||
|
||||
fn load_closure_environment<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
|
||||
arg_scope_id: ScopeId,
|
||||
@ -171,8 +173,8 @@ pub enum Dest<'a, 'tcx: 'a> {
|
||||
}
|
||||
|
||||
pub fn trans_closure_expr<'a, 'tcx>(dest: Dest<'a, 'tcx>,
|
||||
decl: &ast::FnDecl,
|
||||
body: &ast::Block,
|
||||
decl: &hir::FnDecl,
|
||||
body: &hir::Block,
|
||||
id: ast::NodeId,
|
||||
closure_substs: &'tcx ty::ClosureSubsts<'tcx>)
|
||||
-> Option<Block<'a, 'tcx>>
|
||||
|
@ -40,7 +40,8 @@ use middle::traits;
|
||||
use middle::ty::{self, HasTypeFlags, Ty};
|
||||
use middle::ty_fold;
|
||||
use middle::ty_fold::{TypeFolder, TypeFoldable};
|
||||
use rustc::ast_map::{PathElem, PathName};
|
||||
use rustc::front::map::{PathElem, PathName};
|
||||
use rustc_front::hir;
|
||||
use util::nodemap::{FnvHashMap, NodeMap};
|
||||
|
||||
use arena::TypedArena;
|
||||
@ -266,7 +267,7 @@ pub struct NodeIdAndSpan {
|
||||
pub span: Span,
|
||||
}
|
||||
|
||||
pub fn expr_info(expr: &ast::Expr) -> NodeIdAndSpan {
|
||||
pub fn expr_info(expr: &hir::Expr) -> NodeIdAndSpan {
|
||||
NodeIdAndSpan { id: expr.id, span: expr.span }
|
||||
}
|
||||
|
||||
@ -1024,11 +1025,11 @@ pub fn node_id_type<'blk, 'tcx>(bcx: &BlockS<'blk, 'tcx>, id: ast::NodeId) -> Ty
|
||||
monomorphize_type(bcx, t)
|
||||
}
|
||||
|
||||
pub fn expr_ty<'blk, 'tcx>(bcx: &BlockS<'blk, 'tcx>, ex: &ast::Expr) -> Ty<'tcx> {
|
||||
pub fn expr_ty<'blk, 'tcx>(bcx: &BlockS<'blk, 'tcx>, ex: &hir::Expr) -> Ty<'tcx> {
|
||||
node_id_type(bcx, ex.id)
|
||||
}
|
||||
|
||||
pub fn expr_ty_adjusted<'blk, 'tcx>(bcx: &BlockS<'blk, 'tcx>, ex: &ast::Expr) -> Ty<'tcx> {
|
||||
pub fn expr_ty_adjusted<'blk, 'tcx>(bcx: &BlockS<'blk, 'tcx>, ex: &hir::Expr) -> Ty<'tcx> {
|
||||
monomorphize_type(bcx, bcx.tcx().expr_ty_adjusted(ex))
|
||||
}
|
||||
|
||||
|
@ -38,28 +38,31 @@ use middle::subst::Substs;
|
||||
use middle::ty::{self, Ty};
|
||||
use util::nodemap::NodeMap;
|
||||
|
||||
use rustc_front::hir;
|
||||
use rustc_front::attr;
|
||||
|
||||
use std::ffi::{CStr, CString};
|
||||
use libc::c_uint;
|
||||
use syntax::{ast, attr};
|
||||
use syntax::ast;
|
||||
use syntax::parse::token;
|
||||
use syntax::ptr::P;
|
||||
|
||||
pub type FnArgMap<'a> = Option<&'a NodeMap<ValueRef>>;
|
||||
|
||||
pub fn const_lit(cx: &CrateContext, e: &ast::Expr, lit: &ast::Lit)
|
||||
pub fn const_lit(cx: &CrateContext, e: &hir::Expr, lit: &hir::Lit)
|
||||
-> ValueRef {
|
||||
let _icx = push_ctxt("trans_lit");
|
||||
debug!("const_lit: {:?}", lit);
|
||||
match lit.node {
|
||||
ast::LitByte(b) => C_integral(Type::uint_from_ty(cx, ast::TyU8), b as u64, false),
|
||||
ast::LitChar(i) => C_integral(Type::char(cx), i as u64, false),
|
||||
ast::LitInt(i, ast::SignedIntLit(t, _)) => {
|
||||
hir::LitByte(b) => C_integral(Type::uint_from_ty(cx, hir::TyU8), b as u64, false),
|
||||
hir::LitChar(i) => C_integral(Type::char(cx), i as u64, false),
|
||||
hir::LitInt(i, hir::SignedIntLit(t, _)) => {
|
||||
C_integral(Type::int_from_ty(cx, t), i, true)
|
||||
}
|
||||
ast::LitInt(u, ast::UnsignedIntLit(t)) => {
|
||||
hir::LitInt(u, hir::UnsignedIntLit(t)) => {
|
||||
C_integral(Type::uint_from_ty(cx, t), u, false)
|
||||
}
|
||||
ast::LitInt(i, ast::UnsuffixedIntLit(_)) => {
|
||||
hir::LitInt(i, hir::UnsuffixedIntLit(_)) => {
|
||||
let lit_int_ty = cx.tcx().node_id_to_type(e.id);
|
||||
match lit_int_ty.sty {
|
||||
ty::TyInt(t) => {
|
||||
@ -74,10 +77,10 @@ pub fn const_lit(cx: &CrateContext, e: &ast::Expr, lit: &ast::Lit)
|
||||
lit_int_ty))
|
||||
}
|
||||
}
|
||||
ast::LitFloat(ref fs, t) => {
|
||||
hir::LitFloat(ref fs, t) => {
|
||||
C_floating(&fs, Type::float_from_ty(cx, t))
|
||||
}
|
||||
ast::LitFloatUnsuffixed(ref fs) => {
|
||||
hir::LitFloatUnsuffixed(ref fs) => {
|
||||
let lit_float_ty = cx.tcx().node_id_to_type(e.id);
|
||||
match lit_float_ty.sty {
|
||||
ty::TyFloat(t) => {
|
||||
@ -89,9 +92,9 @@ pub fn const_lit(cx: &CrateContext, e: &ast::Expr, lit: &ast::Lit)
|
||||
}
|
||||
}
|
||||
}
|
||||
ast::LitBool(b) => C_bool(cx, b),
|
||||
ast::LitStr(ref s, _) => C_str_slice(cx, (*s).clone()),
|
||||
ast::LitBinary(ref data) => {
|
||||
hir::LitBool(b) => C_bool(cx, b),
|
||||
hir::LitStr(ref s, _) => C_str_slice(cx, (*s).clone()),
|
||||
hir::LitBinary(ref data) => {
|
||||
addr_of(cx, C_bytes(cx, &data[..]), "binary")
|
||||
}
|
||||
}
|
||||
@ -194,8 +197,8 @@ fn const_fn_call<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
|
||||
|
||||
pub fn get_const_expr<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
|
||||
def_id: DefId,
|
||||
ref_expr: &ast::Expr)
|
||||
-> &'tcx ast::Expr {
|
||||
ref_expr: &hir::Expr)
|
||||
-> &'tcx hir::Expr {
|
||||
let def_id = inline::maybe_instantiate_inline(ccx, def_id);
|
||||
|
||||
if def_id.krate != LOCAL_CRATE {
|
||||
@ -213,21 +216,21 @@ pub fn get_const_expr<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
|
||||
|
||||
fn get_const_val(ccx: &CrateContext,
|
||||
def_id: DefId,
|
||||
ref_expr: &ast::Expr) -> ValueRef {
|
||||
ref_expr: &hir::Expr) -> ValueRef {
|
||||
let expr = get_const_expr(ccx, def_id, ref_expr);
|
||||
let empty_substs = ccx.tcx().mk_substs(Substs::trans_empty());
|
||||
get_const_expr_as_global(ccx, expr, check_const::ConstQualif::empty(), empty_substs)
|
||||
}
|
||||
|
||||
pub fn get_const_expr_as_global<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
|
||||
expr: &ast::Expr,
|
||||
expr: &hir::Expr,
|
||||
qualif: check_const::ConstQualif,
|
||||
param_substs: &'tcx Substs<'tcx>)
|
||||
-> ValueRef {
|
||||
debug!("get_const_expr_as_global: {:?}", expr.id);
|
||||
// Special-case constants to cache a common global for all uses.
|
||||
match expr.node {
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
let def = ccx.tcx().def_map.borrow().get(&expr.id).unwrap().full_def();
|
||||
match def {
|
||||
def::DefConst(def_id) | def::DefAssociatedConst(def_id) => {
|
||||
@ -274,7 +277,7 @@ pub fn get_const_expr_as_global<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
|
||||
}
|
||||
|
||||
pub fn const_expr<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
e: &ast::Expr,
|
||||
e: &hir::Expr,
|
||||
param_substs: &'tcx Substs<'tcx>,
|
||||
fn_args: FnArgMap)
|
||||
-> (ValueRef, Ty<'tcx>) {
|
||||
@ -378,11 +381,11 @@ pub fn const_expr<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
(llconst, ety_adjusted)
|
||||
}
|
||||
|
||||
fn check_unary_expr_validity(cx: &CrateContext, e: &ast::Expr, t: Ty,
|
||||
fn check_unary_expr_validity(cx: &CrateContext, e: &hir::Expr, t: Ty,
|
||||
te: ValueRef) {
|
||||
// The only kind of unary expression that we check for validity
|
||||
// here is `-expr`, to check if it "overflows" (e.g. `-i32::MIN`).
|
||||
if let ast::ExprUnary(ast::UnNeg, ref inner_e) = e.node {
|
||||
if let hir::ExprUnary(hir::UnNeg, ref inner_e) = e.node {
|
||||
|
||||
// An unfortunate special case: we parse e.g. -128 as a
|
||||
// negation of the literal 128, which means if we're expecting
|
||||
@ -392,7 +395,7 @@ fn check_unary_expr_validity(cx: &CrateContext, e: &ast::Expr, t: Ty,
|
||||
//
|
||||
// Catch this up front by looking for ExprLit directly,
|
||||
// and just accepting it.
|
||||
if let ast::ExprLit(_) = inner_e.node { return; }
|
||||
if let hir::ExprLit(_) = inner_e.node { return; }
|
||||
|
||||
let result = match t.sty {
|
||||
ty::TyInt(int_type) => {
|
||||
@ -421,9 +424,9 @@ fn check_unary_expr_validity(cx: &CrateContext, e: &ast::Expr, t: Ty,
|
||||
}
|
||||
}
|
||||
|
||||
fn check_binary_expr_validity(cx: &CrateContext, e: &ast::Expr, t: Ty,
|
||||
fn check_binary_expr_validity(cx: &CrateContext, e: &hir::Expr, t: Ty,
|
||||
te1: ValueRef, te2: ValueRef) {
|
||||
let b = if let ast::ExprBinary(b, _, _) = e.node { b } else { return };
|
||||
let b = if let hir::ExprBinary(b, _, _) = e.node { b } else { return };
|
||||
|
||||
let result = match t.sty {
|
||||
ty::TyInt(int_type) => {
|
||||
@ -435,13 +438,13 @@ fn check_binary_expr_validity(cx: &CrateContext, e: &ast::Expr, t: Ty,
|
||||
|
||||
let opt_ety = Some(const_eval::IntTy::from(cx.tcx(), int_type));
|
||||
match b.node {
|
||||
ast::BiAdd => const_int_checked_add(lhs, rhs, e, opt_ety),
|
||||
ast::BiSub => const_int_checked_sub(lhs, rhs, e, opt_ety),
|
||||
ast::BiMul => const_int_checked_mul(lhs, rhs, e, opt_ety),
|
||||
ast::BiDiv => const_int_checked_div(lhs, rhs, e, opt_ety),
|
||||
ast::BiRem => const_int_checked_rem(lhs, rhs, e, opt_ety),
|
||||
ast::BiShl => const_int_checked_shl(lhs, rhs, e, opt_ety),
|
||||
ast::BiShr => const_int_checked_shr(lhs, rhs, e, opt_ety),
|
||||
hir::BiAdd => const_int_checked_add(lhs, rhs, e, opt_ety),
|
||||
hir::BiSub => const_int_checked_sub(lhs, rhs, e, opt_ety),
|
||||
hir::BiMul => const_int_checked_mul(lhs, rhs, e, opt_ety),
|
||||
hir::BiDiv => const_int_checked_div(lhs, rhs, e, opt_ety),
|
||||
hir::BiRem => const_int_checked_rem(lhs, rhs, e, opt_ety),
|
||||
hir::BiShl => const_int_checked_shl(lhs, rhs, e, opt_ety),
|
||||
hir::BiShr => const_int_checked_shr(lhs, rhs, e, opt_ety),
|
||||
_ => return,
|
||||
}
|
||||
}
|
||||
@ -454,13 +457,13 @@ fn check_binary_expr_validity(cx: &CrateContext, e: &ast::Expr, t: Ty,
|
||||
|
||||
let opt_ety = Some(const_eval::UintTy::from(cx.tcx(), uint_type));
|
||||
match b.node {
|
||||
ast::BiAdd => const_uint_checked_add(lhs, rhs, e, opt_ety),
|
||||
ast::BiSub => const_uint_checked_sub(lhs, rhs, e, opt_ety),
|
||||
ast::BiMul => const_uint_checked_mul(lhs, rhs, e, opt_ety),
|
||||
ast::BiDiv => const_uint_checked_div(lhs, rhs, e, opt_ety),
|
||||
ast::BiRem => const_uint_checked_rem(lhs, rhs, e, opt_ety),
|
||||
ast::BiShl => const_uint_checked_shl(lhs, rhs, e, opt_ety),
|
||||
ast::BiShr => const_uint_checked_shr(lhs, rhs, e, opt_ety),
|
||||
hir::BiAdd => const_uint_checked_add(lhs, rhs, e, opt_ety),
|
||||
hir::BiSub => const_uint_checked_sub(lhs, rhs, e, opt_ety),
|
||||
hir::BiMul => const_uint_checked_mul(lhs, rhs, e, opt_ety),
|
||||
hir::BiDiv => const_uint_checked_div(lhs, rhs, e, opt_ety),
|
||||
hir::BiRem => const_uint_checked_rem(lhs, rhs, e, opt_ety),
|
||||
hir::BiShl => const_uint_checked_shl(lhs, rhs, e, opt_ety),
|
||||
hir::BiShr => const_uint_checked_shr(lhs, rhs, e, opt_ety),
|
||||
_ => return,
|
||||
}
|
||||
}
|
||||
@ -473,7 +476,7 @@ fn check_binary_expr_validity(cx: &CrateContext, e: &ast::Expr, t: Ty,
|
||||
}
|
||||
|
||||
fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
e: &ast::Expr,
|
||||
e: &hir::Expr,
|
||||
ety: Ty<'tcx>,
|
||||
param_substs: &'tcx Substs<'tcx>,
|
||||
fn_args: FnArgMap)
|
||||
@ -484,17 +487,17 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
ety,
|
||||
param_substs);
|
||||
|
||||
let map_list = |exprs: &[P<ast::Expr>]| -> Vec<ValueRef> {
|
||||
let map_list = |exprs: &[P<hir::Expr>]| -> Vec<ValueRef> {
|
||||
exprs.iter()
|
||||
.map(|e| const_expr(cx, &**e, param_substs, fn_args).0)
|
||||
.collect()
|
||||
};
|
||||
let _icx = push_ctxt("const_expr");
|
||||
match e.node {
|
||||
ast::ExprLit(ref lit) => {
|
||||
hir::ExprLit(ref lit) => {
|
||||
const_lit(cx, e, &**lit)
|
||||
},
|
||||
ast::ExprBinary(b, ref e1, ref e2) => {
|
||||
hir::ExprBinary(b, ref e1, ref e2) => {
|
||||
/* Neither type is bottom, and we expect them to be unified
|
||||
* already, so the following is safe. */
|
||||
let (te1, ty) = const_expr(cx, &**e1, param_substs, fn_args);
|
||||
@ -510,38 +513,38 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
check_binary_expr_validity(cx, e, ty, te1, te2);
|
||||
|
||||
unsafe { match b.node {
|
||||
ast::BiAdd if is_float => llvm::LLVMConstFAdd(te1, te2),
|
||||
ast::BiAdd => llvm::LLVMConstAdd(te1, te2),
|
||||
hir::BiAdd if is_float => llvm::LLVMConstFAdd(te1, te2),
|
||||
hir::BiAdd => llvm::LLVMConstAdd(te1, te2),
|
||||
|
||||
ast::BiSub if is_float => llvm::LLVMConstFSub(te1, te2),
|
||||
ast::BiSub => llvm::LLVMConstSub(te1, te2),
|
||||
hir::BiSub if is_float => llvm::LLVMConstFSub(te1, te2),
|
||||
hir::BiSub => llvm::LLVMConstSub(te1, te2),
|
||||
|
||||
ast::BiMul if is_float => llvm::LLVMConstFMul(te1, te2),
|
||||
ast::BiMul => llvm::LLVMConstMul(te1, te2),
|
||||
hir::BiMul if is_float => llvm::LLVMConstFMul(te1, te2),
|
||||
hir::BiMul => llvm::LLVMConstMul(te1, te2),
|
||||
|
||||
ast::BiDiv if is_float => llvm::LLVMConstFDiv(te1, te2),
|
||||
ast::BiDiv if signed => llvm::LLVMConstSDiv(te1, te2),
|
||||
ast::BiDiv => llvm::LLVMConstUDiv(te1, te2),
|
||||
hir::BiDiv if is_float => llvm::LLVMConstFDiv(te1, te2),
|
||||
hir::BiDiv if signed => llvm::LLVMConstSDiv(te1, te2),
|
||||
hir::BiDiv => llvm::LLVMConstUDiv(te1, te2),
|
||||
|
||||
ast::BiRem if is_float => llvm::LLVMConstFRem(te1, te2),
|
||||
ast::BiRem if signed => llvm::LLVMConstSRem(te1, te2),
|
||||
ast::BiRem => llvm::LLVMConstURem(te1, te2),
|
||||
hir::BiRem if is_float => llvm::LLVMConstFRem(te1, te2),
|
||||
hir::BiRem if signed => llvm::LLVMConstSRem(te1, te2),
|
||||
hir::BiRem => llvm::LLVMConstURem(te1, te2),
|
||||
|
||||
ast::BiAnd => llvm::LLVMConstAnd(te1, te2),
|
||||
ast::BiOr => llvm::LLVMConstOr(te1, te2),
|
||||
ast::BiBitXor => llvm::LLVMConstXor(te1, te2),
|
||||
ast::BiBitAnd => llvm::LLVMConstAnd(te1, te2),
|
||||
ast::BiBitOr => llvm::LLVMConstOr(te1, te2),
|
||||
ast::BiShl => {
|
||||
hir::BiAnd => llvm::LLVMConstAnd(te1, te2),
|
||||
hir::BiOr => llvm::LLVMConstOr(te1, te2),
|
||||
hir::BiBitXor => llvm::LLVMConstXor(te1, te2),
|
||||
hir::BiBitAnd => llvm::LLVMConstAnd(te1, te2),
|
||||
hir::BiBitOr => llvm::LLVMConstOr(te1, te2),
|
||||
hir::BiShl => {
|
||||
let te2 = base::cast_shift_const_rhs(b.node, te1, te2);
|
||||
llvm::LLVMConstShl(te1, te2)
|
||||
},
|
||||
ast::BiShr => {
|
||||
hir::BiShr => {
|
||||
let te2 = base::cast_shift_const_rhs(b.node, te1, te2);
|
||||
if signed { llvm::LLVMConstAShr(te1, te2) }
|
||||
else { llvm::LLVMConstLShr(te1, te2) }
|
||||
},
|
||||
ast::BiEq | ast::BiNe | ast::BiLt | ast::BiLe | ast::BiGt | ast::BiGe => {
|
||||
hir::BiEq | hir::BiNe | hir::BiLt | hir::BiLe | hir::BiGt | hir::BiGe => {
|
||||
if is_float {
|
||||
let cmp = base::bin_op_to_fcmp_predicate(cx, b.node);
|
||||
ConstFCmp(cmp, te1, te2)
|
||||
@ -552,34 +555,34 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
},
|
||||
} } // unsafe { match b.node {
|
||||
},
|
||||
ast::ExprUnary(u, ref inner_e) => {
|
||||
hir::ExprUnary(u, ref inner_e) => {
|
||||
let (te, ty) = const_expr(cx, &**inner_e, param_substs, fn_args);
|
||||
|
||||
check_unary_expr_validity(cx, e, ty, te);
|
||||
|
||||
let is_float = ty.is_fp();
|
||||
unsafe { match u {
|
||||
ast::UnUniq | ast::UnDeref => const_deref(cx, te, ty).0,
|
||||
ast::UnNot => llvm::LLVMConstNot(te),
|
||||
ast::UnNeg if is_float => llvm::LLVMConstFNeg(te),
|
||||
ast::UnNeg => llvm::LLVMConstNeg(te),
|
||||
hir::UnUniq | hir::UnDeref => const_deref(cx, te, ty).0,
|
||||
hir::UnNot => llvm::LLVMConstNot(te),
|
||||
hir::UnNeg if is_float => llvm::LLVMConstFNeg(te),
|
||||
hir::UnNeg => llvm::LLVMConstNeg(te),
|
||||
} }
|
||||
},
|
||||
ast::ExprField(ref base, field) => {
|
||||
hir::ExprField(ref base, field) => {
|
||||
let (bv, bt) = const_expr(cx, &**base, param_substs, fn_args);
|
||||
let brepr = adt::represent_type(cx, bt);
|
||||
let vinfo = VariantInfo::from_ty(cx.tcx(), bt, None);
|
||||
let ix = vinfo.field_index(field.node.name);
|
||||
adt::const_get_field(cx, &*brepr, bv, vinfo.discr, ix)
|
||||
},
|
||||
ast::ExprTupField(ref base, idx) => {
|
||||
hir::ExprTupField(ref base, idx) => {
|
||||
let (bv, bt) = const_expr(cx, &**base, param_substs, fn_args);
|
||||
let brepr = adt::represent_type(cx, bt);
|
||||
let vinfo = VariantInfo::from_ty(cx.tcx(), bt, None);
|
||||
adt::const_get_field(cx, &*brepr, bv, vinfo.discr, idx.node)
|
||||
},
|
||||
|
||||
ast::ExprIndex(ref base, ref index) => {
|
||||
hir::ExprIndex(ref base, ref index) => {
|
||||
let (bv, bt) = const_expr(cx, &**base, param_substs, fn_args);
|
||||
let iv = match eval_const_expr_partial(cx.tcx(), &index, ExprTypeChecked) {
|
||||
Ok(ConstVal::Int(i)) => i as u64,
|
||||
@ -629,7 +632,7 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
const_get_elt(cx, arr, &[iv as c_uint])
|
||||
}
|
||||
},
|
||||
ast::ExprCast(ref base, _) => {
|
||||
hir::ExprCast(ref base, _) => {
|
||||
let t_cast = ety;
|
||||
let llty = type_of::type_of(cx, t_cast);
|
||||
let (v, t_expr) = const_expr(cx, &**base, param_substs, fn_args);
|
||||
@ -690,15 +693,15 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
},
|
||||
} } // unsafe { match ( ... ) {
|
||||
},
|
||||
ast::ExprAddrOf(ast::MutImmutable, ref sub) => {
|
||||
hir::ExprAddrOf(hir::MutImmutable, ref sub) => {
|
||||
// If this is the address of some static, then we need to return
|
||||
// the actual address of the static itself (short circuit the rest
|
||||
// of const eval).
|
||||
let mut cur = sub;
|
||||
loop {
|
||||
match cur.node {
|
||||
ast::ExprParen(ref sub) => cur = sub,
|
||||
ast::ExprBlock(ref blk) => {
|
||||
hir::ExprParen(ref sub) => cur = sub,
|
||||
hir::ExprBlock(ref blk) => {
|
||||
if let Some(ref sub) = blk.expr {
|
||||
cur = sub;
|
||||
} else {
|
||||
@ -718,16 +721,16 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
addr_of(cx, v, "ref")
|
||||
}
|
||||
},
|
||||
ast::ExprAddrOf(ast::MutMutable, ref sub) => {
|
||||
hir::ExprAddrOf(hir::MutMutable, ref sub) => {
|
||||
let (v, _) = const_expr(cx, &**sub, param_substs, fn_args);
|
||||
addr_of_mut(cx, v, "ref_mut_slice")
|
||||
},
|
||||
ast::ExprTup(ref es) => {
|
||||
hir::ExprTup(ref es) => {
|
||||
let repr = adt::represent_type(cx, ety);
|
||||
let vals = map_list(&es[..]);
|
||||
adt::trans_const(cx, &*repr, 0, &vals[..])
|
||||
},
|
||||
ast::ExprStruct(_, ref fs, ref base_opt) => {
|
||||
hir::ExprStruct(_, ref fs, ref base_opt) => {
|
||||
let repr = adt::represent_type(cx, ety);
|
||||
|
||||
let base_val = match *base_opt {
|
||||
@ -749,7 +752,7 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
adt::trans_const(cx, &*repr, discr, &cs[..])
|
||||
}
|
||||
},
|
||||
ast::ExprVec(ref es) => {
|
||||
hir::ExprVec(ref es) => {
|
||||
let unit_ty = ety.sequence_element_type(cx.tcx());
|
||||
let llunitty = type_of::type_of(cx, unit_ty);
|
||||
let vs = es.iter()
|
||||
@ -762,7 +765,7 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
C_array(llunitty, &vs[..])
|
||||
}
|
||||
},
|
||||
ast::ExprRepeat(ref elem, ref count) => {
|
||||
hir::ExprRepeat(ref elem, ref count) => {
|
||||
let unit_ty = ety.sequence_element_type(cx.tcx());
|
||||
let llunitty = type_of::type_of(cx, unit_ty);
|
||||
let n = cx.tcx().eval_repeat_count(count);
|
||||
@ -774,7 +777,7 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
C_array(llunitty, &vs[..])
|
||||
}
|
||||
},
|
||||
ast::ExprPath(..) => {
|
||||
hir::ExprPath(..) => {
|
||||
let def = cx.tcx().def_map.borrow().get(&e.id).unwrap().full_def();
|
||||
match def {
|
||||
def::DefLocal(id) => {
|
||||
@ -820,12 +823,12 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
}
|
||||
}
|
||||
},
|
||||
ast::ExprCall(ref callee, ref args) => {
|
||||
hir::ExprCall(ref callee, ref args) => {
|
||||
let mut callee = &**callee;
|
||||
loop {
|
||||
callee = match callee.node {
|
||||
ast::ExprParen(ref inner) => &**inner,
|
||||
ast::ExprBlock(ref block) => match block.expr {
|
||||
hir::ExprParen(ref inner) => &**inner,
|
||||
hir::ExprBlock(ref block) => match block.expr {
|
||||
Some(ref tail) => &**tail,
|
||||
None => break,
|
||||
},
|
||||
@ -857,21 +860,21 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
_ => cx.sess().span_bug(e.span, "expected a struct, variant, or const fn def"),
|
||||
}
|
||||
},
|
||||
ast::ExprMethodCall(_, _, ref args) => {
|
||||
hir::ExprMethodCall(_, _, ref args) => {
|
||||
let arg_vals = map_list(args);
|
||||
let method_call = ty::MethodCall::expr(e.id);
|
||||
let method_did = cx.tcx().tables.borrow().method_map[&method_call].def_id;
|
||||
const_fn_call(cx, MethodCallKey(method_call),
|
||||
method_did, &arg_vals, param_substs)
|
||||
},
|
||||
ast::ExprParen(ref e) => const_expr(cx, &**e, param_substs, fn_args).0,
|
||||
ast::ExprBlock(ref block) => {
|
||||
hir::ExprParen(ref e) => const_expr(cx, &**e, param_substs, fn_args).0,
|
||||
hir::ExprBlock(ref block) => {
|
||||
match block.expr {
|
||||
Some(ref expr) => const_expr(cx, &**expr, param_substs, fn_args).0,
|
||||
None => C_nil(cx),
|
||||
}
|
||||
},
|
||||
ast::ExprClosure(_, ref decl, ref body) => {
|
||||
hir::ExprClosure(_, ref decl, ref body) => {
|
||||
match ety.sty {
|
||||
ty::TyClosure(_, ref substs) => {
|
||||
closure::trans_closure_expr(closure::Dest::Ignore(cx), decl,
|
||||
@ -889,10 +892,10 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
|
||||
}
|
||||
}
|
||||
pub fn trans_static(ccx: &CrateContext,
|
||||
m: ast::Mutability,
|
||||
expr: &ast::Expr,
|
||||
m: hir::Mutability,
|
||||
expr: &hir::Expr,
|
||||
id: ast::NodeId,
|
||||
attrs: &Vec<ast::Attribute>)
|
||||
attrs: &Vec<hir::Attribute>)
|
||||
-> ValueRef {
|
||||
unsafe {
|
||||
let _icx = push_ctxt("trans_static");
|
||||
@ -934,7 +937,7 @@ pub fn trans_static(ccx: &CrateContext,
|
||||
|
||||
// As an optimization, all shared statics which do not have interior
|
||||
// mutability are placed into read-only memory.
|
||||
if m != ast::MutMutable {
|
||||
if m != hir::MutMutable {
|
||||
let tcontents = ty.type_contents(ccx.tcx());
|
||||
if !tcontents.interior_unsafe() {
|
||||
llvm::LLVMSetGlobalConstant(g, llvm::True);
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user