Skip to content

Commit

Permalink
add a debug label to storage buffers (#5341)
Browse files Browse the repository at this point in the history
# Objective

- Expose the wgpu debug label on storage buffer types.

## Solution

馃悇

- Add an optional cow static string and pass that to the label field of create_buffer_with_data
- This pattern is already used by Bevy for debug tags on bind group and layout descriptors.

---

Example Usage:

A buffer is given a label using the label function. Alternatively a buffer may be labeled when it is created if the default() convention is not used.
![ray_buf](https://user-images.githubusercontent.com/106117615/179366494-f037bd8c-4d65-4b37-8135-01ac0c5c8ee0.png)

Here is the buffer appearing with the correct name in RenderDoc. Previously the buffer would have an anonymous name such as "Buffer223":
![buffer_named](https://user-images.githubusercontent.com/106117615/179366552-faeb6c27-5373-4e4e-a0e2-c04446f95a4b.png)



Co-authored-by: rebelroad-reinhart <reinhart@rebelroad.gg>
  • Loading branch information
Brandon Reinhart and rebelroad-reinhart committed Jul 28, 2022
1 parent 4e2600b commit 2d2ea33
Show file tree
Hide file tree
Showing 3 changed files with 115 additions and 17 deletions.
23 changes: 21 additions & 2 deletions crates/bevy_render/src/render_resource/buffer_vec.rs
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,8 @@ pub struct BufferVec<T: Pod> {
capacity: usize,
item_size: usize,
buffer_usage: BufferUsages,
label: Option<String>,
label_changed: bool,
}

impl<T: Pod> BufferVec<T> {
Expand All @@ -43,6 +45,8 @@ impl<T: Pod> BufferVec<T> {
capacity: 0,
item_size: std::mem::size_of::<T>(),
buffer_usage,
label: None,
label_changed: false,
}
}

Expand Down Expand Up @@ -72,6 +76,20 @@ impl<T: Pod> BufferVec<T> {
index
}

pub fn set_label(&mut self, label: Option<&str>) {
let label = label.map(str::to_string);

if label != self.label {
self.label_changed = true;
}

self.label = label;
}

pub fn get_label(&self) -> Option<&str> {
self.label.as_deref()
}

/// Creates a [`Buffer`](crate::render_resource::Buffer) on the [`RenderDevice`](crate::renderer::RenderDevice) with size
/// at least `std::mem::size_of::<T>() * capacity`, unless a such a buffer already exists.
///
Expand All @@ -84,15 +102,16 @@ impl<T: Pod> BufferVec<T> {
/// the `BufferVec` was created, the buffer on the [`RenderDevice`](crate::renderer::RenderDevice)
/// is marked as [`BufferUsages::COPY_DST`](crate::render_resource::BufferUsages).
pub fn reserve(&mut self, capacity: usize, device: &RenderDevice) {
if capacity > self.capacity {
if capacity > self.capacity || self.label_changed {
self.capacity = capacity;
let size = self.item_size * capacity;
self.buffer = Some(device.create_buffer(&wgpu::BufferDescriptor {
label: None,
label: self.label.as_deref(),
size: size as wgpu::BufferAddress,
usage: BufferUsages::COPY_DST | self.buffer_usage,
mapped_at_creation: false,
}));
self.label_changed = false;
}
}

Expand Down
48 changes: 44 additions & 4 deletions crates/bevy_render/src/render_resource/storage_buffer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,8 @@ pub struct StorageBuffer<T: ShaderType> {
scratch: StorageBufferWrapper<Vec<u8>>,
buffer: Option<Buffer>,
capacity: usize,
label: Option<String>,
label_changed: bool,
}

impl<T: ShaderType> From<T> for StorageBuffer<T> {
Expand All @@ -41,6 +43,8 @@ impl<T: ShaderType> From<T> for StorageBuffer<T> {
scratch: StorageBufferWrapper::new(Vec::new()),
buffer: None,
capacity: 0,
label: None,
label_changed: false,
}
}
}
Expand All @@ -52,6 +56,8 @@ impl<T: ShaderType + Default> Default for StorageBuffer<T> {
scratch: StorageBufferWrapper::new(Vec::new()),
buffer: None,
capacity: 0,
label: None,
label_changed: false,
}
}
}
Expand Down Expand Up @@ -81,6 +87,20 @@ impl<T: ShaderType + WriteInto> StorageBuffer<T> {
&mut self.value
}

pub fn set_label(&mut self, label: Option<&str>) {
let label = label.map(str::to_string);

if label != self.label {
self.label_changed = true;
}

self.label = label;
}

pub fn get_label(&self) -> Option<&str> {
self.label.as_deref()
}

/// Queues writing of data from system RAM to VRAM using the [`RenderDevice`](crate::renderer::RenderDevice)
/// and the provided [`RenderQueue`](crate::renderer::RenderQueue).
///
Expand All @@ -91,13 +111,14 @@ impl<T: ShaderType + WriteInto> StorageBuffer<T> {

let size = self.scratch.as_ref().len();

if self.capacity < size {
if self.capacity < size || self.label_changed {
self.buffer = Some(device.create_buffer_with_data(&BufferInitDescriptor {
label: None,
label: self.label.as_deref(),
usage: BufferUsages::COPY_DST | BufferUsages::STORAGE,
contents: self.scratch.as_ref(),
}));
self.capacity = size;
self.label_changed = false;
} else if let Some(buffer) = &self.buffer {
queue.write_buffer(buffer, 0, self.scratch.as_ref());
}
Expand Down Expand Up @@ -130,6 +151,8 @@ pub struct DynamicStorageBuffer<T: ShaderType> {
scratch: DynamicStorageBufferWrapper<Vec<u8>>,
buffer: Option<Buffer>,
capacity: usize,
label: Option<String>,
label_changed: bool,
}

impl<T: ShaderType> Default for DynamicStorageBuffer<T> {
Expand All @@ -139,6 +162,8 @@ impl<T: ShaderType> Default for DynamicStorageBuffer<T> {
scratch: DynamicStorageBufferWrapper::new(Vec::new()),
buffer: None,
capacity: 0,
label: None,
label_changed: false,
}
}
}
Expand Down Expand Up @@ -175,17 +200,32 @@ impl<T: ShaderType + WriteInto> DynamicStorageBuffer<T> {
offset
}

pub fn set_label(&mut self, label: Option<&str>) {
let label = label.map(str::to_string);

if label != self.label {
self.label_changed = true;
}

self.label = label;
}

pub fn get_label(&self) -> Option<&str> {
self.label.as_deref()
}

#[inline]
pub fn write_buffer(&mut self, device: &RenderDevice, queue: &RenderQueue) {
let size = self.scratch.as_ref().len();

if self.capacity < size {
if self.capacity < size || self.label_changed {
self.buffer = Some(device.create_buffer_with_data(&BufferInitDescriptor {
label: None,
label: self.label.as_deref(),
usage: BufferUsages::COPY_DST | BufferUsages::STORAGE,
contents: self.scratch.as_ref(),
}));
self.capacity = size;
self.label_changed = false;
} else if let Some(buffer) = &self.buffer {
queue.write_buffer(buffer, 0, self.scratch.as_ref());
}
Expand Down
61 changes: 50 additions & 11 deletions crates/bevy_render/src/render_resource/uniform_buffer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ pub struct UniformBuffer<T: ShaderType> {
value: T,
scratch: UniformBufferWrapper<Vec<u8>>,
buffer: Option<Buffer>,
label: Option<String>,
label_changed: bool,
}

impl<T: ShaderType> From<T> for UniformBuffer<T> {
Expand All @@ -39,6 +41,8 @@ impl<T: ShaderType> From<T> for UniformBuffer<T> {
value,
scratch: UniformBufferWrapper::new(Vec::new()),
buffer: None,
label: None,
label_changed: false,
}
}
}
Expand All @@ -49,6 +53,8 @@ impl<T: ShaderType + Default> Default for UniformBuffer<T> {
value: T::default(),
scratch: UniformBufferWrapper::new(Vec::new()),
buffer: None,
label: None,
label_changed: false,
}
}
}
Expand Down Expand Up @@ -79,6 +85,20 @@ impl<T: ShaderType + WriteInto> UniformBuffer<T> {
&mut self.value
}

pub fn set_label(&mut self, label: Option<&str>) {
let label = label.map(str::to_string);

if label != self.label {
self.label_changed = true;
}

self.label = label;
}

pub fn get_label(&self) -> Option<&str> {
self.label.as_deref()
}

/// Queues writing of data from system RAM to VRAM using the [`RenderDevice`](crate::renderer::RenderDevice)
/// and the provided [`RenderQueue`](crate::renderer::RenderQueue), if a GPU-side backing buffer already exists.
///
Expand All @@ -87,15 +107,15 @@ impl<T: ShaderType + WriteInto> UniformBuffer<T> {
pub fn write_buffer(&mut self, device: &RenderDevice, queue: &RenderQueue) {
self.scratch.write(&self.value).unwrap();

match &self.buffer {
Some(buffer) => queue.write_buffer(buffer, 0, self.scratch.as_ref()),
None => {
self.buffer = Some(device.create_buffer_with_data(&BufferInitDescriptor {
label: None,
usage: BufferUsages::COPY_DST | BufferUsages::UNIFORM,
contents: self.scratch.as_ref(),
}));
}
if self.label_changed || self.buffer.is_none() {
self.buffer = Some(device.create_buffer_with_data(&BufferInitDescriptor {
label: self.label.as_deref(),
usage: BufferUsages::COPY_DST | BufferUsages::UNIFORM,
contents: self.scratch.as_ref(),
}));
self.label_changed = false;
} else if let Some(buffer) = &self.buffer {
queue.write_buffer(buffer, 0, self.scratch.as_ref());
}
}
}
Expand Down Expand Up @@ -124,6 +144,8 @@ pub struct DynamicUniformBuffer<T: ShaderType> {
scratch: DynamicUniformBufferWrapper<Vec<u8>>,
buffer: Option<Buffer>,
capacity: usize,
label: Option<String>,
label_changed: bool,
}

impl<T: ShaderType> Default for DynamicUniformBuffer<T> {
Expand All @@ -133,6 +155,8 @@ impl<T: ShaderType> Default for DynamicUniformBuffer<T> {
scratch: DynamicUniformBufferWrapper::new(Vec::new()),
buffer: None,
capacity: 0,
label: None,
label_changed: false,
}
}
}
Expand Down Expand Up @@ -170,6 +194,20 @@ impl<T: ShaderType + WriteInto> DynamicUniformBuffer<T> {
offset
}

pub fn set_label(&mut self, label: Option<&str>) {
let label = label.map(str::to_string);

if label != self.label {
self.label_changed = true;
}

self.label = label;
}

pub fn get_label(&self) -> Option<&str> {
self.label.as_deref()
}

/// Queues writing of data from system RAM to VRAM using the [`RenderDevice`](crate::renderer::RenderDevice)
/// and the provided [`RenderQueue`](crate::renderer::RenderQueue).
///
Expand All @@ -179,13 +217,14 @@ impl<T: ShaderType + WriteInto> DynamicUniformBuffer<T> {
pub fn write_buffer(&mut self, device: &RenderDevice, queue: &RenderQueue) {
let size = self.scratch.as_ref().len();

if self.capacity < size {
if self.capacity < size || self.label_changed {
self.buffer = Some(device.create_buffer_with_data(&BufferInitDescriptor {
label: None,
label: self.label.as_deref(),
usage: BufferUsages::COPY_DST | BufferUsages::UNIFORM,
contents: self.scratch.as_ref(),
}));
self.capacity = size;
self.label_changed = false;
} else if let Some(buffer) = &self.buffer {
queue.write_buffer(buffer, 0, self.scratch.as_ref());
}
Expand Down

0 comments on commit 2d2ea33

Please sign in to comment.