From 0f68ab03c3dd1df24063dcf8fc84cf56fa83a27b Mon Sep 17 00:00:00 2001 From: Mazdak Farrokhzad Date: Sat, 21 Mar 2020 02:21:21 +0100 Subject: [PATCH] separate out an arena for HIR --- Cargo.lock | 1 + src/libarena/lib.rs | 5 +-- src/librustc/arena.rs | 34 ------------------- src/librustc/ty/codec.rs | 1 + src/librustc_ast_lowering/Cargo.toml | 1 + src/librustc_ast_lowering/item.rs | 2 +- src/librustc_ast_lowering/lib.rs | 5 ++- src/librustc_hir/arena.rs | 49 ++++++++++++++++++++++++++++ src/librustc_hir/lib.rs | 1 + src/librustc_interface/passes.rs | 2 +- src/librustc_interface/queries.rs | 6 ++-- 11 files changed, 66 insertions(+), 41 deletions(-) create mode 100644 src/librustc_hir/arena.rs diff --git a/Cargo.lock b/Cargo.lock index 5f6cda66ebf..e256ccfd446 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -3477,6 +3477,7 @@ dependencies = [ name = "rustc_ast_lowering" version = "0.0.0" dependencies = [ + "arena", "log", "rustc", "rustc_ast", diff --git a/src/libarena/lib.rs b/src/libarena/lib.rs index 18200af8b66..0f0bd617f43 100644 --- a/src/libarena/lib.rs +++ b/src/libarena/lib.rs @@ -624,7 +624,8 @@ macro_rules! declare_arena { } $( - impl ArenaAllocatable for $ty {} + #[allow(unused_lifetimes)] + impl<$tcx> ArenaAllocatable for $ty {} unsafe impl<$tcx> ArenaField<$tcx> for $ty { #[inline] fn arena<'a>(_arena: &'a Arena<$tcx>) -> Option<&'a $crate::TypedArena> { @@ -653,7 +654,7 @@ macro_rules! declare_arena { self.dropless.alloc_slice(value) } - pub fn alloc_from_iter( + pub fn alloc_from_iter<'a, T: ArenaAllocatable>( &'a self, iter: impl ::std::iter::IntoIterator, ) -> &'a mut [T] { diff --git a/src/librustc/arena.rs b/src/librustc/arena.rs index 5644a65c42b..c4214a0f5a2 100644 --- a/src/librustc/arena.rs +++ b/src/librustc/arena.rs @@ -120,40 +120,6 @@ macro_rules! arena_types { // Interned types [] tys: rustc::ty::TyS<$tcx>, - // HIR types - [few] hir_krate: rustc_hir::Crate<$tcx>, - [] arm: rustc_hir::Arm<$tcx>, - [] attribute: rustc_ast::ast::Attribute, - [] block: rustc_hir::Block<$tcx>, - [] bare_fn_ty: rustc_hir::BareFnTy<$tcx>, - [few] global_asm: rustc_hir::GlobalAsm, - [] generic_arg: rustc_hir::GenericArg<$tcx>, - [] generic_args: rustc_hir::GenericArgs<$tcx>, - [] generic_bound: rustc_hir::GenericBound<$tcx>, - [] generic_param: rustc_hir::GenericParam<$tcx>, - [] expr: rustc_hir::Expr<$tcx>, - [] field: rustc_hir::Field<$tcx>, - [] field_pat: rustc_hir::FieldPat<$tcx>, - [] fn_decl: rustc_hir::FnDecl<$tcx>, - [] foreign_item: rustc_hir::ForeignItem<$tcx>, - [] impl_item_ref: rustc_hir::ImplItemRef<$tcx>, - [] inline_asm: rustc_hir::InlineAsm<$tcx>, - [] local: rustc_hir::Local<$tcx>, - [few] macro_def: rustc_hir::MacroDef<$tcx>, - [] param: rustc_hir::Param<$tcx>, - [] pat: rustc_hir::Pat<$tcx>, - [] path: rustc_hir::Path<$tcx>, - [] path_segment: rustc_hir::PathSegment<$tcx>, - [] poly_trait_ref: rustc_hir::PolyTraitRef<$tcx>, - [] qpath: rustc_hir::QPath<$tcx>, - [] stmt: rustc_hir::Stmt<$tcx>, - [] struct_field: rustc_hir::StructField<$tcx>, - [] trait_item_ref: rustc_hir::TraitItemRef, - [] ty: rustc_hir::Ty<$tcx>, - [] type_binding: rustc_hir::TypeBinding<$tcx>, - [] variant: rustc_hir::Variant<$tcx>, - [] where_predicate: rustc_hir::WherePredicate<$tcx>, - // HIR query types [few] indexed_hir: rustc::hir::map::IndexedHir<$tcx>, [few] hir_definitions: rustc::hir::map::definitions::Definitions, diff --git a/src/librustc/ty/codec.rs b/src/librustc/ty/codec.rs index c305999a64b..cbbc937ed7d 100644 --- a/src/librustc/ty/codec.rs +++ b/src/librustc/ty/codec.rs @@ -396,6 +396,7 @@ macro_rules! implement_ty_decoder { // the caller to pick any lifetime for `'tcx`, including `'static`, // by using the unspecialized proxies to them. + rustc_hir::arena_types!(impl_arena_allocatable_decoders, [$DecoderName [$($typaram),*]], 'tcx); arena_types!(impl_arena_allocatable_decoders, [$DecoderName [$($typaram),*]], 'tcx); impl<$($typaram),*> SpecializedDecoder diff --git a/src/librustc_ast_lowering/Cargo.toml b/src/librustc_ast_lowering/Cargo.toml index 23dc80facae..75547ccb814 100644 --- a/src/librustc_ast_lowering/Cargo.toml +++ b/src/librustc_ast_lowering/Cargo.toml @@ -10,6 +10,7 @@ path = "lib.rs" doctest = false [dependencies] +arena = { path = "../libarena" } log = { version = "0.4", features = ["release_max_level_info", "std"] } rustc = { path = "../librustc" } rustc_ast_pretty = { path = "../librustc_ast_pretty" } diff --git a/src/librustc_ast_lowering/item.rs b/src/librustc_ast_lowering/item.rs index c22b2812a9e..bf78d6e4aec 100644 --- a/src/librustc_ast_lowering/item.rs +++ b/src/librustc_ast_lowering/item.rs @@ -1,7 +1,7 @@ use super::{AnonymousLifetimeMode, LoweringContext, ParamMode}; use super::{ImplTraitContext, ImplTraitPosition, ImplTraitTypeIdVisitor}; +use crate::Arena; -use rustc::arena::Arena; use rustc::bug; use rustc_ast::ast::*; use rustc_ast::attr; diff --git a/src/librustc_ast_lowering/lib.rs b/src/librustc_ast_lowering/lib.rs index 24fe51fc4d0..c541ddb7398 100644 --- a/src/librustc_ast_lowering/lib.rs +++ b/src/librustc_ast_lowering/lib.rs @@ -32,9 +32,10 @@ #![feature(array_value_iter)] #![feature(crate_visibility_modifier)] +#![feature(marker_trait_attr)] +#![feature(specialization)] #![recursion_limit = "256"] -use rustc::arena::Arena; use rustc::dep_graph::DepGraph; use rustc::hir::map::definitions::{DefKey, DefPathData, Definitions}; use rustc::{bug, span_bug}; @@ -85,6 +86,8 @@ mod path; const HIR_ID_COUNTER_LOCKED: u32 = 0xFFFFFFFF; +rustc_hir::arena_types!(::arena::declare_arena, [], 'tcx); + struct LoweringContext<'a, 'hir: 'a> { crate_root: Option, diff --git a/src/librustc_hir/arena.rs b/src/librustc_hir/arena.rs new file mode 100644 index 00000000000..978565a4c39 --- /dev/null +++ b/src/librustc_hir/arena.rs @@ -0,0 +1,49 @@ +/// This declares a list of types which can be allocated by `Arena`. +/// +/// The `few` modifier will cause allocation to use the shared arena and recording the destructor. +/// This is faster and more memory efficient if there's only a few allocations of the type. +/// Leaving `few` out will cause the type to get its own dedicated `TypedArena` which is +/// faster and more memory efficient if there is lots of allocations. +/// +/// Specifying the `decode` modifier will add decode impls for &T and &[T] where T is the type +/// listed. These impls will appear in the implement_ty_decoder! macro. +#[macro_export] +macro_rules! arena_types { + ($macro:path, $args:tt, $tcx:lifetime) => ( + $macro!($args, [ + // HIR types + [few] hir_krate: rustc_hir::Crate<$tcx>, + [] arm: rustc_hir::Arm<$tcx>, + [] attribute: rustc_ast::ast::Attribute, + [] block: rustc_hir::Block<$tcx>, + [] bare_fn_ty: rustc_hir::BareFnTy<$tcx>, + [few] global_asm: rustc_hir::GlobalAsm, + [] generic_arg: rustc_hir::GenericArg<$tcx>, + [] generic_args: rustc_hir::GenericArgs<$tcx>, + [] generic_bound: rustc_hir::GenericBound<$tcx>, + [] generic_param: rustc_hir::GenericParam<$tcx>, + [] expr: rustc_hir::Expr<$tcx>, + [] field: rustc_hir::Field<$tcx>, + [] field_pat: rustc_hir::FieldPat<$tcx>, + [] fn_decl: rustc_hir::FnDecl<$tcx>, + [] foreign_item: rustc_hir::ForeignItem<$tcx>, + [] impl_item_ref: rustc_hir::ImplItemRef<$tcx>, + [] inline_asm: rustc_hir::InlineAsm<$tcx>, + [] local: rustc_hir::Local<$tcx>, + [few] macro_def: rustc_hir::MacroDef<$tcx>, + [] param: rustc_hir::Param<$tcx>, + [] pat: rustc_hir::Pat<$tcx>, + [] path: rustc_hir::Path<$tcx>, + [] path_segment: rustc_hir::PathSegment<$tcx>, + [] poly_trait_ref: rustc_hir::PolyTraitRef<$tcx>, + [] qpath: rustc_hir::QPath<$tcx>, + [] stmt: rustc_hir::Stmt<$tcx>, + [] struct_field: rustc_hir::StructField<$tcx>, + [] trait_item_ref: rustc_hir::TraitItemRef, + [] ty: rustc_hir::Ty<$tcx>, + [] type_binding: rustc_hir::TypeBinding<$tcx>, + [] variant: rustc_hir::Variant<$tcx>, + [] where_predicate: rustc_hir::WherePredicate<$tcx>, + ], $tcx); + ) +} diff --git a/src/librustc_hir/lib.rs b/src/librustc_hir/lib.rs index fa5c72b060d..826d8df8374 100644 --- a/src/librustc_hir/lib.rs +++ b/src/librustc_hir/lib.rs @@ -13,6 +13,7 @@ #[macro_use] extern crate rustc_data_structures; +mod arena; pub mod def; pub use rustc_span::def_id; mod hir; diff --git a/src/librustc_interface/passes.rs b/src/librustc_interface/passes.rs index 8d9e287cdc9..c331b1e3d1e 100644 --- a/src/librustc_interface/passes.rs +++ b/src/librustc_interface/passes.rs @@ -437,7 +437,7 @@ pub fn lower_to_hir<'res, 'tcx>( resolver: &'res mut Resolver<'_>, dep_graph: &'res DepGraph, krate: &'res ast::Crate, - arena: &'tcx Arena<'tcx>, + arena: &'tcx rustc_ast_lowering::Arena<'tcx>, ) -> Crate<'tcx> { // Lower AST to HIR. let hir_crate = rustc_ast_lowering::lower_crate( diff --git a/src/librustc_interface/queries.rs b/src/librustc_interface/queries.rs index 3ca92216003..b0eeb57173f 100644 --- a/src/librustc_interface/queries.rs +++ b/src/librustc_interface/queries.rs @@ -68,6 +68,7 @@ pub struct Queries<'tcx> { gcx: Once>, arena: WorkerLocal>, + hir_arena: WorkerLocal>, dep_graph_future: Query>, parse: Query, @@ -87,6 +88,7 @@ impl<'tcx> Queries<'tcx> { compiler, gcx: Once::new(), arena: WorkerLocal::new(|_| Arena::default()), + hir_arena: WorkerLocal::new(|_| rustc_ast_lowering::Arena::default()), dep_graph_future: Default::default(), parse: Default::default(), crate_name: Default::default(), @@ -218,10 +220,10 @@ impl<'tcx> Queries<'tcx> { resolver, &*self.dep_graph()?.peek(), &krate, - &self.arena, + &self.hir_arena, )) })?; - let hir = self.arena.alloc(hir); + let hir = self.hir_arena.alloc(hir); Ok((hir, Steal::new(BoxedResolver::to_resolver_outputs(resolver)))) }) }