Skip to content

Commit

Permalink
Auto merge of #70161 - cjgillot:query-arena, r=nikomatsakis
Browse files Browse the repository at this point in the history
Allocate some query results on an arena

This avoids a cloning few `Lrc` and `Vec`s in the queries.
  • Loading branch information
bors committed Apr 11, 2020
2 parents 7688266 + 802c0be commit e82734e
Show file tree
Hide file tree
Showing 17 changed files with 78 additions and 98 deletions.
9 changes: 4 additions & 5 deletions src/librustc_codegen_llvm/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@ use rustc_target::spec::{HasTargetSpec, Target};
use std::cell::{Cell, RefCell};
use std::ffi::CStr;
use std::str;
use std::sync::Arc;

/// There is one `CodegenCx` per compilation unit. Each one has its own LLVM
/// `llvm::Context` so that several compilation units may be optimized in parallel.
Expand All @@ -39,7 +38,7 @@ pub struct CodegenCx<'ll, 'tcx> {

pub llmod: &'ll llvm::Module,
pub llcx: &'ll llvm::Context,
pub codegen_unit: Arc<CodegenUnit<'tcx>>,
pub codegen_unit: &'tcx CodegenUnit<'tcx>,

/// Cache instances of monomorphic and polymorphic items
pub instances: RefCell<FxHashMap<Instance<'tcx>, &'ll Value>>,
Expand Down Expand Up @@ -232,7 +231,7 @@ pub unsafe fn create_module(
impl<'ll, 'tcx> CodegenCx<'ll, 'tcx> {
crate fn new(
tcx: TyCtxt<'tcx>,
codegen_unit: Arc<CodegenUnit<'tcx>>,
codegen_unit: &'tcx CodegenUnit<'tcx>,
llvm_module: &'ll crate::ModuleLlvm,
) -> Self {
// An interesting part of Windows which MSVC forces our hand on (and
Expand Down Expand Up @@ -402,8 +401,8 @@ impl MiscMethods<'tcx> for CodegenCx<'ll, 'tcx> {
self.check_overflow
}

fn codegen_unit(&self) -> &Arc<CodegenUnit<'tcx>> {
&self.codegen_unit
fn codegen_unit(&self) -> &'tcx CodegenUnit<'tcx> {
self.codegen_unit
}

fn used_statics(&self) -> &RefCell<Vec<&'ll Value>> {
Expand Down
7 changes: 3 additions & 4 deletions src/librustc_codegen_ssa/back/symbol_export.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
use std::collections::hash_map::Entry::*;
use std::sync::Arc;

use rustc_ast::expand::allocator::ALLOCATOR_METHODS;
use rustc_data_structures::fingerprint::Fingerprint;
Expand Down Expand Up @@ -164,11 +163,11 @@ fn is_reachable_non_generic_provider_extern(tcx: TyCtxt<'_>, def_id: DefId) -> b
fn exported_symbols_provider_local(
tcx: TyCtxt<'_>,
cnum: CrateNum,
) -> Arc<Vec<(ExportedSymbol<'_>, SymbolExportLevel)>> {
) -> &'tcx [(ExportedSymbol<'_>, SymbolExportLevel)] {
assert_eq!(cnum, LOCAL_CRATE);

if !tcx.sess.opts.output_types.should_codegen() {
return Arc::new(vec![]);
return &[];
}

let mut symbols: Vec<_> = tcx
Expand Down Expand Up @@ -274,7 +273,7 @@ fn exported_symbols_provider_local(
// Sort so we get a stable incr. comp. hash.
symbols.sort_by_cached_key(|s| s.0.symbol_name_for_local_instance(tcx));

Arc::new(symbols)
tcx.arena.alloc_from_iter(symbols)
}

fn upstream_monomorphizations_provider(
Expand Down
5 changes: 2 additions & 3 deletions src/librustc_codegen_ssa/base.rs
Original file line number Diff line number Diff line change
Expand Up @@ -533,15 +533,14 @@ pub fn codegen_crate<B: ExtraBackendMethods>(
// Run the monomorphization collector and partition the collected items into
// codegen units.
let codegen_units = tcx.collect_and_partition_mono_items(LOCAL_CRATE).1;
let codegen_units = (*codegen_units).clone();

// Force all codegen_unit queries so they are already either red or green
// when compile_codegen_unit accesses them. We are not able to re-execute
// the codegen_unit query from just the DepNode, so an unknown color would
// lead to having to re-execute compile_codegen_unit, possibly
// unnecessarily.
if tcx.dep_graph.is_fully_enabled() {
for cgu in &codegen_units {
for cgu in codegen_units {
tcx.codegen_unit(cgu.name());
}
}
Expand Down Expand Up @@ -603,7 +602,7 @@ pub fn codegen_crate<B: ExtraBackendMethods>(
// We sort the codegen units by size. This way we can schedule work for LLVM
// a bit more efficiently.
let codegen_units = {
let mut codegen_units = codegen_units;
let mut codegen_units = codegen_units.iter().collect::<Vec<_>>();
codegen_units.sort_by_cached_key(|cgu| cmp::Reverse(cgu.size_estimate()));
codegen_units
};
Expand Down
3 changes: 1 addition & 2 deletions src/librustc_codegen_ssa/traits/misc.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ use rustc_middle::mir::mono::CodegenUnit;
use rustc_middle::ty::{self, Instance, Ty};
use rustc_session::Session;
use std::cell::RefCell;
use std::sync::Arc;

pub trait MiscMethods<'tcx>: BackendTypes {
fn vtables(
Expand All @@ -15,7 +14,7 @@ pub trait MiscMethods<'tcx>: BackendTypes {
fn get_fn_addr(&self, instance: Instance<'tcx>) -> Self::Value;
fn eh_personality(&self) -> Self::Value;
fn sess(&self) -> &Session;
fn codegen_unit(&self) -> &Arc<CodegenUnit<'tcx>>;
fn codegen_unit(&self) -> &'tcx CodegenUnit<'tcx>;
fn used_statics(&self) -> &RefCell<Vec<Self::Value>>;
fn set_frame_pointer_elimination(&self, llfn: Self::Function);
fn apply_target_cpu_attr(&self, llfn: Self::Function);
Expand Down
2 changes: 1 addition & 1 deletion src/librustc_infer/traits/error_reporting/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ pub fn report_object_safety_error(
tcx: TyCtxt<'tcx>,
span: Span,
trait_def_id: DefId,
violations: Vec<ObjectSafetyViolation>,
violations: &[ObjectSafetyViolation],
) -> DiagnosticBuilder<'tcx> {
let trait_str = tcx.def_path_str(trait_def_id);
let trait_span = tcx.hir().get_if_local(trait_def_id).and_then(|node| match node {
Expand Down
28 changes: 13 additions & 15 deletions src/librustc_metadata/rmeta/decoder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1196,7 +1196,7 @@ impl<'a, 'tcx> CrateMetadataRef<'a> {
}
}

fn get_item_attrs(&self, node_id: DefIndex, sess: &Session) -> Lrc<[ast::Attribute]> {
fn get_item_attrs(&self, node_id: DefIndex, sess: &Session) -> Vec<ast::Attribute> {
// The attributes for a tuple struct/variant 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
Expand All @@ -1207,15 +1207,13 @@ impl<'a, 'tcx> CrateMetadataRef<'a> {
node_id
};

Lrc::from(
self.root
.tables
.attributes
.get(self, item_id)
.unwrap_or(Lazy::empty())
.decode((self, sess))
.collect::<Vec<_>>(),
)
self.root
.tables
.attributes
.get(self, item_id)
.unwrap_or(Lazy::empty())
.decode((self, sess))
.collect::<Vec<_>>()
}

fn get_struct_field_names(&self, id: DefIndex, sess: &Session) -> Vec<Spanned<ast::Name>> {
Expand Down Expand Up @@ -1330,25 +1328,25 @@ impl<'a, 'tcx> CrateMetadataRef<'a> {
}
}

fn get_fn_param_names(&self, id: DefIndex) -> Vec<ast::Name> {
fn get_fn_param_names(&self, tcx: TyCtxt<'tcx>, id: DefIndex) -> &'tcx [ast::Name] {
let param_names = match self.kind(id) {
EntryKind::Fn(data) | EntryKind::ForeignFn(data) => data.decode(self).param_names,
EntryKind::AssocFn(data) => data.decode(self).fn_data.param_names,
_ => Lazy::empty(),
};
param_names.decode(self).collect()
tcx.arena.alloc_from_iter(param_names.decode(self))
}

fn exported_symbols(
&self,
tcx: TyCtxt<'tcx>,
) -> Vec<(ExportedSymbol<'tcx>, SymbolExportLevel)> {
) -> &'tcx [(ExportedSymbol<'tcx>, SymbolExportLevel)] {
if self.root.is_proc_macro_crate() {
// If this crate is a custom derive crate, then we're not even going to
// link those in so we skip those crates.
vec![]
&[]
} else {
self.root.exported_symbols.decode((self, tcx)).collect()
tcx.arena.alloc_from_iter(self.root.exported_symbols.decode((self, tcx)))
}
}

Expand Down
9 changes: 5 additions & 4 deletions src/librustc_metadata/rmeta/decoder/cstore_impl.rs
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@ use rustc_span::symbol::Symbol;
use rustc_data_structures::sync::Lrc;
use smallvec::SmallVec;
use std::any::Any;
use std::sync::Arc;

macro_rules! provide {
(<$lt:tt> $tcx:ident, $def_id:ident, $other:ident, $cdata:ident,
Expand Down Expand Up @@ -139,12 +138,14 @@ provide! { <'tcx> tcx, def_id, other, cdata,
lookup_deprecation_entry => {
cdata.get_deprecation(def_id.index).map(DeprecationEntry::external)
}
item_attrs => { cdata.get_item_attrs(def_id.index, tcx.sess) }
item_attrs => { tcx.arena.alloc_from_iter(
cdata.get_item_attrs(def_id.index, tcx.sess).into_iter()
) }
// FIXME(#38501) We've skipped a `read` on the `hir_owner_nodes` of
// a `fn` when encoding, so the dep-tracking wouldn't work.
// This is only used by rustdoc anyway, which shouldn't have
// incremental recompilation ever enabled.
fn_arg_names => { cdata.get_fn_param_names(def_id.index) }
fn_arg_names => { cdata.get_fn_param_names(tcx, def_id.index) }
rendered_const => { cdata.get_rendered_const(def_id.index) }
impl_parent => { cdata.get_parent_impl(def_id.index) }
trait_of_item => { cdata.get_trait_of_item(def_id.index) }
Expand Down Expand Up @@ -239,7 +240,7 @@ provide! { <'tcx> tcx, def_id, other, cdata,
// to block export of generics from dylibs, but we must fix
// rust-lang/rust#65890 before we can do that robustly.

Arc::new(syms)
syms
}
}

Expand Down
5 changes: 5 additions & 0 deletions src/librustc_middle/arena.rs
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,11 @@ macro_rules! arena_types {
[few] crate_variances: rustc_middle::ty::CrateVariancesMap<'tcx>,
[few] inferred_outlives_crate: rustc_middle::ty::CratePredicatesMap<'tcx>,
[] upvars: rustc_data_structures::fx::FxIndexMap<rustc_hir::HirId, rustc_hir::Upvar>,
[] object_safety_violations: rustc_middle::traits::ObjectSafetyViolation,
[] codegen_unit: rustc_middle::mir::mono::CodegenUnit<$tcx>,
[] attribute: rustc_ast::ast::Attribute,
[] name_set: rustc_data_structures::fx::FxHashSet<rustc_ast::ast::Name>,
[] hir_id_set: rustc_hir::HirIdSet,

// Interned types
[] tys: rustc_middle::ty::TyS<$tcx>,
Expand Down
16 changes: 8 additions & 8 deletions src/librustc_middle/query/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -610,7 +610,7 @@ rustc_queries! {
}

Other {
query reachable_set(_: CrateNum) -> Lrc<HirIdSet> {
query reachable_set(_: CrateNum) -> &'tcx HirIdSet {
desc { "reachability" }
}

Expand Down Expand Up @@ -642,7 +642,7 @@ rustc_queries! {
query lookup_stability(_: DefId) -> Option<&'tcx attr::Stability> {}
query lookup_const_stability(_: DefId) -> Option<&'tcx attr::ConstStability> {}
query lookup_deprecation_entry(_: DefId) -> Option<DeprecationEntry> {}
query item_attrs(_: DefId) -> Lrc<[ast::Attribute]> {}
query item_attrs(_: DefId) -> &'tcx [ast::Attribute] {}
}

Codegen {
Expand All @@ -652,7 +652,7 @@ rustc_queries! {
}

Other {
query fn_arg_names(_: DefId) -> Vec<ast::Name> {}
query fn_arg_names(_: DefId) -> &'tcx [ast::Name] {}
/// Gets the rendered value of the specified constant or associated constant.
/// Used by rustdoc.
query rendered_const(_: DefId) -> String {}
Expand Down Expand Up @@ -699,7 +699,7 @@ rustc_queries! {
desc { |tcx| "building specialization graph of trait `{}`", tcx.def_path_str(key) }
cache_on_disk_if { true }
}
query object_safety_violations(key: DefId) -> Vec<traits::ObjectSafetyViolation> {
query object_safety_violations(key: DefId) -> &'tcx [traits::ObjectSafetyViolation] {
desc { |tcx| "determine object safety of trait `{}`", tcx.def_path_str(key) }
}

Expand Down Expand Up @@ -1047,7 +1047,7 @@ rustc_queries! {
desc { "looking up all possibly unused extern crates" }
}
query names_imported_by_glob_use(_: DefId)
-> Lrc<FxHashSet<ast::Name>> {
-> &'tcx FxHashSet<ast::Name> {
eval_always
}

Expand Down Expand Up @@ -1075,19 +1075,19 @@ rustc_queries! {
/// correspond to a publicly visible symbol in `cnum` machine code.
/// - The `exported_symbols` sets of different crates do not intersect.
query exported_symbols(_: CrateNum)
-> Arc<Vec<(ExportedSymbol<'tcx>, SymbolExportLevel)>> {
-> &'tcx [(ExportedSymbol<'tcx>, SymbolExportLevel)] {
desc { "exported_symbols" }
}
}

Codegen {
query collect_and_partition_mono_items(_: CrateNum)
-> (Arc<DefIdSet>, Arc<Vec<Arc<CodegenUnit<'tcx>>>>) {
-> (&'tcx DefIdSet, &'tcx [CodegenUnit<'tcx>]) {
eval_always
desc { "collect_and_partition_mono_items" }
}
query is_codegened_item(_: DefId) -> bool {}
query codegen_unit(_: Symbol) -> Arc<CodegenUnit<'tcx>> {
query codegen_unit(_: Symbol) -> &'tcx CodegenUnit<'tcx> {
desc { "codegen_unit" }
}
query backend_optimization_level(_: CrateNum) -> OptLevel {
Expand Down
2 changes: 1 addition & 1 deletion src/librustc_middle/ty/context.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2723,7 +2723,7 @@ pub fn provide(providers: &mut ty::query::Providers<'_>) {
};
providers.names_imported_by_glob_use = |tcx, id| {
assert_eq!(id.krate, LOCAL_CRATE);
Lrc::new(tcx.glob_map.get(&id).cloned().unwrap_or_default())
tcx.arena.alloc(tcx.glob_map.get(&id).cloned().unwrap_or_default())
};

providers.lookup_stability = |tcx, id| {
Expand Down
23 changes: 4 additions & 19 deletions src/librustc_middle/ty/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ use rustc_data_structures::fx::FxHashMap;
use rustc_data_structures::fx::FxIndexMap;
use rustc_data_structures::sorted_map::SortedIndexMultiMap;
use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
use rustc_data_structures::sync::{self, par_iter, Lrc, ParallelIterator};
use rustc_data_structures::sync::{self, par_iter, ParallelIterator};
use rustc_hir as hir;
use rustc_hir::def::{CtorKind, CtorOf, DefKind, Namespace, Res};
use rustc_hir::def_id::{CrateNum, DefId, DefIdMap, LocalDefId, CRATE_DEF_INDEX};
Expand Down Expand Up @@ -2596,22 +2596,7 @@ impl BorrowKind {
}
}

#[derive(Debug, Clone)]
pub enum Attributes<'tcx> {
Owned(Lrc<[ast::Attribute]>),
Borrowed(&'tcx [ast::Attribute]),
}

impl<'tcx> ::std::ops::Deref for Attributes<'tcx> {
type Target = [ast::Attribute];

fn deref(&self) -> &[ast::Attribute] {
match self {
&Attributes::Owned(ref data) => &data,
&Attributes::Borrowed(data) => data,
}
}
}
pub type Attributes<'tcx> = &'tcx [ast::Attribute];

#[derive(Debug, PartialEq, Eq)]
pub enum ImplOverlapKind {
Expand Down Expand Up @@ -2847,9 +2832,9 @@ impl<'tcx> TyCtxt<'tcx> {
/// Gets the attributes of a definition.
pub fn get_attrs(self, did: DefId) -> Attributes<'tcx> {
if let Some(id) = self.hir().as_local_hir_id(did) {
Attributes::Borrowed(self.hir().attrs(id))
self.hir().attrs(id)
} else {
Attributes::Owned(self.item_attrs(did))
self.item_attrs(did)
}
}

Expand Down
Loading

0 comments on commit e82734e

Please sign in to comment.