hal/dx12: implement fill_buffer with zero

This commit is contained in:
Dzmitry Malyshau
2021-07-08 18:02:54 -04:00
parent 2c76b0e656
commit 9069c2301f
3 changed files with 71 additions and 8 deletions

View File

@@ -170,13 +170,21 @@ impl crate::CommandEncoder<super::Api> for super::CommandEncoder {
}
}
unsafe fn fill_buffer(
&mut self,
_buffer: &super::Buffer,
_range: crate::MemoryRange,
_value: u8,
) {
//TODO
unsafe fn fill_buffer(&mut self, buffer: &super::Buffer, range: crate::MemoryRange, value: u8) {
assert_eq!(value, 0, "Only zero is supported!");
let list = self.list.unwrap();
let mut offset = range.start;
while offset < range.end {
let size = super::ZERO_BUFFER_SIZE.min(range.end - offset);
list.CopyBufferRegion(
buffer.resource.as_mut_ptr(),
offset,
self.zero_buffer.as_mut_ptr(),
0,
size,
);
offset += size;
}
}
unsafe fn copy_buffer_to_buffer<T>(

View File

@@ -1,6 +1,6 @@
use super::{conv, descriptor, HResult as _};
use parking_lot::Mutex;
use std::{mem, ptr, sync::Arc};
use std::{mem, ptr, slice, sync::Arc};
use winapi::{
shared::{dxgiformat, dxgitype, winerror},
um::{d3d12, d3d12sdklayers, synchapi, winbase},
@@ -30,6 +30,53 @@ impl super::Device {
};
hr.into_device_result("Idle fence creation")?;
let mut zero_buffer = native::Resource::null();
unsafe {
let raw_desc = d3d12::D3D12_RESOURCE_DESC {
Dimension: d3d12::D3D12_RESOURCE_DIMENSION_BUFFER,
Alignment: 0,
Width: super::ZERO_BUFFER_SIZE,
Height: 1,
DepthOrArraySize: 1,
MipLevels: 1,
Format: dxgiformat::DXGI_FORMAT_UNKNOWN,
SampleDesc: dxgitype::DXGI_SAMPLE_DESC {
Count: 1,
Quality: 0,
},
Layout: d3d12::D3D12_TEXTURE_LAYOUT_ROW_MAJOR,
Flags: d3d12::D3D12_RESOURCE_FLAG_DENY_SHADER_RESOURCE,
};
let heap_properties = d3d12::D3D12_HEAP_PROPERTIES {
Type: d3d12::D3D12_HEAP_TYPE_CUSTOM,
CPUPageProperty: d3d12::D3D12_CPU_PAGE_PROPERTY_WRITE_COMBINE,
MemoryPoolPreference: d3d12::D3D12_MEMORY_POOL_L0,
CreationNodeMask: 0,
VisibleNodeMask: 0,
};
let hr = raw.CreateCommittedResource(
&heap_properties,
d3d12::D3D12_HEAP_FLAG_NONE,
&raw_desc,
d3d12::D3D12_RESOURCE_STATE_COMMON,
ptr::null(),
&d3d12::ID3D12Resource::uuidof(),
zero_buffer.mut_void(),
);
hr.into_device_result("Zero buffer creation")?;
let range = d3d12::D3D12_RANGE { Begin: 0, End: 0 };
let mut ptr = std::ptr::null_mut();
(*zero_buffer)
.Map(0, &range, &mut ptr)
.into_device_result("Map zero buffer")?;
slice::from_raw_parts_mut(ptr as *mut u8, super::ZERO_BUFFER_SIZE as usize).fill(0);
(*zero_buffer).Unmap(0, &range);
};
Ok(super::Device {
raw,
present_queue,
@@ -54,6 +101,7 @@ impl super::Device {
raw,
native::DescriptorHeapType::Sampler,
)),
zero_buffer,
library: Arc::clone(library),
})
}
@@ -424,6 +472,7 @@ impl crate::Device<super::Api> for super::Device {
self.dsv_pool.into_inner().destroy();
self.srv_uav_pool.into_inner().destroy();
self.sampler_pool.into_inner().destroy();
self.zero_buffer.destroy();
//self.descriptor_updater.lock().destroy();
@@ -701,6 +750,7 @@ impl crate::Device<super::Api> for super::Device {
Ok(super::CommandEncoder {
allocator,
device: self.raw,
zero_buffer: self.zero_buffer,
list: None,
free_lists: Vec::new(),
temp: super::Temp::default(),

View File

@@ -93,6 +93,8 @@ impl<T> HResult<T> for (T, i32) {
}
}
const ZERO_BUFFER_SIZE: wgt::BufferAddress = 256 << 10;
pub struct Instance {
factory: native::Factory4,
library: Arc<native::D3D12Lib>,
@@ -166,6 +168,8 @@ pub struct Device {
dsv_pool: Mutex<descriptor::CpuPool>,
srv_uav_pool: Mutex<descriptor::CpuPool>,
sampler_pool: Mutex<descriptor::CpuPool>,
// aux resources
zero_buffer: native::Resource,
// library
library: Arc<native::D3D12Lib>,
}
@@ -194,6 +198,7 @@ impl Temp {
pub struct CommandEncoder {
allocator: native::CommandAllocator,
device: native::Device,
zero_buffer: native::Resource,
list: Option<native::GraphicsCommandList>,
free_lists: Vec<native::GraphicsCommandList>,
temp: Temp,