Skip to content

Commit

Permalink
Initialize rayon lazily
Browse files Browse the repository at this point in the history
  • Loading branch information
konstin committed Nov 26, 2024
1 parent c30a314 commit a9d8de9
Show file tree
Hide file tree
Showing 9 changed files with 48 additions and 17 deletions.
3 changes: 2 additions & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions crates/uv-configuration/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ uv-static = { workspace = true }
clap = { workspace = true, features = ["derive"], optional = true }
either = { workspace = true }
fs-err = { workspace = true }
rayon = { workspace = true }
rustc-hash = { workspace = true }
schemars = { workspace = true, optional = true }
serde = { workspace = true }
Expand Down
2 changes: 2 additions & 0 deletions crates/uv-configuration/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ pub use overrides::*;
pub use package_options::*;
pub use preview::*;
pub use project_build_backend::*;
pub use rayon::*;
pub use sources::*;
pub use target_triple::*;
pub use trusted_host::*;
Expand All @@ -38,6 +39,7 @@ mod overrides;
mod package_options;
mod preview;
mod project_build_backend;
mod rayon;
mod sources;
mod target_triple;
mod trusted_host;
Expand Down
21 changes: 21 additions & 0 deletions crates/uv-configuration/src/rayon.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
//! Initialize the rayon threadpool once, before we need it.
//!
//! The `uv` crate sets [`RAYON_PARALLELISM`] from the user settings, and the extract and install
//! code initialize the threadpool lazily only if they are actually used by calling
//! `LazyLock::force(&RAYON_INITIALIZE)`.
use std::sync::atomic::{AtomicUsize, Ordering};
use std::sync::LazyLock;

/// The number of threads for the rayon threadpool.
///
/// The default of 0 makes rayon use its default.
pub static RAYON_PARALLELISM: AtomicUsize = AtomicUsize::new(0);

/// Initialize the threadpool lazily. Always call before using rayon the potentially first time.
pub static RAYON_INITIALIZE: LazyLock<()> = LazyLock::new(|| {
rayon::ThreadPoolBuilder::new()
.num_threads(RAYON_PARALLELISM.load(Ordering::SeqCst))
.build_global()
.expect("failed to initialize global rayon pool");
});
1 change: 1 addition & 0 deletions crates/uv-extract/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ doctest = false
workspace = true

[dependencies]
uv-configuration = { workspace = true }
uv-distribution-filename = { workspace = true }
uv-pypi-types = { workspace = true }

Expand Down
10 changes: 6 additions & 4 deletions crates/uv-extract/src/sync.rs
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
use std::path::{Path, PathBuf};
use std::sync::Mutex;
use std::sync::{LazyLock, Mutex};

use crate::vendor::{CloneableSeekableReader, HasLength};
use crate::Error;
use rayon::prelude::*;
use rustc_hash::FxHashSet;
use tracing::warn;
use uv_configuration::RAYON_INITIALIZE;
use zip::ZipArchive;

use crate::vendor::{CloneableSeekableReader, HasLength};
use crate::Error;

/// Unzip a `.zip` archive into the target directory.
pub fn unzip<R: Send + std::io::Read + std::io::Seek + HasLength>(
reader: R,
Expand All @@ -18,6 +18,8 @@ pub fn unzip<R: Send + std::io::Read + std::io::Seek + HasLength>(
let reader = std::io::BufReader::new(reader);
let archive = ZipArchive::new(CloneableSeekableReader::new(reader))?;
let directories = Mutex::new(FxHashSet::default());
// Initialize the threadpool with the user settings.
LazyLock::force(&RAYON_INITIALIZE);
(0..archive.len())
.into_par_iter()
.map(|file_number| {
Expand Down
6 changes: 6 additions & 0 deletions crates/uv-installer/src/installer.rs
Original file line number Diff line number Diff line change
@@ -1,11 +1,13 @@
use anyhow::{Context, Error, Result};
use rayon::iter::{IntoParallelRefIterator, ParallelIterator};
use std::convert;
use std::sync::LazyLock;
use tokio::sync::oneshot;
use tracing::instrument;
use uv_install_wheel::{linker::LinkMode, Layout};

use uv_cache::Cache;
use uv_configuration::RAYON_INITIALIZE;
use uv_distribution_types::CachedDist;
use uv_python::PythonEnvironment;

Expand Down Expand Up @@ -85,6 +87,8 @@ impl<'a> Installer<'a> {

let layout = venv.interpreter().layout();
let relocatable = venv.relocatable();
// Initialize the threadpool with the user settings.
LazyLock::force(&RAYON_INITIALIZE);
rayon::spawn(move || {
let result = install(
wheels,
Expand Down Expand Up @@ -136,6 +140,8 @@ fn install(
reporter: Option<Box<dyn Reporter>>,
relocatable: bool,
) -> Result<Vec<CachedDist>> {
// Initialize the threadpool with the user settings.
LazyLock::force(&RAYON_INITIALIZE);
let locks = uv_install_wheel::linker::Locks::default();
wheels.par_iter().try_for_each(|wheel| {
uv_install_wheel::linker::install_wheel(
Expand Down
1 change: 0 additions & 1 deletion crates/uv/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,6 @@ jiff = { workspace = true }
miette = { workspace = true, features = ["fancy-no-backtrace"] }
owo-colors = { workspace = true }
petgraph = { workspace = true }
rayon = { workspace = true }
regex = { workspace = true }
reqwest = { workspace = true }
rkyv = { workspace = true }
Expand Down
20 changes: 9 additions & 11 deletions crates/uv/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,17 +1,17 @@
use anstream::eprintln;
use anyhow::{bail, Result};
use clap::error::{ContextKind, ContextValue};
use clap::{CommandFactory, Parser};
use owo_colors::OwoColorize;
use settings::PipTreeSettings;
use std::borrow::Cow;
use std::env;
use std::ffi::OsString;
use std::fmt::Write;
use std::io::stdout;
use std::path::Path;
use std::process::ExitCode;

use anstream::eprintln;
use anyhow::{bail, Result};
use clap::error::{ContextKind, ContextValue};
use clap::{CommandFactory, Parser};
use owo_colors::OwoColorize;
use settings::PipTreeSettings;
use std::sync::atomic::Ordering;
use tokio::task::spawn_blocking;
use tracing::{debug, instrument};
use uv_cache::{Cache, Refresh};
Expand Down Expand Up @@ -254,10 +254,8 @@ async fn run(mut cli: Cli) -> Result<ExitStatus> {
)
}))?;

rayon::ThreadPoolBuilder::new()
.num_threads(globals.concurrency.installs)
.build_global()
.expect("failed to initialize global rayon pool");
// Don't initialize the rayon threadpool yet, this is too costly when we're doing a noop sync.
uv_configuration::RAYON_PARALLELISM.store(globals.concurrency.installs, Ordering::SeqCst);

debug!("uv {}", uv_cli::version::version());

Expand Down

0 comments on commit a9d8de9

Please sign in to comment.