Skip to content
This repository has been archived by the owner on Dec 29, 2022. It is now read-only.

Commit

Permalink
Wait for all tasks to finish on shutdown
Browse files Browse the repository at this point in the history
Previously, we've waited only for explicit requests, but not for the
notifications. That is, it was possible to receive "file changed"
notification, schedule the build, receive "shutdown" request, respond
to shutdown, and *then* send a bunch of diagnostics from the compiler.

This commit simplifies this logic so that we wait for *all* things
before processing a blocking notification.
  • Loading branch information
matklad committed Jun 30, 2018
1 parent b2e1e5d commit ba80d25
Show file tree
Hide file tree
Showing 3 changed files with 3 additions and 14 deletions.
1 change: 0 additions & 1 deletion src/concurrency.rs
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@ use crossbeam_channel::{bounded, Receiver, Sender};
///
/// `JobToken` is the worker-side counterpart of `ConcurrentJob`. Dropping
/// a `JobToken` signals that the corresponding job has finished.
#[derive(Clone)]
#[must_use]
pub struct ConcurrentJob {
is_abandoned: bool,
Expand Down
14 changes: 2 additions & 12 deletions src/server/dispatch.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ use server;
use server::io::Output;
use server::message::ResponseError;
use server::{Request, Response};
use concurrency::{Jobs, ConcurrentJob, JobToken};
use concurrency::{ConcurrentJob, JobToken};
use std::sync::mpsc;
use std::thread;
use std::time::Duration;
Expand Down Expand Up @@ -113,7 +113,6 @@ define_dispatch_request_enum!(
/// processing if have already timed out before starting.
pub struct Dispatcher {
sender: mpsc::Sender<(DispatchRequest, JobToken)>,
jobs: Jobs,
}

impl Dispatcher {
Expand All @@ -131,21 +130,12 @@ impl Dispatcher {
})
.unwrap();

Self {
sender,
jobs: Jobs::new(),
}
}

/// Blocks until all dispatched requests have been handled
pub fn await_all_dispatched(&mut self) {
self.jobs.wait_for_all();
Self { sender }
}

/// Sends a request to the dispatch-worker thread, does not block
pub fn dispatch<R: Into<DispatchRequest>>(&mut self, request: R) -> ConcurrentJob {
let (job, token) = ConcurrentJob::new();
self.jobs.add(job.clone());
if let Err(err) = self.sender.send((request.into(), token)) {
debug!("Failed to dispatch request: {:?}", err);
}
Expand Down
2 changes: 1 addition & 1 deletion src/server/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -200,7 +200,7 @@ impl<O: Output> LsService<O> {
let request: Request<$br_action> = msg.parse_as_request()?;

// block until all nonblocking requests have been handled ensuring ordering
self.dispatcher.await_all_dispatched();
self.wait_for_background_jobs();

let req_id = request.id.clone();
match request.blocking_dispatch(&mut self.jobs, &mut self.ctx, &self.output) {
Expand Down

0 comments on commit ba80d25

Please sign in to comment.