1use anyhow::{anyhow, Result};
6
7#[cfg(target_family = "windows")]
8use std::path::PathBuf;
9
10pub fn target_arch_to_windows_sdk_platform_path() -> Result<&'static str> {
15 if cfg!(target_arch = "x86") {
16 Ok("x86")
17 } else if cfg!(target_arch = "x86_64") {
18 Ok("x64")
19 } else if cfg!(target_arch = "arm") {
20 Ok("arm")
21 } else if cfg!(target_arch = "aarch64") {
22 Ok("arm64")
23 } else {
24 Err(anyhow!("target architecture not supported on Windows"))
25 }
26}
27
28#[cfg(target_family = "windows")]
32pub fn find_windows_sdk_current_arch_bin_path(
33 version: Option<find_winsdk::SdkVersion>,
34) -> Result<PathBuf> {
35 let sdk_info = find_winsdk::SdkInfo::find(version.unwrap_or(find_winsdk::SdkVersion::Any))?
36 .ok_or_else(|| anyhow!("could not locate Windows SDK"))?;
37
38 let bin_path = sdk_info.installation_folder().join("bin");
39
40 let candidates = [
41 sdk_info.product_version().to_string(),
42 format!("{}.0", sdk_info.product_version()),
43 ];
44
45 let version_path = candidates
46 .iter()
47 .filter_map(|p| {
48 let p = bin_path.join(p);
49
50 if p.exists() {
51 Some(p)
52 } else {
53 None
54 }
55 })
56 .next()
57 .ok_or_else(|| anyhow!("could not locate Windows SDK version path"))?;
58
59 let arch_path = version_path.join(target_arch_to_windows_sdk_platform_path()?);
60
61 if arch_path.exists() {
62 Ok(arch_path)
63 } else {
64 Err(anyhow!("{} does not exist", arch_path.display()))
65 }
66}
67
68#[cfg(test)]
69mod tests {
70 #[cfg(target_family = "windows")]
71 use super::*;
72
73 #[cfg(target_family = "windows")]
74 #[test]
75 pub fn test_find_windows_sdk_current_arch_bin_path() -> Result<()> {
76 find_windows_sdk_current_arch_bin_path(None)?;
77
78 Ok(())
79 }
80}