From f13006182c9df451e7703307467fc1717239cf6e Mon Sep 17 00:00:00 2001 From: Nicholas Nethercote Date: Thu, 22 Nov 2018 16:33:07 +1100 Subject: [PATCH] Introduce `SearchPath` and replace `SearchPaths` with `Vec`. It's more idiomatic, makes the code shorter, and will help with the next commit. --- src/librustc/session/config.rs | 51 +++++++++++------------ src/librustc/session/filesearch.rs | 33 +++++++-------- src/librustc/session/search_paths.rs | 56 +++++++++----------------- src/librustc_codegen_llvm/back/link.rs | 12 +++--- src/librustdoc/config.rs | 11 +++-- src/librustdoc/core.rs | 2 +- src/librustdoc/test.rs | 8 ++-- 7 files changed, 79 insertions(+), 94 deletions(-) diff --git a/src/librustc/session/config.rs b/src/librustc/session/config.rs index 750b7f151f5..7ea7e447987 100644 --- a/src/librustc/session/config.rs +++ b/src/librustc/session/config.rs @@ -14,7 +14,7 @@ use std::str::FromStr; use session::{early_error, early_warn, Session}; -use session::search_paths::SearchPaths; +use session::search_paths::SearchPath; use rustc_target::spec::{LinkerFlavor, PanicStrategy, RelroLevel}; use rustc_target::spec::{Target, TargetTriple}; @@ -374,7 +374,7 @@ pub struct Options { lint_cap: Option [TRACKED], describe_lints: bool [UNTRACKED], output_types: OutputTypes [TRACKED], - search_paths: SearchPaths [UNTRACKED], + search_paths: Vec [UNTRACKED], libs: Vec<(String, Option, Option)> [TRACKED], maybe_sysroot: Option [TRACKED], @@ -593,7 +593,7 @@ fn default() -> Options { lint_cap: None, describe_lints: false, output_types: OutputTypes(BTreeMap::new()), - search_paths: SearchPaths::new(), + search_paths: vec![], maybe_sysroot: None, target_triple: TargetTriple::from_triple(host_triple()), test: false, @@ -2115,9 +2115,9 @@ pub fn build_session_options_and_crate_config( } }; - let mut search_paths = SearchPaths::new(); + let mut search_paths = vec![]; for s in &matches.opt_strs("L") { - search_paths.add_path(&s[..], error_format); + search_paths.push(SearchPath::from_cli_opt(&s[..], error_format)); } let libs = matches @@ -2535,6 +2535,7 @@ mod tests { use session::config::{build_configuration, build_session_options_and_crate_config}; use session::config::{LtoCli, CrossLangLto}; use session::build_session; + use session::search_paths::SearchPath; use std::collections::{BTreeMap, BTreeSet}; use std::iter::FromIterator; use std::path::PathBuf; @@ -2790,48 +2791,48 @@ fn test_search_paths_tracking_hash_different_order() { // Reference v1.search_paths - .add_path("native=abc", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("native=abc", super::ErrorOutputType::Json(false))); v1.search_paths - .add_path("crate=def", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("crate=def", super::ErrorOutputType::Json(false))); v1.search_paths - .add_path("dependency=ghi", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("dependency=ghi", super::ErrorOutputType::Json(false))); v1.search_paths - .add_path("framework=jkl", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("framework=jkl", super::ErrorOutputType::Json(false))); v1.search_paths - .add_path("all=mno", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("all=mno", super::ErrorOutputType::Json(false))); v2.search_paths - .add_path("native=abc", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("native=abc", super::ErrorOutputType::Json(false))); v2.search_paths - .add_path("dependency=ghi", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("dependency=ghi", super::ErrorOutputType::Json(false))); v2.search_paths - .add_path("crate=def", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("crate=def", super::ErrorOutputType::Json(false))); v2.search_paths - .add_path("framework=jkl", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("framework=jkl", super::ErrorOutputType::Json(false))); v2.search_paths - .add_path("all=mno", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("all=mno", super::ErrorOutputType::Json(false))); v3.search_paths - .add_path("crate=def", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("crate=def", super::ErrorOutputType::Json(false))); v3.search_paths - .add_path("framework=jkl", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("framework=jkl", super::ErrorOutputType::Json(false))); v3.search_paths - .add_path("native=abc", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("native=abc", super::ErrorOutputType::Json(false))); v3.search_paths - .add_path("dependency=ghi", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("dependency=ghi", super::ErrorOutputType::Json(false))); v3.search_paths - .add_path("all=mno", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("all=mno", super::ErrorOutputType::Json(false))); v4.search_paths - .add_path("all=mno", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("all=mno", super::ErrorOutputType::Json(false))); v4.search_paths - .add_path("native=abc", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("native=abc", super::ErrorOutputType::Json(false))); v4.search_paths - .add_path("crate=def", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("crate=def", super::ErrorOutputType::Json(false))); v4.search_paths - .add_path("dependency=ghi", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("dependency=ghi", super::ErrorOutputType::Json(false))); v4.search_paths - .add_path("framework=jkl", super::ErrorOutputType::Json(false)); + .push(SearchPath::from_cli_opt("framework=jkl", super::ErrorOutputType::Json(false))); assert!(v1.dep_tracking_hash() == v2.dep_tracking_hash()); assert!(v1.dep_tracking_hash() == v3.dep_tracking_hash()); diff --git a/src/librustc/session/filesearch.rs b/src/librustc/session/filesearch.rs index f5dfde7d518..6f52d285353 100644 --- a/src/librustc/session/filesearch.rs +++ b/src/librustc/session/filesearch.rs @@ -18,7 +18,7 @@ use std::fs; use std::path::{Path, PathBuf}; -use session::search_paths::{SearchPaths, PathKind}; +use session::search_paths::{SearchPath, PathKind}; use rustc_fs_util::fix_windows_verbatim_for_gcc; #[derive(Copy, Clone)] @@ -31,27 +31,28 @@ pub enum FileMatch { pub struct FileSearch<'a> { pub sysroot: &'a Path, - pub search_paths: &'a SearchPaths, + pub search_paths: &'a [SearchPath], pub triple: &'a str, pub kind: PathKind, } impl<'a> FileSearch<'a> { pub fn for_each_lib_search_path(&self, mut f: F) where - F: FnMut(&Path, PathKind) + F: FnMut(&SearchPath) { let mut visited_dirs = FxHashSet::default(); - visited_dirs.reserve(self.search_paths.paths.len() + 1); - for (path, kind) in self.search_paths.iter(self.kind) { - f(path, kind); - visited_dirs.insert(path.to_path_buf()); + visited_dirs.reserve(self.search_paths.len() + 1); + let iter = self.search_paths.iter().filter(|sp| sp.kind.matches(self.kind)); + for search_path in iter { + f(search_path); + visited_dirs.insert(search_path.dir.to_path_buf()); } debug!("filesearch: searching lib path"); let tlib_path = make_target_lib_path(self.sysroot, self.triple); if !visited_dirs.contains(&tlib_path) { - f(&tlib_path, PathKind::All); + f(&SearchPath { kind: PathKind::All, dir: tlib_path }); } } @@ -62,9 +63,9 @@ pub fn get_lib_path(&self) -> PathBuf { pub fn search(&self, mut pick: F) where F: FnMut(&Path, PathKind) -> FileMatch { - self.for_each_lib_search_path(|lib_search_path, kind| { - debug!("searching {}", lib_search_path.display()); - let files = match fs::read_dir(lib_search_path) { + self.for_each_lib_search_path(|search_path| { + debug!("searching {}", search_path.dir.display()); + let files = match fs::read_dir(&search_path.dir) { Ok(files) => files, Err(..) => return, }; @@ -81,7 +82,7 @@ fn is_rlib(p: &Path) -> bool { let files2 = files.iter().filter(|p| !is_rlib(p)); for path in files1.chain(files2) { debug!("testing {}", path.display()); - let maybe_picked = pick(path, kind); + let maybe_picked = pick(path, search_path.kind); match maybe_picked { FileMatches => { debug!("picked {}", path.display()); @@ -96,7 +97,7 @@ fn is_rlib(p: &Path) -> bool { pub fn new(sysroot: &'a Path, triple: &'a str, - search_paths: &'a SearchPaths, + search_paths: &'a Vec, kind: PathKind) -> FileSearch<'a> { debug!("using sysroot = {}, triple = {}", sysroot.display(), triple); FileSearch { @@ -110,8 +111,8 @@ pub fn new(sysroot: &'a Path, // Returns a list of directories where target-specific dylibs might be located. pub fn get_dylib_search_paths(&self) -> Vec { let mut paths = Vec::new(); - self.for_each_lib_search_path(|lib_search_path, _| { - paths.push(lib_search_path.to_path_buf()); + self.for_each_lib_search_path(|search_path| { + paths.push(search_path.dir.to_path_buf()); }); paths } @@ -136,7 +137,7 @@ pub fn relative_target_lib_path(sysroot: &Path, target_triple: &str) -> PathBuf p } -fn make_target_lib_path(sysroot: &Path, +pub fn make_target_lib_path(sysroot: &Path, target_triple: &str) -> PathBuf { sysroot.join(&relative_target_lib_path(sysroot, target_triple)) } diff --git a/src/librustc/session/search_paths.rs b/src/librustc/session/search_paths.rs index 6b0a8a0af2b..7a0bd2ed439 100644 --- a/src/librustc/session/search_paths.rs +++ b/src/librustc/session/search_paths.rs @@ -8,18 +8,14 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::slice; use std::path::{Path, PathBuf}; use session::{early_error, config}; +use session::filesearch::make_target_lib_path; #[derive(Clone, Debug)] -pub struct SearchPaths { - crate paths: Vec<(PathKind, PathBuf)>, -} - -pub struct Iter<'a> { - kind: PathKind, - iter: slice::Iter<'a, (PathKind, PathBuf)>, +pub struct SearchPath { + pub kind: PathKind, + pub dir: PathBuf, } #[derive(Eq, PartialEq, Clone, Copy, Debug, PartialOrd, Ord, Hash)] @@ -32,12 +28,17 @@ pub enum PathKind { All, } -impl SearchPaths { - pub fn new() -> SearchPaths { - SearchPaths { paths: Vec::new() } +impl PathKind { + pub fn matches(&self, kind: PathKind) -> bool { + match (self, kind) { + (PathKind::All, _) | (_, PathKind::All) => true, + _ => *self == kind, + } } +} - pub fn add_path(&mut self, path: &str, output: config::ErrorOutputType) { +impl SearchPath { + pub fn from_cli_opt(path: &str, output: config::ErrorOutputType) -> Self { let (kind, path) = if path.starts_with("native=") { (PathKind::Native, &path["native=".len()..]) } else if path.starts_with("crate=") { @@ -54,34 +55,17 @@ pub fn add_path(&mut self, path: &str, output: config::ErrorOutputType) { if path.is_empty() { early_error(output, "empty search path given via `-L`"); } - self.paths.push((kind, PathBuf::from(path))); - } - pub fn iter(&self, kind: PathKind) -> Iter<'_> { - Iter { kind: kind, iter: self.paths.iter() } + let dir = PathBuf::from(path); + Self::new(kind, dir) } -} - -impl<'a> Iterator for Iter<'a> { - type Item = (&'a Path, PathKind); - fn next(&mut self) -> Option<(&'a Path, PathKind)> { - loop { - match *self.iter.next()? { - (kind, ref p) if self.kind == PathKind::All || - kind == PathKind::All || - kind == self.kind => { - return Some((p, kind)) - } - _ => {} - } - } + pub fn from_sysroot_and_triple(sysroot: &Path, triple: &str) -> Self { + Self::new(PathKind::All, make_target_lib_path(sysroot, triple)) } - fn size_hint(&self) -> (usize, Option) { - // This iterator will never return more elements than the base iterator; - // but it can ignore all the remaining elements. - let (_, upper) = self.iter.size_hint(); - (0, upper) + fn new(kind: PathKind, dir: PathBuf) -> Self { + SearchPath { kind, dir } } } + diff --git a/src/librustc_codegen_llvm/back/link.rs b/src/librustc_codegen_llvm/back/link.rs index 20a7bf9a1a9..da5ad39ad26 100644 --- a/src/librustc_codegen_llvm/back/link.rs +++ b/src/librustc_codegen_llvm/back/link.rs @@ -213,8 +213,8 @@ fn link_binary_output(sess: &Session, fn archive_search_paths(sess: &Session) -> Vec { let mut search = Vec::new(); - sess.target_filesearch(PathKind::Native).for_each_lib_search_path(|path, _| { - search.push(path.to_path_buf()); + sess.target_filesearch(PathKind::Native).for_each_lib_search_path(|search_path| { + search.push(search_path.dir.to_path_buf()); }); search @@ -1067,10 +1067,10 @@ fn link_args(cmd: &mut dyn Linker, fn add_local_native_libraries(cmd: &mut dyn Linker, sess: &Session, codegen_results: &CodegenResults) { - sess.target_filesearch(PathKind::All).for_each_lib_search_path(|path, k| { - match k { - PathKind::Framework => { cmd.framework_path(path); } - _ => { cmd.include_path(&fix_windows_verbatim_for_gcc(path)); } + sess.target_filesearch(PathKind::All).for_each_lib_search_path(|search_path| { + match search_path.kind { + PathKind::Framework => { cmd.framework_path(&search_path.dir); } + _ => { cmd.include_path(&fix_windows_verbatim_for_gcc(&search_path.dir)); } } }); diff --git a/src/librustdoc/config.rs b/src/librustdoc/config.rs index f4d05c6dbd6..b421f07ddaf 100644 --- a/src/librustdoc/config.rs +++ b/src/librustdoc/config.rs @@ -20,7 +20,7 @@ use rustc::session::config::{CodegenOptions, DebuggingOptions, ErrorOutputType, Externs}; use rustc::session::config::{nightly_options, build_codegen_options, build_debugging_options, get_cmd_lint_options}; -use rustc::session::search_paths::SearchPaths; +use rustc::session::search_paths::SearchPath; use rustc_driver; use rustc_target::spec::TargetTriple; use syntax::edition::Edition; @@ -46,7 +46,7 @@ pub struct Options { /// How to format errors and warnings. pub error_format: ErrorOutputType, /// Library search paths to hand to the compiler. - pub libs: SearchPaths, + pub libs: Vec, /// The list of external crates to link against. pub externs: Externs, /// List of `cfg` flags to hand to the compiler. Always includes `rustdoc`. @@ -295,10 +295,9 @@ pub fn from_matches(matches: &getopts::Matches) -> Result { } let input = PathBuf::from(&matches.free[0]); - let mut libs = SearchPaths::new(); - for s in &matches.opt_strs("L") { - libs.add_path(s, error_format); - } + let libs = matches.opt_strs("L").iter() + .map(|s| SearchPath::from_cli_opt(s, error_format)) + .collect(); let externs = match parse_externs(&matches) { Ok(ex) => ex, Err(err) => { diff --git a/src/librustdoc/core.rs b/src/librustdoc/core.rs index 047d3557944..b85342f6311 100644 --- a/src/librustdoc/core.rs +++ b/src/librustdoc/core.rs @@ -51,7 +51,7 @@ use passes; pub use rustc::session::config::{Input, Options, CodegenOptions}; -pub use rustc::session::search_paths::SearchPaths; +pub use rustc::session::search_paths::SearchPath; pub type ExternalPaths = FxHashMap, clean::TypeKind)>; diff --git a/src/librustdoc/test.rs b/src/librustdoc/test.rs index be9327ced26..50acde64cf0 100644 --- a/src/librustdoc/test.rs +++ b/src/librustdoc/test.rs @@ -21,7 +21,7 @@ use rustc::hir::intravisit; use rustc::session::{self, CompileIncomplete, config}; use rustc::session::config::{OutputType, OutputTypes, Externs, CodegenOptions}; -use rustc::session::search_paths::{SearchPaths, PathKind}; +use rustc::session::search_paths::{SearchPath, PathKind}; use syntax::ast; use syntax::source_map::SourceMap; use syntax::edition::Edition; @@ -187,7 +187,7 @@ fn scrape_test_config(krate: &::rustc::hir::Crate) -> TestOptions { } fn run_test(test: &str, cratename: &str, filename: &FileName, line: usize, - cfgs: Vec, libs: SearchPaths, + cfgs: Vec, libs: Vec, cg: CodegenOptions, externs: Externs, should_panic: bool, no_run: bool, as_test_harness: bool, compile_fail: bool, mut error_codes: Vec, opts: &TestOptions, @@ -556,7 +556,7 @@ pub struct Collector { names: Vec, cfgs: Vec, - libs: SearchPaths, + libs: Vec, cg: CodegenOptions, externs: Externs, use_headers: bool, @@ -571,7 +571,7 @@ pub struct Collector { } impl Collector { - pub fn new(cratename: String, cfgs: Vec, libs: SearchPaths, cg: CodegenOptions, + pub fn new(cratename: String, cfgs: Vec, libs: Vec, cg: CodegenOptions, externs: Externs, use_headers: bool, opts: TestOptions, maybe_sysroot: Option, source_map: Option>, filename: Option, linker: Option, edition: Edition) -> Collector { -- 2.44.0