From 93a6d69a621eeeccea181050af3a8ca5c2771afe Mon Sep 17 00:00:00 2001 From: Jeff Vander Stoep Date: Mon, 19 Dec 2022 12:00:50 +0100 Subject: Upgrade which to 4.3.0 This project was upgraded with external_updater. Usage: tools/external_updater/updater.sh update rust/crates/which For more info, check https://cs.android.com/android/platform/superproject/+/master:tools/external_updater/README.md Test: TreeHugger Change-Id: Iedee7f8b500cb8413c53ac78ca61e378a77ea427 --- .cargo_vcs_info.json | 2 +- Android.bp | 6 +++- Cargo.toml | 22 +++++++++--- Cargo.toml.orig | 4 +-- METADATA | 12 ++++--- src/finder.rs | 95 ++++++++++++++++++++++++++++++++++------------------ src/lib.rs | 6 +--- tests/basic.rs | 16 +++++++++ 8 files changed, 113 insertions(+), 50 deletions(-) diff --git a/.cargo_vcs_info.json b/.cargo_vcs_info.json index 4dbf890..d0e4fff 100644 --- a/.cargo_vcs_info.json +++ b/.cargo_vcs_info.json @@ -1,6 +1,6 @@ { "git": { - "sha1": "ca9cc93b392fa1d0eb4eb2a60c74b3b3ecff03bb" + "sha1": "492df704947be42c30f3bc7947e75244f26a0a45" }, "path_in_vcs": "" } \ No newline at end of file diff --git a/Android.bp b/Android.bp index d41ae65..bc8bec7 100644 --- a/Android.bp +++ b/Android.bp @@ -23,11 +23,15 @@ rust_library { host_supported: true, crate_name: "which", cargo_env_compat: true, - cargo_pkg_version: "4.2.5", + cargo_pkg_version: "4.3.0", srcs: ["src/lib.rs"], edition: "2018", rustlibs: [ "libeither", "liblibc", ], + apex_available: [ + "//apex_available:platform", + "//apex_available:anyapex", + ], } diff --git a/Cargo.toml b/Cargo.toml index 3e5545f..84d671a 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -12,17 +12,27 @@ [package] edition = "2018" name = "which" -version = "4.2.5" +version = "4.3.0" authors = ["Harry Fei "] description = "A Rust equivalent of Unix command \"which\". Locate installed executable in cross platforms." documentation = "https://docs.rs/which/" readme = "README.md" -keywords = ["which", "which-rs", "unix", "command"] -categories = ["os", "filesystem"] +keywords = [ + "which", + "which-rs", + "unix", + "command", +] +categories = [ + "os", + "filesystem", +] license = "MIT" repository = "https://github.com/harryfei/which-rs.git" + [package.metadata.docs.rs] all-features = true + [dependencies.either] version = "1.6.1" @@ -32,7 +42,9 @@ version = "0.2.121" [dependencies.regex] version = "1.5.5" optional = true + [dev-dependencies.tempfile] version = "3.3.0" -[target."cfg(windows)".dependencies.lazy_static] -version = "1.4.0" + +[target."cfg(windows)".dependencies.once_cell] +version = "1" diff --git a/Cargo.toml.orig b/Cargo.toml.orig index dccbdb4..d8251f8 100644 --- a/Cargo.toml.orig +++ b/Cargo.toml.orig @@ -1,6 +1,6 @@ [package] name = "which" -version = "4.2.5" +version = "4.3.0" edition = "2018" authors = ["Harry Fei "] repository = "https://github.com/harryfei/which-rs.git" @@ -17,7 +17,7 @@ libc = "0.2.121" regex = { version = "1.5.5", optional = true } [target.'cfg(windows)'.dependencies] -lazy_static = "1.4.0" +once_cell = "1" [dev-dependencies] tempfile = "3.3.0" diff --git a/METADATA b/METADATA index 9d9dd01..36e9b3e 100644 --- a/METADATA +++ b/METADATA @@ -1,3 +1,7 @@ +# This project was upgraded with external_updater. +# Usage: tools/external_updater/updater.sh update rust/crates/which +# For more info, check https://cs.android.com/android/platform/superproject/+/master:tools/external_updater/README.md + name: "which" description: "A Rust equivalent of Unix command \"which\". Locate installed executable in cross platforms." third_party { @@ -7,13 +11,13 @@ third_party { } url { type: ARCHIVE - value: "https://static.crates.io/crates/which/which-4.2.5.crate" + value: "https://static.crates.io/crates/which/which-4.3.0.crate" } - version: "4.2.5" + version: "4.3.0" license_type: NOTICE last_upgrade_date { year: 2022 - month: 4 - day: 18 + month: 12 + day: 19 } } diff --git a/src/finder.rs b/src/finder.rs index 9b64294..858a224 100644 --- a/src/finder.rs +++ b/src/finder.rs @@ -9,7 +9,7 @@ use regex::Regex; use std::borrow::Borrow; use std::env; use std::ffi::OsStr; -#[cfg(feature = "regex")] +#[cfg(any(feature = "regex", target_os = "windows"))] use std::fs; use std::iter; use std::path::{Path, PathBuf}; @@ -80,7 +80,9 @@ impl Finder { } }; - Ok(binary_path_candidates.filter(move |p| binary_checker.is_valid(p))) + Ok(binary_path_candidates + .filter(move |p| binary_checker.is_valid(p)) + .map(correct_casing)) } #[cfg(feature = "regex")] @@ -151,29 +153,31 @@ impl Finder { where P: IntoIterator, { + use once_cell::sync::Lazy; + // Sample %PATHEXT%: .COM;.EXE;.BAT;.CMD;.VBS;.VBE;.JS;.JSE;.WSF;.WSH;.MSC // PATH_EXTENSIONS is then [".COM", ".EXE", ".BAT", …]. // (In one use of PATH_EXTENSIONS we skip the dot, but in the other we need it; // hence its retention.) - lazy_static! { - static ref PATH_EXTENSIONS: Vec = - env::var("PATHEXT") - .map(|pathext| { - pathext.split(';') - .filter_map(|s| { - if s.as_bytes().first() == Some(&b'.') { - Some(s.to_owned()) - } else { - // Invalid segment; just ignore it. - None - } - }) - .collect() - }) - // PATHEXT not being set or not being a proper Unicode string is exceedingly - // improbable and would probably break Windows badly. Still, don't crash: - .unwrap_or_default(); - } + static PATH_EXTENSIONS: Lazy> = Lazy::new(|| { + env::var("PATHEXT") + .map(|pathext| { + pathext + .split(';') + .filter_map(|s| { + if s.as_bytes().first() == Some(&b'.') { + Some(s.to_owned()) + } else { + // Invalid segment; just ignore it. + None + } + }) + .collect() + }) + // PATHEXT not being set or not being a proper Unicode string is exceedingly + // improbable and would probably break Windows badly. Still, don't crash: + .unwrap_or_default() + }); paths .into_iter() @@ -182,20 +186,47 @@ impl Finder { if has_executable_extension(&p, &PATH_EXTENSIONS) { Box::new(iter::once(p)) } else { + let bare_file = p.extension().map(|_| p.clone()); // Appended paths with windows executable extensions. - // e.g. path `c:/windows/bin` will expend to: - // c:/windows/bin.COM - // c:/windows/bin.EXE - // c:/windows/bin.CMD + // e.g. path `c:/windows/bin[.ext]` will expand to: + // [c:/windows/bin.ext] + // c:/windows/bin[.ext].COM + // c:/windows/bin[.ext].EXE + // c:/windows/bin[.ext].CMD // ... - Box::new(PATH_EXTENSIONS.iter().map(move |e| { - // Append the extension. - let mut p = p.clone().into_os_string(); - p.push(e); - - PathBuf::from(p) - })) + Box::new( + bare_file + .into_iter() + .chain(PATH_EXTENSIONS.iter().map(move |e| { + // Append the extension. + let mut p = p.clone().into_os_string(); + p.push(e); + + PathBuf::from(p) + })), + ) } }) } } + +#[cfg(target_os = "windows")] +fn correct_casing(mut p: PathBuf) -> PathBuf { + if let (Some(parent), Some(file_name)) = (p.parent(), p.file_name()) { + if let Ok(iter) = fs::read_dir(parent) { + for e in iter.filter_map(std::result::Result::ok) { + if e.file_name().eq_ignore_ascii_case(file_name) { + p.pop(); + p.push(e.file_name()); + break; + } + } + } + } + p +} + +#[cfg(not(target_os = "windows"))] +fn correct_casing(p: PathBuf) -> PathBuf { + p +} diff --git a/src/lib.rs b/src/lib.rs index 2b27094..b9026ff 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -14,10 +14,6 @@ //! //! ``` -#[cfg(windows)] -#[macro_use] -extern crate lazy_static; - mod checker; mod error; mod finder; @@ -38,7 +34,7 @@ use crate::checker::{CompositeChecker, ExecutableChecker, ExistedChecker}; pub use crate::error::*; use crate::finder::Finder; -/// Find a exectable binary's path by name. +/// Find an executable binary's path by name. /// /// If given an absolute path, returns it if the file exists and is executable. /// diff --git a/tests/basic.rs b/tests/basic.rs index 59c5fb0..32a1a28 100644 --- a/tests/basic.rs +++ b/tests/basic.rs @@ -67,6 +67,10 @@ impl TestFixture { bins.push(mk_bin(&p, BIN_NAME, "cmd").unwrap()); paths.push(p); } + let p = tempdir.path().join("win-bin"); + builder.create(&p).unwrap(); + bins.push(mk_bin(&p, "win-bin", "exe").unwrap()); + paths.push(p); TestFixture { tempdir, paths: env::join_paths(paths).unwrap(), @@ -194,6 +198,17 @@ fn test_which_extension() { assert_eq!(_which(&f, &b).unwrap(), f.bins[2]) } +#[test] +#[cfg(windows)] +fn test_which_no_extension() { + let f = TestFixture::new(); + let b = Path::new("win-bin"); + let which_result = which::which_in(&b, Some(&f.paths), ".").unwrap(); + // Make sure the extension is the correct case. + assert_eq!(which_result.extension(), f.bins[9].extension()); + assert_eq!(fs::canonicalize(&which_result).unwrap(), f.bins[9]) +} + #[test] fn test_which_not_found() { let f = TestFixture::new(); @@ -221,6 +236,7 @@ fn test_which_all() { .collect::>(); #[cfg(windows)] { + expected.retain(|p| p.file_stem().unwrap() == BIN_NAME); expected.retain(|p| p.extension().map(|ext| ext == "exe" || ext == "cmd") == Some(true)); } #[cfg(not(windows))] -- cgit v1.2.3