Skip to content

Commit

Permalink
Fixed #642
Browse files Browse the repository at this point in the history
* Add new dep windows-sys v0.42.0 for win only
* Add new dep windows-dll v0.4.1 for win only
* Add x86_64 fallback targets for windows
* Add x86 fallback targets for windows
* Add arm32 fallback targets for windows
* Add arm64 fallback targets for windows
* Add gnu/gnu-llvm fallback targets for windows

Signed-off-by: Jiahao XU <Jiahao_XU@outlook.com>
  • Loading branch information
NobodyXu committed Jun 3, 2023
1 parent 351b9d0 commit 6b34a7c
Show file tree
Hide file tree
Showing 3 changed files with 193 additions and 5 deletions.
81 changes: 80 additions & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 4 additions & 0 deletions crates/detect-targets/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -14,5 +14,9 @@ tokio = { version = "1.28.2", features = ["rt", "process", "sync"], default-feat
cfg-if = "1.0.0"
guess_host_triple = "0.1.3"

[target.'cfg(target_os = "windows")'.dependencies]
windows-sys = { version = "0.42.0", features = ["Win32_System_Threading", "Win32_System_SystemInformation", "Win32_Foundation"] }
windows-dll = { version = "0.4.1", features = ["windows"], default-features = false }

[dev-dependencies]
tokio = { version = "1.28.2", features = ["macros"], default-features = false }
113 changes: 109 additions & 4 deletions crates/detect-targets/src/detect/windows.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,111 @@
pub(super) fn detect_alternative_targets(target: &str) -> Option<String> {
let (prefix, abi) = target.rsplit_once('-')?;
use std::mem;
use windows_dll::dll;
use windows_sys::{
core::HRESULT,
Win32::System::{
SystemInformation::{
IMAGE_FILE_MACHINE, IMAGE_FILE_MACHINE_AMD64, IMAGE_FILE_MACHINE_ARM,
IMAGE_FILE_MACHINE_ARM64, IMAGE_FILE_MACHINE_I386,
},
Threading::{UserEnabled, Wow64Container, MACHINE_ATTRIBUTES},
},
};

// detect abi in ["gnu", "gnullvm", ...]
(abi != "msvc").then(|| format!("{prefix}-msvc"))
#[dll("Kernel32")]
extern "system" {
#[allow(non_snake_case)]
#[fallible]
fn GetMachineTypeAttributes(
machine: IMAGE_FILE_MACHINE,
machine_attributes: *mut MACHINE_ATTRIBUTES,
) -> HRESULT;
}

fn is_arch_supported(arch: IMAGE_FILE_MACHINE) -> bool {
let mut machine_attributes = mem::MaybeUninit::uninit();

// SAFETY: GetMachineTypeAttributes takes type IMAGE_FILE_MACHINE
// plus it takes a pointer to machine_attributes which is only
// written to.
match unsafe { GetMachineTypeAttributes(arch, machine_attributes.as_mut_ptr()) } {
Ok(0) => {
// SAFETY: Symbol GetMachineTypeAttributes exists and calls to it
// succceeds.
//
// Thus, machine_attributes is initialized.
let machine_attributes = unsafe { machine_attributes.assume_init() };

(machine_attributes & (Wow64Container | UserEnabled)) != 0
}
_ => false,
}
}

pub(super) fn detect_alternative_targets(target: &str) -> impl Iterator<Item = String> {
let (prefix, abi) = target
.rsplit_once('-')
.expect("unwrap: target always has a -");

let arch = prefix
.split_once('-')
.expect("unwrap: target always has at least two -")
.0;

let msvc_fallback_target = (abi != "msvc").then(|| format!("{prefix}-msvc"));

let gnu_fallback_targets = (abi == "msvc")
.then(|| [format!("{prefix}-gnu"), format!("{prefix}-gnullvm")])
.into_iter()
.flatten();

let x64_fallback_targets = (arch != "x86_64" && is_arch_supported(IMAGE_FILE_MACHINE_AMD64))
.then_some([
"x86_64-pc-windows-msvc",
"x86_64-pc-windows-gnu",
"x86_64-pc-windows-gnullvm",
])
.into_iter()
.flatten()
.map(ToString::to_string);

let x86_fallback_targets = (arch != "x86" && is_arch_supported(IMAGE_FILE_MACHINE_I386))
.then_some([
"i586-pc-windows-msvc",
"i586-pc-windows-gnu",
"i586-pc-windows-gnullvm",
"i686-pc-windows-msvc",
"i686-pc-windows-gnu",
"i686-pc-windows-gnullvm",
])
.into_iter()
.flatten()
.map(ToString::to_string);

let arm32_fallback_targets = (arch != "thumbv7a" && is_arch_supported(IMAGE_FILE_MACHINE_ARM))
.then_some([
"thumbv7a-pc-windows-msvc",
"thumbv7a-pc-windows-gnu",
"thumbv7a-pc-windows-gnullvm",
])
.into_iter()
.flatten()
.map(ToString::to_string);

let arm64_fallback_targets = (arch != "aarch64" && is_arch_supported(IMAGE_FILE_MACHINE_ARM64))
.then_some([
"aarch64-pc-windows-msvc",
"aarch64-pc-windows-gnu",
"aarch64-pc-windows-gnullvm",
])
.into_iter()
.flatten()
.map(ToString::to_string);

msvc_fallback_target
.into_iter()
.chain(gnu_fallback_targets)
.chain(x64_fallback_targets)
.chain(x86_fallback_targets)
.chain(arm32_fallback_targets)
.chain(arm64_fallback_targets)
}

0 comments on commit 6b34a7c

Please sign in to comment.