Code Monkey home page Code Monkey logo

windows-drivers-rs's Introduction

windows-drivers-rs

This repo is a collection of Rust crates that enable developers to develop Windows Drivers in Rust. It is the intention to support both WDM and WDF driver development models. This repo contains the following crates:

  • wdk-build: A library to configure a Cargo build script for binding generation and downstream linking of the WDK (Windows Driver Kit). While this crate is written to be flexible with different WDK releases and different WDF version, it is currently only tested for NI eWDK, KMDF 1.33, UMDF 2.33, and WDM Drivers. There may be missing linker options for older DDKs.
  • wdk-sys: Direct FFI bindings to APIs available in the Windows Development Kit (WDK). This includes both autogenerated ffi bindings from bindgen, and also manual re-implementations of macros that bindgen fails to generate.
  • wdk: Safe idiomatic bindings to APIs available in the Windows Development Kit (WDK)
  • wdk-panic: Default panic handler implementations for programs built with WDK
  • wdk-alloc: alloc support for binaries compiled with the Windows Development Kit (WDK)
  • wdk-macros: A collection of macros that help make it easier to interact with wdk-sys's direct bindings. This crate is re-exported via wdk-sys and crates should typically never need to directly depend on wdk-macros

To see an example of this repo used to create drivers, see Windows-rust-driver-samples.

Note: This project is still in early stages of development and is not yet recommended for production use. We encourage community experimentation, suggestions and discussions! We will be using our GitHub Discussions forum as the main form of engagement with the community!

This project was built with support of WDM, KMDF, and UMDF drivers in mind, as well as Win32 Services. This includes support for all versions of WDF included in WDK 22H2 and newer. Currently, the crates available on crates.io only support KMDF v1.33, but bindings can be generated for everything else by cloning windows-drivers-rs and modifying the config specified in build.rs of wdk-sys. Crates.io support for other WDK configurations is planned in the near future.

Getting Started

Build Requirements

  • Binding generation via bindgen requires libclang. The easiest way to acquire this is via winget

    • winget install -i LLVM.LLVM
      • Ensure you select the GUI option to add LLVM to the PATH
  • To execute post-build tasks (ie. inf2cat, infverif, etc.), cargo make is used

    • cargo install --locked cargo-make --no-default-features --features tls-native
  • Building programs with the WDK also requires being in a valid WDK environment. The recommended way to do this is to enter an eWDK developer prompt

Adding windows-drivers-rs to Your Driver Package

The crates in this repository are available from crates.io, but take into account the current limitations outlined in Supported Configurations. If you need to support a different config, try cloning this repo and using path dependencies

  1. Create a new Cargo package with a lib crate:

    cargo new <driver_name> --lib
  2. Add dependencies on windows-drivers-rs crates:

    cd <driver_name>
    cargo add --build wdk-build
    cargo add wdk wdk-sys wdk-alloc wdk-panic
  3. Set the crate type to cdylib by adding the following snippet to Cargo.toml:

    [lib]
    crate-type = ["cdylib"]
  4. Mark the crate as a driver with a wdk metadata section. This lets the cargo-make tasks know that the package is a driver and that the driver packaging steps need to run.

    [package.metadata.wdk]
  5. Set crate panic strategy to abort in Cargo.toml:

    [profile.dev]
    panic = "abort"
    lto = true # optional setting to enable Link Time Optimizations
    
    [profile.release]
    panic = "abort"
    lto = true # optional setting to enable Link Time Optimizations
  6. Create a build.rs and add the following snippet:

    fn main() -> Result<(), wdk_build::ConfigError> {
       wdk_build::Config::from_env_auto()?.configure_binary_build()?;
       Ok(())
    }
  7. Mark your driver crate as no_std in lib.rs:

    #![no_std]
  8. Add a panic handler in lib.rs:

    #[cfg(not(test))]
    extern crate wdk_panic;
  9. Optional: Add a global allocator in lib.rs:

    #[cfg(not(test))]
    use wdk_alloc::WDKAllocator;
    
    #[cfg(not(test))]
    #[global_allocator]
    static GLOBAL_ALLOCATOR: WDKAllocator = WDKAllocator;

    This is only required if you want to be able to use the alloc modules in the rust standard library. You are also free to use your own implementations of global allocators.

  10. Add a DriverEntry in lib.rs:

use wdk_sys::{
   DRIVER_OBJECT,
   NTSTATUS,
   PCUNICODE_STRING,
};

#[export_name = "DriverEntry"] // WDF expects a symbol with the name DriverEntry
pub unsafe extern "system" fn driver_entry(
   driver: &mut DRIVER_OBJECT,
   registry_path: PCUNICODE_STRING,
) -> NTSTATUS {
   0
}
  1. Add a Makefile.toml:
extend = "target/rust-driver-makefile.toml"

[env]
CARGO_MAKE_EXTEND_WORKSPACE_MAKEFILE = true

[config]
load_script = '''
#!@rust
//! ```cargo
//! [dependencies]
//! wdk-build = "0.2.0"
//! ```
#![allow(unused_doc_comments)]

wdk_build::cargo_make::load_rust_driver_makefile()?
'''
  1. Add an inx file that matches the name of your cdylib crate.

  2. Build the driver:

cargo make

A signed driver package, including a WDRLocalTestCert.cer file, will be generated at target/<Cargo profile>/package. If a specific target architecture was specified, the driver package will be generated at target/<target architecture>/<Cargo profile>/package

Cargo Make

cargo-make is used to facilitate builds using windows-drivers-rs, including for executing post-build driver packaging steps.

To execute the default action (build and package driver):

cargo make default

When executing the default task, just cargo make make also works since the default task is implied.

