Skip to content

Commit 6560412

Browse files
kpreidcwfitzgerald
authored andcommitted
Make StagingBelt own the Device it uses.
This means that usage of a `StagingBelt` only requires passing along the current `CommandEncoder` instead of both the encoder and the device. It also makes the API reflect the fact that a `StagingBelt` cannot be reused with a fresh device. As far as I know, the only reason this was not done previously was that `Device` was not clonable, and so doing this would have required an `Arc<Device>` or other specific mechanism.
1 parent ad0f311 commit 6560412

File tree

4 files changed

+22
-18
lines changed

4 files changed

+22
-18
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,6 +121,7 @@ By @SupaMaggie70Incorporated in [#8206](https://github.com/gfx-rs/wgpu/pull/8206
121121
- Added support for rendering onto multi-planar textures. By @noituri in [#8307](https://github.com/gfx-rs/wgpu/pull/8307).
122122
- Validation errors from `CommandEncoder::finish()` will report the label of the invalid encoder. By @kpreid in [#8449](https://github.com/gfx-rs/wgpu/pull/8449).
123123
- Corrected documentation of the minimum alignment of the *end* of a mapped range of a buffer (it is 4, not 8). By @kpreid in [#8450](https://github.com/gfx-rs/wgpu/pull/8450).
124+
- `util::StagingBelt` now takes a `Device` when it is created instead of when it is used. By @kpreid in [#8462](https://github.com/gfx-rs/wgpu/pull/8462).
124125

125126
### Bug Fixes
126127

examples/features/src/skybox/mod.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -372,7 +372,7 @@ impl crate::framework::Example for Example {
372372
uniform_buf,
373373
entities,
374374
depth_view,
375-
staging_belt: wgpu::util::StagingBelt::new(0x100),
375+
staging_belt: wgpu::util::StagingBelt::new(device.clone(), 0x100),
376376
}
377377
}
378378

@@ -411,7 +411,6 @@ impl crate::framework::Example for Example {
411411
&self.uniform_buf,
412412
0,
413413
wgpu::BufferSize::new((raw_uniforms.len() * 4) as wgpu::BufferAddress).unwrap(),
414-
device,
415414
)
416415
.copy_from_slice(bytemuck::cast_slice(&raw_uniforms));
417416

tests/tests/wgpu-validation/util.rs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ fn staging_belt_random_test() {
99
let mut rng = nanorand::WyRand::new_seed(0xDEAD_BEEF);
1010
let buffer_size = 1024;
1111
let align = wgpu::COPY_BUFFER_ALIGNMENT;
12-
let mut belt = wgpu::util::StagingBelt::new(buffer_size / 2);
12+
let mut belt = wgpu::util::StagingBelt::new(device.clone(), buffer_size / 2);
1313
let target_buffer = device.create_buffer(&wgpu::BufferDescriptor {
1414
label: None,
1515
size: buffer_size,
@@ -30,7 +30,6 @@ fn staging_belt_random_test() {
3030
&target_buffer,
3131
offset,
3232
wgpu::BufferSize::new(size).unwrap(),
33-
&device,
3433
);
3534
slice[0] = 1; // token amount of actual writing, just in case it makes a difference
3635
}

wgpu/src/util/belt.rs

Lines changed: 19 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ use crate::COPY_BUFFER_ALIGNMENT;
2424
///
2525
/// [`Queue::write_buffer_with()`]: crate::Queue::write_buffer_with
2626
pub struct StagingBelt {
27+
device: Device,
2728
chunk_size: BufferAddress,
2829
/// Chunks into which we are accumulating data to be transferred.
2930
active_chunks: Vec<Chunk>,
@@ -50,9 +51,10 @@ impl StagingBelt {
5051
/// * 1-4 times less than the total amount of data uploaded per submission
5152
/// (per [`StagingBelt::finish()`]); and
5253
/// * bigger is better, within these bounds.
53-
pub fn new(chunk_size: BufferAddress) -> Self {
54+
pub fn new(device: Device, chunk_size: BufferAddress) -> Self {
5455
let (sender, receiver) = mpsc::channel();
5556
StagingBelt {
57+
device,
5658
chunk_size,
5759
active_chunks: Vec::new(),
5860
closed_chunks: Vec::new(),
@@ -82,7 +84,6 @@ impl StagingBelt {
8284
target: &Buffer,
8385
offset: BufferAddress,
8486
size: BufferSize,
85-
device: &Device,
8687
) -> BufferViewMut {
8788
// Asserting this explicitly gives a usefully more specific, and more prompt, error than
8889
// leaving it to regular API validation.
@@ -95,7 +96,6 @@ impl StagingBelt {
9596
let slice_of_belt = self.allocate(
9697
size,
9798
const { BufferSize::new(crate::COPY_BUFFER_ALIGNMENT).unwrap() },
98-
device,
9999
);
100100
encoder.copy_buffer_to_buffer(
101101
slice_of_belt.buffer(),
@@ -130,12 +130,7 @@ impl StagingBelt {
130130
/// which may be used to meet alignment requirements for the operation you wish to perform
131131
/// with the slice. This does not necessarily affect the alignment of the [`BufferViewMut`].
132132
#[track_caller]
133-
pub fn allocate(
134-
&mut self,
135-
size: BufferSize,
136-
alignment: BufferSize,
137-
device: &Device,
138-
) -> BufferSlice<'_> {
133+
pub fn allocate(&mut self, size: BufferSize, alignment: BufferSize) -> BufferSlice<'_> {
139134
assert!(
140135
size.get().is_multiple_of(COPY_BUFFER_ALIGNMENT),
141136
"StagingBelt allocation size {size} must be a multiple of `COPY_BUFFER_ALIGNMENT`"
@@ -164,7 +159,7 @@ impl StagingBelt {
164159
self.free_chunks.swap_remove(index)
165160
} else {
166161
Chunk {
167-
buffer: device.create_buffer(&BufferDescriptor {
162+
buffer: self.device.create_buffer(&BufferDescriptor {
168163
label: Some("(wgpu internal) StagingBelt staging buffer"),
169164
size: self.chunk_size.max(size.get()),
170165
usage: BufferUsages::MAP_WRITE | BufferUsages::COPY_SRC,
@@ -232,11 +227,21 @@ impl StagingBelt {
232227

233228
impl fmt::Debug for StagingBelt {
234229
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
230+
let Self {
231+
device,
232+
chunk_size,
233+
active_chunks,
234+
closed_chunks,
235+
free_chunks,
236+
sender: _,
237+
receiver: _,
238+
} = self;
235239
f.debug_struct("StagingBelt")
236-
.field("chunk_size", &self.chunk_size)
237-
.field("active_chunks", &self.active_chunks.len())
238-
.field("closed_chunks", &self.closed_chunks.len())
239-
.field("free_chunks", &self.free_chunks.len())
240+
.field("device", device)
241+
.field("chunk_size", chunk_size)
242+
.field("active_chunks", &active_chunks.len())
243+
.field("closed_chunks", &closed_chunks.len())
244+
.field("free_chunks", &free_chunks.len())
240245
.finish_non_exhaustive()
241246
}
242247
}

0 commit comments

Comments
 (0)