mirror of
https://github.com/doitsujin/dxvk.git
synced 2025-01-19 05:52:11 +01:00
[dxvk] Spill render pass for pipelines that use vertex stage UAVs
We cannot use simple pipeline barriers in this case because of the extremely strict restrictions surrounding self-dependencies.
This commit is contained in:
parent
76b63efedb
commit
e15e693dc4
@ -3032,8 +3032,15 @@ namespace dxvk {
|
||||
|
||||
|
||||
void DxvkContext::commitGraphicsPostBarriers() {
|
||||
if (m_state.gp.flags.test(DxvkGraphicsPipelineFlag::HasStorageDescriptors)) {
|
||||
// FIXME support vertex stage SSBO synchronization
|
||||
bool fs = m_state.gp.flags.test(DxvkGraphicsPipelineFlag::HasFsStorageDescriptors);
|
||||
bool vs = m_state.gp.flags.test(DxvkGraphicsPipelineFlag::HasVsStorageDescriptors);
|
||||
|
||||
if (vs) {
|
||||
// External subpass dependencies serve as full memory
|
||||
// and execution barriers, so we can use this to allow
|
||||
// inter-stage synchronization.
|
||||
this->spillRenderPass();
|
||||
} else if (fs) {
|
||||
this->emitMemoryBarrier(
|
||||
VK_PIPELINE_STAGE_FRAGMENT_SHADER_BIT,
|
||||
VK_ACCESS_SHADER_WRITE_BIT,
|
||||
|
@ -73,8 +73,13 @@ namespace dxvk {
|
||||
if (gs != nullptr && gs->hasCapability(spv::CapabilityTransformFeedback))
|
||||
m_flags.set(DxvkGraphicsPipelineFlag::HasTransformFeedback);
|
||||
|
||||
if (m_layout->hasStorageDescriptors())
|
||||
m_flags.set(DxvkGraphicsPipelineFlag::HasStorageDescriptors);
|
||||
VkShaderStageFlags stoStages = m_layout->getStorageDescriptorStages();
|
||||
|
||||
if (stoStages & VK_SHADER_STAGE_FRAGMENT_BIT)
|
||||
m_flags.set(DxvkGraphicsPipelineFlag::HasFsStorageDescriptors);
|
||||
|
||||
if (stoStages & ~VK_SHADER_STAGE_FRAGMENT_BIT)
|
||||
m_flags.set(DxvkGraphicsPipelineFlag::HasVsStorageDescriptors);
|
||||
|
||||
m_common.msSampleShadingEnable = fs != nullptr && fs->hasCapability(spv::CapabilitySampleRateShading);
|
||||
m_common.msSampleShadingFactor = 1.0f;
|
||||
|
@ -21,7 +21,8 @@ namespace dxvk {
|
||||
*/
|
||||
enum class DxvkGraphicsPipelineFlag {
|
||||
HasTransformFeedback,
|
||||
HasStorageDescriptors,
|
||||
HasFsStorageDescriptors,
|
||||
HasVsStorageDescriptors,
|
||||
};
|
||||
|
||||
using DxvkGraphicsPipelineFlags = Flags<DxvkGraphicsPipelineFlag>;
|
||||
|
@ -224,13 +224,23 @@ namespace dxvk {
|
||||
* It is assumed that storage images and buffers
|
||||
* will be written to if they are present. Used
|
||||
* for synchronization purposes.
|
||||
* \param [in] stages Shader stages to check
|
||||
*/
|
||||
bool hasStorageDescriptors() const {
|
||||
return m_descriptorTypes.any(
|
||||
VK_DESCRIPTOR_TYPE_STORAGE_IMAGE,
|
||||
VK_DESCRIPTOR_TYPE_STORAGE_BUFFER,
|
||||
VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC,
|
||||
VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER);
|
||||
VkShaderStageFlags getStorageDescriptorStages() const {
|
||||
VkShaderStageFlags stages = 0;
|
||||
|
||||
for (const auto& slot : m_bindingSlots) {
|
||||
bool isStorageDescriptor =
|
||||
slot.type == VK_DESCRIPTOR_TYPE_STORAGE_BUFFER ||
|
||||
slot.type == VK_DESCRIPTOR_TYPE_STORAGE_BUFFER_DYNAMIC ||
|
||||
slot.type == VK_DESCRIPTOR_TYPE_STORAGE_TEXEL_BUFFER ||
|
||||
slot.type == VK_DESCRIPTOR_TYPE_STORAGE_IMAGE;
|
||||
|
||||
if (isStorageDescriptor)
|
||||
stages |= slot.stages;
|
||||
}
|
||||
|
||||
return stages;
|
||||
}
|
||||
|
||||
private:
|
||||
|
Loading…
x
Reference in New Issue
Block a user