[dxvk] Move buffer initialization to transfer queue

This commit is contained in:
Philip Rebohle 2025-03-01 13:17:48 +01:00
parent 83023cb63d
commit 49479a27e5

View file

@ -1008,45 +1008,49 @@ namespace dxvk {
void DxvkContext::initBuffer(
const Rc<DxvkBuffer>& buffer) {
auto slice = buffer->getSliceHandle();
auto dstSlice = buffer->getSliceHandle();
// Buffer size may be misaligned, in which case we have
// to use a plain buffer copy to fill the last few bytes.
constexpr VkDeviceSize MinCopyAndFillSize = 1u << 20;
VkDeviceSize copySize = slice.length & 3u;
VkDeviceSize fillSize = slice.length - copySize;
VkDeviceSize copySize = dstSlice.length & 3u;
VkDeviceSize fillSize = dstSlice.length - copySize;
// If the buffer is small, just dispatch one single copy
if (copySize && slice.length < MinCopyAndFillSize) {
copySize = slice.length;
if (copySize && dstSlice.length < MinCopyAndFillSize) {
copySize = dstSlice.length;
fillSize = 0u;
}
if (fillSize) {
m_cmd->cmdFillBuffer(DxvkCmdBuffer::InitBuffer,
slice.handle, slice.offset, fillSize, 0u);
m_cmd->cmdFillBuffer(DxvkCmdBuffer::SdmaBuffer,
dstSlice.handle, dstSlice.offset, fillSize, 0u);
}
if (copySize) {
auto zero = createZeroBuffer(copySize)->getSliceHandle();
auto srcSlice = createZeroBuffer(copySize)->getSliceHandle();
VkBufferCopy2 copyRegion = { VK_STRUCTURE_TYPE_BUFFER_COPY_2 };
copyRegion.srcOffset = zero.offset;
copyRegion.dstOffset = slice.offset + fillSize;
copyRegion.srcOffset = srcSlice.offset;
copyRegion.dstOffset = dstSlice.offset + fillSize;
copyRegion.size = copySize;
VkCopyBufferInfo2 copyInfo = { VK_STRUCTURE_TYPE_COPY_BUFFER_INFO_2 };
copyInfo.srcBuffer = zero.handle;
copyInfo.dstBuffer = slice.handle;
copyInfo.srcBuffer = srcSlice.handle;
copyInfo.dstBuffer = dstSlice.handle;
copyInfo.regionCount = 1;
copyInfo.pRegions = &copyRegion;
m_cmd->cmdCopyBuffer(DxvkCmdBuffer::InitBuffer, &copyInfo);
m_cmd->cmdCopyBuffer(DxvkCmdBuffer::SdmaBuffer, &copyInfo);
}
accessMemory(DxvkCmdBuffer::InitBuffer,
accessMemory(DxvkCmdBuffer::SdmaBuffer,
VK_PIPELINE_STAGE_2_TRANSFER_BIT, VK_ACCESS_2_TRANSFER_WRITE_BIT,
VK_PIPELINE_STAGE_2_TRANSFER_BIT, VK_ACCESS_2_NONE);
accessMemory(DxvkCmdBuffer::InitBarriers,
VK_PIPELINE_STAGE_2_TRANSFER_BIT, VK_ACCESS_2_NONE,
buffer->info().stages, buffer->info().access);
m_cmd->track(buffer, DxvkAccess::Write);