Argument Forwarding

windows-drivers-rs extends cargo make to forward specific arguments to the underlying cargo commands. In order to specify arguments to forward, they must be provided after explicitly specifying the cargo-make task name (ie. omitting the name for the default task is not supported).

Examples

For a specific target:

cargo make default --target <TARGET TRIPLE>

For release builds:

cargo make default --release or cargo make default --profile release

To specify specific features:

cargo make default --feature <FEATURES>

To specify a specific rust toolchain:

cargo make default +<TOOLCHAIN>

To display help and see the full list of supported CLI args to forward to Cargo:

cargo make help

Driver Package Signature Verification

The WDK_BUILD_ENABLE_SIGNTOOL_VERIFY cargo-make environment variable can be set to true to enable tasks that handle signature verification of the generated .sys and .cat files. signtool verify requires the certificate to be installed as in the Trusted Root Certification Authorities for this verification to function. These tasks are not enabled by default as the default behavior of WDR is to sign with a generated test certificate. These test certificates are typically only installed into Trusted Root Certification Authorities on computers dedicated to testing drivers, and not personal development machines, given the security implications of installing your own root certificates.

If you understand these implications, and have installed the test certificate, then you may validate the signatures as follows:

cargo make --env WDK_BUILD_ENABLE_SIGNTOOL_VERIFY=true

Crates.io Release Policy

Releases to crates.io are not made after every change merged to main. Releases will only be made when requested by the community, or when the windows-drivers-rs team believes there is sufficient value in pushing a release.

Trademark Notice

Trademarks This project may contain trademarks or logos for projects, products, or services. Authorized use of Microsoft trademarks or logos is subject to and must follow Microsoft’s Trademark & Brand Guidelines. Use of Microsoft trademarks or logos in modified versions of this project must not cause confusion or imply Microsoft sponsorship. Any use of third-party trademarks or logos are subject to those third-party’s policies.

windows-drivers-rs's People

Contributors

dependabot[bot] avatar maheshrijal avatar olljanat avatar omer54463 avatar prototypenm1 avatar wmmc88 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

windows-drivers-rs's Issues

Choose between windows-rs and this crate

Hi! Thanks for your awesome work, but I have a question: windows-rs has bindings for WDK based on wdkmetadata, your crate uses bindgen. So... which crate should I use for a long-term project? Which crate is "official" WDK port that Microsoft recommends to use for drivers? And which approach is better (wdkmetadata vs bindgen) in terms of accuracy and completeness?

Structured Exception Handling

First, I'm very pleased to see this effort being open sourced. Big kudos to you all at Microsoft for formalizing a repository on this subject ❤️.

This is not an issue against the repository, rather, I hope to open a discussion on the topic of structured exception handling. For the Windows Kernel (and the OS in general) structured exception handling is an integral part of developing for Windows and a real blockers to making Rust a reality for Windows Kernel development.

Structured exception handling is a requirement in a number of workflows in the Windows Kernel. There are cases where structured exception handling is unavoidable, e.g. cases where an exported Kernel API expects the caller to handle a structured exception. Here are some examples where structured exceptions are used:

  • Reading memory from user mode must be done inside a __try/__except block.
  • Paging I/O might raise an exception if the related file data could not be accessed, and must be handled handled appropriately.
  • Some APIs for the kernel that are documented to raise exceptions, for example FsRtlIsNameInExpression states, "In low resource conditions, FsRtlIsNameInExpression can raise a structured exception with a code of STATUS_NO_MEMORY, which callers should be prepared to handle."

It looks like the issue is that the Rust code is missing a definition for the _DllMainCRTStartup symbol.

Error: link using link.exe failed: exit code: 1120
|
= note: "C:\Program Files (x86)\\Microsoft Visual Studio\\2022\\BuildTools\\VC\Tools\\MSVC\\14.36.32532\\bin\HostX64\x64\link. exe" "/DEF:C:\Users\\kelac\AppData\Local\\Temp\rustciNoZXt\lib. def" "/NOLOGO" "C:\Users\kelac\\AppData\Local\Temp\rustciNoZXt\symbols. o" "C:\Users\kelac\OneDrive\Desktop\joe\driver\target\debug\deps\driver.wdk_alloc-fab5448edb774dc7.wdk_alloc.d3d3930f6a8c5a64-cgu.0 .rcgu.o.rcgu.o" "/LIBPATH:C:\Users\kelac\OneDrive\Desktop\joe\\driver\\target\\debug\deps" "/LIBPATH:D:\Program Files\Windows Kits\\10\Lib\10.0.22621. 0\km\x64" "/LIBPATH:D:\Program Files\\Windows Kits\\10\Lib\\wdf\kmdf\x64\1.33" "/LIBPATH:C:\Users\kelac. rustup\toolchains\nightly-x86_64-pc-windows-msvc\lib\rustlib\x86_64-pc-windows-msvc\lib" "C:\Users\kelac\. rustup\toolchains\nightly-x86_64-pc-windows-msvc\lib\rustlib\x86_64-pc-windows-msvc\lib\libcompiler_builtins-ea81af1caf017ce1. rlib" "BufferOverflowFastFailK.lib" "ntoskrnl.lib" "hal.lib" "wmilib.lib" "WdfLdr.lib" "WdfDriverEntry.lib" "/NXCOMPATH" "/LIBPATH:C:\Users\\kelac\. rustup\toolchains\nightly-x86_64-pc-windows-msvc\lib\rustlib\x86_64-pc-windows-msvc\lib" "/OUT:C:\Users\kelac\OneDrive\Desktop\joe\driver\target\debug\deps\driver. dll" "/OPT:REF,NOICF" "/DLL" "/IMPLIB:C:\Users\kelac\OneDrive\Desktop\joe\driver\\target\debug\deps\driver.dll. lib" "/DEBUG" "/NATVIS:C:\Users\\kelac\. rustup\\toolchains\\nightly-x86_64-pc-windows-msvc\\lib\\rustlib\etc\intrinsic. natvis" "/NATVIS:C:\Users\\kelac\. rustup\toolchains\nightly-x86_64-pc-windows-msvc\lib\rustlib\\etc\liballoc.natvis" "/NATVIS:C:\Users\kelac. rustup\\toolchains\nightly-x86_64-pc-windows-msvc\\lib\\rustlib\\etc\libcore.natvis" "/NATVIS:C:\Users\\kelac.rustup\toolchains\nightly-x86_64-pc-windows-msvc\\lib\rustlib\etc\libstd.natvis"
= Note: This creates the library C:\Users\kelac\OneDrive\Desktop\joe\driver\target\debug\deps\driver.dll.lib and the object C:\Users\kelac\OneDrive\Desktop\joe\driver\target\debug\deps\driver.dll.exp.
LINK : error LNK2001: Unrecognized external symbol _DllMainCRTStartup
C:\Users\kelac\OneDrive\Desktop\joe\driver\target\debug\deps\driver.dll : fatal error LNK1120: Number of unrecognized external types: 1

