pico_driver/
kernel_driver.rs

1#[cfg(not(target_os = "windows"))]
2pub fn is_missing() -> bool {
3    false
4}
5
6#[cfg(target_os = "windows")]
7pub fn is_missing() -> bool {
8    use std::{
9        ffi::OsStr,
10        iter::once,
11        mem::size_of,
12        os::windows::ffi::OsStrExt,
13        ptr::{null, null_mut},
14    };
15
16    use winapi::um::setupapi::*;
17
18    let flags = DIGCF_ALLCLASSES;
19    let wide: Vec<u16> = OsStr::new("USB").encode_wide().chain(once(0)).collect();
20
21    let dev_info = unsafe { SetupDiGetClassDevsW(null(), wide.as_ptr(), null_mut(), flags) };
22
23    let mut dev_info_data = SP_DEVINFO_DATA {
24        cbSize: size_of::<SP_DEVINFO_DATA>() as u32,
25        ..Default::default()
26    };
27
28    let mut i = 0;
29    while unsafe { SetupDiEnumDeviceInfo(dev_info, i, &mut dev_info_data) } > 0 {
30        if unsafe { SetupDiBuildDriverInfoList(dev_info, &mut dev_info_data, SPDIT_COMPATDRIVER) }
31            > 0
32        {
33            let mut j = 0;
34            loop {
35                let mut drv_info_data = SP_DRVINFO_DATA_V2_W {
36                    cbSize: std::mem::size_of::<SP_DRVINFO_DATA_V2_W>() as u32,
37                    ..Default::default()
38                };
39
40                if unsafe {
41                    SetupDiEnumDriverInfoW(
42                        dev_info,
43                        &mut dev_info_data,
44                        SPDIT_COMPATDRIVER,
45                        j,
46                        &mut drv_info_data,
47                    )
48                } == 0
49                {
50                    break;
51                }
52
53                let mfg = drv_info_data.MfgName;
54                if String::from_utf16_lossy(&mfg)
55                    .trim_matches(char::from(0))
56                    .contains("Pico Technology Ltd")
57                {
58                    return false;
59                }
60
61                j += 1;
62            }
63        }
64
65        i += 1;
66    }
67
68    true
69}