Switch QueryJobId to a single global counter

This replaces the per-shard counters with a single global counter, simplifying
the JobId struct down to just a u64 and removing the need to pipe a DepKind
generic through a bunch of code. The performance implications on non-parallel
compilers are likely minimal (this switches to `Cell<u64>` as the backing
storage over a `u64`, but the latter was already inside a `RefCell` so it's not
really a significance divergence). On parallel compilers, the cost of a single
global u64 counter may be more significant: it adds a serialization point in
theory. On the other hand, we can imagine changing the counter to have a
thread-local component if it becomes worrisome or some similar structure.

The new design is sufficiently simpler that it warrants the potential for slight
changes down the line if/when we get parallel compilation to be more of a
default.

A u64 counter, instead of u32 (the old per-shard width), is chosen to avoid
possibly overflowing it and causing problems; it is effectively impossible that
we would overflow a u64 counter in this context.
This commit is contained in:
Mark Rousskov 2022-02-07 11:03:51 -05:00
parent 88fb06a1f3
commit e240783a4d
7 changed files with 116 additions and 178 deletions

View file

@ -15,6 +15,7 @@ extern crate rustc_macros;
extern crate rustc_middle;
use rustc_data_structures::stable_hasher::{HashStable, StableHasher};
use rustc_data_structures::sync::AtomicU64;
use rustc_middle::arena::Arena;
use rustc_middle::dep_graph::{self, DepKindStruct, SerializedDepNodeIndex};
use rustc_middle::ty::query::{query_keys, query_storage, query_stored, query_values};

View file

@ -3,7 +3,7 @@
//! manage the caches, and so forth.
use crate::{on_disk_cache, Queries};
use rustc_middle::dep_graph::{DepKind, DepNodeIndex, SerializedDepNodeIndex};
use rustc_middle::dep_graph::{DepNodeIndex, SerializedDepNodeIndex};
use rustc_middle::ty::tls::{self, ImplicitCtxt};
use rustc_middle::ty::TyCtxt;
use rustc_query_system::dep_graph::HasDepContext;
@ -15,6 +15,7 @@ use rustc_errors::{Diagnostic, Handler};
use rustc_serialize::opaque;
use std::any::Any;
use std::num::NonZeroU64;
#[derive(Copy, Clone)]
pub struct QueryCtxt<'tcx> {
@ -42,11 +43,20 @@ impl<'tcx> HasDepContext for QueryCtxt<'tcx> {
}
impl QueryContext for QueryCtxt<'_> {
fn current_query_job(&self) -> Option<QueryJobId<Self::DepKind>> {
fn next_job_id(&self) -> QueryJobId {
QueryJobId(
NonZeroU64::new(
self.queries.jobs.fetch_add(1, rustc_data_structures::sync::Ordering::Relaxed),
)
.unwrap(),
)
}
fn current_query_job(&self) -> Option<QueryJobId> {
tls::with_related_context(**self, |icx| icx.query)
}
fn try_collect_active_jobs(&self) -> Option<QueryMap<Self::DepKind>> {
fn try_collect_active_jobs(&self) -> Option<QueryMap> {
self.queries.try_collect_active_jobs(**self)
}
@ -81,7 +91,7 @@ impl QueryContext for QueryCtxt<'_> {
#[inline(always)]
fn start_query<R>(
&self,
token: QueryJobId<Self::DepKind>,
token: QueryJobId,
diagnostics: Option<&Lock<ThinVec<Diagnostic>>>,
compute: impl FnOnce() -> R,
) -> R {
@ -152,7 +162,7 @@ impl<'tcx> QueryCtxt<'tcx> {
pub fn try_print_query_stack(
self,
query: Option<QueryJobId<DepKind>>,
query: Option<QueryJobId>,
handler: &Handler,
num_frames: Option<usize>,
) -> usize {
@ -320,7 +330,7 @@ macro_rules! define_queries {
type Cache = query_storage::$name<$tcx>;
#[inline(always)]
fn query_state<'a>(tcx: QueryCtxt<$tcx>) -> &'a QueryState<crate::dep_graph::DepKind, Self::Key>
fn query_state<'a>(tcx: QueryCtxt<$tcx>) -> &'a QueryState<Self::Key>
where QueryCtxt<$tcx>: 'a
{
&tcx.queries.$name
@ -471,10 +481,9 @@ macro_rules! define_queries_struct {
pub on_disk_cache: Option<OnDiskCache<$tcx>>,
$($(#[$attr])* $name: QueryState<
crate::dep_graph::DepKind,
query_keys::$name<$tcx>,
>,)*
jobs: AtomicU64,
$($(#[$attr])* $name: QueryState<query_keys::$name<$tcx>>,)*
}
impl<$tcx> Queries<$tcx> {
@ -487,6 +496,7 @@ macro_rules! define_queries_struct {
local_providers: Box::new(local_providers),
extern_providers: Box::new(extern_providers),
on_disk_cache,
jobs: AtomicU64::new(1),
$($name: Default::default()),*
}
}
@ -494,14 +504,13 @@ macro_rules! define_queries_struct {
pub(crate) fn try_collect_active_jobs(
&$tcx self,
tcx: TyCtxt<$tcx>,
) -> Option<QueryMap<crate::dep_graph::DepKind>> {
) -> Option<QueryMap> {
let tcx = QueryCtxt { tcx, queries: self };
let mut jobs = QueryMap::default();
$(
self.$name.try_collect_active_jobs(
tcx,
dep_graph::DepKind::$name,
make_query::$name,
&mut jobs,
)?;