mirror of
https://github.com/doitsujin/dxvk.git
synced 2025-03-01 19:29:16 +01:00
[dxvk] Add way to create partial pipeline layouts
This commit is contained in:
parent
3b10efbc30
commit
30c25ee1f0
@ -208,8 +208,8 @@ namespace dxvk {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
DxvkBindingLayout::DxvkBindingLayout()
|
DxvkBindingLayout::DxvkBindingLayout(VkShaderStageFlags stages)
|
||||||
: m_pushConst { 0, 0, 0 } {
|
: m_pushConst { 0, 0, 0 }, m_stages(stages) {
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -219,6 +219,21 @@ namespace dxvk {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
uint32_t DxvkBindingLayout::getSetMask() const {
|
||||||
|
uint32_t mask = 0;
|
||||||
|
|
||||||
|
if (m_stages & (VK_SHADER_STAGE_COMPUTE_BIT | VK_SHADER_STAGE_FRAGMENT_BIT)) {
|
||||||
|
mask |= (1u << DxvkDescriptorSets::FsViews)
|
||||||
|
| (1u << DxvkDescriptorSets::FsBuffers);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (m_stages & (VK_SHADER_STAGE_COMPUTE_BIT | VK_SHADER_STAGE_VERTEX_BIT))
|
||||||
|
mask |= (1u << DxvkDescriptorSets::VsAll);
|
||||||
|
|
||||||
|
return mask;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void DxvkBindingLayout::addBinding(const DxvkBindingInfo& binding) {
|
void DxvkBindingLayout::addBinding(const DxvkBindingInfo& binding) {
|
||||||
uint32_t set = binding.computeSetIndex();
|
uint32_t set = binding.computeSetIndex();
|
||||||
m_bindings[set].addBinding(binding);
|
m_bindings[set].addBinding(binding);
|
||||||
@ -244,6 +259,9 @@ namespace dxvk {
|
|||||||
|
|
||||||
|
|
||||||
bool DxvkBindingLayout::eq(const DxvkBindingLayout& other) const {
|
bool DxvkBindingLayout::eq(const DxvkBindingLayout& other) const {
|
||||||
|
if (m_stages != other.m_stages)
|
||||||
|
return false;
|
||||||
|
|
||||||
for (uint32_t i = 0; i < m_bindings.size(); i++) {
|
for (uint32_t i = 0; i < m_bindings.size(); i++) {
|
||||||
if (!m_bindings[i].eq(other.m_bindings[i]))
|
if (!m_bindings[i].eq(other.m_bindings[i]))
|
||||||
return false;
|
return false;
|
||||||
@ -260,6 +278,7 @@ namespace dxvk {
|
|||||||
|
|
||||||
size_t DxvkBindingLayout::hash() const {
|
size_t DxvkBindingLayout::hash() const {
|
||||||
DxvkHashState hash;
|
DxvkHashState hash;
|
||||||
|
hash.add(m_stages);
|
||||||
|
|
||||||
for (uint32_t i = 0; i < m_bindings.size(); i++)
|
for (uint32_t i = 0; i < m_bindings.size(); i++)
|
||||||
hash.add(m_bindings[i].hash());
|
hash.add(m_bindings[i].hash());
|
||||||
@ -278,26 +297,30 @@ namespace dxvk {
|
|||||||
: m_device(device), m_layout(layout) {
|
: m_device(device), m_layout(layout) {
|
||||||
auto vk = m_device->vkd();
|
auto vk = m_device->vkd();
|
||||||
|
|
||||||
std::array<VkDescriptorSetLayout, DxvkDescriptorSets::SetCount> setLayouts;
|
std::array<VkDescriptorSetLayout, DxvkDescriptorSets::SetCount> setLayouts = { };
|
||||||
|
|
||||||
for (uint32_t i = 0; i < DxvkDescriptorSets::SetCount; i++) {
|
for (uint32_t i = 0; i < DxvkDescriptorSets::SetCount; i++) {
|
||||||
m_bindingObjects[i] = setObjects[i];
|
m_bindingObjects[i] = setObjects[i];
|
||||||
setLayouts[i] = setObjects[i]->getSetLayout();
|
|
||||||
|
|
||||||
uint32_t bindingCount = m_layout.getBindingCount(i);
|
// Sets can be null for partial layouts
|
||||||
|
if (setObjects[i]) {
|
||||||
|
setLayouts[i] = setObjects[i]->getSetLayout();
|
||||||
|
|
||||||
for (uint32_t j = 0; j < bindingCount; j++) {
|
uint32_t bindingCount = m_layout.getBindingCount(i);
|
||||||
const DxvkBindingInfo& binding = m_layout.getBinding(i, j);
|
|
||||||
|
|
||||||
DxvkBindingMapping mapping;
|
for (uint32_t j = 0; j < bindingCount; j++) {
|
||||||
mapping.set = i;
|
const DxvkBindingInfo& binding = m_layout.getBinding(i, j);
|
||||||
mapping.binding = j;
|
|
||||||
|
|
||||||
m_mapping.insert({ binding.resourceBinding, mapping });
|
DxvkBindingMapping mapping;
|
||||||
|
mapping.set = i;
|
||||||
|
mapping.binding = j;
|
||||||
|
|
||||||
|
m_mapping.insert({ binding.resourceBinding, mapping });
|
||||||
|
}
|
||||||
|
|
||||||
|
if (bindingCount)
|
||||||
|
m_setMask |= 1u << i;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (bindingCount)
|
|
||||||
m_setMask |= 1u << i;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
VkPushConstantRange pushConst = m_layout.getPushConstantRange();
|
VkPushConstantRange pushConst = m_layout.getPushConstantRange();
|
||||||
@ -306,6 +329,9 @@ namespace dxvk {
|
|||||||
pipelineLayoutInfo.setLayoutCount = setLayouts.size();
|
pipelineLayoutInfo.setLayoutCount = setLayouts.size();
|
||||||
pipelineLayoutInfo.pSetLayouts = setLayouts.data();
|
pipelineLayoutInfo.pSetLayouts = setLayouts.data();
|
||||||
|
|
||||||
|
if (m_layout.getSetMask() != (1u << DxvkDescriptorSets::SetCount) - 1)
|
||||||
|
pipelineLayoutInfo.flags = VK_PIPELINE_LAYOUT_CREATE_INDEPENDENT_SETS_BIT_EXT;
|
||||||
|
|
||||||
if (pushConst.stageFlags && pushConst.size) {
|
if (pushConst.stageFlags && pushConst.size) {
|
||||||
pipelineLayoutInfo.pushConstantRangeCount = 1;
|
pipelineLayoutInfo.pushConstantRangeCount = 1;
|
||||||
pipelineLayoutInfo.pPushConstantRanges = &pushConst;
|
pipelineLayoutInfo.pPushConstantRanges = &pushConst;
|
||||||
|
@ -261,7 +261,7 @@ namespace dxvk {
|
|||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
DxvkBindingLayout();
|
DxvkBindingLayout(VkShaderStageFlags stages);
|
||||||
~DxvkBindingLayout();
|
~DxvkBindingLayout();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -304,6 +304,14 @@ namespace dxvk {
|
|||||||
return m_pushConst;
|
return m_pushConst;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* \brief Queries defined descriptor set layouts
|
||||||
|
*
|
||||||
|
* Any set layout not included in this must be null.
|
||||||
|
* \returns Bit mask of defined descriptor sets
|
||||||
|
*/
|
||||||
|
uint32_t getSetMask() const;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* \brief Adds a binding to the layout
|
* \brief Adds a binding to the layout
|
||||||
* \param [in] binding Binding info
|
* \param [in] binding Binding info
|
||||||
@ -345,6 +353,7 @@ namespace dxvk {
|
|||||||
|
|
||||||
std::array<DxvkBindingList, DxvkDescriptorSets::SetCount> m_bindings;
|
std::array<DxvkBindingList, DxvkDescriptorSets::SetCount> m_bindings;
|
||||||
VkPushConstantRange m_pushConst;
|
VkPushConstantRange m_pushConst;
|
||||||
|
VkShaderStageFlags m_stages;
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -52,7 +52,7 @@ namespace dxvk {
|
|||||||
if (pair != m_graphicsPipelines.end())
|
if (pair != m_graphicsPipelines.end())
|
||||||
return &pair->second;
|
return &pair->second;
|
||||||
|
|
||||||
DxvkBindingLayout mergedLayout;
|
DxvkBindingLayout mergedLayout(VK_SHADER_STAGE_ALL_GRAPHICS);
|
||||||
mergedLayout.merge(shaders.vs->getBindings());
|
mergedLayout.merge(shaders.vs->getBindings());
|
||||||
|
|
||||||
if (shaders.tcs != nullptr)
|
if (shaders.tcs != nullptr)
|
||||||
@ -157,9 +157,12 @@ namespace dxvk {
|
|||||||
return &pair->second;
|
return &pair->second;
|
||||||
|
|
||||||
std::array<const DxvkBindingSetLayout*, DxvkDescriptorSets::SetCount> setLayouts = { };
|
std::array<const DxvkBindingSetLayout*, DxvkDescriptorSets::SetCount> setLayouts = { };
|
||||||
|
uint32_t setMask = layout.getSetMask();
|
||||||
|
|
||||||
for (uint32_t i = 0; i < setLayouts.size(); i++)
|
for (uint32_t i = 0; i < setLayouts.size(); i++) {
|
||||||
setLayouts[i] = createDescriptorSetLayout(layout.getBindingList(i));
|
if (setMask & (1u << i))
|
||||||
|
setLayouts[i] = createDescriptorSetLayout(layout.getBindingList(i));
|
||||||
|
}
|
||||||
|
|
||||||
auto iter = m_pipelineLayouts.emplace(
|
auto iter = m_pipelineLayouts.emplace(
|
||||||
std::piecewise_construct,
|
std::piecewise_construct,
|
||||||
|
@ -63,7 +63,7 @@ namespace dxvk {
|
|||||||
DxvkShader::DxvkShader(
|
DxvkShader::DxvkShader(
|
||||||
const DxvkShaderCreateInfo& info,
|
const DxvkShaderCreateInfo& info,
|
||||||
SpirvCodeBuffer&& spirv)
|
SpirvCodeBuffer&& spirv)
|
||||||
: m_info(info), m_code(spirv) {
|
: m_info(info), m_code(spirv), m_bindings(info.stage) {
|
||||||
m_info.uniformData = nullptr;
|
m_info.uniformData = nullptr;
|
||||||
m_info.bindings = nullptr;
|
m_info.bindings = nullptr;
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user