Commit 054aeeed by Charlie Lao Committed by Commit Bot

Vulkan: Batch vkUpdateDescriptorSets calls

Right now we are making this calls multiple times as we loop through each shader stage. Qualcomm performance validation layer warns about this. This change will aggregate the calls into one call per dispatch. Bug: b/158787299 Change-Id: I48aa3752f708c26ffbca2fb7947cb8bbc0f76dcd Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/2243321 Commit-Queue: Charlie Lao <cclao@google.com> Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Reviewed-by: 's avatarShahbaz Youssefi <syoussefi@chromium.org> Reviewed-by: 's avatarCourtney Goeltzenleuchter <courtneygo@google.com> Reviewed-by: 's avatarTim Van Patten <timvp@google.com>
parent 70e706f4
......@@ -47,6 +47,12 @@ namespace rx
namespace
{
// For DesciptorSetUpdates
constexpr size_t kDescriptorBufferInfosInitialSize = 8;
constexpr size_t kDescriptorImageInfosInitialSize = 4;
constexpr size_t kDescriptorWriteInfosInitialSize =
kDescriptorBufferInfosInitialSize + kDescriptorImageInfosInitialSize;
// For shader uniforms such as gl_DepthRange and the viewport size.
struct GraphicsDriverUniforms
{
......@@ -620,7 +626,10 @@ ContextVk::ContextVk(const gl::State &state, gl::ErrorSet *errorSet, RendererVk
mPrimaryBufferCounter(0),
mRenderPassCounter(0),
mContextPriority(renderer->getDriverPriority(GetContextPriority(state))),
mCurrentIndirectBuffer(nullptr)
mCurrentIndirectBuffer(nullptr),
mBufferInfos(),
mImageInfos(),
mWriteInfos()
{
ANGLE_TRACE_EVENT0("gpu.angle", "ContextVk::ContextVk");
memset(&mClearColorValue, 0, sizeof(mClearColorValue));
......@@ -709,6 +718,11 @@ ContextVk::ContextVk(const gl::State &state, gl::ErrorSet *errorSet, RendererVk
mPipelineDirtyBitsMask.set();
mPipelineDirtyBitsMask.reset(gl::State::DIRTY_BIT_TEXTURE_BINDINGS);
// Reserve reasonable amount of spaces so that for majority of apps we don't need to grow at all
mBufferInfos.reserve(kDescriptorBufferInfosInitialSize);
mImageInfos.reserve(kDescriptorImageInfosInitialSize);
mWriteInfos.reserve(kDescriptorWriteInfosInitialSize);
}
ContextVk::~ContextVk() = default;
......@@ -935,6 +949,10 @@ angle::Result ContextVk::setupDraw(const gl::Context *context,
*commandBufferOut = mRenderPassCommandBuffer;
ASSERT(*commandBufferOut);
// Create a local object to ensure we flush the descriptor updates to device when we leave this
// function
ScopedDescriptorSetUpdates descriptorSetUpdates(this);
if (mProgram && mProgram->dirtyUniforms())
{
ANGLE_TRY(mProgram->updateUniforms(this));
......@@ -1163,6 +1181,10 @@ angle::Result ContextVk::setupDispatch(const gl::Context *context,
ANGLE_TRY(endRenderPass());
*commandBufferOut = &mOutsideRenderPassCommands->getCommandBuffer();
// Create a local object to ensure we flush the descriptor updates to device when we leave this
// function
ScopedDescriptorSetUpdates descriptorSetUpdates(this);
if (mProgram && mProgram->dirtyUniforms())
{
ANGLE_TRY(mProgram->updateUniforms(this));
......@@ -3600,23 +3622,21 @@ angle::Result ContextVk::updateDriverUniformsDescriptorSet(
&driverUniforms->descriptorPoolBinding, &driverUniforms->descriptorSet));
// Update the driver uniform descriptor set.
VkDescriptorBufferInfo bufferInfo = {};
bufferInfo.buffer = buffer;
bufferInfo.offset = 0;
bufferInfo.range = driverUniformsSize;
VkWriteDescriptorSet writeInfo = {};
writeInfo.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
writeInfo.dstSet = driverUniforms->descriptorSet;
writeInfo.dstBinding = 0;
writeInfo.dstArrayElement = 0;
writeInfo.descriptorCount = 1;
writeInfo.descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC;
writeInfo.pImageInfo = nullptr;
writeInfo.pTexelBufferView = nullptr;
writeInfo.pBufferInfo = &bufferInfo;
vkUpdateDescriptorSets(getDevice(), 1, &writeInfo, 0, nullptr);
VkDescriptorBufferInfo &bufferInfo = allocBufferInfo();
bufferInfo.buffer = buffer;
bufferInfo.offset = 0;
bufferInfo.range = driverUniformsSize;
VkWriteDescriptorSet &writeInfo = allocWriteInfo();
writeInfo.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
writeInfo.dstSet = driverUniforms->descriptorSet;
writeInfo.dstBinding = 0;
writeInfo.dstArrayElement = 0;
writeInfo.descriptorCount = 1;
writeInfo.descriptorType = VK_DESCRIPTOR_TYPE_UNIFORM_BUFFER_DYNAMIC;
writeInfo.pImageInfo = nullptr;
writeInfo.pTexelBufferView = nullptr;
writeInfo.pBufferInfo = &bufferInfo;
return angle::Result::Continue;
}
......@@ -4474,4 +4494,74 @@ bool ContextVk::isRobustResourceInitEnabled() const
return mState.isRobustResourceInitEnabled();
}
VkDescriptorBufferInfo &ContextVk::allocBufferInfos(size_t count)
{
return allocInfos<VkDescriptorBufferInfo, &VkWriteDescriptorSet::pBufferInfo>(&mBufferInfos,
count);
}
VkDescriptorImageInfo &ContextVk::allocImageInfos(size_t count)
{
return allocInfos<VkDescriptorImageInfo, &VkWriteDescriptorSet::pImageInfo>(&mImageInfos,
count);
}
template <typename T, const T *VkWriteDescriptorSet::*pInfo>
T &ContextVk::allocInfos(std::vector<T> *mInfos, size_t count)
{
size_t oldSize = mInfos->size();
size_t newSize = oldSize + count;
if (newSize > mInfos->capacity())
{
// If we have reached capacity, grow the storage and patch the descriptor set with new
// buffer info pointer
growCapacity<T, pInfo>(mInfos, newSize);
}
mInfos->resize(newSize);
return (*mInfos)[oldSize];
}
template <typename T, const T *VkWriteDescriptorSet::*pInfo>
void ContextVk::growCapacity(std::vector<T> *mInfos, size_t newSize)
{
const T *const oldInfoStart = mInfos->empty() ? nullptr : &(*mInfos)[0];
size_t newCapacity = std::max(mInfos->capacity() << 1, newSize);
mInfos->reserve(newCapacity);
if (oldInfoStart)
{
// patch mWriteInfo with new BufferInfo/ImageInfo pointers
for (VkWriteDescriptorSet &set : mWriteInfos)
{
if (set.*pInfo)
{
size_t index = set.*pInfo - oldInfoStart;
set.*pInfo = &(*mInfos)[index];
}
}
}
}
// ScopedDescriptorSetUpdates
ANGLE_INLINE ContextVk::ScopedDescriptorSetUpdates::ScopedDescriptorSetUpdates(ContextVk *contextVk)
: mContextVk(contextVk)
{}
ANGLE_INLINE ContextVk::ScopedDescriptorSetUpdates::~ScopedDescriptorSetUpdates()
{
if (mContextVk->mWriteInfos.empty())
{
ASSERT(mContextVk->mBufferInfos.empty());
ASSERT(mContextVk->mImageInfos.empty());
return;
}
vkUpdateDescriptorSets(mContextVk->getDevice(),
static_cast<uint32_t>(mContextVk->mWriteInfos.size()),
mContextVk->mWriteInfos.data(), 0, nullptr);
mContextVk->mWriteInfos.clear();
mContextVk->mBufferInfos.clear();
mContextVk->mImageInfos.clear();
}
} // namespace rx
......@@ -526,6 +526,20 @@ class ContextVk : public ContextImpl, public vk::Context
// When worker thread completes, it releases command buffers back to context queue
void recycleCommandBuffer(vk::CommandBufferHelper *commandBuffer);
// DescriptorSet writes
VkDescriptorBufferInfo &allocBufferInfo() { return allocBufferInfos(1); }
VkDescriptorBufferInfo &allocBufferInfos(size_t count);
VkDescriptorImageInfo &allocImageInfo() { return allocImageInfos(1); }
VkDescriptorImageInfo &allocImageInfos(size_t count);
VkWriteDescriptorSet &allocWriteInfo() { return allocWriteInfos(1); }
VkWriteDescriptorSet &allocWriteInfos(size_t count)
{
size_t oldSize = mWriteInfos.size();
size_t newSize = oldSize + count;
mWriteInfos.resize(newSize);
return mWriteInfos[oldSize];
}
private:
// Dirty bits.
enum DirtyBitType : size_t
......@@ -616,6 +630,7 @@ class ContextVk : public ContextImpl, public vk::Context
const void *indices,
DirtyBits dirtyBitMask,
vk::CommandBuffer **commandBufferOut);
angle::Result setupIndexedDraw(const gl::Context *context,
gl::PrimitiveMode mode,
GLsizei indexCount,
......@@ -800,6 +815,12 @@ class ContextVk : public ContextImpl, public vk::Context
size_t bufferCount,
const gl::TransformFeedbackBuffersArray<vk::BufferHelper *> &buffers);
// DescriptorSet writes
template <typename T, const T *VkWriteDescriptorSet::*pInfo>
T &allocInfos(std::vector<T> *mInfos, size_t count);
template <typename T, const T *VkWriteDescriptorSet::*pInfo>
void growCapacity(std::vector<T> *mInfos, size_t newSize);
std::array<DirtyBitHandler, DIRTY_BIT_MAX> mGraphicsDirtyBitHandlers;
std::array<DirtyBitHandler, DIRTY_BIT_MAX> mComputeDirtyBitHandlers;
......@@ -976,6 +997,20 @@ class ContextVk : public ContextImpl, public vk::Context
const vk::BufferHelper *mCurrentIndirectBuffer;
// Storage for vkUpdateDescriptorSets
std::vector<VkDescriptorBufferInfo> mBufferInfos;
std::vector<VkDescriptorImageInfo> mImageInfos;
std::vector<VkWriteDescriptorSet> mWriteInfos;
class ScopedDescriptorSetUpdates final : angle::NonCopyable
{
public:
ScopedDescriptorSetUpdates(ContextVk *contextVk);
~ScopedDescriptorSetUpdates();
private:
ContextVk *mContextVk;
};
std::vector<std::string> mCommandBufferDiagnostics;
};
......
......@@ -832,9 +832,9 @@ void ProgramExecutableVk::updateDefaultUniformsDescriptorSet(
return;
}
DefaultUniformBlock &uniformBlock = defaultUniformBlocks[shaderType];
VkDescriptorBufferInfo bufferInfo;
VkWriteDescriptorSet writeInfo;
DefaultUniformBlock &uniformBlock = defaultUniformBlocks[shaderType];
VkWriteDescriptorSet &writeInfo = contextVk->allocWriteInfo();
VkDescriptorBufferInfo &bufferInfo = contextVk->allocBufferInfo();
if (!uniformBlock.uniformData.empty())
{
......@@ -862,10 +862,6 @@ void ProgramExecutableVk::updateDefaultUniformsDescriptorSet(
writeInfo.pImageInfo = nullptr;
writeInfo.pBufferInfo = &bufferInfo;
writeInfo.pTexelBufferView = nullptr;
VkDevice device = contextVk->getDevice();
vkUpdateDescriptorSets(device, 1, &writeInfo, 0, nullptr);
}
void ProgramExecutableVk::updateBuffersDescriptorSet(ContextVk *contextVk,
......@@ -891,10 +887,6 @@ void ProgramExecutableVk::updateBuffersDescriptorSet(ContextVk *contextVk,
gl::IMPLEMENTATION_MAX_UNIFORM_BUFFER_BINDINGS,
"The descriptor arrays here would have inadequate size for uniform buffer objects");
gl::StorageBuffersArray<VkDescriptorBufferInfo> descriptorBufferInfo;
gl::StorageBuffersArray<VkWriteDescriptorSet> writeDescriptorInfo;
uint32_t writeCount = 0;
// Write uniform or storage buffers.
const gl::State &glState = contextVk->getState();
for (uint32_t bufferIndex = 0; bufferIndex < blocks.size(); ++bufferIndex)
......@@ -933,8 +925,8 @@ void ProgramExecutableVk::updateBuffersDescriptorSet(ContextVk *contextVk,
"VkDeviceSize too small");
ASSERT(bufferBinding.getSize() >= 0);
VkDescriptorBufferInfo &bufferInfo = descriptorBufferInfo[writeCount];
VkWriteDescriptorSet &writeInfo = writeDescriptorInfo[writeCount];
VkDescriptorBufferInfo &bufferInfo = contextVk->allocBufferInfo();
VkWriteDescriptorSet &writeInfo = contextVk->allocWriteInfo();
BufferVk *bufferVk = vk::GetImpl(bufferBinding.get());
vk::BufferHelper &bufferHelper = bufferVk->getBuffer();
......@@ -955,13 +947,7 @@ void ProgramExecutableVk::updateBuffersDescriptorSet(ContextVk *contextVk,
commandBufferHelper->bufferRead(resourceUseList, VK_ACCESS_UNIFORM_READ_BIT,
kPipelineStageShaderMap[shaderType], &bufferHelper);
}
++writeCount;
}
VkDevice device = contextVk->getDevice();
vkUpdateDescriptorSets(device, writeCount, writeDescriptorInfo.data(), 0, nullptr);
}
void ProgramExecutableVk::updateAtomicCounterBuffersDescriptorSet(
......@@ -990,8 +976,6 @@ void ProgramExecutableVk::updateAtomicCounterBuffersDescriptorSet(
return;
}
gl::AtomicCounterBuffersArray<VkDescriptorBufferInfo> descriptorBufferInfo;
gl::AtomicCounterBuffersArray<VkWriteDescriptorSet> writeDescriptorInfo;
gl::AtomicCounterBufferMask writtenBindings;
RendererVk *rendererVk = contextVk->getRenderer();
......@@ -1011,8 +995,8 @@ void ProgramExecutableVk::updateAtomicCounterBuffersDescriptorSet(
continue;
}
VkDescriptorBufferInfo &bufferInfo = descriptorBufferInfo[binding];
VkWriteDescriptorSet &writeInfo = writeDescriptorInfo[binding];
VkDescriptorBufferInfo &bufferInfo = contextVk->allocBufferInfo();
VkWriteDescriptorSet &writeInfo = contextVk->allocWriteInfo();
BufferVk *bufferVk = vk::GetImpl(bufferBinding.get());
vk::BufferHelper &bufferHelper = bufferVk->getBuffer();
......@@ -1033,31 +1017,28 @@ void ProgramExecutableVk::updateAtomicCounterBuffersDescriptorSet(
// Bind the empty buffer to every array slot that's unused.
mEmptyBuffer.retain(&contextVk->getResourceUseList());
size_t count = (~writtenBindings).count();
VkDescriptorBufferInfo *bufferInfos = &contextVk->allocBufferInfos(count);
VkWriteDescriptorSet *writeInfos = &contextVk->allocWriteInfos(count);
size_t writeCount = 0;
for (size_t binding : ~writtenBindings)
{
VkDescriptorBufferInfo &bufferInfo = descriptorBufferInfo[binding];
VkWriteDescriptorSet &writeInfo = writeDescriptorInfo[binding];
bufferInfo.buffer = mEmptyBuffer.getBuffer().getHandle();
bufferInfo.offset = 0;
bufferInfo.range = VK_WHOLE_SIZE;
writeInfo.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
writeInfo.pNext = nullptr;
writeInfo.dstSet = descriptorSet;
writeInfo.dstBinding = info.binding;
writeInfo.dstArrayElement = static_cast<uint32_t>(binding);
writeInfo.descriptorCount = 1;
writeInfo.descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
writeInfo.pImageInfo = nullptr;
writeInfo.pBufferInfo = &bufferInfo;
writeInfo.pTexelBufferView = nullptr;
bufferInfos[writeCount].buffer = mEmptyBuffer.getBuffer().getHandle();
bufferInfos[writeCount].offset = 0;
bufferInfos[writeCount].range = VK_WHOLE_SIZE;
writeInfos[writeCount].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
writeInfos[writeCount].pNext = nullptr;
writeInfos[writeCount].dstSet = descriptorSet;
writeInfos[writeCount].dstBinding = info.binding;
writeInfos[writeCount].dstArrayElement = static_cast<uint32_t>(binding);
writeInfos[writeCount].descriptorCount = 1;
writeInfos[writeCount].descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
writeInfos[writeCount].pImageInfo = nullptr;
writeInfos[writeCount].pBufferInfo = &bufferInfos[writeCount];
writeInfos[writeCount].pTexelBufferView = nullptr;
writeCount++;
}
VkDevice device = contextVk->getDevice();
vkUpdateDescriptorSets(device, gl::IMPLEMENTATION_MAX_ATOMIC_COUNTER_BUFFERS,
writeDescriptorInfo.data(), 0, nullptr);
}
angle::Result ProgramExecutableVk::updateImagesDescriptorSet(
......@@ -1078,10 +1059,6 @@ angle::Result ProgramExecutableVk::updateImagesDescriptorSet(
const gl::ActiveTextureArray<TextureVk *> &activeImages = contextVk->getActiveImages();
gl::ImagesArray<VkDescriptorImageInfo> descriptorImageInfo;
gl::ImagesArray<VkWriteDescriptorSet> writeDescriptorInfo;
uint32_t writeCount = 0;
// Write images.
for (uint32_t imageIndex = 0; imageIndex < imageBindings.size(); ++imageIndex)
{
......@@ -1117,8 +1094,8 @@ angle::Result ProgramExecutableVk::updateImagesDescriptorSet(
// TODO(syoussefi): Support image data reinterpretation by using binding.format.
// http://anglebug.com/3563
VkDescriptorImageInfo &imageInfo = descriptorImageInfo[writeCount];
VkWriteDescriptorSet &writeInfo = writeDescriptorInfo[writeCount];
VkDescriptorImageInfo &imageInfo = contextVk->allocImageInfo();
VkWriteDescriptorSet &writeInfo = contextVk->allocWriteInfo();
imageInfo.sampler = VK_NULL_HANDLE;
imageInfo.imageView = imageView->getHandle();
......@@ -1134,15 +1111,9 @@ angle::Result ProgramExecutableVk::updateImagesDescriptorSet(
writeInfo.pImageInfo = &imageInfo;
writeInfo.pBufferInfo = nullptr;
writeInfo.pTexelBufferView = nullptr;
++writeCount;
}
}
VkDevice device = contextVk->getDevice();
vkUpdateDescriptorSets(device, writeCount, writeDescriptorInfo.data(), 0, nullptr);
return angle::Result::Continue;
}
......@@ -1267,10 +1238,6 @@ angle::Result ProgramExecutableVk::updateTexturesDescriptorSet(ContextVk *contex
VkDescriptorSet descriptorSet = mDescriptorSets[kTextureDescriptorSetIndex];
gl::ActiveTextureArray<VkDescriptorImageInfo> descriptorImageInfo;
gl::ActiveTextureArray<VkWriteDescriptorSet> writeDescriptorInfo;
uint32_t writeCount = 0;
const gl::ActiveTextureArray<vk::TextureUnit> &activeTextures = contextVk->getActiveTextures();
bool emulateSeamfulCubeMapSampling = contextVk->emulateSeamfulCubeMapSampling();
......@@ -1312,6 +1279,8 @@ angle::Result ProgramExecutableVk::updateTexturesDescriptorSet(ContextVk *contex
mappedSamplerNameToArrayOffset[mappedSamplerName] += arraySize;
}
VkDescriptorImageInfo *imageInfos = &contextVk->allocImageInfos(arraySize);
VkWriteDescriptorSet *writeInfos = &contextVk->allocWriteInfos(arraySize);
for (uint32_t arrayElement = 0; arrayElement < arraySize; ++arrayElement)
{
GLuint textureUnit = samplerBinding.boundTextureUnits[arrayElement];
......@@ -1320,26 +1289,24 @@ angle::Result ProgramExecutableVk::updateTexturesDescriptorSet(ContextVk *contex
vk::ImageHelper &image = textureVk->getImage();
VkDescriptorImageInfo &imageInfo = descriptorImageInfo[writeCount];
// Use bound sampler object if one present, otherwise use texture's sampler
const vk::Sampler &sampler =
(samplerVk != nullptr) ? samplerVk->getSampler() : textureVk->getSampler();
imageInfo.sampler = sampler.getHandle();
imageInfo.imageLayout = image.getCurrentLayout();
imageInfos[arrayElement].sampler = sampler.getHandle();
imageInfos[arrayElement].imageLayout = image.getCurrentLayout();
if (emulateSeamfulCubeMapSampling)
{
// If emulating seamful cubemapping, use the fetch image view. This is
// basically the same image view as read, except it's a 2DArray view for
// cube maps.
imageInfo.imageView =
imageInfos[arrayElement].imageView =
textureVk->getFetchImageViewAndRecordUse(contextVk).getHandle();
}
else
{
imageInfo.imageView =
imageInfos[arrayElement].imageView =
textureVk->getReadImageViewAndRecordUse(contextVk).getHandle();
}
......@@ -1350,30 +1317,20 @@ angle::Result ProgramExecutableVk::updateTexturesDescriptorSet(ContextVk *contex
: GlslangGetMappedSamplerName(samplerUniform.name);
ShaderInterfaceVariableInfo &info = variableInfoMap[samplerName];
VkWriteDescriptorSet &writeInfo = writeDescriptorInfo[writeCount];
writeInfo.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
writeInfo.pNext = nullptr;
writeInfo.dstSet = descriptorSet;
writeInfo.dstBinding = info.binding;
writeInfo.dstArrayElement = arrayOffset + arrayElement;
writeInfo.descriptorCount = 1;
writeInfo.descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
writeInfo.pImageInfo = &imageInfo;
writeInfo.pBufferInfo = nullptr;
writeInfo.pTexelBufferView = nullptr;
++writeCount;
writeInfos[arrayElement].sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
writeInfos[arrayElement].pNext = nullptr;
writeInfos[arrayElement].dstSet = descriptorSet;
writeInfos[arrayElement].dstBinding = info.binding;
writeInfos[arrayElement].dstArrayElement = arrayOffset + arrayElement;
writeInfos[arrayElement].descriptorCount = 1;
writeInfos[arrayElement].descriptorType = VK_DESCRIPTOR_TYPE_COMBINED_IMAGE_SAMPLER;
writeInfos[arrayElement].pImageInfo = &imageInfos[arrayElement];
writeInfos[arrayElement].pBufferInfo = nullptr;
writeInfos[arrayElement].pTexelBufferView = nullptr;
}
}
}
VkDevice device = contextVk->getDevice();
ASSERT(writeCount > 0);
vkUpdateDescriptorSets(device, writeCount, writeDescriptorInfo.data(), 0, nullptr);
mTextureDescriptorsCache.emplace(texturesDesc, descriptorSet);
return angle::Result::Continue;
......
......@@ -193,7 +193,7 @@ void TransformFeedbackVk::initDescriptorSet(ContextVk *contextVk,
if (!contextVk->getFeatures().emulateTransformFeedback.enabled)
return;
gl::TransformFeedbackBuffersArray<VkDescriptorBufferInfo> descriptorBufferInfo;
VkDescriptorBufferInfo *descriptorBufferInfo = &contextVk->allocBufferInfos(xfbBufferCount);
for (size_t bufferIndex = 0; bufferIndex < xfbBufferCount; ++bufferIndex)
{
......@@ -203,7 +203,7 @@ void TransformFeedbackVk::initDescriptorSet(ContextVk *contextVk,
bufferInfo.range = VK_WHOLE_SIZE;
}
writeDescriptorSet(contextVk, xfbBufferCount, descriptorBufferInfo.data(), descSet);
writeDescriptorSet(contextVk, xfbBufferCount, descriptorBufferInfo, descSet);
}
void TransformFeedbackVk::updateDescriptorSet(ContextVk *contextVk,
......@@ -221,7 +221,7 @@ void TransformFeedbackVk::updateDescriptorSet(ContextVk *contextVk,
ASSERT(programState.getTransformFeedbackBufferMode() != GL_INTERLEAVED_ATTRIBS ||
xfbBufferCount == 1);
gl::TransformFeedbackBuffersArray<VkDescriptorBufferInfo> descriptorBufferInfo;
VkDescriptorBufferInfo *descriptorBufferInfo = &contextVk->allocBufferInfos(xfbBufferCount);
// Update buffer descriptor binding info for output buffers
for (size_t bufferIndex = 0; bufferIndex < xfbBufferCount; ++bufferIndex)
......@@ -235,7 +235,7 @@ void TransformFeedbackVk::updateDescriptorSet(ContextVk *contextVk,
ASSERT(bufferInfo.range != 0);
}
writeDescriptorSet(contextVk, xfbBufferCount, descriptorBufferInfo.data(), descSet);
writeDescriptorSet(contextVk, xfbBufferCount, descriptorBufferInfo, descSet);
}
void TransformFeedbackVk::getBufferOffsets(ContextVk *contextVk,
......@@ -281,25 +281,22 @@ void TransformFeedbackVk::writeDescriptorSet(ContextVk *contextVk,
VkDescriptorBufferInfo *pBufferInfo,
VkDescriptorSet descSet) const
{
VkDevice device = contextVk->getDevice();
ProgramExecutableVk *executableVk = contextVk->getExecutable();
ShaderMapInterfaceVariableInfoMap variableInfoMap =
executableVk->getShaderInterfaceVariableInfoMap();
const std::string bufferName = GetXfbBufferName(0);
ShaderInterfaceVariableInfo &info = variableInfoMap[gl::ShaderType::Vertex][bufferName];
VkWriteDescriptorSet writeDescriptorInfo = {};
writeDescriptorInfo.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
writeDescriptorInfo.dstSet = descSet;
writeDescriptorInfo.dstBinding = info.binding;
writeDescriptorInfo.dstArrayElement = 0;
writeDescriptorInfo.descriptorCount = static_cast<uint32_t>(xfbBufferCount);
writeDescriptorInfo.descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
writeDescriptorInfo.pImageInfo = nullptr;
writeDescriptorInfo.pBufferInfo = pBufferInfo;
writeDescriptorInfo.pTexelBufferView = nullptr;
vkUpdateDescriptorSets(device, 1, &writeDescriptorInfo, 0, nullptr);
VkWriteDescriptorSet &writeDescriptorInfo = contextVk->allocWriteInfo();
writeDescriptorInfo.sType = VK_STRUCTURE_TYPE_WRITE_DESCRIPTOR_SET;
writeDescriptorInfo.dstSet = descSet;
writeDescriptorInfo.dstBinding = info.binding;
writeDescriptorInfo.dstArrayElement = 0;
writeDescriptorInfo.descriptorCount = static_cast<uint32_t>(xfbBufferCount);
writeDescriptorInfo.descriptorType = VK_DESCRIPTOR_TYPE_STORAGE_BUFFER;
writeDescriptorInfo.pImageInfo = nullptr;
writeDescriptorInfo.pBufferInfo = pBufferInfo;
writeDescriptorInfo.pTexelBufferView = nullptr;
}
} // namespace rx
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment