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

* Testing: Add `detect-targets/src/main.rs` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix `detect-targets` linux: `guess_host_triple` could return wrong libc info so it has to check it manually instead of simply providing alternatives like other OSes. Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix `get_ld_flavor` for Alpine's gcompat glibc Its output is different from regular glibc, so we need to hardcode that particular cases. Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix detection of alpine specific musl target Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Add ci testing for Alpine Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Add CI test for detect-targets on ubuntu Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Refactor `get_ld_flavor` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix shellcheck Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Add more CI test for ubuntu and fixed typo in it Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Rm distro specific target as it breaks `cargo-install` fallback Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Make sure all binaries are built in CI Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Add `package.metadata.binstall` for `detect-targets` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix justfile Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix `detect-targets-{alpine, ubuntu}-test` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix `detect-targets-ubuntu-test` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix `debug-targets-ubuntu-test` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * `set -exuo pipefail` in `detect-targets-ubuntu-test` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Simplify `detect-targets-*-test`: Use `Swatinem/rust-cache@v2` directly instead of using `just-setup` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Rm dup steps in `detect-targets-ubuntu-test` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Add `ls` to detect-targets-alpine-test for debugging Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * FIx `detect-targets-alpine-test` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix `get_ld_flavor` Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * Fix `linux::detect_targets` on ubuntu & glibc system Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> * FIx `linux::detect_targets` glibc checking Check dynlib suffix Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com> --------- Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com>
107 lines
3.2 KiB
Rust
107 lines
3.2 KiB
Rust
use std::{
|
|
borrow::Cow,
|
|
env,
|
|
ffi::OsStr,
|
|
process::{Output, Stdio},
|
|
};
|
|
|
|
use cfg_if::cfg_if;
|
|
use tokio::process::Command;
|
|
|
|
cfg_if! {
|
|
if #[cfg(target_os = "linux")] {
|
|
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.unwrap_or_else(|| {
|
|
guess_host_triple::guess_host_triple()
|
|
.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(target_os = "linux")] {
|
|
// 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
|
|
}
|
|
}
|
|
}
|
|
|
|
/// 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("-"))
|
|
}
|