RUST_TAG in wdk-alloc

lazy_static! {
static ref RUST_TAG: ULONG = u32::from_ne_bytes(
#[allow(clippy::string_lit_as_bytes)] // A u8 slice is required here
"rust"
.as_bytes()
.try_into()
.expect("tag string.as_bytes() should be able to convert into [u8; 4]"),
);
}

Is there a reason this uses lazy_static instead of just a const and a byte string literal (of type &[u8;4])? u32::from_ne_bytes is const stable since 1.44.

C.f. https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=2be24215859c818308542b6893f36ca2

Any plan impl to AVstream API?

Hi, thanks for this repo, it provide great help, I setup a kmdf driver from the example

But I need to know the status of the repo, is it fully function for WDM ? May I expect any plan about some upper level wrapping such as AVstream?

How to avoid unsafe keyword?

Main reason to use Rust instead C is its memory safety features. However it is only true if code when unsafe keyword is not used in code.

Now example drivers in here and microsoft/Windows-rust-driver-samples uses unsafe keyword multiple times.

As far I understand best way to solve it would be that Microsoft creates crates around of all Windows APIs and those handles all unsafe logic and memory handling requirement by it.

Is that something we can expect to see?

Of course if Windows kernel is someday rewritten with Rust it would remove need for this but it will take years and don't help situation with any existing Windows installations.

Unable to make fresh project

I am attempting to work off git main with a fresh project. I have followed the steps outlined in the readme and I am receiving an error:

  |                                                                                                                                                                                                                          
7 | wdk_build::cargo_make::load_rust_driver_makefile()?                                                                                                                                                                      
  |                                                 ^ expected one of `!` or `::`      

I have since updated my Cargo.toml:

[dependencies]
wdk = { git = "https://github.com/microsoft/windows-drivers-rs", branch = "main" }
wdk-alloc = { git = "https://github.com/microsoft/windows-drivers-rs", branch = "main" }
wdk-panic = { git = "https://github.com/microsoft/windows-drivers-rs", branch = "main" }
wdk-sys = { git = "https://github.com/microsoft/windows-drivers-rs", branch = "main" }

[build-dependencies]
wdk-build = { git = "https://github.com/microsoft/windows-drivers-rs", branch = "main" }

And Makefile.toml:

extend = "target/rust-driver-makefile.toml"

[env]
CARGO_MAKE_EXTEND_WORKSPACE_MAKEFILE = true

[config]
load_script = '''
#!@rust
//! ```cargo
//! [dependencies]
//! wdk-build = { git = "https://github.com/microsoft/windows-drivers-rs", branch = "main" } # "0.1.0" gives same output
//! ```
#![allow(unused_doc_comments)]

wdk_build::cargo_make::load_rust_driver_makefile()?
'''

Bindgen Clang compile error in wdk-sys - missing preprocessor defines

I had trouble compiling my own test driver, so I wanted to compile the sample-kmdf-driver crate to see if the problem is with my driver.

But I get the same error from that project (full output below):

