mirror of
https://github.com/cargo-bins/cargo-binstall.git
synced 2025-04-20 12:38:43 +00:00

* Fix detect-targets on android targets By enabling linux fallback on Android. Also add CI regression test for aarch64-linux-android target. Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix CI: Add job `detect-targets-android-check` as required for merging Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> --------- Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com>
115 lines
3.6 KiB
Rust
115 lines
3.6 KiB
Rust
use std::{
|
|
borrow::Cow,
|
|
env,
|
|
ffi::OsStr,
|
|
process::{Output, Stdio},
|
|
};
|
|
|
|
use cfg_if::cfg_if;
|
|
use tokio::process::Command;
|
|
#[cfg(feature = "tracing")]
|
|
use tracing::debug;
|
|
|
|
cfg_if! {
|
|
if #[cfg(any(target_os = "linux", target_os = "android"))] {
|
|
mod linux;
|
|
} else if #[cfg(target_os = "macos")] {
|
|
mod macos;
|
|
} else if #[cfg(target_os = "windows")] {
|
|
mod windows;
|
|
}
|
|
}
|
|
|
|
/// Detect the targets supported at runtime,
|
|
/// which might be different from `TARGET` which is detected
|
|
/// at compile-time.
|
|
///
|
|
/// Return targets supported in the order of preference.
|
|
/// If target_os is linux and it support gnu, then it is preferred
|
|
/// to musl.
|
|
///
|
|
/// If target_os is mac and it is aarch64, then aarch64 is preferred
|
|
/// to x86_64.
|
|
///
|
|
/// Check [this issue](https://github.com/ryankurte/cargo-binstall/issues/155)
|
|
/// for more information.
|
|
pub async fn detect_targets() -> Vec<String> {
|
|
let target = get_target_from_rustc().await;
|
|
#[cfg(feature = "tracing")]
|
|
debug!("get_target_from_rustc()={target:?}");
|
|
let target = target.unwrap_or_else(|| {
|
|
let target = guess_host_triple::guess_host_triple();
|
|
#[cfg(feature = "tracing")]
|
|
debug!("guess_host_triple::guess_host_triple()={target:?}");
|
|
target.unwrap_or(crate::TARGET).to_string()
|
|
});
|
|
|
|
cfg_if! {
|
|
if #[cfg(target_os = "macos")] {
|
|
let mut targets = vec![target];
|
|
targets.extend(macos::detect_alternative_targets(&targets[0]).await);
|
|
targets
|
|
} else if #[cfg(target_os = "windows")] {
|
|
let mut targets = vec![target];
|
|
targets.extend(windows::detect_alternative_targets(&targets[0]));
|
|
targets
|
|
} else if #[cfg(any(target_os = "linux", target_os = "android"))] {
|
|
// Linux is a bit special, since the result from `guess_host_triple`
|
|
// might be wrong about whether glibc or musl is used.
|
|
linux::detect_targets(target).await
|
|
} else {
|
|
vec![target]
|
|
}
|
|
}
|
|
}
|
|
|
|
/// Figure out what the host target is using `rustc`.
|
|
/// If `rustc` is absent, then it would return `None`.
|
|
///
|
|
/// If environment variable `CARGO` is present, then
|
|
/// `$CARGO -vV` will be run instead.
|
|
///
|
|
/// Otherwise, it will run `rustc -vV` to detect target.
|
|
async fn get_target_from_rustc() -> Option<String> {
|
|
let cmd = env::var_os("CARGO")
|
|
.map(Cow::Owned)
|
|
.unwrap_or_else(|| Cow::Borrowed(OsStr::new("rustc")));
|
|
|
|
let Output { status, stdout, .. } = Command::new(cmd)
|
|
.arg("-vV")
|
|
.stdin(Stdio::null())
|
|
.stdout(Stdio::piped())
|
|
.stderr(Stdio::null())
|
|
.spawn()
|
|
.ok()?
|
|
.wait_with_output()
|
|
.await
|
|
.ok()?;
|
|
|
|
if !status.success() {
|
|
return None;
|
|
}
|
|
|
|
let stdout = String::from_utf8_lossy(&stdout);
|
|
let target = stdout
|
|
.lines()
|
|
.find_map(|line| line.strip_prefix("host: "))?;
|
|
|
|
// The target triplets have the form of 'arch-vendor-system'.
|
|
//
|
|
// When building for Linux (e.g. the 'system' part is
|
|
// 'linux-something'), replace the vendor with 'unknown'
|
|
// so that mapping to rust standard targets happens correctly.
|
|
//
|
|
// For example, alpine set `rustc` host triple to
|
|
// `x86_64-alpine-linux-musl`.
|
|
//
|
|
// Here we use splitn with n=4 since we just need to check
|
|
// the third part to see if it equals to "linux" and verify
|
|
// that we have at least three parts.
|
|
let mut parts: Vec<&str> = target.splitn(4, '-').collect();
|
|
if *parts.get(2)? == "linux" {
|
|
parts[1] = "unknown";
|
|
}
|
|
Some(parts.join("-"))
|
|
}
|