mirror of
https://github.com/doitsujin/dxvk.git
synced 2024-12-03 04:24:11 +01:00
[d3d11] Don't use data buffer for small buffer updates
Embed an array instead and lower the size threshold.
This commit is contained in:
parent
01a7457a6f
commit
1cefe90ce7
@ -3142,29 +3142,6 @@ namespace dxvk {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
template<typename ContextType>
|
|
||||||
DxvkDataSlice D3D11CommonContext<ContextType>::AllocUpdateBufferSlice(size_t Size) {
|
|
||||||
constexpr size_t UpdateBufferSize = 1 * 1024 * 1024;
|
|
||||||
|
|
||||||
if (Size >= UpdateBufferSize) {
|
|
||||||
Rc<DxvkDataBuffer> buffer = new DxvkDataBuffer(Size);
|
|
||||||
return buffer->alloc(Size);
|
|
||||||
} else {
|
|
||||||
if (m_updateBuffer == nullptr)
|
|
||||||
m_updateBuffer = new DxvkDataBuffer(UpdateBufferSize);
|
|
||||||
|
|
||||||
DxvkDataSlice slice = m_updateBuffer->alloc(Size);
|
|
||||||
|
|
||||||
if (slice.ptr() == nullptr) {
|
|
||||||
m_updateBuffer = new DxvkDataBuffer(UpdateBufferSize);
|
|
||||||
slice = m_updateBuffer->alloc(Size);
|
|
||||||
}
|
|
||||||
|
|
||||||
return slice;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
template<typename ContextType>
|
template<typename ContextType>
|
||||||
DxvkBufferSlice D3D11CommonContext<ContextType>::AllocStagingBuffer(
|
DxvkBufferSlice D3D11CommonContext<ContextType>::AllocStagingBuffer(
|
||||||
VkDeviceSize Size) {
|
VkDeviceSize Size) {
|
||||||
@ -5143,27 +5120,28 @@ namespace dxvk {
|
|||||||
UINT Offset,
|
UINT Offset,
|
||||||
UINT Length,
|
UINT Length,
|
||||||
const void* pSrcData) {
|
const void* pSrcData) {
|
||||||
|
constexpr uint32_t MaxDirectUpdateSize = 64u;
|
||||||
|
|
||||||
DxvkBufferSlice bufferSlice = pDstBuffer->GetBufferSlice(Offset, Length);
|
DxvkBufferSlice bufferSlice = pDstBuffer->GetBufferSlice(Offset, Length);
|
||||||
|
|
||||||
if (Length <= 1024 && !(Offset & 0x3) && !(Length & 0x3)) {
|
if (Length <= MaxDirectUpdateSize && !((Offset | Length) & 0x3)) {
|
||||||
// The backend has special code paths for small buffer updates,
|
// The backend has special code paths for small buffer updates,
|
||||||
// however both offset and size must be aligned to four bytes.
|
// however both offset and size must be aligned to four bytes.
|
||||||
DxvkDataSlice dataSlice = AllocUpdateBufferSlice(Length);
|
std::array<char, MaxDirectUpdateSize> data;
|
||||||
std::memcpy(dataSlice.ptr(), pSrcData, Length);
|
std::memcpy(data.data(), pSrcData, Length);
|
||||||
|
|
||||||
EmitCs([
|
EmitCs([
|
||||||
cDataBuffer = std::move(dataSlice),
|
cBufferData = data,
|
||||||
cBufferSlice = std::move(bufferSlice)
|
cBufferSlice = std::move(bufferSlice)
|
||||||
] (DxvkContext* ctx) {
|
] (DxvkContext* ctx) {
|
||||||
ctx->updateBuffer(
|
ctx->updateBuffer(
|
||||||
cBufferSlice.buffer(),
|
cBufferSlice.buffer(),
|
||||||
cBufferSlice.offset(),
|
cBufferSlice.offset(),
|
||||||
cBufferSlice.length(),
|
cBufferSlice.length(),
|
||||||
cDataBuffer.ptr());
|
cBufferData.data());
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
// Otherwise, to avoid large data copies on the CS thread,
|
// Write directly to a staging buffer and dispatch a copy
|
||||||
// write directly to a staging buffer and dispatch a copy
|
|
||||||
DxvkBufferSlice stagingSlice = AllocStagingBuffer(Length);
|
DxvkBufferSlice stagingSlice = AllocStagingBuffer(Length);
|
||||||
std::memcpy(stagingSlice.mapPtr(0), pSrcData, Length);
|
std::memcpy(stagingSlice.mapPtr(0), pSrcData, Length);
|
||||||
|
|
||||||
|
@ -769,7 +769,6 @@ namespace dxvk {
|
|||||||
UINT m_flags;
|
UINT m_flags;
|
||||||
|
|
||||||
DxvkStagingBuffer m_staging;
|
DxvkStagingBuffer m_staging;
|
||||||
Rc<DxvkDataBuffer> m_updateBuffer;
|
|
||||||
|
|
||||||
DxvkCsChunkFlags m_csFlags;
|
DxvkCsChunkFlags m_csFlags;
|
||||||
DxvkCsChunkRef m_csChunk;
|
DxvkCsChunkRef m_csChunk;
|
||||||
@ -779,8 +778,6 @@ namespace dxvk {
|
|||||||
|
|
||||||
DxvkCsChunkRef AllocCsChunk();
|
DxvkCsChunkRef AllocCsChunk();
|
||||||
|
|
||||||
DxvkDataSlice AllocUpdateBufferSlice(size_t Size);
|
|
||||||
|
|
||||||
DxvkBufferSlice AllocStagingBuffer(
|
DxvkBufferSlice AllocStagingBuffer(
|
||||||
VkDeviceSize Size);
|
VkDeviceSize Size);
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user