feat: wdk_build::DerivesMap for derives collection of bindgen output#652
feat: wdk_build::DerivesMap for derives collection of bindgen output#652leon-xd wants to merge 5 commits intomicrosoft:mainfrom
wdk_build::DerivesMap for derives collection of bindgen output#652Conversation
There was a problem hiding this comment.
Pull request overview
Adds an internal wdk_build::derives module that can parse bindgen-generated Rust (types.rs-style) and reconstruct which auto-derives apply to each emitted type, enabling future multi-pass bindgen runs (e.g., mutually exclusive headers) to preserve derive parity via blocklisted_type_implements_trait.
Changes:
- Introduces
crates/wdk-build/src/derives.rswithDerivesMap, alias resolution, and aParseCallbacksimplementation (BaseDerivesCallback). - Updates the default bindgen builder configuration to force
size_t/ssize_tto map tousize/isize. - Bumps workspace
bindgenand adds workspacebitflags, plussynparsing support inwdk-build.
Reviewed changes
Copilot reviewed 5 out of 6 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
| Cargo.toml | Bumps bindgen and adds workspace bitflags dependency. |
| Cargo.lock | Lockfile updates for new/updated dependencies. |
| crates/wdk-build/Cargo.toml | Adds bitflags and syn(parsing) dependencies for derive parsing. |
| crates/wdk-build/src/lib.rs | Exposes internal derives module (doc-hidden). |
| crates/wdk-build/src/bindgen.rs | Sets size_t_is_usize(true) to match Windows driver targets and derive-map assumptions. |
| crates/wdk-build/src/derives.rs | New derive parsing + alias-resolution logic + unit tests. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 5 out of 6 changed files in this pull request and generated 3 comments.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Codecov Report❌ Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## main #652 +/- ##
==========================================
+ Coverage 78.44% 79.69% +1.24%
==========================================
Files 25 26 +1
Lines 5201 5668 +467
Branches 5201 5668 +467
==========================================
+ Hits 4080 4517 +437
- Misses 1001 1016 +15
- Partials 120 135 +15 ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 6 out of 7 changed files in this pull request and generated 2 comments.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
|
@leon-xd can parsing base types have any measurable impact on build time? |
@gurry in the pr description of Leon's other pr which uses this new feature, he says:
So while technically its not attributable to only this change, as a whole the change reduces build time. I think a theory was that bindgen's parsing of header seems to scale non-linearly |
This PR introduces
wdk_build::DerivesMap, a struct to collect the info of all#[derive()]attributes for each type emitted bybindgen. See #654 for the related PR.Purpose
These changes are a pre-requisite to solve the current issues with generating bindings for mutually exclusive WDK headers (tracked by #514 , #515 , and #516 ). The solution requires types and constants for subsystems to be generated in independent
bindgenruns, and will be published in a follow-up PR. In order to prevent duplicate type generation,bindgeninvocation for subsystem types will utilize ablocklist_filefor every file traversed in the initial base types run.bindgenby default assumes very minimal derives when encountering a blocklisted type, so this implementation on its own would leave most subsystem types with a sparse set of automaticderives. This is a regression that is unacceptable. In order to prevent this while still keeping our mutual exclusive headers solution, we need to gather the derive information for all of the generated base types, and pass it off to subsystembindgentype generators via the callbackblocklisted_type_implements_trait.This PR introduces the mechanism to be able to parse a
bindgengenerated file usingsynand extract the derive information for each individual type. In practice, the future bindings generation pipeline will generate the types for thebaselayer of the WDK, parse it viaDerivesMap::from_file, and then insert the createdDerivesMapinto each subsystem typebindgenviaBaseDerivesCallback.Changes
Cargo.tomlbindgenfrom0.71.0to0.72.1bitflags = "2.6.0"workspace dependencycrates/wdk-build/Cargo.tomlbitflagsdependencysyndependency with theparsingfeature enabledcrates/wdk-build/src/lib.rspub mod derives(gated with#[doc(hidden)]since the module is intended for internalwdk-sysbuild-script use, not public API)crates/wdk-build/src/bindgen.rssize_t_is_usize(true)onwdk_default.size_t/ssize_tare pointer-width on every supported Windows driver target (x64, ARM64, x86), matching Rust'susize/isize. This is the invariant thatderives.rsrelies on when seeding stdint integer types into its derive map.crates/wdk-build/src/derives.rsDerivesError: typed error enum for derive-map construction failures.DerivesSet: abitflags!set over the five derive traits bindgen tracks (Copy,Clone,Debug,Default,PartialEq).DerivesSource: enum distinguishing whether a type's derives are immediately known (from a#[derive()]attribute or from a base type) or come from an aliased type.BaseDerivesCallback: abindgen::callbacks::ParseCallbacksimplementation that answersblocklisted_type_implements_traitfrom a populatedDerivesMap. Plugs into bindgen's chain so types blocklisted in one bindings module can still be referenced from another. Used in follow up PR.DerivesMap: a map from type name toDerivesSet. Builds incrementally from Rust source files viasyn, and resolves alias chains.synhelpers:idents_and_derives_for_items: walk a slice ofItems, collect(name, DerivesSource)pairs.idents_and_derives_for_mod: recurse into amodand forward toidents_and_derives_for_items.ident_and_derives_for_use: resolve ause a::b as Foo;re-export to(Foo, DerivesSource::Alias(...)).derives_for_type: given aType, classify into aDerivesSource(named alias, function pointer, primitive, etc.).derives_from_attrs: extract the derive-trait names from a#[derive(...)]attribute list.inner_is_bare_fn,path_is_option,path_is_core_ffi_type#[derive(...)]attributes, and stdint seeding.Validation
Tested this with the full implementation of the mutually exclusive header resolution and ensured that all outputted bindings had full
#[derive]parity against bindings generated frommicrosoft/main.