From e54a13d9ec63b5c642c76b8d3f974b8978a9f2f9 Mon Sep 17 00:00:00 2001 From: Michael Woerister Date: Tue, 13 Feb 2018 13:37:32 +0100 Subject: [PATCH 1/3] incr.comp.: Run cache directory garbage collection before loading dep-graph. --- src/librustc_driver/driver.rs | 9 +++++++++ src/librustc_incremental/lib.rs | 1 + src/librustc_incremental/persist/fs.rs | 16 +++++++++++++++- src/librustc_incremental/persist/mod.rs | 3 ++- 4 files changed, 27 insertions(+), 2 deletions(-) diff --git a/src/librustc_driver/driver.rs b/src/librustc_driver/driver.rs index f344624666a6c..b8a1fe9910540 100644 --- a/src/librustc_driver/driver.rs +++ b/src/librustc_driver/driver.rs @@ -660,6 +660,15 @@ pub fn phase_2_configure_and_expand_inner<'a, F>(sess: &'a Session, disambiguator, ); + if sess.opts.incremental.is_some() { + time(time_passes, "garbage collect incremental cache directory", || { + if let Err(e) = rustc_incremental::garbage_collect_session_directories(sess) { + warn!("Error while trying to garbage collect incremental \ + compilation cache directory: {}", e); + } + }); + } + // If necessary, compute the dependency graph (in the background). let future_dep_graph = if sess.opts.build_dep_graph() { Some(rustc_incremental::load_dep_graph(sess, time_passes)) diff --git a/src/librustc_incremental/lib.rs b/src/librustc_incremental/lib.rs index b53ee1daada42..65fbd9d0bf8f1 100644 --- a/src/librustc_incremental/lib.rs +++ b/src/librustc_incremental/lib.rs @@ -46,3 +46,4 @@ pub use persist::in_incr_comp_dir; pub use persist::prepare_session_directory; pub use persist::finalize_session_directory; pub use persist::delete_workproduct_files; +pub use persist::garbage_collect_session_directories; diff --git a/src/librustc_incremental/persist/fs.rs b/src/librustc_incremental/persist/fs.rs index f4171f951f407..795825f180c9d 100644 --- a/src/librustc_incremental/persist/fs.rs +++ b/src/librustc_incremental/persist/fs.rs @@ -603,7 +603,7 @@ fn timestamp_to_string(timestamp: SystemTime) -> String { } fn string_to_timestamp(s: &str) -> Result { - let micros_since_unix_epoch = u64::from_str_radix(s, 36); + let micros_since_unix_epoch = u64::from_str_radix(s, INT_ENCODE_BASE as u32); if micros_since_unix_epoch.is_err() { return Err(()) @@ -733,6 +733,20 @@ pub fn garbage_collect_session_directories(sess: &Session) -> io::Result<()> { }) .collect(); + // Delete all session directories that don't have a lock file. + for directory_name in session_directories { + if !lock_file_to_session_dir.values().any(|dir| *dir == directory_name) { + let path = crate_directory.join(directory_name); + if let Err(err) = safe_remove_dir_all(&path) { + sess.warn(&format!("Failed to garbage collect invalid incremental \ + compilation session directory `{}`: {}", + path.display(), + err)); + } + } + } + + // Now garbage collect the valid session directories. let mut deletion_candidates = vec![]; let mut definitely_delete = vec![]; diff --git a/src/librustc_incremental/persist/mod.rs b/src/librustc_incremental/persist/mod.rs index 82a43d85bc608..2f864aaefba89 100644 --- a/src/librustc_incremental/persist/mod.rs +++ b/src/librustc_incremental/persist/mod.rs @@ -20,9 +20,10 @@ mod save; mod work_product; mod file_format; -pub use self::fs::prepare_session_directory; pub use self::fs::finalize_session_directory; +pub use self::fs::garbage_collect_session_directories; pub use self::fs::in_incr_comp_dir; +pub use self::fs::prepare_session_directory; pub use self::load::dep_graph_tcx_init; pub use self::load::load_dep_graph; pub use self::load::load_query_result_cache; From a1af69881a5ecae7a4136b47c7ac4d320568dad1 Mon Sep 17 00:00:00 2001 From: Josh Stone Date: Mon, 19 Feb 2018 14:05:21 -0800 Subject: [PATCH 2/3] rustbuild: Restore Config.libdir_relative This re-introduces a `Config.libdir_relative` field, now derived from `libdir` and made relative to `prefix` if necessary. This fixes a regression from #46592 when `--libdir` is given an absolute path. `Builder::sysroot_libdir` should always use a relative path so its callers don't clobber system locations, and `librustc` also asserts that `CFG_LIBDIR_RELATIVE` is really relative. --- src/bootstrap/builder.rs | 4 ++-- src/bootstrap/compile.rs | 2 +- src/bootstrap/config.rs | 17 +++++++++++++++++ 3 files changed, 20 insertions(+), 3 deletions(-) diff --git a/src/bootstrap/builder.rs b/src/bootstrap/builder.rs index 66a1c97246200..05aa6283ee579 100644 --- a/src/bootstrap/builder.rs +++ b/src/bootstrap/builder.rs @@ -444,8 +444,8 @@ impl<'a> Builder<'a> { fn run(self, builder: &Builder) -> Interned { let compiler = self.compiler; - let lib = if compiler.stage >= 1 && builder.build.config.libdir.is_some() { - builder.build.config.libdir.clone().unwrap() + let lib = if compiler.stage >= 1 && builder.build.config.libdir_relative.is_some() { + builder.build.config.libdir_relative.clone().unwrap() } else { PathBuf::from("lib") }; diff --git a/src/bootstrap/compile.rs b/src/bootstrap/compile.rs index 2dcc0e0e7cd9f..e6389f27785b5 100644 --- a/src/bootstrap/compile.rs +++ b/src/bootstrap/compile.rs @@ -517,7 +517,7 @@ fn rustc_cargo_env(build: &Build, cargo: &mut Command) { .env("CFG_PREFIX", build.config.prefix.clone().unwrap_or_default()); let libdir_relative = - build.config.libdir.clone().unwrap_or(PathBuf::from("lib")); + build.config.libdir_relative.clone().unwrap_or(PathBuf::from("lib")); cargo.env("CFG_LIBDIR_RELATIVE", libdir_relative); // If we're not building a compiler with debugging information then remove diff --git a/src/bootstrap/config.rs b/src/bootstrap/config.rs index 812ca6d64fb6a..6d98153e233ba 100644 --- a/src/bootstrap/config.rs +++ b/src/bootstrap/config.rs @@ -126,6 +126,7 @@ pub struct Config { pub docdir: Option, pub bindir: Option, pub libdir: Option, + pub libdir_relative: Option, pub mandir: Option, pub codegen_tests: bool, pub nodejs: Option, @@ -417,6 +418,22 @@ impl Config { config.mandir = install.mandir.clone().map(PathBuf::from); } + // Try to infer `libdir_relative` from `libdir`. + if let Some(ref libdir) = config.libdir { + let mut libdir = libdir.as_path(); + if !libdir.is_relative() { + // Try to make it relative to the prefix. + if let Some(ref prefix) = config.prefix { + if let Ok(suffix) = libdir.strip_prefix(prefix) { + libdir = suffix; + } + } + } + if libdir.is_relative() { + config.libdir_relative = Some(libdir.to_path_buf()); + } + } + // Store off these values as options because if they're not provided // we'll infer default values for them later let mut thinlto = None; From 62e9f2bc382ca95fe048f468a6556cc1c5526e17 Mon Sep 17 00:00:00 2001 From: Josh Stone Date: Mon, 19 Feb 2018 16:08:36 -0800 Subject: [PATCH 3/3] rustbuild: make libdir_relative a method --- src/bootstrap/builder.rs | 7 ++++--- src/bootstrap/compile.rs | 3 +-- src/bootstrap/config.rs | 30 ++++++++++++------------------ 3 files changed, 17 insertions(+), 23 deletions(-) diff --git a/src/bootstrap/builder.rs b/src/bootstrap/builder.rs index 05aa6283ee579..fcb78c479fa27 100644 --- a/src/bootstrap/builder.rs +++ b/src/bootstrap/builder.rs @@ -444,10 +444,11 @@ impl<'a> Builder<'a> { fn run(self, builder: &Builder) -> Interned { let compiler = self.compiler; - let lib = if compiler.stage >= 1 && builder.build.config.libdir_relative.is_some() { - builder.build.config.libdir_relative.clone().unwrap() + let config = &builder.build.config; + let lib = if compiler.stage >= 1 && config.libdir_relative().is_some() { + builder.build.config.libdir_relative().unwrap() } else { - PathBuf::from("lib") + Path::new("lib") }; let sysroot = builder.sysroot(self.compiler).join(lib) .join("rustlib").join(self.target).join("lib"); diff --git a/src/bootstrap/compile.rs b/src/bootstrap/compile.rs index e6389f27785b5..c85b04ddc0245 100644 --- a/src/bootstrap/compile.rs +++ b/src/bootstrap/compile.rs @@ -516,8 +516,7 @@ fn rustc_cargo_env(build: &Build, cargo: &mut Command) { .env("CFG_VERSION", build.rust_version()) .env("CFG_PREFIX", build.config.prefix.clone().unwrap_or_default()); - let libdir_relative = - build.config.libdir_relative.clone().unwrap_or(PathBuf::from("lib")); + let libdir_relative = build.config.libdir_relative().unwrap_or(Path::new("lib")); cargo.env("CFG_LIBDIR_RELATIVE", libdir_relative); // If we're not building a compiler with debugging information then remove diff --git a/src/bootstrap/config.rs b/src/bootstrap/config.rs index 6d98153e233ba..3cf8f36df25ee 100644 --- a/src/bootstrap/config.rs +++ b/src/bootstrap/config.rs @@ -17,7 +17,7 @@ use std::collections::{HashMap, HashSet}; use std::env; use std::fs::File; use std::io::prelude::*; -use std::path::PathBuf; +use std::path::{Path, PathBuf}; use std::process; use std::cmp; @@ -126,7 +126,6 @@ pub struct Config { pub docdir: Option, pub bindir: Option, pub libdir: Option, - pub libdir_relative: Option, pub mandir: Option, pub codegen_tests: bool, pub nodejs: Option, @@ -418,22 +417,6 @@ impl Config { config.mandir = install.mandir.clone().map(PathBuf::from); } - // Try to infer `libdir_relative` from `libdir`. - if let Some(ref libdir) = config.libdir { - let mut libdir = libdir.as_path(); - if !libdir.is_relative() { - // Try to make it relative to the prefix. - if let Some(ref prefix) = config.prefix { - if let Ok(suffix) = libdir.strip_prefix(prefix) { - libdir = suffix; - } - } - } - if libdir.is_relative() { - config.libdir_relative = Some(libdir.to_path_buf()); - } - } - // Store off these values as options because if they're not provided // we'll infer default values for them later let mut thinlto = None; @@ -581,6 +564,17 @@ impl Config { config } + /// Try to find the relative path of `libdir`. + pub fn libdir_relative(&self) -> Option<&Path> { + let libdir = self.libdir.as_ref()?; + if libdir.is_relative() { + Some(libdir) + } else { + // Try to make it relative to the prefix. + libdir.strip_prefix(self.prefix.as_ref()?).ok() + } + } + pub fn verbose(&self) -> bool { self.verbose > 0 }