Commit d1462228 by Shahbaz Youssefi Committed by Commit Bot

Vulkan: Use VK_EXT_multisampled_render_to_single_sampled

Additionally, makes the emulation path not require independentResolveNone. This was only used to select the NONE resolve mode when the attachment format doesn't have either of depth or stencil aspects, but it's ok to specify the same resolve mode for both aspects even if one aspect is missing. Bug: chromium:1088005 Change-Id: Ifc37cbf5331145179c5927853b996a0d62b871ee Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/2743666Reviewed-by: 's avatarDavid Reveman <reveman@chromium.org> Reviewed-by: 's avatarJamie Madill <jmadill@chromium.org> Reviewed-by: 's avatarTim Van Patten <timvp@google.com> Commit-Queue: Shahbaz Youssefi <syoussefi@chromium.org>
parent c4da42e1
...@@ -218,6 +218,13 @@ struct FeaturesVk : FeatureSetBase ...@@ -218,6 +218,13 @@ struct FeaturesVk : FeatureSetBase
"extension with the independentResolveNone feature", "extension with the independentResolveNone feature",
&members, "http://anglebug.com/4836"}; &members, "http://anglebug.com/4836"};
// Whether the VkDevice supports the VK_EXT_multisampled_render_to_single_sampled extension.
// http://anglebug.com/4836
Feature supportsMultisampledRenderToSingleSampled = {
"supportsMultisampledRenderToSingleSampled", FeatureCategory::VulkanFeatures,
"VkDevice supports the VK_EXT_multisampled_render_to_single_sampled extension", &members,
"http://anglebug.com/4836"};
// VK_PRESENT_MODE_FIFO_KHR causes random timeouts on Linux Intel. http://anglebug.com/3153 // VK_PRESENT_MODE_FIFO_KHR causes random timeouts on Linux Intel. http://anglebug.com/3153
Feature disableFifoPresentMode = {"disableFifoPresentMode", FeatureCategory::VulkanWorkarounds, Feature disableFifoPresentMode = {"disableFifoPresentMode", FeatureCategory::VulkanWorkarounds,
"VK_PRESENT_MODE_FIFO_KHR causes random timeouts", &members, "VK_PRESENT_MODE_FIFO_KHR causes random timeouts", &members,
......
...@@ -16,6 +16,36 @@ ...@@ -16,6 +16,36 @@
# include <vulkan/vulkan.h> # include <vulkan/vulkan.h>
#endif #endif
// For the unreleased VK_EXT_multisampled_render_to_single_sampled
#if !defined(VK_EXT_multisampled_render_to_single_sampled)
# define VK_EXT_multisampled_render_to_single_sampled 1
# define VK_EXT_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_SPEC_VERSION 1
# define VK_EXT_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_EXTENSION_NAME \
"VK_EXT_multisampled_render_to_single_sampled"
# define VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_FEATURES_EXT \
((VkStructureType)(1000376000))
# define VK_STRUCTURE_TYPE_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_INFO_EXT \
((VkStructureType)(1000376001))
typedef struct VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT
{
VkStructureType sType;
const void *pNext;
VkBool32 multisampledRenderToSingleSampled;
} VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT;
typedef struct VkMultisampledRenderToSingleSampledInfoEXT
{
VkStructureType sType;
const void *pNext;
VkBool32 multisampledRenderToSingleSampledEnable;
VkSampleCountFlagBits rasterizationSamples;
VkResolveModeFlagBits depthResolveMode;
VkResolveModeFlagBits stencilResolveMode;
} VkMultisampledRenderToSingleSampledInfoEXT;
#endif /* VK_EXT_multisampled_render_to_single_sampled */
#if !defined(ANGLE_SHARED_LIBVULKAN) #if !defined(ANGLE_SHARED_LIBVULKAN)
namespace rx namespace rx
......
...@@ -117,6 +117,10 @@ class FramebufferAttachment final ...@@ -117,6 +117,10 @@ class FramebufferAttachment final
bool isMultiview() const; bool isMultiview() const;
GLint getBaseViewIndex() const; GLint getBaseViewIndex() const;
bool isRenderToTexture() const
{
return mRenderToTextureSamples != kDefaultRenderToTextureSamples;
}
GLsizei getRenderToTextureSamples() const { return mRenderToTextureSamples; } GLsizei getRenderToTextureSamples() const { return mRenderToTextureSamples; }
// The size of the underlying resource the attachment points to. The 'depth' value will // The size of the underlying resource the attachment points to. The 'depth' value will
......
...@@ -1938,11 +1938,7 @@ void FramebufferVk::updateRenderPassDesc(ContextVk *contextVk) ...@@ -1938,11 +1938,7 @@ void FramebufferVk::updateRenderPassDesc(ContextVk *contextVk)
// Add the resolve attachment, if any. // Add the resolve attachment, if any.
if (depthStencilRenderTarget->hasResolveAttachment()) if (depthStencilRenderTarget->hasResolveAttachment())
{ {
const vk::Format &format = depthStencilRenderTarget->getImageFormat(); mRenderPassDesc.packDepthStencilResolveAttachment();
bool hasDepth = format.intendedFormat().depthBits > 0;
bool hasStencil = format.intendedFormat().stencilBits > 0;
mRenderPassDesc.packDepthStencilResolveAttachment(hasDepth, hasStencil);
} }
} }
...@@ -1962,6 +1958,31 @@ void FramebufferVk::updateRenderPassDesc(ContextVk *contextVk) ...@@ -1962,6 +1958,31 @@ void FramebufferVk::updateRenderPassDesc(ContextVk *contextVk)
mRenderPassDesc.setFramebufferFetchMode(programUsesFramebufferFetch); mRenderPassDesc.setFramebufferFetchMode(programUsesFramebufferFetch);
} }
if (contextVk->getFeatures().supportsMultisampledRenderToSingleSampled.enabled)
{
// Update descriptions regarding multisampled-render-to-texture use.
bool isRenderToTexture = false;
for (size_t colorIndexGL : mState.getEnabledDrawBuffers())
{
const gl::FramebufferAttachment *color = mState.getColorAttachment(colorIndexGL);
ASSERT(color);
if (color->isRenderToTexture())
{
isRenderToTexture = true;
break;
}
}
const gl::FramebufferAttachment *depthStencil = mState.getDepthStencilAttachment();
if (depthStencil && depthStencil->isRenderToTexture())
{
isRenderToTexture = true;
}
mCurrentFramebufferDesc.updateRenderToTexture(isRenderToTexture);
mRenderPassDesc.updateRenderToTexture(isRenderToTexture);
}
mCurrentFramebufferDesc.updateUnresolveMask({}); mCurrentFramebufferDesc.updateUnresolveMask({});
mRenderPassDesc.setWriteControlMode(mCurrentFramebufferDesc.getWriteControlMode()); mRenderPassDesc.setWriteControlMode(mCurrentFramebufferDesc.getWriteControlMode());
} }
...@@ -2731,23 +2752,35 @@ gl::Rectangle FramebufferVk::getRotatedScissoredRenderArea(ContextVk *contextVk) ...@@ -2731,23 +2752,35 @@ gl::Rectangle FramebufferVk::getRotatedScissoredRenderArea(ContextVk *contextVk)
return rotatedScissoredArea; return rotatedScissoredArea;
} }
RenderTargetVk *FramebufferVk::getFirstRenderTarget() const GLint FramebufferVk::getSamples() const
{ {
for (auto *renderTarget : mRenderTargetCache.getColors()) const gl::FramebufferAttachment *lastAttachment = nullptr;
for (size_t colorIndexGL : mState.getEnabledDrawBuffers())
{ {
if (renderTarget) const gl::FramebufferAttachment *color = mState.getColorAttachment(colorIndexGL);
ASSERT(color);
if (color->isRenderToTexture())
{ {
return renderTarget; return color->getSamples();
} }
}
return getDepthStencilRenderTarget(); lastAttachment = color;
} }
const gl::FramebufferAttachment *depthStencil = mState.getDepthOrStencilAttachment();
if (depthStencil)
{
if (depthStencil->isRenderToTexture())
{
return depthStencil->getSamples();
}
lastAttachment = depthStencil;
}
GLint FramebufferVk::getSamples() const // If none of the attachments are multisampled-render-to-texture, take the sample count from the
{ // last attachment (any would have worked, as they would all have the same sample count).
RenderTargetVk *firstRT = getFirstRenderTarget(); return std::max(lastAttachment ? lastAttachment->getSamples() : 1, 1);
return firstRT ? firstRT->getImageForRenderPass().getSamples() : 1;
} }
angle::Result FramebufferVk::flushDeferredClears(ContextVk *contextVk) angle::Result FramebufferVk::flushDeferredClears(ContextVk *contextVk)
......
...@@ -141,7 +141,6 @@ class FramebufferVk : public FramebufferImpl ...@@ -141,7 +141,6 @@ class FramebufferVk : public FramebufferImpl
vk::CommandBuffer **commandBufferOut, vk::CommandBuffer **commandBufferOut,
bool *renderPassDescChangedOut); bool *renderPassDescChangedOut);
RenderTargetVk *getFirstRenderTarget() const;
GLint getSamples() const; GLint getSamples() const;
const vk::RenderPassDesc &getRenderPassDesc() const { return mRenderPassDesc; } const vk::RenderPassDesc &getRenderPassDesc() const { return mRenderPassDesc; }
......
...@@ -88,13 +88,15 @@ angle::Result RenderbufferVk::setStorageImpl(const gl::Context *context, ...@@ -88,13 +88,15 @@ angle::Result RenderbufferVk::setStorageImpl(const gl::Context *context,
const bool isRenderToTexture = const bool isRenderToTexture =
mode == gl::MultisamplingMode::MultisampledRenderToTexture && mode == gl::MultisamplingMode::MultisampledRenderToTexture &&
(!isDepthStencilFormat || renderer->getFeatures().supportsDepthStencilResolve.enabled); (!isDepthStencilFormat || renderer->getFeatures().supportsDepthStencilResolve.enabled);
const bool hasRenderToTextureEXT =
renderer->getFeatures().supportsMultisampledRenderToSingleSampled.enabled;
const VkImageUsageFlags usage = const VkImageUsageFlags usage =
VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_BIT | VK_IMAGE_USAGE_TRANSFER_SRC_BIT |
VK_IMAGE_USAGE_SAMPLED_BIT | VK_IMAGE_USAGE_SAMPLED_BIT |
(isDepthStencilFormat ? VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT (isDepthStencilFormat ? VK_IMAGE_USAGE_DEPTH_STENCIL_ATTACHMENT_BIT
: VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT) | : VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT) |
(isRenderToTexture ? VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT : 0); (isRenderToTexture && !hasRenderToTextureEXT ? VK_IMAGE_USAGE_INPUT_ATTACHMENT_BIT : 0);
const uint32_t imageSamples = isRenderToTexture ? 1 : samples; const uint32_t imageSamples = isRenderToTexture ? 1 : samples;
...@@ -112,7 +114,7 @@ angle::Result RenderbufferVk::setStorageImpl(const gl::Context *context, ...@@ -112,7 +114,7 @@ angle::Result RenderbufferVk::setStorageImpl(const gl::Context *context,
// If multisampled render to texture, an implicit multisampled image is created which is used as // If multisampled render to texture, an implicit multisampled image is created which is used as
// the color or depth/stencil attachment. At the end of the render pass, this image is // the color or depth/stencil attachment. At the end of the render pass, this image is
// automatically resolved into |mImage| and its contents are discarded. // automatically resolved into |mImage| and its contents are discarded.
if (isRenderToTexture) if (isRenderToTexture && !hasRenderToTextureEXT)
{ {
mMultisampledImageViews.init(renderer); mMultisampledImageViews.init(renderer);
......
...@@ -991,6 +991,10 @@ void RendererVk::queryDeviceExtensionFeatures(const vk::ExtensionNameList &devic ...@@ -991,6 +991,10 @@ void RendererVk::queryDeviceExtensionFeatures(const vk::ExtensionNameList &devic
mDepthStencilResolveProperties.sType = mDepthStencilResolveProperties.sType =
VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_STENCIL_RESOLVE_PROPERTIES; VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_STENCIL_RESOLVE_PROPERTIES;
mMultisampledRenderToSingleSampledFeatures = {};
mMultisampledRenderToSingleSampledFeatures.sType =
VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_FEATURES_EXT;
mDriverProperties = {}; mDriverProperties = {};
mDriverProperties.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DRIVER_PROPERTIES; mDriverProperties.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DRIVER_PROPERTIES;
...@@ -1077,6 +1081,13 @@ void RendererVk::queryDeviceExtensionFeatures(const vk::ExtensionNameList &devic ...@@ -1077,6 +1081,13 @@ void RendererVk::queryDeviceExtensionFeatures(const vk::ExtensionNameList &devic
vk::AddToPNextChain(&deviceProperties, &mDepthStencilResolveProperties); vk::AddToPNextChain(&deviceProperties, &mDepthStencilResolveProperties);
} }
// Query multisampled render to single-sampled properties
if (ExtensionFound(VK_EXT_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_EXTENSION_NAME,
deviceExtensionNames))
{
vk::AddToPNextChain(&deviceFeatures, &mMultisampledRenderToSingleSampledFeatures);
}
// Query driver properties // Query driver properties
if (ExtensionFound(VK_KHR_DRIVER_PROPERTIES_EXTENSION_NAME, deviceExtensionNames)) if (ExtensionFound(VK_KHR_DRIVER_PROPERTIES_EXTENSION_NAME, deviceExtensionNames))
{ {
...@@ -1112,19 +1123,20 @@ void RendererVk::queryDeviceExtensionFeatures(const vk::ExtensionNameList &devic ...@@ -1112,19 +1123,20 @@ void RendererVk::queryDeviceExtensionFeatures(const vk::ExtensionNameList &devic
} }
// Clean up pNext chains // Clean up pNext chains
mLineRasterizationFeatures.pNext = nullptr; mLineRasterizationFeatures.pNext = nullptr;
mMemoryReportFeatures.pNext = nullptr; mMemoryReportFeatures.pNext = nullptr;
mProvokingVertexFeatures.pNext = nullptr; mProvokingVertexFeatures.pNext = nullptr;
mVertexAttributeDivisorFeatures.pNext = nullptr; mVertexAttributeDivisorFeatures.pNext = nullptr;
mVertexAttributeDivisorProperties.pNext = nullptr; mVertexAttributeDivisorProperties.pNext = nullptr;
mTransformFeedbackFeatures.pNext = nullptr; mTransformFeedbackFeatures.pNext = nullptr;
mIndexTypeUint8Features.pNext = nullptr; mIndexTypeUint8Features.pNext = nullptr;
mSubgroupProperties.pNext = nullptr; mSubgroupProperties.pNext = nullptr;
mExternalMemoryHostProperties.pNext = nullptr; mExternalMemoryHostProperties.pNext = nullptr;
mShaderFloat16Int8Features.pNext = nullptr; mShaderFloat16Int8Features.pNext = nullptr;
mDepthStencilResolveProperties.pNext = nullptr; mDepthStencilResolveProperties.pNext = nullptr;
mDriverProperties.pNext = nullptr; mMultisampledRenderToSingleSampledFeatures.pNext = nullptr;
mSamplerYcbcrConversionFeatures.pNext = nullptr; mDriverProperties.pNext = nullptr;
mSamplerYcbcrConversionFeatures.pNext = nullptr;
} }
angle::Result RendererVk::initializeDevice(DisplayVk *displayVk, uint32_t queueFamilyIndex) angle::Result RendererVk::initializeDevice(DisplayVk *displayVk, uint32_t queueFamilyIndex)
...@@ -1469,6 +1481,13 @@ angle::Result RendererVk::initializeDevice(DisplayVk *displayVk, uint32_t queueF ...@@ -1469,6 +1481,13 @@ angle::Result RendererVk::initializeDevice(DisplayVk *displayVk, uint32_t queueF
enabledDeviceExtensions.push_back(VK_KHR_DEPTH_STENCIL_RESOLVE_EXTENSION_NAME); enabledDeviceExtensions.push_back(VK_KHR_DEPTH_STENCIL_RESOLVE_EXTENSION_NAME);
} }
if (getFeatures().supportsMultisampledRenderToSingleSampled.enabled)
{
enabledDeviceExtensions.push_back(
VK_EXT_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_EXTENSION_NAME);
vk::AddToPNextChain(&createInfo, &mMultisampledRenderToSingleSampledFeatures);
}
if (mMemoryReportFeatures.deviceMemoryReport && if (mMemoryReportFeatures.deviceMemoryReport &&
(getFeatures().logMemoryReportCallbacks.enabled || (getFeatures().logMemoryReportCallbacks.enabled ||
getFeatures().logMemoryReportStats.enabled)) getFeatures().logMemoryReportStats.enabled))
...@@ -2034,7 +2053,13 @@ void RendererVk::initFeatures(DisplayVk *displayVk, ...@@ -2034,7 +2053,13 @@ void RendererVk::initFeatures(DisplayVk *displayVk,
ANGLE_FEATURE_CONDITION(&mFeatures, supportsDepthStencilResolve, ANGLE_FEATURE_CONDITION(&mFeatures, supportsDepthStencilResolve,
mFeatures.supportsRenderpass2.enabled && mFeatures.supportsRenderpass2.enabled &&
mDepthStencilResolveProperties.independentResolveNone == VK_TRUE); mDepthStencilResolveProperties.supportedDepthResolveModes != 0);
ANGLE_FEATURE_CONDITION(
&mFeatures, supportsMultisampledRenderToSingleSampled,
mFeatures.supportsRenderpass2.enabled && mFeatures.supportsDepthStencilResolve.enabled &&
mMultisampledRenderToSingleSampledFeatures.multisampledRenderToSingleSampled ==
VK_TRUE);
ANGLE_FEATURE_CONDITION(&mFeatures, emulateTransformFeedback, ANGLE_FEATURE_CONDITION(&mFeatures, emulateTransformFeedback,
(!mFeatures.supportsTransformFeedbackExtension.enabled && (!mFeatures.supportsTransformFeedbackExtension.enabled &&
...@@ -2130,8 +2155,10 @@ void RendererVk::initFeatures(DisplayVk *displayVk, ...@@ -2130,8 +2155,10 @@ void RendererVk::initFeatures(DisplayVk *displayVk,
// - Swiftshader on mac: http://anglebug.com/4937 // - Swiftshader on mac: http://anglebug.com/4937
// - Intel on windows: http://anglebug.com/5032 // - Intel on windows: http://anglebug.com/5032
// - AMD on windows: http://crbug.com/1132366 // - AMD on windows: http://crbug.com/1132366
ANGLE_FEATURE_CONDITION(&mFeatures, enableMultisampledRenderToTexture, ANGLE_FEATURE_CONDITION(
!(IsApple() && isSwiftShader) && !(IsWindows() && (isIntel || isAMD))); &mFeatures, enableMultisampledRenderToTexture,
mFeatures.supportsMultisampledRenderToSingleSampled.enabled ||
!(IsApple() && isSwiftShader) && !(IsWindows() && (isIntel || isAMD)));
// Feature disabled due to driver bugs: // Feature disabled due to driver bugs:
// //
......
...@@ -419,6 +419,8 @@ class RendererVk : angle::NonCopyable ...@@ -419,6 +419,8 @@ class RendererVk : angle::NonCopyable
VkPhysicalDeviceExternalMemoryHostPropertiesEXT mExternalMemoryHostProperties; VkPhysicalDeviceExternalMemoryHostPropertiesEXT mExternalMemoryHostProperties;
VkPhysicalDeviceShaderFloat16Int8FeaturesKHR mShaderFloat16Int8Features; VkPhysicalDeviceShaderFloat16Int8FeaturesKHR mShaderFloat16Int8Features;
VkPhysicalDeviceDepthStencilResolvePropertiesKHR mDepthStencilResolveProperties; VkPhysicalDeviceDepthStencilResolvePropertiesKHR mDepthStencilResolveProperties;
VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT
mMultisampledRenderToSingleSampledFeatures;
VkPhysicalDeviceDriverPropertiesKHR mDriverProperties; VkPhysicalDeviceDriverPropertiesKHR mDriverProperties;
VkExternalFenceProperties mExternalFenceProperties; VkExternalFenceProperties mExternalFenceProperties;
VkExternalSemaphoreProperties mExternalSemaphoreProperties; VkExternalSemaphoreProperties mExternalSemaphoreProperties;
......
...@@ -2117,13 +2117,18 @@ angle::Result TextureVk::getAttachmentRenderTarget(const gl::Context *context, ...@@ -2117,13 +2117,18 @@ angle::Result TextureVk::getAttachmentRenderTarget(const gl::Context *context,
levelCount)); levelCount));
} }
const bool hasRenderToTextureEXT =
contextVk->getFeatures().supportsMultisampledRenderToSingleSampled.enabled;
// If samples > 1 here, we have a singlesampled texture that's being multisampled rendered to. // If samples > 1 here, we have a singlesampled texture that's being multisampled rendered to.
// In this case, create a multisampled image that is otherwise identical to the single sampled // In this case, create a multisampled image that is otherwise identical to the single sampled
// image. That multisampled image is used as color or depth/stencil attachment, while the // image. That multisampled image is used as color or depth/stencil attachment, while the
// original image is used as the resolve attachment. // original image is used as the resolve attachment.
const gl::RenderToTextureImageIndex renderToTextureIndex = const gl::RenderToTextureImageIndex renderToTextureIndex =
static_cast<gl::RenderToTextureImageIndex>(PackSampleCount(samples)); hasRenderToTextureEXT
if (samples > 1 && !mMultisampledImages[renderToTextureIndex].valid()) ? gl::RenderToTextureImageIndex::Default
: static_cast<gl::RenderToTextureImageIndex>(PackSampleCount(samples));
if (samples > 1 && !mMultisampledImages[renderToTextureIndex].valid() && !hasRenderToTextureEXT)
{ {
ASSERT(mState.getBaseLevelDesc().samples <= 1); ASSERT(mState.getBaseLevelDesc().samples <= 1);
vk::ImageHelper *multisampledImage = &mMultisampledImages[renderToTextureIndex]; vk::ImageHelper *multisampledImage = &mMultisampledImages[renderToTextureIndex];
......
...@@ -157,7 +157,7 @@ class alignas(4) RenderPassDesc final ...@@ -157,7 +157,7 @@ class alignas(4) RenderPassDesc final
void packColorUnresolveAttachment(size_t colorIndexGL); void packColorUnresolveAttachment(size_t colorIndexGL);
void removeColorUnresolveAttachment(size_t colorIndexGL); void removeColorUnresolveAttachment(size_t colorIndexGL);
// Indicate that a depth/stencil attachment should have a corresponding resolve attachment. // Indicate that a depth/stencil attachment should have a corresponding resolve attachment.
void packDepthStencilResolveAttachment(bool resolveDepth, bool resolveStencil); void packDepthStencilResolveAttachment();
// Indicate that a depth/stencil attachment should take its data from the resolve attachment // Indicate that a depth/stencil attachment should take its data from the resolve attachment
// initially. // initially.
void packDepthStencilUnresolveAttachment(bool unresolveDepth, bool unresolveStencil); void packDepthStencilUnresolveAttachment(bool unresolveDepth, bool unresolveStencil);
...@@ -187,15 +187,7 @@ class alignas(4) RenderPassDesc final ...@@ -187,15 +187,7 @@ class alignas(4) RenderPassDesc final
} }
bool hasDepthStencilResolveAttachment() const bool hasDepthStencilResolveAttachment() const
{ {
return (mAttachmentFormats.back() & (kResolveDepthFlag | kResolveStencilFlag)) != 0; return (mAttachmentFormats.back() & kResolveDepthStencilFlag) != 0;
}
bool hasDepthResolveAttachment() const
{
return (mAttachmentFormats.back() & kResolveDepthFlag) != 0;
}
bool hasStencilResolveAttachment() const
{
return (mAttachmentFormats.back() & kResolveStencilFlag) != 0;
} }
bool hasDepthStencilUnresolveAttachment() const bool hasDepthStencilUnresolveAttachment() const
{ {
...@@ -227,6 +219,9 @@ class alignas(4) RenderPassDesc final ...@@ -227,6 +219,9 @@ class alignas(4) RenderPassDesc final
void setFramebufferFetchMode(bool hasFramebufferFetch); void setFramebufferFetchMode(bool hasFramebufferFetch);
bool getFramebufferFetchMode() const { return mHasFramebufferFetch; } bool getFramebufferFetchMode() const { return mHasFramebufferFetch; }
void updateRenderToTexture(bool isRenderToTexture);
bool isRenderToTexture() const { return (mAttachmentFormats.back() & kIsRenderToTexture) != 0; }
angle::FormatID operator[](size_t index) const angle::FormatID operator[](size_t index) const
{ {
ASSERT(index < gl::IMPLEMENTATION_MAX_DRAW_BUFFERS + 1); ASSERT(index < gl::IMPLEMENTATION_MAX_DRAW_BUFFERS + 1);
...@@ -248,17 +243,14 @@ class alignas(4) RenderPassDesc final ...@@ -248,17 +243,14 @@ class alignas(4) RenderPassDesc final
// Whether each color attachment has a corresponding resolve attachment. Color resolve // Whether each color attachment has a corresponding resolve attachment. Color resolve
// attachments can be used to optimize resolve through glBlitFramebuffer() as well as support // attachments can be used to optimize resolve through glBlitFramebuffer() as well as support
// GL_EXT_multisampled_render_to_texture and GL_EXT_multisampled_render_to_texture2. // GL_EXT_multisampled_render_to_texture and GL_EXT_multisampled_render_to_texture2.
//
// Note that depth/stencil resolve attachments require VK_KHR_depth_stencil_resolve which is
// currently not well supported, so ANGLE always takes a fallback path for them. When a resolve
// path is implemented for depth/stencil attachments, another bit must be made free
// (mAttachmentFormats is one element too large, so there are 8 bits there to take).
gl::DrawBufferMask mColorResolveAttachmentMask; gl::DrawBufferMask mColorResolveAttachmentMask;
// Whether each color attachment with a corresponding resolve attachment should be initialized // Whether each color attachment with a corresponding resolve attachment should be initialized
// with said resolve attachment in an initial subpass. This is an optimization to avoid // with said resolve attachment in an initial subpass. This is an optimization to avoid
// loadOp=LOAD on the implicit multisampled image used with multisampled-render-to-texture // loadOp=LOAD on the implicit multisampled image used with multisampled-render-to-texture
// render targets. This operation is referred to as "unresolve". // render targets. This operation is referred to as "unresolve".
//
// Unused when VK_EXT_multisampled_render_to_single_sampled is available.
gl::DrawBufferMask mColorUnresolveAttachmentMask; gl::DrawBufferMask mColorUnresolveAttachmentMask;
// Color attachment formats are stored with their GL attachment indices. The depth/stencil // Color attachment formats are stored with their GL attachment indices. The depth/stencil
...@@ -293,11 +285,11 @@ class alignas(4) RenderPassDesc final ...@@ -293,11 +285,11 @@ class alignas(4) RenderPassDesc final
static constexpr uint8_t kDepthStencilFormatStorageMask = 0x7; static constexpr uint8_t kDepthStencilFormatStorageMask = 0x7;
// Flags stored in the upper 5 bits of mAttachmentFormats.back(). // Flags stored in the upper 5 bits of mAttachmentFormats.back().
static constexpr uint8_t kResolveDepthFlag = 0x80; static constexpr uint8_t kIsRenderToTexture = 0x80;
static constexpr uint8_t kResolveStencilFlag = 0x40; static constexpr uint8_t kResolveDepthStencilFlag = 0x40;
static constexpr uint8_t kUnresolveDepthFlag = 0x20; static constexpr uint8_t kUnresolveDepthFlag = 0x20;
static constexpr uint8_t kUnresolveStencilFlag = 0x10; static constexpr uint8_t kUnresolveStencilFlag = 0x10;
static constexpr uint8_t kSrgbWriteControlFlag = 0x08; static constexpr uint8_t kSrgbWriteControlFlag = 0x08;
}; };
bool operator==(const RenderPassDesc &lhs, const RenderPassDesc &rhs); bool operator==(const RenderPassDesc &lhs, const RenderPassDesc &rhs);
...@@ -1195,6 +1187,8 @@ class FramebufferDesc ...@@ -1195,6 +1187,8 @@ class FramebufferDesc
uint32_t getLayerCount() const { return mLayerCount; } uint32_t getLayerCount() const { return mLayerCount; }
void updateFramebufferFetchMode(bool hasFramebufferFetch); void updateFramebufferFetchMode(bool hasFramebufferFetch);
void updateRenderToTexture(bool isRenderToTexture);
private: private:
void reset(); void reset();
void update(uint32_t index, ImageOrBufferViewSubresourceSerial serial); void update(uint32_t index, ImageOrBufferViewSubresourceSerial serial);
...@@ -1213,7 +1207,11 @@ class FramebufferDesc ...@@ -1213,7 +1207,11 @@ class FramebufferDesc
// If the render pass contains an initial subpass to unresolve a number of attachments, the // If the render pass contains an initial subpass to unresolve a number of attachments, the
// subpass description is derived from the following mask, specifying which attachments need // subpass description is derived from the following mask, specifying which attachments need
// to be unresolved. Includes both color and depth/stencil attachments. // to be unresolved. Includes both color and depth/stencil attachments.
FramebufferNonResolveAttachmentMask mUnresolveAttachmentMask; uint16_t mUnresolveAttachmentMask : kMaxFramebufferNonResolveAttachments;
// Whether this is a multisampled-render-to-single-sampled framebuffer. Only used when using
// VK_EXT_multisampled_render_to_single_sampled. Only one bit is used and the rest is padding.
uint16_t mIsRenderToTexture : 16 - kMaxFramebufferNonResolveAttachments;
FramebufferAttachmentArray<ImageOrBufferViewSubresourceSerial> mSerials; FramebufferAttachmentArray<ImageOrBufferViewSubresourceSerial> mSerials;
}; };
......
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