aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorGravatar egdaniel <egdaniel@google.com>2016-06-08 06:48:09 -0700
committerGravatar Commit bot <commit-bot@chromium.org>2016-06-08 06:48:10 -0700
commit2feb0938dcf223da3641daf15f5d525db88a6967 (patch)
tree1d62a546adbe261f1d4bf61bf8310c712fdfc7cb
parentdae6b97705fde08958b1a36fa6ce685d28fc692c (diff)
Add support for finding/creating general GrVkRenderPass from the VkResourceProvider.
-rw-r--r--src/gpu/vk/GrVkRenderPass.cpp67
-rw-r--r--src/gpu/vk/GrVkRenderPass.h47
-rw-r--r--src/gpu/vk/GrVkRenderTarget.h1
-rw-r--r--src/gpu/vk/GrVkResourceProvider.cpp46
-rw-r--r--src/gpu/vk/GrVkResourceProvider.h31
5 files changed, 164 insertions, 28 deletions
diff --git a/src/gpu/vk/GrVkRenderPass.cpp b/src/gpu/vk/GrVkRenderPass.cpp
index c56bafa92d..6a0f953a1c 100644
--- a/src/gpu/vk/GrVkRenderPass.cpp
+++ b/src/gpu/vk/GrVkRenderPass.cpp
@@ -23,16 +23,16 @@ void setup_vk_attachment_description(VkAttachmentDescription* attachment,
SkAssertResult(GrSampleCountToVkSampleCount(desc.fSamples, &attachment->samples));
switch (layout) {
case VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL:
- attachment->loadOp = desc.fLoadOp;
- attachment->storeOp = desc.fStoreOp;
+ attachment->loadOp = desc.fLoadStoreOps.fLoadOp;
+ attachment->storeOp = desc.fLoadStoreOps.fStoreOp;
attachment->stencilLoadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachment->stencilStoreOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
break;
case VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL:
attachment->loadOp = VK_ATTACHMENT_LOAD_OP_DONT_CARE;
attachment->storeOp = VK_ATTACHMENT_STORE_OP_DONT_CARE;
- attachment->stencilLoadOp = desc.fLoadOp;
- attachment->stencilStoreOp = desc.fStoreOp;
+ attachment->stencilLoadOp = desc.fLoadStoreOps.fLoadOp;
+ attachment->stencilStoreOp = desc.fLoadStoreOps.fStoreOp;
break;
default:
SkFAIL("Unexpected attachment layout");
@@ -43,15 +43,21 @@ void setup_vk_attachment_description(VkAttachmentDescription* attachment,
}
void GrVkRenderPass::initSimple(const GrVkGpu* gpu, const GrVkRenderTarget& target) {
- // Get attachment information from render target. This includes which attachments the render
- // target has (color, resolve, stencil) and the attachments format and sample count.
- target.getAttachmentsDescriptor(&fAttachmentsDescriptor, &fAttachmentFlags);
+ static const GrVkRenderPass::LoadStoreOps kBasicLoadStoreOps(VK_ATTACHMENT_LOAD_OP_LOAD,
+ VK_ATTACHMENT_STORE_OP_STORE);
+ this->init(gpu, target, kBasicLoadStoreOps, kBasicLoadStoreOps, kBasicLoadStoreOps);
+}
+
+void GrVkRenderPass::init(const GrVkGpu* gpu,
+ const LoadStoreOps& colorOp,
+ const LoadStoreOps& resolveOp,
+ const LoadStoreOps& stencilOp) {
uint32_t numAttachments = fAttachmentsDescriptor.fAttachmentCount;
// Attachment descriptions to be set on the render pass
SkTArray<VkAttachmentDescription> attachments(numAttachments);
attachments.reset(numAttachments);
- memset(attachments.begin(), 0, numAttachments*sizeof(VkAttachmentDescription));
+ memset(attachments.begin(), 0, numAttachments * sizeof(VkAttachmentDescription));
// Refs to attachments on the render pass (as described by teh VkAttachmentDescription above),
// that are used by the subpass.
@@ -70,6 +76,7 @@ void GrVkRenderPass::initSimple(const GrVkGpu* gpu, const GrVkRenderTarget& targ
subpassDesc.pInputAttachments = nullptr;
if (fAttachmentFlags & kColor_AttachmentFlag) {
// set up color attachment
+ fAttachmentsDescriptor.fColor.fLoadStoreOps = colorOp;
setup_vk_attachment_description(&attachments[currentAttachment],
fAttachmentsDescriptor.fColor,
VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL);
@@ -88,6 +95,7 @@ void GrVkRenderPass::initSimple(const GrVkGpu* gpu, const GrVkRenderTarget& targ
if (fAttachmentFlags & kResolve_AttachmentFlag) {
// set up resolve attachment
+ fAttachmentsDescriptor.fResolve.fLoadStoreOps = resolveOp;
setup_vk_attachment_description(&attachments[currentAttachment],
fAttachmentsDescriptor.fResolve,
VK_IMAGE_LAYOUT_COLOR_ATTACHMENT_OPTIMAL);
@@ -102,6 +110,7 @@ void GrVkRenderPass::initSimple(const GrVkGpu* gpu, const GrVkRenderTarget& targ
if (fAttachmentFlags & kStencil_AttachmentFlag) {
// set up stencil attachment
+ fAttachmentsDescriptor.fStencil.fLoadStoreOps = stencilOp;
setup_vk_attachment_description(&attachments[currentAttachment],
fAttachmentsDescriptor.fStencil,
VK_IMAGE_LAYOUT_DEPTH_STENCIL_ATTACHMENT_OPTIMAL);
@@ -138,6 +147,27 @@ void GrVkRenderPass::initSimple(const GrVkGpu* gpu, const GrVkRenderTarget& targ
&fRenderPass));
}
+void GrVkRenderPass::init(const GrVkGpu* gpu,
+ const GrVkRenderPass& compatibleRenderPass,
+ const LoadStoreOps& colorOp,
+ const LoadStoreOps& resolveOp,
+ const LoadStoreOps& stencilOp) {
+ fAttachmentFlags = compatibleRenderPass.fAttachmentFlags;
+ fAttachmentsDescriptor = compatibleRenderPass.fAttachmentsDescriptor;
+ this->init(gpu, colorOp, resolveOp, stencilOp);
+}
+
+void GrVkRenderPass::init(const GrVkGpu* gpu,
+ const GrVkRenderTarget& target,
+ const LoadStoreOps& colorOp,
+ const LoadStoreOps& resolveOp,
+ const LoadStoreOps& stencilOp) {
+ // Get attachment information from render target. This includes which attachments the render
+ // target has (color, resolve, stencil) and the attachments format and sample count.
+ target.getAttachmentsDescriptor(&fAttachmentsDescriptor, &fAttachmentFlags);
+ this->init(gpu, colorOp, resolveOp, stencilOp);
+}
+
void GrVkRenderPass::freeGPUData(const GrVkGpu* gpu) const {
GR_VK_CALL(gpu->vkInterface(), DestroyRenderPass(gpu->device(), fRenderPass, nullptr));
}
@@ -231,6 +261,27 @@ bool GrVkRenderPass::isCompatible(const GrVkRenderTarget& target) const {
return true;
}
+bool GrVkRenderPass::equalLoadStoreOps(const LoadStoreOps& colorOps,
+ const LoadStoreOps& resolveOps,
+ const LoadStoreOps& stencilOps) const {
+ if (fAttachmentFlags & kColor_AttachmentFlag) {
+ if (fAttachmentsDescriptor.fColor.fLoadStoreOps != colorOps) {
+ return false;
+ }
+ }
+ if (fAttachmentFlags & kResolve_AttachmentFlag) {
+ if (fAttachmentsDescriptor.fResolve.fLoadStoreOps != resolveOps) {
+ return false;
+ }
+ }
+ if (fAttachmentFlags & kStencil_AttachmentFlag) {
+ if (fAttachmentsDescriptor.fStencil.fLoadStoreOps != stencilOps) {
+ return false;
+ }
+ }
+ return true;
+}
+
void GrVkRenderPass::genKey(GrProcessorKeyBuilder* b) const {
b->add32(fAttachmentFlags);
if (fAttachmentFlags & kColor_AttachmentFlag) {
diff --git a/src/gpu/vk/GrVkRenderPass.h b/src/gpu/vk/GrVkRenderPass.h
index 082cccda77..b4f4b2b2bb 100644
--- a/src/gpu/vk/GrVkRenderPass.h
+++ b/src/gpu/vk/GrVkRenderPass.h
@@ -21,25 +21,51 @@ class GrVkRenderTarget;
class GrVkRenderPass : public GrVkResource {
public:
GrVkRenderPass() : INHERITED(), fRenderPass(VK_NULL_HANDLE) {}
+
+ struct LoadStoreOps {
+ VkAttachmentLoadOp fLoadOp;
+ VkAttachmentStoreOp fStoreOp;
+
+ LoadStoreOps(VkAttachmentLoadOp loadOp, VkAttachmentStoreOp storeOp)
+ : fLoadOp(loadOp)
+ , fStoreOp(storeOp) {}
+
+ bool operator==(const LoadStoreOps& right) const {
+ return fLoadOp == right.fLoadOp && fStoreOp == right.fStoreOp;
+ }
+
+ bool operator!=(const LoadStoreOps& right) const {
+ return !(*this == right);
+ }
+ };
+
void initSimple(const GrVkGpu* gpu, const GrVkRenderTarget& target);
+ void init(const GrVkGpu* gpu,
+ const GrVkRenderTarget& target,
+ const LoadStoreOps& colorOp,
+ const LoadStoreOps& resolveOp,
+ const LoadStoreOps& stencilOp);
+
+ void init(const GrVkGpu* gpu,
+ const GrVkRenderPass& compatibleRenderPass,
+ const LoadStoreOps& colorOp,
+ const LoadStoreOps& resolveOp,
+ const LoadStoreOps& stencilOp);
struct AttachmentsDescriptor {
struct AttachmentDesc {
VkFormat fFormat;
int fSamples;
- VkAttachmentLoadOp fLoadOp;
- VkAttachmentStoreOp fStoreOp;
+ LoadStoreOps fLoadStoreOps;
AttachmentDesc()
: fFormat(VK_FORMAT_UNDEFINED)
, fSamples(0)
- , fLoadOp(VK_ATTACHMENT_LOAD_OP_LOAD)
- , fStoreOp(VK_ATTACHMENT_STORE_OP_STORE) {}
+ , fLoadStoreOps(VK_ATTACHMENT_LOAD_OP_LOAD, VK_ATTACHMENT_STORE_OP_STORE) {}
bool operator==(const AttachmentDesc& right) const {
return (fFormat == right.fFormat &&
fSamples == right.fSamples &&
- fLoadOp == right.fLoadOp &&
- fStoreOp == right.fStoreOp);
+ fLoadStoreOps == right.fLoadStoreOps);
}
bool operator!=(const AttachmentDesc& right) const {
return !(*this == right);
@@ -84,6 +110,10 @@ public:
// basic RenderPasses that can be used when creating a VkFrameBuffer object.
bool isCompatible(const GrVkRenderTarget& target) const;
+ bool equalLoadStoreOps(const LoadStoreOps& colorOps,
+ const LoadStoreOps& resolveOps,
+ const LoadStoreOps& stencilOps) const;
+
VkRenderPass vkRenderPass() const { return fRenderPass; }
void genKey(GrProcessorKeyBuilder* b) const;
@@ -91,6 +121,11 @@ public:
private:
GrVkRenderPass(const GrVkRenderPass&);
+ void init(const GrVkGpu* gpu,
+ const LoadStoreOps& colorOps,
+ const LoadStoreOps& resolveOps,
+ const LoadStoreOps& stencilOps);
+
void freeGPUData(const GrVkGpu* gpu) const override;
VkRenderPass fRenderPass;
diff --git a/src/gpu/vk/GrVkRenderTarget.h b/src/gpu/vk/GrVkRenderTarget.h
index 0467371ecb..735f5cdf7c 100644
--- a/src/gpu/vk/GrVkRenderTarget.h
+++ b/src/gpu/vk/GrVkRenderTarget.h
@@ -65,7 +65,6 @@ public:
GrBackendObject getRenderTargetHandle() const override;
- // Returns the total number of attachments
void getAttachmentsDescriptor(GrVkRenderPass::AttachmentsDescriptor* desc,
GrVkRenderPass::AttachmentFlags* flags) const;
diff --git a/src/gpu/vk/GrVkResourceProvider.cpp b/src/gpu/vk/GrVkResourceProvider.cpp
index fdc9e90686..cd3ba47bca 100644
--- a/src/gpu/vk/GrVkResourceProvider.cpp
+++ b/src/gpu/vk/GrVkResourceProvider.cpp
@@ -10,7 +10,6 @@
#include "GrTextureParams.h"
#include "GrVkCommandBuffer.h"
#include "GrVkPipeline.h"
-#include "GrVkRenderPass.h"
#include "GrVkSampler.h"
#include "GrVkUtil.h"
@@ -134,6 +133,33 @@ GrVkResourceProvider::findCompatibleRenderPass(const CompatibleRPHandle& compati
return renderPass;
}
+const GrVkRenderPass* GrVkResourceProvider::findRenderPass(
+ const GrVkRenderTarget& target,
+ const GrVkRenderPass::LoadStoreOps& colorOps,
+ const GrVkRenderPass::LoadStoreOps& resolveOps,
+ const GrVkRenderPass::LoadStoreOps& stencilOps,
+ CompatibleRPHandle* compatibleHandle) {
+ // This will get us the handle to (and possible create) the compatible set for the specific
+ // GrVkRenderPass we are looking for.
+ this->findCompatibleRenderPass(target, compatibleHandle);
+ return this->findRenderPass(*compatibleHandle, colorOps, resolveOps, stencilOps);
+}
+
+const GrVkRenderPass*
+GrVkResourceProvider::findRenderPass(const CompatibleRPHandle& compatibleHandle,
+ const GrVkRenderPass::LoadStoreOps& colorOps,
+ const GrVkRenderPass::LoadStoreOps& resolveOps,
+ const GrVkRenderPass::LoadStoreOps& stencilOps) {
+ SkASSERT(compatibleHandle.isValid() && compatibleHandle.toIndex() < fRenderPassArray.count());
+ CompatibleRenderPassSet& compatibleSet = fRenderPassArray[compatibleHandle.toIndex()];
+ const GrVkRenderPass* renderPass = compatibleSet.getRenderPass(fGpu,
+ colorOps,
+ resolveOps,
+ stencilOps);
+ renderPass->ref();
+ return renderPass;
+}
+
GrVkDescriptorPool* GrVkResourceProvider::findOrCreateCompatibleDescriptorPool(
VkDescriptorType type, uint32_t count) {
return new GrVkDescriptorPool(fGpu, type, count);
@@ -295,6 +321,24 @@ bool GrVkResourceProvider::CompatibleRenderPassSet::isCompatible(
return fRenderPasses[0]->isCompatible(target);
}
+GrVkRenderPass* GrVkResourceProvider::CompatibleRenderPassSet::getRenderPass(
+ const GrVkGpu* gpu,
+ const GrVkRenderPass::LoadStoreOps& colorOps,
+ const GrVkRenderPass::LoadStoreOps& resolveOps,
+ const GrVkRenderPass::LoadStoreOps& stencilOps) {
+ for (int i = 0; i < fRenderPasses.count(); ++i) {
+ int idx = (i + fLastReturnedIndex) % fRenderPasses.count();
+ if (fRenderPasses[idx]->equalLoadStoreOps(colorOps, resolveOps, stencilOps)) {
+ fLastReturnedIndex = idx;
+ return fRenderPasses[idx];
+ }
+ }
+ GrVkRenderPass* renderPass = fRenderPasses.push_back();
+ renderPass->init(gpu, *this->getCompatibleRenderPass(), colorOps, resolveOps, stencilOps);
+ fLastReturnedIndex = fRenderPasses.count() - 1;
+ return renderPass;
+}
+
void GrVkResourceProvider::CompatibleRenderPassSet::releaseResources(const GrVkGpu* gpu) {
for (int i = 0; i < fRenderPasses.count(); ++i) {
if (fRenderPasses[i]) {
diff --git a/src/gpu/vk/GrVkResourceProvider.h b/src/gpu/vk/GrVkResourceProvider.h
index 5368a212b4..e754501cba 100644
--- a/src/gpu/vk/GrVkResourceProvider.h
+++ b/src/gpu/vk/GrVkResourceProvider.h
@@ -12,6 +12,7 @@
#include "GrResourceHandle.h"
#include "GrVkDescriptorPool.h"
#include "GrVkPipelineState.h"
+#include "GrVkRenderPass.h"
#include "GrVkResource.h"
#include "GrVkUtil.h"
#include "SkTArray.h"
@@ -27,7 +28,6 @@ class GrTextureParams;
class GrVkCommandBuffer;
class GrVkGpu;
class GrVkPipeline;
-class GrVkRenderPass;
class GrVkRenderTarget;
class GrVkSampler;
@@ -59,21 +59,23 @@ public:
// findCompatibleRenderPass(GrVkRenderTarget&, CompatibleRPHandle*).
const GrVkRenderPass* findCompatibleRenderPass(const CompatibleRPHandle& compatibleHandle);
-#if 0
- // TODO:
+ // Finds or creates a render pass that matches the target and LoadStoreOps, increments the
+ // refcount, and returns. The caller can optionally pass in a pointer to a CompatibleRPHandle.
+ // If this is non null it will be set to a handle that can be used in the furutre to quickly
+ // return a GrVkRenderPasses without the need inspecting a GrVkRenderTarget.
const GrVkRenderPass* findRenderPass(const GrVkRenderTarget& target,
- VkAttachmentLoadOp colorLoad,
- VkAttachmentStoreOp colorStore,
- VkAttachmentLoadOp stencilLoad,
- VkAttachmentStoreOp stencilStore,
+ const GrVkRenderPass::LoadStoreOps& colorOps,
+ const GrVkRenderPass::LoadStoreOps& resolveOps,
+ const GrVkRenderPass::LoadStoreOps& stencilOps,
CompatibleRPHandle* compatibleHandle = nullptr);
+ // The CompatibleRPHandle must be a valid handle previously set by a call to findRenderPass or
+ // findCompatibleRenderPass.
const GrVkRenderPass* findRenderPass(const CompatibleRPHandle& compatibleHandle,
- VkAttachmentLoadOp colorLoad,
- VkAttachmentStoreOp colorStore,
- VkAttachmentLoadOp stencilLoad,
- VkAttachmentStoreOp stencilStore);
-#endif
+ const GrVkRenderPass::LoadStoreOps& colorOps,
+ const GrVkRenderPass::LoadStoreOps& resolveOps,
+ const GrVkRenderPass::LoadStoreOps& stencilOps);
+
GrVkCommandBuffer* createCommandBuffer();
void checkCommandBuffers();
@@ -175,6 +177,11 @@ private:
return fRenderPasses[0];
}
+ GrVkRenderPass* getRenderPass(const GrVkGpu* gpu,
+ const GrVkRenderPass::LoadStoreOps& colorOps,
+ const GrVkRenderPass::LoadStoreOps& resolveOps,
+ const GrVkRenderPass::LoadStoreOps& stencilOps);
+
void releaseResources(const GrVkGpu* gpu);
void abandonResources();