Add a local counter that tracks how many tasks are pushed or not pushed,
so that we can still get assertion failures even when dep-graph construction is disabled.
This commit is contained in:
parent
98422e8c15
commit
37fbfaf183
1 changed files with 48 additions and 5 deletions
|
@ -19,6 +19,7 @@
|
||||||
//! allocated (and both have a fairly large capacity).
|
//! allocated (and both have a fairly large capacity).
|
||||||
|
|
||||||
use rustc_data_structures::veccell::VecCell;
|
use rustc_data_structures::veccell::VecCell;
|
||||||
|
use std::cell::Cell;
|
||||||
use std::sync::mpsc::{self, Sender, Receiver};
|
use std::sync::mpsc::{self, Sender, Receiver};
|
||||||
use std::thread;
|
use std::thread;
|
||||||
|
|
||||||
|
@ -39,6 +40,13 @@ pub enum DepMessage {
|
||||||
pub struct DepGraphThreadData {
|
pub struct DepGraphThreadData {
|
||||||
enabled: bool,
|
enabled: bool,
|
||||||
|
|
||||||
|
// Local counter that just tracks how many tasks are pushed onto the
|
||||||
|
// stack, so that we still get an error in the case where one is
|
||||||
|
// missing. If dep-graph construction is enabled, we'd get the same
|
||||||
|
// error when processing tasks later on, but that's annoying because
|
||||||
|
// it lacks precision about the source of the error.
|
||||||
|
tasks_pushed: Cell<usize>,
|
||||||
|
|
||||||
// current buffer, where we accumulate messages
|
// current buffer, where we accumulate messages
|
||||||
messages: VecCell<DepMessage>,
|
messages: VecCell<DepMessage>,
|
||||||
|
|
||||||
|
@ -59,11 +67,14 @@ impl DepGraphThreadData {
|
||||||
let (tx1, rx1) = mpsc::channel();
|
let (tx1, rx1) = mpsc::channel();
|
||||||
let (tx2, rx2) = mpsc::channel();
|
let (tx2, rx2) = mpsc::channel();
|
||||||
let (txq, rxq) = mpsc::channel();
|
let (txq, rxq) = mpsc::channel();
|
||||||
|
|
||||||
if enabled {
|
if enabled {
|
||||||
thread::spawn(move || main(rx1, tx2, txq));
|
thread::spawn(move || main(rx1, tx2, txq));
|
||||||
}
|
}
|
||||||
|
|
||||||
DepGraphThreadData {
|
DepGraphThreadData {
|
||||||
enabled: enabled,
|
enabled: enabled,
|
||||||
|
tasks_pushed: Cell::new(0),
|
||||||
messages: VecCell::with_capacity(INITIAL_CAPACITY),
|
messages: VecCell::with_capacity(INITIAL_CAPACITY),
|
||||||
swap_in: rx2,
|
swap_in: rx2,
|
||||||
swap_out: tx1,
|
swap_out: tx1,
|
||||||
|
@ -71,6 +82,11 @@ impl DepGraphThreadData {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
pub fn enabled(&self) -> bool {
|
||||||
|
self.enabled
|
||||||
|
}
|
||||||
|
|
||||||
/// Sends the current batch of messages to the thread. Installs a
|
/// Sends the current batch of messages to the thread. Installs a
|
||||||
/// new vector of messages.
|
/// new vector of messages.
|
||||||
fn swap(&self) {
|
fn swap(&self) {
|
||||||
|
@ -100,12 +116,39 @@ impl DepGraphThreadData {
|
||||||
/// the buffer is full, this may swap.)
|
/// the buffer is full, this may swap.)
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn enqueue(&self, message: DepMessage) {
|
pub fn enqueue(&self, message: DepMessage) {
|
||||||
if self.enabled {
|
// Regardless of whether dep graph construction is enabled, we
|
||||||
let len = self.messages.push(message);
|
// still want to check that we always have a valid task on the
|
||||||
if len == INITIAL_CAPACITY {
|
// stack when a read/write/etc event occurs.
|
||||||
self.swap();
|
match message {
|
||||||
}
|
DepMessage::Read(_) | DepMessage::Write(_) =>
|
||||||
|
if self.tasks_pushed.get() == 0 {
|
||||||
|
self.invalid_message("read/write but no current task")
|
||||||
|
},
|
||||||
|
DepMessage::PushTask(_) | DepMessage::PushIgnore =>
|
||||||
|
self.tasks_pushed.set(self.tasks_pushed.get() + 1),
|
||||||
|
DepMessage::PopTask(_) | DepMessage::PopIgnore =>
|
||||||
|
self.tasks_pushed.set(self.tasks_pushed.get() - 1),
|
||||||
|
DepMessage::Query =>
|
||||||
|
(),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if self.enabled {
|
||||||
|
self.enqueue_enabled(message);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Outline this fn since I expect it may want to be inlined
|
||||||
|
// separately.
|
||||||
|
fn enqueue_enabled(&self, message: DepMessage) {
|
||||||
|
let len = self.messages.push(message);
|
||||||
|
if len == INITIAL_CAPACITY {
|
||||||
|
self.swap();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Outline this too.
|
||||||
|
fn invalid_message(&self, string: &str) {
|
||||||
|
panic!("{}; see src/librustc/dep_graph/README.md for more information", string)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue