1 pub use jobserver_crate::Client;
2 use std::sync::LazyLock;
4 // We can only call `from_env` once per process
6 // Note that this is unsafe because it may misinterpret file descriptors
7 // on Unix as jobserver file descriptors. We hopefully execute this near
8 // the beginning of the process though to ensure we don't get false
9 // positives, or in other words we try to execute this before we open
10 // any file descriptors ourselves.
12 // Pick a "reasonable maximum" if we don't otherwise have
13 // a jobserver in our environment, capping out at 32 so we
14 // don't take everything down by hogging the process run queue.
15 // The fixed number is used to have deterministic compilation
18 // Also note that we stick this in a global because there could be
19 // multiple rustc instances in this process, and the jobserver is
21 static GLOBAL_CLIENT: LazyLock<Client> = LazyLock::new(|| unsafe {
22 Client::from_env().unwrap_or_else(|| {
23 let client = Client::new(32).expect("failed to create jobserver");
24 // Acquire a token for the main thread which we can release later
25 client.acquire_raw().ok();
30 pub fn client() -> Client {
34 pub fn acquire_thread() {
35 GLOBAL_CLIENT.acquire_raw().ok();
38 pub fn release_thread() {
39 GLOBAL_CLIENT.release_raw().ok();