Bindings should succeed to generate: ClangDiagnostic("E:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/ntifs.h:25:2: error: Compiler version not supported by Windows DDK...

I'm running Windows 10 LTSC, with the latest (10.0.22621) EWDK iso mounted to E:
It looks like the compiler doesn't set preprocessor defines such as _MSC_VER for some reason

C:\dev\rust-kernel\windows-drivers-rs\crates\sample-kmdf-driver>cargo make
[cargo-make] INFO - cargo make 0.37.9
[cargo-make] INFO - Calling cargo metadata to extract project info
[cargo-make] INFO - Cargo metadata done
[cargo-make] INFO - Project: sample-kmdf-driver
[cargo-make] INFO - Build File: Makefile.toml
[cargo-make] INFO - Task: default
[cargo-make] INFO - Profile: development
[cargo-make] INFO - Running Task: legacy-migration
Building and packaging driver: sample-kmdf-driver...
[cargo-make] INFO - Running Task: default
[cargo-make] INFO - Running Task: build
[cargo-make] INFO - Execute Command: "cargo" "build"
   Compiling wdk-sys v0.2.0 (C:\dev\rust-kernel\windows-drivers-rs\crates\wdk-sys)
error: failed to run custom build command for `wdk-sys v0.2.0 (C:\dev\rust-kernel\windows-drivers-rs\crates\wdk-sys)`
note: To improve backtraces for build dependencies, set the CARGO_PROFILE_DEV_BUILD_OVERRIDE_DEBUG=true environment variable to enable debug information generation.

Caused by:
  process didn't exit successfully: `C:\dev\rust-kernel\windows-drivers-rs\target\debug\build\wdk-sys-83dd066b1c411ae7\build-script-build` (exit code: 101)
  --- stdout
  cargo:rerun-if-env-changed=TARGET
  cargo:rerun-if-env-changed=BINDGEN_EXTRA_CLANG_ARGS_x86_64-pc-windows-msvc
  cargo:rerun-if-env-changed=BINDGEN_EXTRA_CLANG_ARGS_x86_64_pc_windows_msvc
  cargo:rerun-if-env-changed=BINDGEN_EXTRA_CLANG_ARGS
  cargo:rerun-if-changed=src/ntddk-input.h
  cargo:rerun-if-changed=src/wdf-input.h

  --- stderr
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/ntifs.h:25:2: error: Compiler version not supported by Windows DDK
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/ntddk.h:28:2: error: Compiler version not supported by Windows DDK
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:38:2: error: Compiler version not supported by Windows DDK
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\shared/basetsd.h:318:33: warning: cast to smaller integer type 'unsigned long' from 'const void *' [-Wvoid-pointer-to-int-cast]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\shared/basetsd.h:327:32: warning: cast to smaller integer type 'long' from 'const void *' [-Wvoid-pointer-to-int-cast]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\shared/basetsd.h:336:12: warning: cast to 'void *' from smaller integer type 'unsigned long' [-Wint-to-void-pointer-cast]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\shared/ntdef.h:1390:2: error: Must define a target architecture.
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4864:19: error: call to undeclared function 'ReadAcquire8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4875:19: error: call to undeclared function 'ReadNoFence8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4886:21: error: call to undeclared function 'ReadAcquire8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4897:21: error: call to undeclared function 'ReadNoFence8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4930:5: error: call to undeclared function 'WriteRelease8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4943:5: error: call to undeclared function 'WriteNoFence8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4956:5: error: call to undeclared function 'WriteRelease8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4969:5: error: call to undeclared function 'WriteNoFence8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:4994:20: error: call to undeclared function 'ReadAcquire16'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:5005:20: error: call to undeclared function 'ReadNoFence16'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:5028:5: error: call to undeclared function 'WriteRelease16'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:5041:5: error: call to undeclared function 'WriteNoFence16'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:5066:19: error: call to undeclared function 'ReadAcquire'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:5077:19: error: call to undeclared function 'ReadNoFence'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  E:\Program Files\Windows Kits\10\Include\10.0.22621.0\km/wdm.h:5100:5: error: call to undeclared function 'WriteRelease'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
  fatal error: too many errors emitted, stopping now [-ferror-limit=]
  clang diag: E:\Program Files\Windows Kits\10\Include\10.0.22621.0\shared/basetsd.h:318:33: warning: cast to smaller integer type 'unsigned long' from 'const void *' [-Wvoid-pointer-to-int-cast]
  clang diag: E:\Program Files\Windows Kits\10\Include\10.0.22621.0\shared/basetsd.h:327:32: warning: cast to smaller integer type 'long' from 'const void *' [-Wvoid-pointer-to-int-cast]
  clang diag: E:\Program Files\Windows Kits\10\Include\10.0.22621.0\shared/basetsd.h:336:12: warning: cast to 'void *' from smaller integer type 'unsigned long' [-Wint-to-void-pointer-cast]
  thread 'main' panicked at crates\wdk-sys\build.rs:27:14:
  Bindings should succeed to generate: ClangDiagnostic("E:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/ntifs.h:25:2: error: Compiler version not supported by Windows DDK\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/ntddk.h:28:2: error: Compiler version not supported by Windows DDK\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:38:2: error: Compiler version not supported by Windows DDK\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\shared/ntdef.h:1390:2: error: Must define a target architecture.\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4864:19: error: call to undeclared function 'ReadAcquire8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4875:19: error: call to undeclared function 'ReadNoFence8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4886:21: error: call to undeclared function 'ReadAcquire8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4897:21: error: call to undeclared function 'ReadNoFence8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4930:5: error: call to undeclared function 'WriteRelease8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4943:5: error: call to undeclared function 'WriteNoFence8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4956:5: error: call to undeclared function 'WriteRelease8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4969:5: error: call to undeclared function 'WriteNoFence8'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:4994:20: error: call to undeclared function 'ReadAcquire16'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:5005:20: error: call to undeclared function 'ReadNoFence16'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:5028:5: error: call to undeclared function 'WriteRelease16'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:5041:5: error: call to undeclared function 'WriteNoFence16'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:5066:19: error: call to undeclared function 'ReadAcquire'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:5077:19: error: call to undeclared function 'ReadNoFence'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nE:\\Program Files\\Windows Kits\\10\\Include\\10.0.22621.0\\km/wdm.h:5100:5: error: call to undeclared function 'WriteRelease'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]\nfatal error: too many errors emitted, stopping now [-ferror-limit=]\n")
  stack backtrace:
     0:     0x7ff68772b1b3 - std::sys_common::backtrace::_print::impl$0::fmt
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\sys_common\backtrace.rs:44
     1:     0x7ff68774c49d - core::fmt::rt::Argument::fmt
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\core\src\fmt\rt.rs:142
     2:     0x7ff68774c49d - core::fmt::write
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\core\src\fmt\mod.rs:1120
     3:     0x7ff6877268a1 - std::io::Write::write_fmt<std::sys::windows::stdio::Stderr>
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\io\mod.rs:1762
     4:     0x7ff68772afba - std::sys_common::backtrace::_print
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\sys_common\backtrace.rs:47
     5:     0x7ff68772afba - std::sys_common::backtrace::print
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\sys_common\backtrace.rs:34
     6:     0x7ff68772d509 - std::panicking::default_hook::closure$1
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\panicking.rs:272
     7:     0x7ff68772d1cb - std::panicking::default_hook
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\panicking.rs:292
     8:     0x7ff68772d9f4 - std::panicking::rust_panic_with_hook
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\panicking.rs:779
     9:     0x7ff68772d8c5 - std::panicking::begin_panic_handler::closure$0
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\panicking.rs:657
    10:     0x7ff68772baa9 - std::sys_common::backtrace::__rust_end_short_backtrace<std::panicking::begin_panic_handler::closure_env$0,never$>
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\sys_common\backtrace.rs:170
    11:     0x7ff68772d5d4 - std::panicking::begin_panic_handler
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\panicking.rs:645
    12:     0x7ff687755147 - core::panicking::panic_fmt
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\core\src\panicking.rs:72
    13:     0x7ff687755703 - core::result::unwrap_failed
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\core\src\result.rs:1653
    14:     0x7ff6870b78b2 - core::result::Result<T,E>::expect::h0d737977ad35a758
    15:     0x7ff6870b7e1c - <tracing_core::span::Id as core::clone::Clone>::clone::h6924d960d20cc670
    16:     0x7ff6870b9651 - <tracing_core::span::Id as core::clone::Clone>::clone::h6924d960d20cc670
    17:     0x7ff6870b25a6 - core::ops::function::FnOnce::call_once::h2363bccbde1a8686
    18:     0x7ff6870b5259 - std::sys_common::backtrace::__rust_begin_short_backtrace::h01d5257eb604a13c
    19:     0x7ff6870b330c - std::rt::lang_start::{{closure}}::h0741405682e202fc
    20:     0x7ff6877216a8 - std::rt::lang_start_internal::closure$2
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\rt.rs:148
    21:     0x7ff6877216a8 - std::panicking::try::do_call
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\panicking.rs:552
    22:     0x7ff6877216a8 - std::panicking::try
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\panicking.rs:516
    23:     0x7ff6877216a8 - std::panic::catch_unwind
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\panic.rs:142
    24:     0x7ff6877216a8 - std::rt::lang_start_internal
                                 at /rustc/82e1608dfa6e0b5569232559e3d385fea5a93112/library\std\src\rt.rs:148
    25:     0x7ff6870b32e7 - std::rt::lang_start::hdc2616c860b3953a
    26:     0x7ff6870ba069 - main
    27:     0x7ff687752a60 - invoke_main
                                 at d:\a01\_work\43\s\src\vctools\crt\vcstartup\src\startup\exe_common.inl:78
    28:     0x7ff687752a60 - __scrt_common_main_seh
                                 at d:\a01\_work\43\s\src\vctools\crt\vcstartup\src\startup\exe_common.inl:288
    29:     0x7ffde0ab7344 - BaseThreadInitThunk
    30:     0x7ffde28226b1 - RtlUserThreadStart
[cargo-make] ERROR - Error while executing command, exit code: 101
[cargo-make] WARN - Build Failed.

Support WDK Configuration in crates.io-distributed crate

Currently, the crate that's distributed via crates.io has several things hardcoded in the configuration. Some examples of this include the WdfFunctions_01033 functional table reference, and the WdfMinimumVersionDesired symbol. The wdk-build::Config used in wdk-sys also defaults to KMDF 1.33.

While the repo supports different WDF versions, different driver models (WDM, KMDF, UMDF), etc, it is currently cumbersome to use anything that is not KMDF v1.33. Our goal should be to expose allow the user to be able to use the crate off crates.io and be able to configure all of the common configuration options of the WDK.

A possible way to do this would be to have mutually-exclusive cargo-features for wdk-sys and wdk that configure what bindings are created by the crate.
There are some caveats for using mutually exclusive features, but it might be the best way forward that's currently available. There is extensive discussion about better ways to accomplish this in the future here and here, but we must make do with what is available right now.

Another possible approach is to use environment variables to control the various features. Env variables can only have one value at any given time, so they are already mutually exclusive. They could be set via normal environment variable in shell, via env section in a config.toml, or in any of the numerous ways cargo-make provides. This does harm discoverability of options, and there are some issues with some ways to configure env variables in Cargo right now (ex. rust-lang/cargo#10358. This one in particular seems like it will not be resolved for a while).

Some other thoughts:

  • How will this support multiple drivers in the same workspace?
    • If we go the path of mutually-exclusive features, workspace dependency resolution would make it so that each cargo workspace can only contain one combination of mutually-exclusive features. Its possible to get multiple drivers in the same file tree to have different combinations of mutually-exclusive features, by having multiple subfolders that are each a cargo workspace and orchestrating the entire build via cargo-make
    • The environment variable approach would have the same caveats as features.
  • Cargo currently has a 300 feature limit due to an incident where the icondata crate (v0.1.0 and earlier) used a build crate to generate over 23000 mutually exclusive features. I don't think we will get anywhere near 300 features though.

failed to load source for dependency `wdk-build`

ERROR - Error while running plugin: Source: Unknown Line: 38 - [tasks.wdk-build-init]'s script failed with exit code: 1

Caused by:
failed to load source for dependency wdk-build

I got same error in the closed issues.however, there is not information about how to fix this error

error[E0554]: `#![feature]` may not be used on the stable release channel when invoking `cargo make` in repo root

error[E0554]: `#![feature]` may not be used on the stable release channel
 --> crates\wdk-macros\src\lib.rs:6:42
  |
6 | #![cfg_attr(feature = "nightly", feature(hint_must_use))]
  |                                          ^^^^^^^^^^^^^

For more information about this error, try `rustc --explain E0554`.
error: could not compile `wdk-macros` (lib) due to previous error
warning: build failed, waiting for other jobs to finish...
[cargo-make][1] ERROR - Error while executing command, exit code: 101
[cargo-make][1] WARN - Build Failed.
[cargo-make] ERROR - Error while running duckscript: Source: Unknown Line: 8 - Error while executing command, exit code: 1
[cargo-make] WARN - Build Failed.

error

**********************************************************************
** Visual Studio 2022 Developer Command Prompt v17.7.4
** Copyright (c) 2022 Microsoft Corporation
**********************************************************************
[vcvarsall.bat] Environment initialized for: 'x64'

C:\Program Files\Microsoft Visual Studio\2022\Enterprise>cd /d D:\code\rust\code\windows\windows-drivers-rs

D:\code\rust\code\windows\windows-drivers-rs>cargo build
   Compiling wdk-sys v0.1.0 (D:\code\rust\code\windows\windows-drivers-rs\crates\wdk-sys)
error: failed to run custom build command for `wdk-sys v0.1.0 (D:\code\rust\code\windows\windows-drivers-rs\crates\wdk-sys)`

Caused by:
  process didn't exit successfully: `D:\code\rust\code\windows\windows-drivers-rs\target\debug\build\wdk-sys-bd0a85a523038361\build-script-build` (exit code: 101)
  --- stderr
  thread 'main' panicked at 'WDKContentRoot should be able to be detected. Ensure that the WDK is installed, or that the environment setup scripts in the eWDK have been run.', crates\wdk-build\src\lib.rs:111:64
  note: run with `RUST_BACKTRACE=1` environment variable to display a backtrace

D:\code\rust\code\windows\windows-drivers-rs>

staticlib

When I use this warehouse to create a static library, the compilation is successful. However, when I connect this static library to a driver (written in c/cpp/rust), a connection error occurs.

1>Ntstrsafe.lib(stubs.obj) : error LNK2005: _fltused 已经在 lib_drv_rs.lib(lib_drv_rs-7edd6e2e9cf34bd7.wdk_alloc-2f7aa50fc157ee7f.wdk_alloc.c21c9f9d55100c01-cgu.0.rcgu.o.rcgu.o) 中定义
1>lib_drv_rs.lib(lib_drv_rs-7edd6e2e9cf34bd7.wdk_alloc-2f7aa50fc157ee7f.wdk_alloc.c21c9f9d55100c01-cgu.0.rcgu.o.rcgu.o) : error LNK2019: 无法解析的外部符号 WdfFunctions_01033,函数 _ZN4core3ops8function6FnOnce9call_once17hae8e3e88db06564dE 中引用了该符号
D:\git\gitlab\code\test\rust\src\wdm_rs>cargo build
   Compiling wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs)
   Compiling wdk-sys v0.2.0
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
error: language item required, but not found: `eh_personality`
  |
  = note: this can occur when a binary crate with `#![no_std]` is compiled for a target where `eh_personality` is defined in the standard library
  = help: you may be able to compile for a target that doesn't need `eh_personality`, specify a target with `--target` or in `.cargo/config`

The following warnings were emitted during compilation:

warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.
warning: [email protected]: cargo:rustc-cdylib-link-arg was specified in the build script of wdm_lib_rs v0.1.0 (D:\git\gitlab\code\test\rust\src\wdm_lib_rs), but that package does not contain a cdylib target

Allowing this was an unintended change in the 1.50 release, and may become an error in the future. For more information, see <https://github.com/rust-lang/cargo/issues/9562>.

error: could not compile `wdm_lib_rs` (lib) due to 1 previous error
warning: build failed, waiting for other jobs to finish...

D:\git\gitlab\code\test\rust\src\wdm_rs>

failed to get `wdk-build` as a dependency of package

I created a demo, but when running cargo make, I encountered an error.
Below is the error message:

C:\Users\Administrator\Desktop\rust_driver>cargo make
[cargo-make] INFO - cargo make 0.37.8

C:\Users\Administrator\Desktop\rust_driver>cd "C:\Users\Administrator\Desktop\rust_driver"

C:\Users\Administrator\Desktop\rust_driver>pwsh.exe -Command "if ($env:CARGO_MAKE_CRATE_IS_WORKSPACE) { return };$cargoMakeURI = 'https://raw.githubusercontent.com/microsoft/windows-drivers-rs/main/rust-driver-makefile.toml';New-Item -ItemType Directory .cargo-make-loadscripts -Force;Invoke-RestMethod -Method GET -Uri $CargoMakeURI -OutFile $env:CARGO_MAKE_WORKSPACE_WORKING_DIRECTORY/.cargo-make-loadscripts/rust-driver-makefile.toml"

    Directory: C:\Users\Administrator\Desktop\rust_driver

Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
d----            2024/2/1     5:57                .cargo-make-loadscripts

[cargo-make] INFO - Calling cargo metadata to extract project info
[cargo-make] INFO - Cargo metadata done
[cargo-make] INFO - Project: rust_driver
[cargo-make] INFO - Build File: Makefile.toml
[cargo-make] INFO - Task: default
[cargo-make] INFO - Profile: development
[cargo-make] INFO - Running Task: legacy-migration
[cargo-make] ERROR - Error while running plugin: Source: Unknown Line: 37 - [tasks.wdk-build-init]'s script failed with exit code: 1
stdout:

stderr:
error: failed to get `wdk-build` as a dependency of package `main_f41fa1c176f19b8ce8394bac v0.1.0 (C:\Users\Administrator\AppData\Local\rust-script\projects\f41fa1c176f19b8ce8394bac)`

Caused by:
  failed to load source for dependency `wdk-build`

Caused by:
  Unable to update C:\Users\Administrator\Desktop\rust_driver\.cargo-make-loadscripts\crates\wdk-build

Caused by:
  failed to read `C:\Users\Administrator\Desktop\rust_driver\.cargo-make-loadscripts\crates\wdk-build\Cargo.toml`

Caused by:
  系统找不到指定的路径。 (os error 3)
error: Could not execute cargo

The temporary rust-script file is located at C:\Users\Administrator\Desktop\rust_driver\target/cargo-make-script/wdk-build-init/main.rs
[cargo-make] WARN - Build Failed.

I checked, and the wdk-build-0.1.0 dependency was successfully downloaded.
I also tried downloading a sample project and encountered the same error.

Driver installation crashes when using `EvtIoInternalDeviceControl`

I'm trying to use the repo to write a keyboard driver - https://github.com/lurebat/interustception

My problem is as such:

When using WDF_IO_QUEUE_CONFIG, everything is fine as long as I use EvtIoDeviceControl.

But as soon as I try to set EvtIoInternalDeviceControl, installing hangs forever. The setup file in C:\windows\inf writes binary gibberish.

The callback function has the correct signature, and marked with

        #[no_mangle]
        #[link_section = "PAGE"]
        pub unsafe extern "C"

I can gurantee the object is initialized correctly (as I have debug prints).
The device_create functions returns with a successful code, it hangs later on when trying to start the device.

I even tried marking all of my user-made functions with link_section=PAGE, and I suspect it might be something in this area, or something deallocates before it needs to - but I can't figure it out.

The callback isn't even called as far as I can tell - breakpoints don't set, prints don't print, etc.

I haven't found anything online on a similar problem, and at this point I'm desperate - so maybe it's the framework or rust.

Even ideas to how to debug it would be great help.

Thanks!

Windows 10 `wdk-sys` Driver Compilation and Loading Error

Hello friend,

I've noticed that a lot of people, especially in various Discord communities, are discussing an issue with the Windows 10 driver not working correctly for wdk-sys. Here's a step-by-step outline of the problem:

Steps to Reproduce:

  1. Start with a Windows 10 environment.
  2. Attempt to compile the Hello World Driver.
  3. Load the driver using the following commands:
    sc.exe create test type= kernel binPath= C:\Windows\System32\drivers\test.sys
    sc.exe query test
    sc.exe start test
    

Observed Issue:
On executing the above steps, the following error messages are observed:

[SC] CreateService FAILED 1073:

The specified service already exists.


SERVICE_NAME: test
        TYPE               : 1  KERNEL_DRIVER 
        STATE              : 1  STOPPED 
        WIN32_EXIT_CODE    : 87  (0x57)
        SERVICE_EXIT_CODE  : 0  (0x0)
        CHECKPOINT         : 0x0
        WAIT_HINT          : 0x0
[SC] StartService FAILED 87:

The parameter is incorrect.

Additional Notes:

  • When the same steps are executed on Windows 11, there are no such issues, and the driver works as expected.

I'd appreciate any insights or solutions to resolve this issue on Windows 10.

Thank you!

error

   Compiling sample-kmdf-driver v0.1.0 (D:\code\rust\code\windows\windows-drivers-rs\crates\sample-kmdf-driver)
error: failed to run custom build command for `wdk-sys v0.1.0 (D:\code\rust\code\windows\windows-drivers-rs\crates\wdk-sys)`

Caused by:
  process didn't exit successfully: `D:\code\rust\code\windows\windows-drivers-rs\target\debug\build\wdk-sys-f908dc45cde94a15\build-script-build` (exit code: 1)
  --- stderr
  Error: cannot find directory: C:\Program Files (x86)\Windows Kits\10\Include\wdf/kmdf/1.33
warning: build failed, waiting for other jobs to finish...

D:\code\rust\code\windows\windows-drivers-rs>cargo make
[cargo-make] INFO - cargo make 0.37.9
[cargo-make] INFO - Calling cargo metadata to extract project info
[cargo-make] INFO - Cargo metadata done
[cargo-make] INFO - Build File: Makefile.toml
[cargo-make] INFO - Task: default
[cargo-make] INFO - Profile: development
[cargo-make] INFO - Running Task: legacy-migration
[cargo-make] ERROR - Error while running plugin: Source: Unknown Line: 37 - [tasks.wdk-build-init]'s script failed with exit code: 1
stdout:
FORWARDING ARGS TO CARGO-MAKE:
CARGO_MAKE_CARGO_PROFILE=dev
WDK_BUILD_OUTPUT_DIRECTORY=D:\code\rust\code\windows\windows-drivers-rs\target/debug

stderr:
Error: IoError(Os { code: 2, kind: NotFound, message: "系统找不到指定的文件。" })

The temporary rust-script file is located at D:\code\rust\code\windows\windows-drivers-rs\target/cargo-make-script/wdk-build-init/main.rs
[cargo-make] WARN - Build Failed.

D:\code\rust\code\windows\windows-drivers-rs>

Usability improvements

  1. Define the CTL_CODE macro and the IoGetCurrentIrpStackLocation function.

  2. Move constants and macros (such as FILE_DEVICE_UNKNOWN, METHOD_BUFFERED, and others) from this crate and windows-rs to a shared crate.
    Motivation: This enables the definition of IOCTL codes in a shared crate that can be linked to both the driver and application sides.

  3. Change the types of some constants, like IRP_MJ_* to usize, and IO_NO_INCREMENT to CCHAR. It would also be beneficial to define TRUE and FALSE as pub const TRUE: BOOLEAN = 1; and pub const FALSE: BOOLEAN = 0; respectively, or even better, eliminate all BOOLEAN types from the API and replace them with the plain Rust bool, although I understand that this might be nearly impossible.
    Motivation: To eliminate unnecessary type casting where it logically should not exist.

  4. Do something with __bindgen_anon_*.
    Motivation: The statement (*irp).IoStatus.__bindgen_anon_1.Status = status; looks very awkward, and it's also challenging to locate the needed field in more complex cases like (*irp).Tail.Overlay.__bindgen_anon_2.__bindgen_anon_1.CurrentStackLocation.

  5. In general, it would be beneficial if constants in constants.rs had types from types.rs.

Macro for driver registration

Would it be possible to add a macro that handles allocator setup, panic handler, and DriverEntry? These are sort of boilerplate things that everyone has to do, so I wonder if this could be simplified for the common use case.

The way the RFL project does this is by having a trait Module that can be implemented for any struct, and then registered with module! which sets up the statics. Maybe something like this could work? Example: https://github.com/torvalds/linux/blob/6bc986ab839c844e78a2333a02e55f02c9e57935/samples/rust/rust_print.rs#L8

Panic Strategy

"Panic" in the Windows Kernel (or "bugchecking" the system KeBugCheckEx) is a last resort and should be reserved only for cases where the kernel is in a corrupted and unrecoverable state. It is usually never acceptable to bugcheck the system. I find it unlikely that any Rust crate would ever need to bugcheck the kernel.

Today this library notes a "TODO" on this topic:

#[panic_handler]
const fn panic(_info: &PanicInfo) -> ! {
loop {}
// FIXME: Should this trigger Bugcheck via KeBugCheckEx?
}

Ultimately the kernel should handle errors cleanly and, by all means necessary, prevent itself from getting into a corrupted or unrecoverable state. I worry that the introduction of a panic handler and the interactions between other crates written for the Windows Kernel could degrade the overall reliability of the kernel.

I'm not certain the best way to approach this problem. My initial reaction is disallow panic handlers when developing against the Windows Kernel and reserve "panics" (bugchecks) for the rare and extreme cases. To achieve this the crates used in the kernel would need to always communicate errors rather than giving up with a panic. Thankfully, Rust has robust and capable error handling patterns with things like match and Result. I'd like to raise this as an open topic to the community to discuss strategies for panic handling for the Windows Kernel.

Need install wdk?

Error: failed to run custom build command for wdk-sys v0.2.0

Caused by:
process didn't exit successfully: D:\Myself\RustProjects\wdk-rs\target\debug\build\wdk-sys-d4ff924bcbc978d5\build-script-build (exit code: 1)
--- stderr
Error: 系统找不到指定的路径。 (os error 3)

Generic Fail-able, Pool and Tag Aware Allocators

Development in the Windows Kernel requires allocations from different pools and the capability to tag allocations is an invaluable tool for debugging/triage.

Today this repository looks to recommend a global allocator and one that allocates exclusively from non-paged pool with a hard-coded pool tag.

unsafe impl GlobalAlloc for WDKAllocator {
unsafe fn alloc(&self, layout: Layout) -> *mut u8 {
let ptr = ExAllocatePool2(POOL_FLAG_NON_PAGED, layout.size() as SIZE_T, *RUST_TAG);
assert!(!ptr.is_null(), "wdk-alloc failed to allocate memory.");
ptr.cast()
}
unsafe fn dealloc(&self, ptr: *mut u8, _layout: Layout) {
ExFreePool(ptr.cast());
}
}

Rust crates for the Windows Kernel probably shouldn't provide a global kernel allocator. Else everyone using these crates may subtly end up allocating memory using identical tags. This will make debugging and triage a nightmare in the long term. Additionally I'll note, the non-paged pools are far more limited resource that the paged pools. I recognize that the safer option when implementing a global allocator is to force it into non-paged memory, since not doing so has the potential to introduce other issues. However resource exhaustion is far more likely when forcing all allocations into non-paged pools.

For Rust to be a first-class citizen in the Windows Kernel. The language must support generic fail-able allocators. And the crates for the Windows Kernel should expose and support appropriate allocators that are capable of specifying pool types and tags.

Proposal for Improving the Binding Generation Process for Windows Headers with bindgen

Hello,

I would like to submit this proposal for enhancing the Rust binding generation process for Windows headers. Currently, the process involves using bindgen multiple times to create separate Rust modules from different header files. This method leads to significant code duplication, as many headers share common functions and structures.

Proposal:
My proposal is to optimize this process by using bindgen once with a complete list of Windows headers, and then segmenting the generated binding file into multiple Rust sub-modules. This approach aims to reduce code duplication and improve the overall efficiency of the process.

To facilitate this segmentation, I suggest developing a function that analyzes the generated binding file, constructs a hashmap linking each element (function, variable, etc.) to its original header, and uses this information to appropriately divide the file into sub-modules. Additionally, this function could identify elements that bindgen was unable to convert, thus maintaining a tracking file for developers, indicating areas that require manual attention or implementation.

Personal Context:
I would like to note that I am a beginner in Rust and system programming. Therefore, it's possible that my proposal might not fully align with the best practices or current standards of the project. If that's the case, I apologize in advance for any inconvenience caused and would be grateful for any advice or suggestions to improve my proposal.

Thank you for your consideration and time.

Best regards

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.