diff --git a/src/d3d11/d3d11_buffer.cpp b/src/d3d11/d3d11_buffer.cpp index 4448e46d..1aae7f72 100644 --- a/src/d3d11/d3d11_buffer.cpp +++ b/src/d3d11/d3d11_buffer.cpp @@ -5,7 +5,9 @@ namespace dxvk { D3D11Buffer::D3D11Buffer( D3D11Device* device, - const D3D11_BUFFER_DESC& desc) { + const D3D11_BUFFER_DESC& desc) + : m_device(device), m_desc(desc), + m_buffer(this->createBuffer()) { TRACE(this, device); } @@ -40,4 +42,93 @@ namespace dxvk { *pDesc = m_desc; } + + Rc D3D11Buffer::createBuffer() { + VkMemoryPropertyFlags memoryType = 0; + + DxvkBufferCreateInfo info; + info.size = m_desc.ByteWidth; + info.usage = VK_BUFFER_USAGE_TRANSFER_DST_BIT + | VK_BUFFER_USAGE_TRANSFER_SRC_BIT; + info.stages = VK_PIPELINE_STAGE_TRANSFER_BIT; + info.access = VK_ACCESS_TRANSFER_WRITE_BIT + | VK_ACCESS_TRANSFER_READ_BIT; + + switch (m_desc.Usage) { + case D3D11_USAGE_DEFAULT: + case D3D11_USAGE_IMMUTABLE: + memoryType |= VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT; + break; + + case D3D11_USAGE_DYNAMIC: + memoryType |= VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT + | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT; + break; + + case D3D11_USAGE_STAGING: + memoryType |= VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT + | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT + | VK_MEMORY_PROPERTY_HOST_CACHED_BIT; + break; + } + + if (m_desc.BindFlags & D3D11_BIND_VERTEX_BUFFER) { + info.usage |= VK_BUFFER_USAGE_VERTEX_BUFFER_BIT; + info.stages |= VK_PIPELINE_STAGE_VERTEX_INPUT_BIT; + info.access |= VK_ACCESS_VERTEX_ATTRIBUTE_READ_BIT; + } + + if (m_desc.BindFlags & D3D11_BIND_INDEX_BUFFER) { + info.usage |= VK_BUFFER_USAGE_INDEX_BUFFER_BIT; + info.stages |= VK_PIPELINE_STAGE_VERTEX_INPUT_BIT; + info.access |= VK_ACCESS_INDEX_READ_BIT; + } + + if (m_desc.BindFlags & (D3D11_BIND_CONSTANT_BUFFER & D3D11_BIND_SHADER_RESOURCE)) { + info.usage |= VK_BUFFER_USAGE_UNIFORM_BUFFER_BIT + | VK_BUFFER_USAGE_UNIFORM_TEXEL_BUFFER_BIT; + info.stages |= VK_PIPELINE_STAGE_VERTEX_SHADER_BIT + | VK_PIPELINE_STAGE_TESSELLATION_CONTROL_SHADER_BIT + | VK_PIPELINE_STAGE_TESSELLATION_EVALUATION_SHADER_BIT + | VK_PIPELINE_STAGE_GEOMETRY_SHADER_BIT + | VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT + | VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT; + info.access |= VK_ACCESS_SHADER_READ_BIT; + } + + if (m_desc.BindFlags & D3D11_BIND_STREAM_OUTPUT) { + info.usage |= VK_BUFFER_USAGE_STORAGE_BUFFER_BIT + | VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT; + info.stages |= VK_PIPELINE_STAGE_GEOMETRY_SHADER_BIT; + info.access |= VK_ACCESS_SHADER_WRITE_BIT; + } + + if (m_desc.BindFlags & D3D11_BIND_UNORDERED_ACCESS) { + info.usage |= VK_BUFFER_USAGE_STORAGE_BUFFER_BIT + | VK_BUFFER_USAGE_STORAGE_TEXEL_BUFFER_BIT; + info.stages |= VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT + | VK_PIPELINE_STAGE_COMPUTE_SHADER_BIT; + info.access |= VK_ACCESS_SHADER_READ_BIT + | VK_ACCESS_SHADER_WRITE_BIT; + } + + if (m_desc.CPUAccessFlags & D3D11_CPU_ACCESS_WRITE) { + info.stages |= VK_PIPELINE_STAGE_HOST_BIT; + info.access |= VK_ACCESS_HOST_WRITE_BIT; + } + + if (m_desc.CPUAccessFlags & D3D11_CPU_ACCESS_READ) { + info.stages |= VK_PIPELINE_STAGE_HOST_BIT; + info.access |= VK_ACCESS_HOST_READ_BIT; + } + + if (m_desc.MiscFlags & D3D11_RESOURCE_MISC_DRAWINDIRECT_ARGS) { + info.usage |= VK_BUFFER_USAGE_INDIRECT_BUFFER_BIT; + info.stages |= VK_PIPELINE_STAGE_DRAW_INDIRECT_BIT; + info.access |= VK_ACCESS_INDIRECT_COMMAND_READ_BIT; + } + + return m_device->GetDXVKDevice()->createBuffer(info, memoryType); + } + } diff --git a/src/d3d11/d3d11_buffer.h b/src/d3d11/d3d11_buffer.h index 801e27f2..7ede40ff 100644 --- a/src/d3d11/d3d11_buffer.h +++ b/src/d3d11/d3d11_buffer.h @@ -34,6 +34,9 @@ namespace dxvk { Com m_device; D3D11_BUFFER_DESC m_desc; + Rc m_buffer; + + Rc createBuffer(); }; diff --git a/src/d3d11/d3d11_device.cpp b/src/d3d11/d3d11_device.cpp index d74a950b..ed28b71e 100644 --- a/src/d3d11/d3d11_device.cpp +++ b/src/d3d11/d3d11_device.cpp @@ -47,13 +47,12 @@ namespace dxvk { if (ppBuffer == nullptr) return S_OK; - if (pInitialData != nullptr) { - Logger::err("D3D11Device::CreateBuffer: pInitialData != NULL not supported"); - return E_FAIL; - } - try { *ppBuffer = ref(new D3D11Buffer(this, *pDesc)); + + if (pInitialData != nullptr) + Logger::warn("D3D11Device::CreateBuffer: pInitialData != NULL not supported"); + return S_OK; } catch (const DxvkError& e) { Logger::err(e.message());