Suballocate DX12 buffer creation (#3163)

closes https://github.com/gfx-rs/wgpu/issues/2720
This commit is contained in:
Elabajaba 2022-12-20 12:23:44 -05:00 committed by GitHub
parent 62e932b0a8
commit f3c50918c2
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 678 additions and 192 deletions

View File

@ -103,6 +103,10 @@ Additionally `Surface::get_default_config` now returns an Option and returns Non
`Instance::create_surface()` now returns `Result<Surface, CreateSurfaceError>` instead of `Surface`. This allows an error to be returned instead of panicking if the given window is a HTML canvas and obtaining a WebGPU or WebGL 2 context fails. (No other platforms currently report any errors through this path.) By @kpreid in [#3052](https://github.com/gfx-rs/wgpu/pull/3052/)
#### Suballocate DX12 buffers and textures
`wgpu`'s DX12 backend can now suballocate buffers and textures when the `windows_rs` feature is enabled, which can give a significant increase in performance (in testing I've seen a 10000%+ improvement in a simple scene with 200 `write_buffer` calls per frame, and a 40%+ improvement in [Bistro using Bevy](https://github.com/vleue/bevy_bistro_playground)). Previously `wgpu-hal`'s DX12 backend created a new heap on the GPU every time you called write_buffer (by calling `CreateCommittedResource`), whereas now with the `windows_rs` feature enabled it uses [`gpu_allocator`](https://crates.io/crates/gpu-allocator) to manage GPU memory (and calls `CreatePlacedResource` with a suballocated heap). By @Elabajaba in [#3163](https://github.com/gfx-rs/wgpu/pull/3163)
### Changes
#### General

393
Cargo.lock generated
View File

@ -2,6 +2,15 @@
# It is not intended for manual editing.
version = 3
[[package]]
name = "addr2line"
version = "0.17.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b9ecd88a8c8378ca913a680cd98f0f13ac67383d35993f86c90a70e3f137816b"
dependencies = [
"gimli",
]
[[package]]
name = "adler"
version = "1.0.2"
@ -14,16 +23,16 @@ version = "0.7.6"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fcb51a0695d8f838b1ee009b3fbf66bda078cd64590202a864a8f3e8c4315c47"
dependencies = [
"getrandom 0.2.7",
"getrandom 0.2.8",
"once_cell",
"version_check",
]
[[package]]
name = "aho-corasick"
version = "0.7.19"
version = "0.7.20"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b4f55bd91a0978cbfd91c457a164bab8b4001c833b7f323132c0a4e1922dd44e"
checksum = "cc936419f96fa211c1b9166887b38e5e40b19958e5b895be7c1f93adec7071ac"
dependencies = [
"memchr",
]
@ -39,9 +48,9 @@ dependencies = [
[[package]]
name = "anyhow"
version = "1.0.65"
version = "1.0.66"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "98161a4e3e2184da77bb14f02184cdd111e83bbbcc9979dfee3c44b9a85f5602"
checksum = "216261ddc8289130e551ddcd5ce8a064710c0d064a4d2895c67151c92b5443f6"
[[package]]
name = "arrayref"
@ -75,18 +84,28 @@ dependencies = [
[[package]]
name = "async-executor"
version = "1.4.1"
version = "1.5.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "871f9bb5e0a22eeb7e8cf16641feb87c9dc67032ccf8ff49e772eb9941d3a965"
checksum = "17adb73da160dfb475c183343c8cccd80721ea5a605d3eb57125f0a7b7a92d0b"
dependencies = [
"async-lock",
"async-task",
"concurrent-queue",
"fastrand",
"futures-lite",
"once_cell",
"slab",
]
[[package]]
name = "async-lock"
version = "2.6.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c8101efe8695a6c17e02911402145357e718ac92d3ff88ae8419e84b1707b685"
dependencies = [
"event-listener",
"futures-lite",
]
[[package]]
name = "async-task"
version = "4.3.0"
@ -95,9 +114,9 @@ checksum = "7a40729d2133846d9ed0ea60a8b9541bccddab49cd30f0715a1da672fe9a2524"
[[package]]
name = "async-trait"
version = "0.1.57"
version = "0.1.59"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "76464446b8bc32758d7e88ee1a804d9914cd9b1cb264c029899680b0be29826f"
checksum = "31e6e93155431f3931513b243d371981bb2770112b370c82745a1d19d2f99364"
dependencies = [
"proc-macro2",
"quote",
@ -121,6 +140,21 @@ version = "1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
[[package]]
name = "backtrace"
version = "0.3.66"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "cab84319d616cfb654d03394f38ab7e6f0919e181b1b57e1fd15e7fb4077d9a7"
dependencies = [
"addr2line",
"cc",
"cfg-if",
"libc",
"miniz_oxide 0.5.4",
"object",
"rustc-demangle",
]
[[package]]
name = "base64"
version = "0.9.3"
@ -133,9 +167,9 @@ dependencies = [
[[package]]
name = "base64"
version = "0.13.0"
version = "0.13.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "904dfeac50f3cdaba28fc6f57fdcddb75f49ed61346676a78c4ffe55877802fd"
checksum = "9e1b586273c5702936fe7b7d6896644d8be71e6314cfe09d3167c95f712589e8"
[[package]]
name = "base64-simd"
@ -175,24 +209,24 @@ checksum = "0d8c1fef690941d3e7788d328517591fecc684c084084702d6ff1641e993699a"
[[package]]
name = "bumpalo"
version = "3.11.0"
version = "3.11.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c1ad822118d20d2c234f427000d5acc36eabe1e29a348c89b63dd60b13f28e5d"
checksum = "572f695136211188308f16ad2ca5c851a712c464060ae6974944458eb83880ba"
[[package]]
name = "bytemuck"
version = "1.12.1"
version = "1.12.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2f5715e491b5a1598fc2bef5a606847b5dc1d48ea625bd3c02c00de8285591da"
checksum = "aaa3a8d9a1ca92e282c96a32d6511b695d7d994d1d102ba85d279f9b2756947f"
dependencies = [
"bytemuck_derive",
]
[[package]]
name = "bytemuck_derive"
version = "1.2.1"
version = "1.3.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1b9e1f5fa78f69496407a27ae9ed989e3c3b072310286f5ef385525e4cbc24a9"
checksum = "5fe233b960f12f8007e3db2d136e3cb1c291bfd7396e384ee76025fc1a3932b4"
dependencies = [
"proc-macro2",
"quote",
@ -211,17 +245,11 @@ version = "1.2.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ec8a7b6a70fde80372154c65702f00a0f56f3e1c36abbc6c440484be248856db"
[[package]]
name = "cache-padded"
version = "1.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c1db59621ec70f09c5e9b597b220c7a2b43611f4710dc03ceb8748637775692c"
[[package]]
name = "calloop"
version = "0.10.1"
version = "0.10.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a22a6a8f622f797120d452c630b0ab12e1331a1a753e2039ce7868d4ac77b4ee"
checksum = "595eb0438b3c6d262395fe30e6de9a61beb57ea56290b00a07f227fe6e20cbf2"
dependencies = [
"log",
"nix",
@ -243,9 +271,9 @@ dependencies = [
[[package]]
name = "cc"
version = "1.0.73"
version = "1.0.77"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2fff2a6927b3bb87f9595d67196a70493f627687a71d87a0d692242c33f58c11"
checksum = "e9f73505338f7d905b19d18738976aae232eb46b8efc15554ffc56deb5d9ebe4"
[[package]]
name = "cfg-if"
@ -264,18 +292,18 @@ dependencies = [
[[package]]
name = "cmake"
version = "0.1.48"
version = "0.1.49"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e8ad8cef104ac57b68b89df3208164d228503abbdce70f6880ffa3d970e7443a"
checksum = "db34956e100b30725f2eb215f90d4871051239535632f84fea3bc92722c66b7c"
dependencies = [
"cc",
]
[[package]]
name = "cocoa"
version = "0.24.0"
version = "0.24.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6f63902e9223530efb4e26ccd0cf55ec30d592d3b42e21a28defc42a9586e832"
checksum = "f425db7937052c684daec3bd6375c8abe2d146dca4b8b143d6db777c39138f3a"
dependencies = [
"bitflags",
"block",
@ -314,11 +342,11 @@ dependencies = [
[[package]]
name = "concurrent-queue"
version = "1.2.4"
version = "2.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "af4780a44ab5696ea9e28294517f1fffb421a83a25af521333c838635509db9c"
checksum = "bd7bef69dc86e3c610e4e7aed41035e2a7ed12e72dd7530f61327a6579a4390b"
dependencies = [
"cache-padded",
"crossbeam-utils",
]
[[package]]
@ -410,10 +438,19 @@ dependencies = [
]
[[package]]
name = "crossfont"
version = "0.5.0"
name = "crossbeam-utils"
version = "0.8.14"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f66b1c1979c4362323f03ab6bf7fb522902bfc418e0c37319ab347f9561d980f"
checksum = "4fb766fa798726286dbbb842f174001dab8abc7b627a1dd86e0b7222a95d929f"
dependencies = [
"cfg-if",
]
[[package]]
name = "crossfont"
version = "0.5.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "21fd3add36ea31aba1520aa5288714dd63be506106753226d0eb387a93bc9c45"
dependencies = [
"cocoa",
"core-foundation",
@ -693,9 +730,9 @@ dependencies = [
[[package]]
name = "env_logger"
version = "0.9.1"
version = "0.9.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c90bf5f19754d10198ccb95b70664fc925bd1fc090a0fd9a6ebc54acc8cd6272"
checksum = "a12e6657c4c97ebab115a42dcee77225f7f482cdd841cf7088c657a42e9e00e7"
dependencies = [
"atty",
"humantime",
@ -704,6 +741,12 @@ dependencies = [
"termcolor",
]
[[package]]
name = "event-listener"
version = "2.5.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0206175f82b8d6bf6652ff7d71a1e27fd2e4efde587fd368662814d6ec1d9ce0"
[[package]]
name = "expat-sys"
version = "2.1.6"
@ -736,7 +779,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f82b0f4c27ad9f8bfd1f3208d882da2b09c301bc1c828fd3a00d0216d2fbbff6"
dependencies = [
"crc32fast",
"miniz_oxide",
"miniz_oxide 0.5.4",
]
[[package]]
@ -830,9 +873,9 @@ dependencies = [
[[package]]
name = "futures"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7f21eda599937fba36daeb58a22e8f5cee2d14c4a17b5b7739c7c8e5e3b8230c"
checksum = "38390104763dc37a5145a53c29c63c1290b5d316d6086ec32c293f6736051bb0"
dependencies = [
"futures-channel",
"futures-core",
@ -845,9 +888,9 @@ dependencies = [
[[package]]
name = "futures-channel"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "30bdd20c28fadd505d0fd6712cdfcb0d4b5648baf45faef7f852afb2399bb050"
checksum = "52ba265a92256105f45b719605a571ffe2d1f0fea3807304b522c1d778f79eed"
dependencies = [
"futures-core",
"futures-sink",
@ -855,15 +898,15 @@ dependencies = [
[[package]]
name = "futures-core"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4e5aa3de05362c3fb88de6531e6296e85cde7739cccad4b9dfeeb7f6ebce56bf"
checksum = "04909a7a7e4633ae6c4a9ab280aeb86da1236243a77b694a49eacd659a4bd3ac"
[[package]]
name = "futures-executor"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9ff63c23854bee61b6e9cd331d523909f238fc7636290b96826e9cfa5faa00ab"
checksum = "7acc85df6714c176ab5edf386123fafe217be88c0840ec11f199441134a074e2"
dependencies = [
"futures-core",
"futures-task",
@ -872,9 +915,9 @@ dependencies = [
[[package]]
name = "futures-intrusive"
version = "0.4.0"
version = "0.4.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "62007592ac46aa7c2b6416f7deb9a8a8f63a01e0f1d6e1787d5630170db2b63e"
checksum = "a604f7a68fbf8103337523b1fadc8ade7361ee3f112f7c680ad179651616aed5"
dependencies = [
"futures-core",
"lock_api",
@ -883,9 +926,9 @@ dependencies = [
[[package]]
name = "futures-io"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bbf4d2a7a308fd4578637c0b17c7e1c7ba127b8f6ba00b29f717e9655d85eb68"
checksum = "00f5fb52a06bdcadeb54e8d3671f8888a39697dcb0b81b23b55174030427f4eb"
[[package]]
name = "futures-lite"
@ -904,9 +947,9 @@ dependencies = [
[[package]]
name = "futures-macro"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "42cd15d1c7456c04dbdf7e88bcd69760d74f3a798d6444e16974b505b0e62f17"
checksum = "bdfb8ce053d86b91919aad980c220b1fb8401a9394410e1c289ed7e66b61835d"
dependencies = [
"proc-macro2",
"quote",
@ -915,21 +958,21 @@ dependencies = [
[[package]]
name = "futures-sink"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "21b20ba5a92e727ba30e72834706623d94ac93a725410b6a6b6fbc1b07f7ba56"
checksum = "39c15cf1a4aa79df40f1bb462fb39676d0ad9e366c2a33b590d7c66f4f81fcf9"
[[package]]
name = "futures-task"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a6508c467c73851293f390476d4491cf4d227dbabcd4170f3bb6044959b294f1"
checksum = "2ffb393ac5d9a6eaa9d3fdf37ae2776656b706e200c8e16b1bdb227f5198e6ea"
[[package]]
name = "futures-util"
version = "0.3.24"
version = "0.3.25"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "44fb6cb1be61cc1d2e43b262516aafcf63b241cffdb1d3fa115f91d9c7b09c90"
checksum = "197676987abd2f9cadff84926f410af1c183608d36641465df73ae8211dc65d6"
dependencies = [
"futures-channel",
"futures-core",
@ -965,15 +1008,21 @@ dependencies = [
[[package]]
name = "getrandom"
version = "0.2.7"
version = "0.2.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4eb1a864a501629691edf6c15a593b7a51eebaa1e8468e9ddc623de7c9b58ec6"
checksum = "c05aeb6a22b8f62540c194aac980f2115af067bfe15a0734d7277a768d396b31"
dependencies = [
"cfg-if",
"libc",
"wasi 0.11.0+wasi-snapshot-preview1",
]
[[package]]
name = "gimli"
version = "0.26.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "22030e2c5a68ec659fde1e949a745124b48e6fa8b045b7ed5bd1fe4ccc5c4e5d"
[[package]]
name = "gl_generator"
version = "0.14.0"
@ -1086,6 +1135,19 @@ dependencies = [
"bitflags",
]
[[package]]
name = "gpu-allocator"
version = "0.21.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "434618454f74b63f9b39328298097256977c41ea0ba9d75a47238b77790b6163"
dependencies = [
"backtrace",
"log",
"thiserror",
"winapi",
"windows",
]
[[package]]
name = "gpu-descriptor"
version = "0.2.3"
@ -1175,9 +1237,9 @@ checksum = "cb56e1aa765b4b4f3aadfab769793b7087bb03a4ea4920644a6d238e2df5b9ed"
[[package]]
name = "indexmap"
version = "1.9.1"
version = "1.9.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "10a35a97730320ffe8e2d410b5d3b69279b98d2c14bdb8b70ea89ecf7888d41e"
checksum = "1885e79c1fc4b10f0e172c475f458b7f7b93061064d98c3293e98c5ba0c8b399"
dependencies = [
"autocfg",
"hashbrown",
@ -1198,9 +1260,9 @@ dependencies = [
[[package]]
name = "itoa"
version = "1.0.3"
version = "1.0.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6c8af84674fe1f223a982c933a0ee1086ac4d4052aa0fb8060c12c6ad838e754"
checksum = "4217ad341ebadf8d8e724e264f13e593e0648f5b3e94b3896a5df283be015ecc"
[[package]]
name = "jni-sys"
@ -1254,9 +1316,9 @@ checksum = "349d5a591cd28b49e1d1037471617a32ddcda5731b99419008085f72d5a53836"
[[package]]
name = "libloading"
version = "0.7.3"
version = "0.7.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "efbc0f03f9a775e9f6aed295c6a1ba2253c5757a9e03d55c6caa46a681abcddd"
checksum = "b67380fd3b2fbe7527a606e18729d21c6f3951633d0500574c4dc22d2d638b9f"
dependencies = [
"cfg-if",
"winapi",
@ -1298,9 +1360,9 @@ checksum = "2dffe52ecf27772e601905b7522cb4ef790d2cc203488bbd0e2fe85fcb74566d"
[[package]]
name = "memmap2"
version = "0.5.7"
version = "0.5.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "95af15f345b17af2efc8ead6080fb8bc376f8cec1b35277b935637595fe77498"
checksum = "4b182332558b18d807c4ce1ca8ca983b34c3ee32765e47b3f0f69b90355cc1dc"
dependencies = [
"libc",
]
@ -1344,15 +1406,24 @@ dependencies = [
]
[[package]]
name = "mio"
version = "0.8.4"
name = "miniz_oxide"
version = "0.6.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "57ee1c23c7c63b0c9250c339ffdc69255f110b298b901b9f6c82547b7b87caaf"
checksum = "b275950c28b37e794e8c55d88aeb5e139d0ce23fdbbeda68f8d7174abdf9e8fa"
dependencies = [
"adler",
]
[[package]]
name = "mio"
version = "0.8.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e5d732bc30207a6423068df043e3d02e0735b155ad7ce1a6f76fe2baa5b158de"
dependencies = [
"libc",
"log",
"wasi 0.11.0+wasi-snapshot-preview1",
"windows-sys",
"windows-sys 0.42.0",
]
[[package]]
@ -1443,9 +1514,9 @@ dependencies = [
[[package]]
name = "nix"
version = "0.24.2"
version = "0.24.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "195cdbc1741b8134346d515b3a56a1c94b0912758009cfd53f99ea0f57b065fc"
checksum = "fa52e972a9a719cecb6864fb88568781eb706bac2cd1d4f04a648542dbf78069"
dependencies = [
"bitflags",
"cfg-if",
@ -1493,9 +1564,9 @@ dependencies = [
[[package]]
name = "num_cpus"
version = "1.13.1"
version = "1.14.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "19e64526ebdee182341572e50e9ad03965aa510cd94427a4549448f285e957a1"
checksum = "f6058e64324c71e02bc2b150e4f3bc8286db6c83092132ffa3f6b1eab0f9def5"
dependencies = [
"hermit-abi",
"libc",
@ -1547,6 +1618,15 @@ dependencies = [
"cc",
]
[[package]]
name = "object"
version = "0.29.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "21158b2c33aa6d4561f1c0a6ea283ca92bc54802a93b263e910746d679a7eb53"
dependencies = [
"memchr",
]
[[package]]
name = "once_cell"
version = "1.14.0"
@ -1592,7 +1672,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f"
dependencies = [
"lock_api",
"parking_lot_core 0.9.3",
"parking_lot_core 0.9.5",
]
[[package]]
@ -1611,15 +1691,15 @@ dependencies = [
[[package]]
name = "parking_lot_core"
version = "0.9.3"
version = "0.9.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "09a279cbf25cb0757810394fbc1e359949b59e348145c643a939a525692e6929"
checksum = "7ff9f3fef3968a3ec5945535ed654cb38ff72d7495a25619e2247fb15a2ed9ba"
dependencies = [
"cfg-if",
"libc",
"redox_syscall",
"smallvec",
"windows-sys",
"windows-sys 0.42.0",
]
[[package]]
@ -1678,9 +1758,9 @@ checksum = "8b870d8c151b6f2fb93e84a13146138f05d02ed11c7e7c54f8826aaaf7c9f184"
[[package]]
name = "pkg-config"
version = "0.3.25"
version = "0.3.26"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1df8c4ec4b0627e53bdf214615ad287367e482558cf84b109250b37464dc03ae"
checksum = "6ac9a59f73473f1b8d852421e59e64809f025994837ef743615c6d0c5b305160"
[[package]]
name = "player"
@ -1709,14 +1789,14 @@ dependencies = [
[[package]]
name = "png"
version = "0.17.6"
version = "0.17.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "8f0e7f4c94ec26ff209cee506314212639d6c91b80afb82984819fafce9df01c"
checksum = "5d708eaf860a19b19ce538740d2b4bdeeb8337fa53f7738455e706623ad5c638"
dependencies = [
"bitflags",
"crc32fast",
"flate2",
"miniz_oxide",
"miniz_oxide 0.6.2",
]
[[package]]
@ -1736,9 +1816,9 @@ dependencies = [
[[package]]
name = "ppv-lite86"
version = "0.2.16"
version = "0.2.17"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "eb9f9e6e233e5c4a35559a617bf40a4ec447db2e84c20b55a6f83167b7e57872"
checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de"
[[package]]
name = "proc-macro-crate"
@ -1753,18 +1833,18 @@ dependencies = [
[[package]]
name = "proc-macro2"
version = "1.0.46"
version = "1.0.47"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "94e2ef8dbfc347b10c094890f778ee2e36ca9bb4262e86dc99cd217e35f3470b"
checksum = "5ea3d908b0e36316caf9e9e2c4625cdde190a7e6f440d794667ed17a1855e725"
dependencies = [
"unicode-ident",
]
[[package]]
name = "profiling"
version = "1.0.6"
version = "1.0.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2f61dcf0b917cd75d4521d7343d1ffff3d1583054133c9b5cbea3375c703c40d"
checksum = "74605f360ce573babfe43964cbe520294dcb081afbf8c108fc6e23036b4da2df"
[[package]]
name = "quote"
@ -1871,9 +1951,9 @@ dependencies = [
[[package]]
name = "regex-syntax"
version = "0.6.27"
version = "0.6.28"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a3f87b73ce11b1619a3c6332f45341e0047173771e8b8b73f87bfeefb7b56244"
checksum = "456c603be3e8d448b072f410900c09faf164fbce2d480456f50eea6e25f9c848"
[[package]]
name = "remove_dir_all"
@ -1896,7 +1976,7 @@ version = "0.8.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "300a51053b1cb55c80b7a9fde4120726ddf25ca241a1cbb926626f62fb136bff"
dependencies = [
"base64 0.13.0",
"base64 0.13.1",
"bitflags",
"serde",
]
@ -1961,9 +2041,9 @@ checksum = "ef703b7cb59335eae2eb93ceb664c0eb7ea6bf567079d843e09420219668e072"
[[package]]
name = "scoped-tls"
version = "1.0.0"
version = "1.0.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ea6a9290e3c9cf0f18145ef7ffa62d68ee0bf5fcd651017e586dc7fd5da448c2"
checksum = "e1cf6437eb19a8f4a6cc0f7dca544973b0b78843adbfeb3683d1a94a0024a294"
[[package]]
name = "scopeguard"
@ -1973,9 +2053,9 @@ checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd"
[[package]]
name = "sctk-adwaita"
version = "0.4.2"
version = "0.4.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "04b7c47a572f73de28bee5b5060d085b42b6ce1e4ee2b49c956ea7b25e94b6f0"
checksum = "61270629cc6b4d77ec1907db1033d5c2e1a404c412743621981a871dc9c12339"
dependencies = [
"crossfont",
"log",
@ -2178,7 +2258,7 @@ version = "6.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c46fdc1838ff49cf692226f5c2b0f5b7538f556863d0eca602984714667ac6e7"
dependencies = [
"base64 0.13.0",
"base64 0.13.1",
"if_chain",
"lazy_static",
"regex",
@ -2212,9 +2292,9 @@ checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623"
[[package]]
name = "syn"
version = "1.0.101"
version = "1.0.105"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e90cde112c4b9690b8cbe810cba9ddd8bc1d7472e2cae317b69e9438c1cba7d2"
checksum = "60b9b43d45702de4c839cb9b51d9f529c5dd26a4aff255b42b1ebc03e88ee908"
dependencies = [
"proc-macro2",
"quote",
@ -2327,9 +2407,9 @@ dependencies = [
[[package]]
name = "tokio-macros"
version = "1.8.0"
version = "1.8.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9724f9a975fb987ef7a3cd9be0350edcbe130698af5b8f7a631e23d42d052484"
checksum = "d266c00fde287f55d3f1c3e96c500c362a2b8c695076ec180f27918820bc6df8"
dependencies = [
"proc-macro2",
"quote",
@ -2394,9 +2474,9 @@ checksum = "099b7128301d285f79ddd55b9a83d5e6b9e97c92e0ea0daebee7263e932de992"
[[package]]
name = "unicode-ident"
version = "1.0.4"
version = "1.0.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dcc811dc4066ac62f84f11307873c4850cb653bfa9b1719cee2bd2204a4bc5dd"
checksum = "6ceab39d59e4c9499d4e5a8ee0e2735b891bb7308ac83dfb4e80cad195c9f6f3"
[[package]]
name = "unicode-normalization"
@ -2456,7 +2536,7 @@ version = "1.1.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dd6469f4314d5f1ffec476e05f17cc9a78bc7a27a6a857842170bdf8d6f98d2f"
dependencies = [
"getrandom 0.2.7",
"getrandom 0.2.8",
"serde",
]
@ -2888,6 +2968,7 @@ dependencies = [
"glow",
"glutin",
"gpu-alloc",
"gpu-allocator",
"gpu-descriptor",
"js-sys",
"khronos-egl",
@ -2969,43 +3050,109 @@ version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"
[[package]]
name = "windows"
version = "0.43.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "04662ed0e3e5630dfa9b26e4cb823b817f1a9addda855d973a9458c236556244"
dependencies = [
"windows_aarch64_gnullvm",
"windows_aarch64_msvc 0.42.0",
"windows_i686_gnu 0.42.0",
"windows_i686_msvc 0.42.0",
"windows_x86_64_gnu 0.42.0",
"windows_x86_64_gnullvm",
"windows_x86_64_msvc 0.42.0",
]
[[package]]
name = "windows-sys"
version = "0.36.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ea04155a16a59f9eab786fe12a4a450e75cdb175f9e0d80da1e17db09f55b8d2"
dependencies = [
"windows_aarch64_msvc",
"windows_i686_gnu",
"windows_i686_msvc",
"windows_x86_64_gnu",
"windows_x86_64_msvc",
"windows_aarch64_msvc 0.36.1",
"windows_i686_gnu 0.36.1",
"windows_i686_msvc 0.36.1",
"windows_x86_64_gnu 0.36.1",
"windows_x86_64_msvc 0.36.1",
]
[[package]]
name = "windows-sys"
version = "0.42.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5a3e1820f08b8513f676f7ab6c1f99ff312fb97b553d30ff4dd86f9f15728aa7"
dependencies = [
"windows_aarch64_gnullvm",
"windows_aarch64_msvc 0.42.0",
"windows_i686_gnu 0.42.0",
"windows_i686_msvc 0.42.0",
"windows_x86_64_gnu 0.42.0",
"windows_x86_64_gnullvm",
"windows_x86_64_msvc 0.42.0",
]
[[package]]
name = "windows_aarch64_gnullvm"
version = "0.42.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "41d2aa71f6f0cbe00ae5167d90ef3cfe66527d6f613ca78ac8024c3ccab9a19e"
[[package]]
name = "windows_aarch64_msvc"
version = "0.36.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9bb8c3fd39ade2d67e9874ac4f3db21f0d710bee00fe7cab16949ec184eeaa47"
[[package]]
name = "windows_aarch64_msvc"
version = "0.42.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dd0f252f5a35cac83d6311b2e795981f5ee6e67eb1f9a7f64eb4500fbc4dcdb4"
[[package]]
name = "windows_i686_gnu"
version = "0.36.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "180e6ccf01daf4c426b846dfc66db1fc518f074baa793aa7d9b9aaeffad6a3b6"
[[package]]
name = "windows_i686_gnu"
version = "0.42.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fbeae19f6716841636c28d695375df17562ca208b2b7d0dc47635a50ae6c5de7"
[[package]]
name = "windows_i686_msvc"
version = "0.36.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e2e7917148b2812d1eeafaeb22a97e4813dfa60a3f8f78ebe204bcc88f12f024"
[[package]]
name = "windows_i686_msvc"
version = "0.42.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "84c12f65daa39dd2babe6e442988fc329d6243fdce47d7d2d155b8d874862246"
[[package]]
name = "windows_x86_64_gnu"
version = "0.36.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4dcd171b8776c41b97521e5da127a2d86ad280114807d0b2ab1e462bc764d9e1"
[[package]]
name = "windows_x86_64_gnu"
version = "0.42.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bf7b1b21b5362cbc318f686150e5bcea75ecedc74dd157d874d754a2ca44b0ed"
[[package]]
name = "windows_x86_64_gnullvm"
version = "0.42.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "09d525d2ba30eeb3297665bd434a54297e4170c7f1a44cad4ef58095b4cd2028"
[[package]]
name = "windows_x86_64_msvc"
version = "0.36.1"
@ -3013,10 +3160,16 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "c811ca4a8c853ef420abd8592ba53ddbbac90410fab6903b3e79972a631f7680"
[[package]]
name = "winit"
version = "0.27.3"
name = "windows_x86_64_msvc"
version = "0.42.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "a22e94ba35ca3ff11820044bfa0dc48b95a3a15569c0068555566a12ef41c9e5"
checksum = "f40009d85759725a34da6d89a94e63d7bdc50a862acf0dbc7c8e488f1edcb6f5"
[[package]]
name = "winit"
version = "0.27.5"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "bb796d6fbd86b2fd896c9471e6f04d39d750076ebe5680a3958f00f5ab97657c"
dependencies = [
"bitflags",
"cocoa",
@ -3041,7 +3194,7 @@ dependencies = [
"wayland-client",
"wayland-protocols",
"web-sys",
"windows-sys",
"windows-sys 0.36.1",
"x11-dl",
]
@ -3120,9 +3273,9 @@ dependencies = [
[[package]]
name = "x11-dl"
version = "2.20.0"
version = "2.20.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "0c83627bc137605acc00bb399c7b908ef460b621fc37c953db2b09f88c449ea6"
checksum = "b1536d6965a5d4e573c7ef73a2c15ebcd0b2de3347bdf526c34c297c00ac40f0"
dependencies = [
"lazy_static",
"libc",

View File

@ -95,6 +95,7 @@ android_system_properties = "0.1.1"
# DX dependencies
bit-set = "0.5"
gpu-allocator = { version = "0.21", default_features = false, features = ["d3d12", "windows", "public-winapi"] }
native = { package = "d3d12", version = "0.5.0" }
range-alloc = "0.1"
winapi = "0.3"

View File

@ -33,6 +33,8 @@ vulkan = ["naga/spv-out", "ash", "gpu-alloc", "gpu-descriptor", "libloading", "s
gles = ["naga/glsl-out", "glow", "egl", "libloading"]
dx11 = ["naga/hlsl-out", "native", "libloading", "winapi/d3d11", "winapi/d3d11_1", "winapi/d3d11_2", "winapi/d3d11sdklayers", "winapi/dxgi1_6"]
dx12 = ["naga/hlsl-out", "native", "bit-set", "range-alloc", "winapi/d3d12", "winapi/d3d12shader", "winapi/d3d12sdklayers", "winapi/dxgi1_6"]
# TODO: This is a separate feature until Mozilla okays windows-rs, see https://github.com/gfx-rs/wgpu/issues/3207 for the tracking issue.
windows_rs = ["gpu-allocator"]
renderdoc = ["libloading", "renderdoc-sys"]
emscripten = ["gles"]
@ -72,6 +74,7 @@ glow = { git = "https://github.com/grovesNL/glow", rev = "c8a011fcd57a5c68cc917e
# backend: Dx12
bit-set = { version = "0.5", optional = true }
range-alloc = { version = "0.1", optional = true }
gpu-allocator = { version = "0.21", default_features = false, features = ["d3d12", "windows", "public-winapi"], optional = true }
[dependencies.wgt]
package = "wgpu-types"

View File

@ -14,8 +14,6 @@ use winapi::{
// this has to match Naga's HLSL backend, and also needs to be null-terminated
const NAGA_LOCATION_SEMANTIC: &[u8] = b"LOC\0";
//TODO: find the exact value
const D3D12_HEAP_FLAG_CREATE_NOT_ZEROED: u32 = d3d12::D3D12_HEAP_FLAG_NONE;
impl super::Device {
pub(super) fn new(
@ -24,6 +22,8 @@ impl super::Device {
private_caps: super::PrivateCapabilities,
library: &Arc<native::D3D12Lib>,
) -> Result<Self, crate::DeviceError> {
let mem_allocator = super::suballocation::create_allocator_wrapper(&raw)?;
let mut idle_fence = native::Fence::null();
let hr = unsafe {
profiling::scope!("ID3D12Device::CreateFence");
@ -165,6 +165,7 @@ impl super::Device {
#[cfg(feature = "renderdoc")]
render_doc: Default::default(),
null_rtv_handle,
mem_allocator,
})
}
@ -312,12 +313,13 @@ impl super::Device {
size,
mip_level_count,
sample_count,
allocation: None,
}
}
}
impl crate::Device<super::Api> for super::Device {
unsafe fn exit(self, queue: super::Queue) {
unsafe fn exit(mut self, queue: super::Queue) {
self.rtv_pool.lock().free_handle(self.null_rtv_handle);
unsafe { self.rtv_pool.into_inner().destroy() };
unsafe { self.dsv_pool.into_inner().destroy() };
@ -325,6 +327,7 @@ impl crate::Device<super::Api> for super::Device {
unsafe { self.sampler_pool.into_inner().destroy() };
unsafe { self.shared.destroy() };
unsafe { self.idler.destroy() };
self.mem_allocator = None;
unsafe { queue.raw.destroy() };
}
@ -355,43 +358,8 @@ impl crate::Device<super::Api> for super::Device {
Flags: conv::map_buffer_usage_to_resource_flags(desc.usage),
};
let is_cpu_read = desc.usage.contains(crate::BufferUses::MAP_READ);
let is_cpu_write = desc.usage.contains(crate::BufferUses::MAP_WRITE);
let heap_properties = d3d12::D3D12_HEAP_PROPERTIES {
Type: d3d12::D3D12_HEAP_TYPE_CUSTOM,
CPUPageProperty: if is_cpu_read {
d3d12::D3D12_CPU_PAGE_PROPERTY_WRITE_BACK
} else if is_cpu_write {
d3d12::D3D12_CPU_PAGE_PROPERTY_WRITE_COMBINE
} else {
d3d12::D3D12_CPU_PAGE_PROPERTY_NOT_AVAILABLE
},
MemoryPoolPreference: match self.private_caps.memory_architecture {
super::MemoryArchitecture::NonUnified if !is_cpu_read && !is_cpu_write => {
d3d12::D3D12_MEMORY_POOL_L1
}
_ => d3d12::D3D12_MEMORY_POOL_L0,
},
CreationNodeMask: 0,
VisibleNodeMask: 0,
};
let hr = unsafe {
self.raw.CreateCommittedResource(
&heap_properties,
if self.private_caps.heap_create_not_zeroed {
D3D12_HEAP_FLAG_CREATE_NOT_ZEROED
} else {
d3d12::D3D12_HEAP_FLAG_NONE
},
&raw_desc,
d3d12::D3D12_RESOURCE_STATE_COMMON,
ptr::null(),
&d3d12::ID3D12Resource::uuidof(),
resource.mut_void(),
)
};
let (hr, allocation) =
super::suballocation::create_buffer_resource(self, desc, raw_desc, &mut resource)?;
hr.into_device_result("Buffer creation")?;
if let Some(label) = desc.label {
@ -399,30 +367,48 @@ impl crate::Device<super::Api> for super::Device {
unsafe { resource.SetName(cwstr.as_ptr()) };
}
Ok(super::Buffer { resource, size })
Ok(super::Buffer {
resource,
size,
allocation,
})
}
unsafe fn destroy_buffer(&self, buffer: super::Buffer) {
unsafe fn destroy_buffer(&self, mut buffer: super::Buffer) {
unsafe { buffer.resource.destroy() };
// Only happens when it's using the windows_rs feature and there's an allocation
if let Some(alloc) = buffer.allocation.take() {
super::suballocation::free_buffer_allocation(
alloc,
// SAFETY: for allocations to exist, the allocator must exist
unsafe { self.mem_allocator.as_ref().unwrap_unchecked() },
);
}
}
unsafe fn map_buffer(
&self,
buffer: &super::Buffer,
range: crate::MemoryRange,
) -> Result<crate::BufferMapping, crate::DeviceError> {
let mut ptr = ptr::null_mut();
// TODO: 0 for subresource should be fine here until map and unmap buffer is subresource aware?
let hr = unsafe { (*buffer.resource).Map(0, ptr::null(), &mut ptr) };
hr.into_device_result("Map buffer")?;
Ok(crate::BufferMapping {
ptr: ptr::NonNull::new(unsafe { ptr.offset(range.start as isize) } as *mut _).unwrap(),
ptr: ptr::NonNull::new(unsafe { ptr.offset(range.start as isize).cast::<u8>() })
.unwrap(),
//TODO: double-check this. Documentation is a bit misleading -
// it implies that Map/Unmap is needed to invalidate/flush memory.
is_coherent: true,
})
}
unsafe fn unmap_buffer(&self, buffer: &super::Buffer) -> Result<(), crate::DeviceError> {
unsafe { (*buffer.resource).Unmap(0, ptr::null()) };
Ok(())
}
unsafe fn flush_mapped_ranges<I>(&self, _buffer: &super::Buffer, _ranges: I) {}
unsafe fn invalidate_mapped_ranges<I>(&self, _buffer: &super::Buffer, _ranges: I) {}
@ -430,6 +416,8 @@ impl crate::Device<super::Api> for super::Device {
&self,
desc: &crate::TextureDescriptor,
) -> Result<super::Texture, crate::DeviceError> {
use super::suballocation::create_texture_resource;
let mut resource = native::Resource::null();
let raw_desc = d3d12::D3D12_RESOURCE_DESC {
@ -461,32 +449,7 @@ impl crate::Device<super::Api> for super::Device {
Flags: conv::map_texture_usage_to_resource_flags(desc.usage),
};
let heap_properties = d3d12::D3D12_HEAP_PROPERTIES {
Type: d3d12::D3D12_HEAP_TYPE_CUSTOM,
CPUPageProperty: d3d12::D3D12_CPU_PAGE_PROPERTY_NOT_AVAILABLE,
MemoryPoolPreference: match self.private_caps.memory_architecture {
super::MemoryArchitecture::NonUnified => d3d12::D3D12_MEMORY_POOL_L1,
super::MemoryArchitecture::Unified { .. } => d3d12::D3D12_MEMORY_POOL_L0,
},
CreationNodeMask: 0,
VisibleNodeMask: 0,
};
let hr = unsafe {
self.raw.CreateCommittedResource(
&heap_properties,
if self.private_caps.heap_create_not_zeroed {
D3D12_HEAP_FLAG_CREATE_NOT_ZEROED
} else {
d3d12::D3D12_HEAP_FLAG_NONE
},
&raw_desc,
d3d12::D3D12_RESOURCE_STATE_COMMON,
ptr::null(), // clear value
&d3d12::ID3D12Resource::uuidof(),
resource.mut_void(),
)
};
let (hr, allocation) = create_texture_resource(self, desc, raw_desc, &mut resource)?;
hr.into_device_result("Texture creation")?;
if let Some(label) = desc.label {
@ -501,10 +464,19 @@ impl crate::Device<super::Api> for super::Device {
size: desc.size,
mip_level_count: desc.mip_level_count,
sample_count: desc.sample_count,
allocation,
})
}
unsafe fn destroy_texture(&self, texture: super::Texture) {
unsafe fn destroy_texture(&self, mut texture: super::Texture) {
unsafe { texture.resource.destroy() };
if let Some(alloc) = texture.allocation.take() {
super::suballocation::free_texture_allocation(
alloc,
// SAFETY: for allocations to exist, the allocator must exist
unsafe { self.mem_allocator.as_ref().unwrap_unchecked() },
);
}
}
unsafe fn create_texture_view(

View File

@ -39,6 +39,7 @@ mod conv;
mod descriptor;
mod device;
mod instance;
mod suballocation;
mod view;
use crate::auxil::{self, dxgi::result::HResult as _};
@ -152,6 +153,7 @@ struct PrivateCapabilities {
#[allow(unused)]
heterogeneous_resource_heaps: bool,
memory_architecture: MemoryArchitecture,
#[allow(unused)] // TODO: Exists until windows-rs is standard, then it can probably be removed?
heap_create_not_zeroed: bool,
}
@ -237,6 +239,7 @@ pub struct Device {
#[cfg(feature = "renderdoc")]
render_doc: crate::auxil::renderdoc::RenderDoc,
null_rtv_handle: descriptor::Handle,
mem_allocator: Option<Mutex<suballocation::GpuAllocatorWrapper>>,
}
unsafe impl Send for Device {}
@ -372,6 +375,7 @@ unsafe impl Sync for CommandBuffer {}
pub struct Buffer {
resource: native::Resource,
size: wgt::BufferAddress,
allocation: Option<suballocation::AllocationWrapper>,
}
unsafe impl Send for Buffer {}
@ -398,6 +402,7 @@ pub struct Texture {
size: wgt::Extent3d,
mip_level_count: u32,
sample_count: u32,
allocation: Option<suballocation::AllocationWrapper>,
}
unsafe impl Send for Texture {}
@ -764,6 +769,7 @@ impl crate::Surface<Api> for Surface {
size: sc.size,
mip_level_count: 1,
sample_count: 1,
allocation: None,
};
Ok(Some(crate::AcquiredSurfaceTexture {
texture,

View File

@ -0,0 +1,327 @@
pub(crate) use allocation::{
create_allocator_wrapper, create_buffer_resource, create_texture_resource,
free_buffer_allocation, free_texture_allocation, AllocationWrapper, GpuAllocatorWrapper,
};
// This exists to work around https://github.com/gfx-rs/wgpu/issues/3207
// Currently this will work the older, slower way if the windows_rs feature is disabled,
// and will use the fast path of suballocating buffers and textures using gpu_allocator if
// the windows_rs feature is enabled.
// This is the fast path using gpu_allocator to suballocate buffers and textures.
#[cfg(feature = "windows_rs")]
mod allocation {
use native::WeakPtr;
use parking_lot::Mutex;
use std::ptr;
use wgt::assertions::StrictAssertUnwrapExt;
use winapi::{
um::{
d3d12::{self, ID3D12Resource},
winnt::HRESULT,
},
Interface,
};
use gpu_allocator::{
d3d12::{AllocationCreateDesc, ToWinapi, ToWindows},
MemoryLocation,
};
#[derive(Debug)]
pub(crate) struct GpuAllocatorWrapper {
pub(crate) allocator: gpu_allocator::d3d12::Allocator,
}
#[derive(Debug)]
pub(crate) struct AllocationWrapper {
pub(crate) allocation: gpu_allocator::d3d12::Allocation,
}
pub(crate) fn create_allocator_wrapper(
raw: &native::Device,
) -> Result<Option<Mutex<GpuAllocatorWrapper>>, crate::DeviceError> {
let device = raw.as_ptr();
match gpu_allocator::d3d12::Allocator::new(&gpu_allocator::d3d12::AllocatorCreateDesc {
device: device.as_windows().clone(),
debug_settings: Default::default(),
}) {
Ok(allocator) => Ok(Some(Mutex::new(GpuAllocatorWrapper { allocator }))),
Err(e) => {
log::error!("Failed to create d3d12 allocator, error: {}", e);
Err(e)?
}
}
}
pub(crate) fn create_buffer_resource(
device: &crate::dx12::Device,
desc: &crate::BufferDescriptor,
raw_desc: d3d12::D3D12_RESOURCE_DESC,
resource: &mut WeakPtr<ID3D12Resource>,
) -> Result<(HRESULT, Option<AllocationWrapper>), crate::DeviceError> {
let is_cpu_read = desc.usage.contains(crate::BufferUses::MAP_READ);
let is_cpu_write = desc.usage.contains(crate::BufferUses::MAP_WRITE);
let location = match (is_cpu_read, is_cpu_write) {
(true, true) => MemoryLocation::CpuToGpu,
(true, false) => MemoryLocation::GpuToCpu,
(false, true) => MemoryLocation::CpuToGpu,
(false, false) => MemoryLocation::GpuOnly,
};
let name = desc.label.unwrap_or("Unlabeled buffer");
// SAFETY: allocator exists when the windows_rs feature is enabled
let mut allocator = device
.mem_allocator
.as_ref()
.strict_unwrap_unchecked()
.lock();
// let mut allocator = unsafe { device.mem_allocator.as_ref().unwrap_unchecked().lock() };
let allocation_desc = AllocationCreateDesc::from_winapi_d3d12_resource_desc(
allocator.allocator.device().as_winapi(),
&raw_desc,
name,
location,
);
let allocation = allocator.allocator.allocate(&allocation_desc)?;
let hr = unsafe {
device.raw.CreatePlacedResource(
allocation.heap().as_winapi() as *mut _,
allocation.offset(),
&raw_desc,
d3d12::D3D12_RESOURCE_STATE_COMMON,
ptr::null(),
&d3d12::ID3D12Resource::uuidof(),
resource.mut_void(),
)
};
Ok((hr, Some(AllocationWrapper { allocation })))
}
pub(crate) fn create_texture_resource(
device: &crate::dx12::Device,
desc: &crate::TextureDescriptor,
raw_desc: d3d12::D3D12_RESOURCE_DESC,
resource: &mut WeakPtr<ID3D12Resource>,
) -> Result<(HRESULT, Option<AllocationWrapper>), crate::DeviceError> {
let location = MemoryLocation::GpuOnly;
let name = desc.label.unwrap_or("Unlabeled texture");
// SAFETY: allocator exists when the windows_rs feature is enabled
let mut allocator = device
.mem_allocator
.as_ref()
.strict_unwrap_unchecked()
.lock();
let allocation_desc = AllocationCreateDesc::from_winapi_d3d12_resource_desc(
allocator.allocator.device().as_winapi(),
&raw_desc,
name,
location,
);
let allocation = allocator.allocator.allocate(&allocation_desc)?;
let hr = unsafe {
device.raw.CreatePlacedResource(
allocation.heap().as_winapi() as *mut _,
allocation.offset(),
&raw_desc,
d3d12::D3D12_RESOURCE_STATE_COMMON,
ptr::null(), // clear value
&d3d12::ID3D12Resource::uuidof(),
resource.mut_void(),
)
};
Ok((hr, Some(AllocationWrapper { allocation })))
}
pub(crate) fn free_buffer_allocation(
allocation: AllocationWrapper,
allocator: &Mutex<GpuAllocatorWrapper>,
) {
match allocator.lock().allocator.free(allocation.allocation) {
Ok(_) => (),
// TODO: Don't panic here
Err(e) => panic!("Failed to destroy dx12 buffer, {}", e),
};
}
pub(crate) fn free_texture_allocation(
allocation: AllocationWrapper,
allocator: &Mutex<GpuAllocatorWrapper>,
) {
match allocator.lock().allocator.free(allocation.allocation) {
Ok(_) => (),
// TODO: Don't panic here
Err(e) => panic!("Failed to destroy dx12 texture, {}", e),
};
}
#[cfg(feature = "windows_rs")]
impl From<gpu_allocator::AllocationError> for crate::DeviceError {
fn from(result: gpu_allocator::AllocationError) -> Self {
match result {
gpu_allocator::AllocationError::OutOfMemory => Self::OutOfMemory,
gpu_allocator::AllocationError::FailedToMap(e) => {
log::error!("DX12 gpu-allocator: Failed to map: {}", e);
Self::Lost
}
gpu_allocator::AllocationError::NoCompatibleMemoryTypeFound => {
log::error!("DX12 gpu-allocator: No Compatible Memory Type Found");
Self::Lost
}
gpu_allocator::AllocationError::InvalidAllocationCreateDesc => {
log::error!("DX12 gpu-allocator: Invalid Allocation Creation Description");
Self::Lost
}
gpu_allocator::AllocationError::InvalidAllocatorCreateDesc(e) => {
log::error!(
"DX12 gpu-allocator: Invalid Allocator Creation Description: {}",
e
);
Self::Lost
}
gpu_allocator::AllocationError::Internal(e) => {
log::error!("DX12 gpu-allocator: Internal Error: {}", e);
Self::Lost
}
}
}
}
}
// This is the older, slower path where it doesn't suballocate buffers.
// Tracking issue for when it can be removed: https://github.com/gfx-rs/wgpu/issues/3207
#[cfg(not(feature = "windows_rs"))]
mod allocation {
use native::WeakPtr;
use parking_lot::Mutex;
use std::ptr;
use winapi::{
um::{
d3d12::{self, ID3D12Resource},
winnt::HRESULT,
},
Interface,
};
const D3D12_HEAP_FLAG_CREATE_NOT_ZEROED: u32 = d3d12::D3D12_HEAP_FLAG_NONE; // TODO: find the exact value
// Allocator isn't needed when not suballocating with gpu_allocator
#[derive(Debug)]
pub(crate) struct GpuAllocatorWrapper {}
// Allocations aren't needed when not suballocating with gpu_allocator
#[derive(Debug)]
pub(crate) struct AllocationWrapper {}
pub(crate) fn create_allocator_wrapper(
_raw: &native::Device,
) -> Result<Option<Mutex<GpuAllocatorWrapper>>, crate::DeviceError> {
Ok(None)
}
pub(crate) fn create_buffer_resource(
device: &crate::dx12::Device,
desc: &crate::BufferDescriptor,
raw_desc: d3d12::D3D12_RESOURCE_DESC,
resource: &mut WeakPtr<ID3D12Resource>,
) -> Result<(HRESULT, Option<AllocationWrapper>), crate::DeviceError> {
let is_cpu_read = desc.usage.contains(crate::BufferUses::MAP_READ);
let is_cpu_write = desc.usage.contains(crate::BufferUses::MAP_WRITE);
let heap_properties = d3d12::D3D12_HEAP_PROPERTIES {
Type: d3d12::D3D12_HEAP_TYPE_CUSTOM,
CPUPageProperty: if is_cpu_read {
d3d12::D3D12_CPU_PAGE_PROPERTY_WRITE_BACK
} else if is_cpu_write {
d3d12::D3D12_CPU_PAGE_PROPERTY_WRITE_COMBINE
} else {
d3d12::D3D12_CPU_PAGE_PROPERTY_NOT_AVAILABLE
},
MemoryPoolPreference: match device.private_caps.memory_architecture {
crate::dx12::MemoryArchitecture::NonUnified if !is_cpu_read && !is_cpu_write => {
d3d12::D3D12_MEMORY_POOL_L1
}
_ => d3d12::D3D12_MEMORY_POOL_L0,
},
CreationNodeMask: 0,
VisibleNodeMask: 0,
};
let hr = unsafe {
device.raw.CreateCommittedResource(
&heap_properties,
if device.private_caps.heap_create_not_zeroed {
D3D12_HEAP_FLAG_CREATE_NOT_ZEROED
} else {
d3d12::D3D12_HEAP_FLAG_NONE
},
&raw_desc,
d3d12::D3D12_RESOURCE_STATE_COMMON,
ptr::null(),
&d3d12::ID3D12Resource::uuidof(),
resource.mut_void(),
)
};
Ok((hr, None))
}
pub(crate) fn create_texture_resource(
device: &crate::dx12::Device,
_desc: &crate::TextureDescriptor,
raw_desc: d3d12::D3D12_RESOURCE_DESC,
resource: &mut WeakPtr<ID3D12Resource>,
) -> Result<(HRESULT, Option<AllocationWrapper>), crate::DeviceError> {
let heap_properties = d3d12::D3D12_HEAP_PROPERTIES {
Type: d3d12::D3D12_HEAP_TYPE_CUSTOM,
CPUPageProperty: d3d12::D3D12_CPU_PAGE_PROPERTY_NOT_AVAILABLE,
MemoryPoolPreference: match device.private_caps.memory_architecture {
crate::dx12::MemoryArchitecture::NonUnified => d3d12::D3D12_MEMORY_POOL_L1,
crate::dx12::MemoryArchitecture::Unified { .. } => d3d12::D3D12_MEMORY_POOL_L0,
},
CreationNodeMask: 0,
VisibleNodeMask: 0,
};
let hr = unsafe {
device.raw.CreateCommittedResource(
&heap_properties,
if device.private_caps.heap_create_not_zeroed {
D3D12_HEAP_FLAG_CREATE_NOT_ZEROED
} else {
d3d12::D3D12_HEAP_FLAG_NONE
},
&raw_desc,
d3d12::D3D12_RESOURCE_STATE_COMMON,
ptr::null(), // clear value
&d3d12::ID3D12Resource::uuidof(),
resource.mut_void(),
)
};
Ok((hr, None))
}
pub(crate) fn free_buffer_allocation(
_allocation: AllocationWrapper,
_allocator: &Mutex<GpuAllocatorWrapper>,
) {
// No-op when not using gpu-allocator
}
pub(crate) fn free_texture_allocation(
_allocation: AllocationWrapper,
_allocator: &Mutex<GpuAllocatorWrapper>,
) {
// No-op when not using gpu-allocator
}
}

View File

@ -64,3 +64,23 @@ macro_rules! strict_assert_ne {
debug_assert_ne!( $( $arg )* )
};
}
/// Used to implement strict_assert for unwrap_unchecked
pub trait StrictAssertUnwrapExt<T> {
/// Implementation of strict_assert for unwrap_unchecked
fn strict_unwrap_unchecked(self) -> T;
}
impl<T> StrictAssertUnwrapExt<T> for Option<T> {
fn strict_unwrap_unchecked(self) -> T {
strict_assert!(self.is_some(), "Called strict_unwrap_unchecked on None");
unsafe { self.unwrap_unchecked() }
}
}
impl<T, E> StrictAssertUnwrapExt<T> for Result<T, E> {
fn strict_unwrap_unchecked(self) -> T {
strict_assert!(self.is_ok(), "Called strict_unwrap_unchecked on Err");
unsafe { self.unwrap_unchecked() }
}
}

View File

@ -14,7 +14,7 @@ use serde::{Deserialize, Serialize};
use std::hash::{Hash, Hasher};
use std::{num::NonZeroU32, ops::Range};
mod assertions;
pub mod assertions;
// Use this macro instead of the one provided by the bitflags_serde_shim crate
// because the latter produces an error when deserializing bits that are not

View File

@ -137,7 +137,7 @@ hal = { workspace = true }
hal = { workspace = true, features = ["renderdoc"] }
[target.'cfg(windows)'.dependencies]
hal = { workspace = true, features = ["renderdoc"] }
hal = { workspace = true, features = ["renderdoc", "windows_rs"] }
[target.'cfg(target_arch = "wasm32")'.dependencies.hal]
workspace = true