diff options
author | Brian Salomon <bsalomon@google.com> | 2018-12-05 14:36:35 -0500 |
---|---|---|
committer | Skia Commit-Bot <skia-commit-bot@chromium.org> | 2018-12-05 20:12:42 +0000 |
commit | 796693af3cda0e24a76a89a092ed8de0e46ccb18 (patch) | |
tree | 5772619f44c3891189444ad61fe83fe4c4bf2082 | |
parent | 10273c1d5fe18f41a62c5ff4faf8bbdb5d5656cc (diff) | |
download | platform_external_skqp-796693af3cda0e24a76a89a092ed8de0e46ccb18.tar.gz platform_external_skqp-796693af3cda0e24a76a89a092ed8de0e46ccb18.tar.bz2 platform_external_skqp-796693af3cda0e24a76a89a092ed8de0e46ccb18.zip |
Mark wrapped textures imported into SkImages as "read only".
Read only textures and proxies fail writePixels, as copy dsts, and mip
regeneration.
Bug: skia:8509
Change-Id: Iaa0b473cc9a9930fde3ef0e91373d5040650de35
Reviewed-on: https://skia-review.googlesource.com/c/174316
Commit-Queue: Brian Salomon <bsalomon@google.com>
Reviewed-by: Robert Phillips <robertphillips@google.com>
53 files changed, 317 insertions, 114 deletions
diff --git a/include/gpu/GrSurface.h b/include/gpu/GrSurface.h index bcd854f11e..3211a1e90a 100644 --- a/include/gpu/GrSurface.h +++ b/include/gpu/GrSurface.h @@ -65,6 +65,12 @@ public: static size_t ComputeSize(GrPixelConfig config, int width, int height, int colorSamplesPerPixel, GrMipMapped, bool useNextPow2 = false); + /** + * The pixel values of this surface cannot be modified (e.g. doesn't support write pixels or + * MIP map level regen). + */ + bool readOnly() const { return fSurfaceFlags & GrInternalSurfaceFlags::kReadOnly; } + protected: void setHasMixedSamples() { SkASSERT(this->asRenderTarget()); @@ -88,6 +94,11 @@ protected: return fSurfaceFlags & GrInternalSurfaceFlags::kGLRTFBOIDIs0; } + void setReadOnly() { + SkASSERT(!this->asRenderTarget()); + fSurfaceFlags |= GrInternalSurfaceFlags::kReadOnly; + } + // Methods made available via GrSurfacePriv bool hasPendingRead() const; bool hasPendingWrite() const; diff --git a/include/private/GrSurfaceProxy.h b/include/private/GrSurfaceProxy.h index 887400a60c..df8505e7fe 100644 --- a/include/private/GrSurfaceProxy.h +++ b/include/private/GrSurfaceProxy.h @@ -365,6 +365,12 @@ public: */ SkBudgeted isBudgeted() const { return fBudgeted; } + /** + * The pixel values of this proxy's surface cannot be modified (e.g. doesn't support write + * pixels or MIP map level regen), + */ + bool readOnly() const { return fSurfaceFlags & GrInternalSurfaceFlags::kReadOnly; } + void setLastOpList(GrOpList* opList); GrOpList* getLastOpList() { return fLastOpList; } @@ -432,7 +438,7 @@ protected: const GrBackendFormat& format, const GrSurfaceDesc&, GrSurfaceOrigin, SkBackingFit, SkBudgeted, GrInternalSurfaceFlags); - // Wrapped version + // Wrapped version. GrSurfaceProxy(sk_sp<GrSurface>, GrSurfaceOrigin, SkBackingFit); virtual ~GrSurfaceProxy(); diff --git a/include/private/GrTypesPriv.h b/include/private/GrTypesPriv.h index e9fd0a332d..c14e337459 100644 --- a/include/private/GrTypesPriv.h +++ b/include/private/GrTypesPriv.h @@ -825,11 +825,19 @@ enum class GrInternalSurfaceFlags { kNone = 0, // Surface-level + kNoPendingIO = 1 << 0, kSurfaceMask = kNoPendingIO, - // RT-only + // Texture-level + + // Means the pixels in the texture are read-only. Cannot also be a GrRenderTarget[Proxy]. + kReadOnly = 1 << 1, + + kTextureMask = kReadOnly, + + // RT-level // For internal resources: // this is enabled whenever MSAA is enabled and GrCaps reports mixed samples are supported diff --git a/src/gpu/GrAHardwareBufferImageGenerator.cpp b/src/gpu/GrAHardwareBufferImageGenerator.cpp index b6cc28d070..8b86721c7c 100644 --- a/src/gpu/GrAHardwareBufferImageGenerator.cpp +++ b/src/gpu/GrAHardwareBufferImageGenerator.cpp @@ -574,8 +574,8 @@ sk_sp<GrTextureProxy> GrAHardwareBufferImageGenerator::makeProxy(GrContext* cont const bool isProtectedContent = fIsProtectedContent; sk_sp<GrTextureProxy> texProxy = proxyProvider->createLazyProxy( - [context, hardwareBuffer, width, height, pixelConfig, isProtectedContent, backendFormat] - (GrResourceProvider* resourceProvider) { + [context, hardwareBuffer, width, height, pixelConfig, isProtectedContent, + backendFormat](GrResourceProvider* resourceProvider) { if (!resourceProvider) { AHardwareBuffer_release(hardwareBuffer); return sk_sp<GrTexture>(); @@ -596,7 +596,8 @@ sk_sp<GrTextureProxy> GrAHardwareBufferImageGenerator::makeProxy(GrContext* cont SkASSERT(deleteImageProc && deleteImageCtx); backendTex.fConfig = pixelConfig; - sk_sp<GrTexture> tex = resourceProvider->wrapBackendTexture(backendTex); + sk_sp<GrTexture> tex = resourceProvider->wrapBackendTexture( + backendTex, kBorrow_GrWrapOwnership, kRead_GrIOType); if (!tex) { deleteImageProc(deleteImageCtx); return sk_sp<GrTexture>(); @@ -610,8 +611,8 @@ sk_sp<GrTextureProxy> GrAHardwareBufferImageGenerator::makeProxy(GrContext* cont return tex; }, - backendFormat, desc, fSurfaceOrigin, GrMipMapped::kNo, SkBackingFit::kExact, - SkBudgeted::kNo); + backendFormat, desc, fSurfaceOrigin, GrMipMapped::kNo, + GrInternalSurfaceFlags::kReadOnly, SkBackingFit::kExact, SkBudgeted::kNo); if (!texProxy) { AHardwareBuffer_release(hardwareBuffer); diff --git a/src/gpu/GrBackendTextureImageGenerator.cpp b/src/gpu/GrBackendTextureImageGenerator.cpp index 4f887f22ad..1785823297 100644 --- a/src/gpu/GrBackendTextureImageGenerator.cpp +++ b/src/gpu/GrBackendTextureImageGenerator.cpp @@ -138,8 +138,8 @@ sk_sp<GrTextureProxy> GrBackendTextureImageGenerator::onGenerateTexture( SkASSERT(format.isValid()); sk_sp<GrTextureProxy> proxy = proxyProvider->createLazyProxy( - [refHelper, releaseProcHelper, semaphore, backendTexture] - (GrResourceProvider* resourceProvider) { + [refHelper, releaseProcHelper, semaphore, + backendTexture](GrResourceProvider* resourceProvider) { if (!resourceProvider) { return sk_sp<GrTexture>(); } @@ -163,9 +163,8 @@ sk_sp<GrTextureProxy> GrBackendTextureImageGenerator::onGenerateTexture( // informs us that the context is done with it. This is unfortunate - we'll have // two texture objects referencing the same GPU object. However, no client can // ever see the original texture, so this should be safe. - tex = resourceProvider->wrapBackendTexture(backendTexture, - kBorrow_GrWrapOwnership, - true); + tex = resourceProvider->wrapBackendTexture( + backendTexture, kBorrow_GrWrapOwnership, kRead_GrIOType, true); if (!tex) { return sk_sp<GrTexture>(); } @@ -176,7 +175,8 @@ sk_sp<GrTextureProxy> GrBackendTextureImageGenerator::onGenerateTexture( return tex; }, - format, desc, fSurfaceOrigin, mipMapped, SkBackingFit::kExact, SkBudgeted::kNo); + format, desc, fSurfaceOrigin, mipMapped, GrInternalSurfaceFlags::kReadOnly, + SkBackingFit::kExact, SkBudgeted::kNo); if (!proxy) { return nullptr; diff --git a/src/gpu/GrCaps.cpp b/src/gpu/GrCaps.cpp index 64625d91fc..562a7fce92 100644 --- a/src/gpu/GrCaps.cpp +++ b/src/gpu/GrCaps.cpp @@ -6,9 +6,10 @@ */ #include "GrCaps.h" - #include "GrBackendSurface.h" #include "GrContextOptions.h" +#include "GrSurface.h" +#include "GrSurfaceProxy.h" #include "GrTypesPriv.h" #include "GrWindowRectangles.h" #include "SkJSONWriter.h" @@ -242,6 +243,15 @@ void GrCaps::dumpJSON(SkJSONWriter* writer) const { void GrCaps::dumpJSON(SkJSONWriter* writer) const { } #endif +bool GrCaps::surfaceSupportsWritePixels(const GrSurface* surface) const { + return surface->readOnly() ? false : this->onSurfaceSupportsWritePixels(surface); +} + +bool GrCaps::canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const { + return dst->readOnly() ? false : this->onCanCopySurface(dst, src, srcRect, dstPoint); +} + bool GrCaps::validateSurfaceDesc(const GrSurfaceDesc& desc, GrMipMapped mipped) const { if (!this->isConfigTexturable(desc.fConfig)) { return false; diff --git a/src/gpu/GrCaps.h b/src/gpu/GrCaps.h index c695ebeec2..7a9285d441 100644 --- a/src/gpu/GrCaps.h +++ b/src/gpu/GrCaps.h @@ -192,7 +192,7 @@ public: * If this returns false then the caller should implement a fallback where a temporary texture * is created, pixels are written to it, and then that is copied or drawn into the the surface. */ - virtual bool surfaceSupportsWritePixels(const GrSurface*) const = 0; + bool surfaceSupportsWritePixels(const GrSurface*) const; /** * Backends may have restrictions on what types of surfaces support GrGpu::readPixels(). @@ -246,8 +246,8 @@ public: /** * Returns whether or not we will be able to do a copy given the passed in params */ - virtual bool canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, - const SkIRect& srcRect, const SkIPoint& dstPoint) const = 0; + bool canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const; bool dynamicStateArrayGeometryProcessorTextureSupport() const { return fDynamicStateArrayGeometryProcessorTextureSupport; @@ -389,6 +389,9 @@ protected: private: virtual void onApplyOptionsOverrides(const GrContextOptions&) {} virtual void onDumpJSON(SkJSONWriter*) const {} + virtual bool onSurfaceSupportsWritePixels(const GrSurface*) const = 0; + virtual bool onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const = 0; // Backends should implement this if they have any extra requirements for use of window // rectangles for a specific GrBackendRenderTarget outside of basic support. diff --git a/src/gpu/GrContext.cpp b/src/gpu/GrContext.cpp index 06eb6c4838..1b2d13c775 100644 --- a/src/gpu/GrContext.cpp +++ b/src/gpu/GrContext.cpp @@ -928,7 +928,8 @@ sk_sp<GrTextureContext> GrContextPriv::makeBackendTextureContext(const GrBackend sk_sp<SkColorSpace> colorSpace) { ASSERT_SINGLE_OWNER_PRIV - sk_sp<GrSurfaceProxy> proxy = this->proxyProvider()->wrapBackendTexture(tex, origin); + sk_sp<GrSurfaceProxy> proxy = this->proxyProvider()->wrapBackendTexture( + tex, origin, kBorrow_GrWrapOwnership, kRW_GrIOType); if (!proxy) { return nullptr; } diff --git a/src/gpu/GrGpu.cpp b/src/gpu/GrGpu.cpp index 8e18fb8e25..7b7ff2e0b6 100644 --- a/src/gpu/GrGpu.cpp +++ b/src/gpu/GrGpu.cpp @@ -145,7 +145,9 @@ sk_sp<GrTexture> GrGpu::createTexture(const GrSurfaceDesc& desc, SkBudgeted budg sk_sp<GrTexture> GrGpu::wrapBackendTexture(const GrBackendTexture& backendTex, GrWrapOwnership ownership, + GrIOType ioType, bool purgeImmediately) { + SkASSERT(ioType != kWrite_GrIOType); this->handleDirtyContext(); if (!this->caps()->isConfigTexturable(backendTex.config())) { return nullptr; @@ -154,7 +156,7 @@ sk_sp<GrTexture> GrGpu::wrapBackendTexture(const GrBackendTexture& backendTex, backendTex.height() > this->caps()->maxTextureSize()) { return nullptr; } - return this->onWrapBackendTexture(backendTex, ownership, purgeImmediately); + return this->onWrapBackendTexture(backendTex, ownership, ioType, purgeImmediately); } sk_sp<GrTexture> GrGpu::wrapRenderableBackendTexture(const GrBackendTexture& backendTex, @@ -214,7 +216,13 @@ bool GrGpu::copySurface(GrSurface* dst, GrSurfaceOrigin dstOrigin, bool canDiscardOutsideDstRect) { GR_CREATE_TRACE_MARKER_CONTEXT("GrGpu", "copySurface", fContext); SkASSERT(dst && src); + + if (dst->readOnly()) { + return false; + } + this->handleDirtyContext(); + return this->onCopySurface(dst, dstOrigin, src, srcOrigin, srcRect, dstPoint, canDiscardOutsideDstRect); } @@ -239,6 +247,11 @@ bool GrGpu::readPixels(GrSurface* surface, int left, int top, int width, int hei bool GrGpu::writePixels(GrSurface* surface, int left, int top, int width, int height, GrColorType srcColorType, const GrMipLevel texels[], int mipLevelCount) { SkASSERT(surface); + + if (surface->readOnly()) { + return false; + } + if (1 == mipLevelCount) { // We require that if we are not mipped, then the write region is contained in the surface SkIRect subRect = SkIRect::MakeXYWH(left, top, width, height); @@ -271,8 +284,13 @@ bool GrGpu::writePixels(GrSurface* surface, int left, int top, int width, int he bool GrGpu::transferPixels(GrTexture* texture, int left, int top, int width, int height, GrColorType bufferColorType, GrBuffer* transferBuffer, size_t offset, size_t rowBytes) { + SkASSERT(texture); SkASSERT(transferBuffer); + if (texture->readOnly()) { + return false; + } + // We require that the write region is contained in the texture SkIRect subRect = SkIRect::MakeXYWH(left, top, width, height); SkIRect bounds = SkIRect::MakeWH(texture->width(), texture->height()); @@ -298,6 +316,9 @@ bool GrGpu::regenerateMipMapLevels(GrTexture* texture) { SkASSERT(texture->texturePriv().mipMapped() == GrMipMapped::kYes); SkASSERT(texture->texturePriv().mipMapsAreDirty()); SkASSERT(!texture->asRenderTarget() || !texture->asRenderTarget()->needsResolve()); + if (texture->readOnly()) { + return false; + } if (this->onRegenerateMipMapLevels(texture)) { texture->texturePriv().markMipMapsClean(); return true; @@ -314,6 +335,7 @@ void GrGpu::resolveRenderTarget(GrRenderTarget* target) { void GrGpu::didWriteToSurface(GrSurface* surface, GrSurfaceOrigin origin, const SkIRect* bounds, uint32_t mipLevels) const { SkASSERT(surface); + SkASSERT(!surface->readOnly()); // Mark any MIP chain and resolve buffer as dirty if and only if there is a non-empty bounds. if (nullptr == bounds || !bounds->isEmpty()) { if (GrRenderTarget* target = surface->asRenderTarget()) { diff --git a/src/gpu/GrGpu.h b/src/gpu/GrGpu.h index cb8b2e9820..99985f1be4 100644 --- a/src/gpu/GrGpu.h +++ b/src/gpu/GrGpu.h @@ -104,7 +104,7 @@ public: /** * Implements GrResourceProvider::wrapBackendTexture */ - sk_sp<GrTexture> wrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, + sk_sp<GrTexture> wrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, GrIOType, bool purgeImmediately); /** @@ -445,7 +445,7 @@ private: const GrMipLevel texels[], int mipLevelCount) = 0; virtual sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, - bool purgeImmediately) = 0; + GrIOType, bool purgeImmediately) = 0; virtual sk_sp<GrTexture> onWrapRenderableBackendTexture(const GrBackendTexture&, int sampleCnt, GrWrapOwnership) = 0; diff --git a/src/gpu/GrProxyProvider.cpp b/src/gpu/GrProxyProvider.cpp index 3259f28ff0..dcf642badd 100644 --- a/src/gpu/GrProxyProvider.cpp +++ b/src/gpu/GrProxyProvider.cpp @@ -415,8 +415,10 @@ sk_sp<GrTextureProxy> GrProxyProvider::createProxy(const GrBackendFormat& format sk_sp<GrTextureProxy> GrProxyProvider::wrapBackendTexture(const GrBackendTexture& backendTex, GrSurfaceOrigin origin, GrWrapOwnership ownership, + GrIOType ioType, ReleaseProc releaseProc, ReleaseContext releaseCtx) { + SkASSERT(ioType != kWrite_GrIOType); if (this->isAbandoned()) { return nullptr; } @@ -426,7 +428,7 @@ sk_sp<GrTextureProxy> GrProxyProvider::wrapBackendTexture(const GrBackendTexture return nullptr; } - sk_sp<GrTexture> tex = fResourceProvider->wrapBackendTexture(backendTex, ownership); + sk_sp<GrTexture> tex = fResourceProvider->wrapBackendTexture(backendTex, ownership, ioType); if (!tex) { return nullptr; } diff --git a/src/gpu/GrProxyProvider.h b/src/gpu/GrProxyProvider.h index 1e26f519d7..1aec328e3f 100644 --- a/src/gpu/GrProxyProvider.h +++ b/src/gpu/GrProxyProvider.h @@ -104,11 +104,12 @@ public: typedef void (*ReleaseProc)(ReleaseContext); /* - * Create a texture proxy that wraps a (non-renderable) backend texture. + * Create a texture proxy that wraps a (non-renderable) backend texture. GrIOType must be + * kRead or kRW. */ sk_sp<GrTextureProxy> wrapBackendTexture(const GrBackendTexture&, GrSurfaceOrigin, - GrWrapOwnership = kBorrow_GrWrapOwnership, - ReleaseProc = nullptr, ReleaseContext = nullptr); + GrWrapOwnership, GrIOType, ReleaseProc = nullptr, + ReleaseContext = nullptr); /* * Create a texture proxy that wraps a backend texture and is both texture-able and renderable @@ -119,7 +120,7 @@ public: GrWrapOwnership = kBorrow_GrWrapOwnership); /* - * Create a render target proxy that wraps a backend rendertarget + * Create a render target proxy that wraps a backend render target */ sk_sp<GrSurfaceProxy> wrapBackendRenderTarget(const GrBackendRenderTarget&, GrSurfaceOrigin); diff --git a/src/gpu/GrResourceProvider.cpp b/src/gpu/GrResourceProvider.cpp index 78bd97bbee..1193246ebe 100644 --- a/src/gpu/GrResourceProvider.cpp +++ b/src/gpu/GrResourceProvider.cpp @@ -226,12 +226,13 @@ sk_sp<GrTexture> GrResourceProvider::refScratchTexture(const GrSurfaceDesc& desc sk_sp<GrTexture> GrResourceProvider::wrapBackendTexture(const GrBackendTexture& tex, GrWrapOwnership ownership, + GrIOType ioType, bool purgeImmediately) { ASSERT_SINGLE_OWNER if (this->isAbandoned()) { return nullptr; } - return fGpu->wrapBackendTexture(tex, ownership, purgeImmediately); + return fGpu->wrapBackendTexture(tex, ownership, ioType, purgeImmediately); } sk_sp<GrTexture> GrResourceProvider::wrapRenderableBackendTexture(const GrBackendTexture& tex, diff --git a/src/gpu/GrResourceProvider.h b/src/gpu/GrResourceProvider.h index 74e1dcea84..c86136f1e2 100644 --- a/src/gpu/GrResourceProvider.h +++ b/src/gpu/GrResourceProvider.h @@ -98,13 +98,17 @@ public: /** * Wraps an existing texture with a GrTexture object. * + * GrIOType must either be kRead or kRW. kRead blocks any operations that would modify the + * pixels (e.g. dst for a copy, regenerating MIP levels, write pixels). + * * OpenGL: if the object is a texture Gr may change its GL texture params * when it is drawn. * * @return GrTexture object or NULL on failure. */ sk_sp<GrTexture> wrapBackendTexture(const GrBackendTexture& tex, - GrWrapOwnership = kBorrow_GrWrapOwnership, + GrWrapOwnership /* = kBorrow_GrWrapOwnership*/, + GrIOType, bool purgeImmediately = false); /** diff --git a/src/gpu/GrTextureOpList.cpp b/src/gpu/GrTextureOpList.cpp index 4b93803520..ae51807335 100644 --- a/src/gpu/GrTextureOpList.cpp +++ b/src/gpu/GrTextureOpList.cpp @@ -25,6 +25,7 @@ GrTextureOpList::GrTextureOpList(GrResourceProvider* resourceProvider, GrAuditTrail* auditTrail) : INHERITED(resourceProvider, std::move(opMemoryPool), proxy, auditTrail) { SkASSERT(fOpMemoryPool); + SkASSERT(!proxy->readOnly()); } void GrTextureOpList::deleteOp(int index) { diff --git a/src/gpu/GrTextureProxy.cpp b/src/gpu/GrTextureProxy.cpp index 854ed1766d..b732818ea0 100644 --- a/src/gpu/GrTextureProxy.cpp +++ b/src/gpu/GrTextureProxy.cpp @@ -173,7 +173,14 @@ void GrTextureProxy::onValidateSurface(const GrSurface* surface) { SkASSERT(surface->asTexture()); SkASSERT(GrMipMapped::kNo == this->proxyMipMapped() || GrMipMapped::kYes == surface->asTexture()->texturePriv().mipMapped()); + SkASSERT(surface->asTexture()->texturePriv().textureType() == this->textureType()); + + GrInternalSurfaceFlags proxyFlags = fSurfaceFlags; + GrInternalSurfaceFlags surfaceFlags = surface->surfacePriv().flags(); + SkASSERT((proxyFlags & GrInternalSurfaceFlags::kTextureMask) == + (surfaceFlags & GrInternalSurfaceFlags::kTextureMask)); } + #endif diff --git a/src/gpu/GrTextureRenderTargetProxy.cpp b/src/gpu/GrTextureRenderTargetProxy.cpp index a665270799..3e52b2c898 100644 --- a/src/gpu/GrTextureRenderTargetProxy.cpp +++ b/src/gpu/GrTextureRenderTargetProxy.cpp @@ -124,11 +124,19 @@ void GrTextureRenderTargetProxy::onValidateSurface(const GrSurface* surface) { SkASSERT(surface->asRenderTarget()); SkASSERT(surface->asRenderTarget()->numStencilSamples() == this->numStencilSamples()); + SkASSERT(surface->asTexture()->texturePriv().textureType() == this->textureType()); + GrInternalSurfaceFlags proxyFlags = fSurfaceFlags; GrInternalSurfaceFlags surfaceFlags = surface->surfacePriv().flags(); + + // Only non-RT textures can be read only. + SkASSERT(!(proxyFlags & GrInternalSurfaceFlags::kReadOnly)); + SkASSERT(!(surfaceFlags & GrInternalSurfaceFlags::kReadOnly)); + SkASSERT((proxyFlags & GrInternalSurfaceFlags::kRenderTargetMask) == (surfaceFlags & GrInternalSurfaceFlags::kRenderTargetMask)); - SkASSERT(surface->asTexture()->texturePriv().textureType() == this->textureType()); + SkASSERT((proxyFlags & GrInternalSurfaceFlags::kTextureMask) == + (surfaceFlags & GrInternalSurfaceFlags::kTextureMask)); } #endif diff --git a/src/gpu/gl/GrGLCaps.cpp b/src/gpu/gl/GrGLCaps.cpp index 9f26a7c06d..f90a1b0cbf 100644 --- a/src/gpu/gl/GrGLCaps.cpp +++ b/src/gpu/gl/GrGLCaps.cpp @@ -2172,8 +2172,8 @@ static bool has_msaa_render_buffer(const GrSurfaceProxy* surf, const GrGLCaps& g !rt->rtPriv().glRTFBOIDIs0(); } -bool GrGLCaps::canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, - const SkIRect& srcRect, const SkIPoint& dstPoint) const { +bool GrGLCaps::onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const { GrSurfaceOrigin dstOrigin = dst->origin(); GrSurfaceOrigin srcOrigin = src->origin(); @@ -2756,7 +2756,7 @@ void GrGLCaps::onApplyOptionsOverrides(const GrContextOptions& options) { } } -bool GrGLCaps::surfaceSupportsWritePixels(const GrSurface* surface) const { +bool GrGLCaps::onSurfaceSupportsWritePixels(const GrSurface* surface) const { if (fDisallowTexSubImageForUnormConfigTexturesEverBoundToFBO) { if (auto tex = static_cast<const GrGLTexture*>(surface->asTexture())) { if (tex->hasBaseLevelBeenBoundToFBO()) { diff --git a/src/gpu/gl/GrGLCaps.h b/src/gpu/gl/GrGLCaps.h index 4cdd316fa1..54dc126120 100644 --- a/src/gpu/gl/GrGLCaps.h +++ b/src/gpu/gl/GrGLCaps.h @@ -311,7 +311,6 @@ public: /// Use indices or vertices in CPU arrays rather than VBOs for dynamic content. bool useNonVBOVertexAndIndexDynamicData() const { return fUseNonVBOVertexAndIndexDynamicData; } - bool surfaceSupportsWritePixels(const GrSurface*) const override; bool surfaceSupportsReadPixels(const GrSurface*) const override; GrColorType supportedReadPixelsColorType(GrPixelConfig, GrColorType) const override; @@ -419,9 +418,6 @@ public: const SkIRect& srcRect, const SkIPoint& dstPoint) const; bool canCopyAsDraw(GrPixelConfig dstConfig, bool srcIsTextureable) const; - bool canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, - const SkIRect& srcRect, const SkIPoint& dstPoint) const override; - bool initDescForDstCopy(const GrRenderTargetProxy* src, GrSurfaceDesc* desc, GrSurfaceOrigin*, bool* rectsMustMatch, bool* disallowSubrect) const override; @@ -480,6 +476,9 @@ private: // This must be called after initFSAASupport(). void initConfigTable(const GrContextOptions&, const GrGLContextInfo&, const GrGLInterface*, GrShaderCaps*); + bool onSurfaceSupportsWritePixels(const GrSurface*) const override; + bool onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const override; GrGLStandard fStandard; diff --git a/src/gpu/gl/GrGLGpu.cpp b/src/gpu/gl/GrGLGpu.cpp index 63bf0322df..d344c3b44c 100644 --- a/src/gpu/gl/GrGLGpu.cpp +++ b/src/gpu/gl/GrGLGpu.cpp @@ -652,7 +652,8 @@ static bool check_backend_texture(const GrBackendTexture& backendTex, const GrGL } sk_sp<GrTexture> GrGLGpu::onWrapBackendTexture(const GrBackendTexture& backendTex, - GrWrapOwnership ownership, bool purgeImmediately) { + GrWrapOwnership ownership, GrIOType ioType, + bool purgeImmediately) { GrGLTexture::IDDesc idDesc; if (!check_backend_texture(backendTex, this->glCaps(), &idDesc)) { return nullptr; @@ -676,7 +677,7 @@ sk_sp<GrTexture> GrGLGpu::onWrapBackendTexture(const GrBackendTexture& backendTe GrMipMapsStatus mipMapsStatus = backendTex.hasMipMaps() ? GrMipMapsStatus::kValid : GrMipMapsStatus::kNotAllocated; - auto texture = GrGLTexture::MakeWrapped(this, surfDesc, mipMapsStatus, idDesc, + auto texture = GrGLTexture::MakeWrapped(this, surfDesc, mipMapsStatus, idDesc, ioType, purgeImmediately); // We don't know what parameters are already set on wrapped textures. texture->textureParamsModified(); diff --git a/src/gpu/gl/GrGLGpu.h b/src/gpu/gl/GrGLGpu.h index eb920dbe54..f74b98e751 100644 --- a/src/gpu/gl/GrGLGpu.h +++ b/src/gpu/gl/GrGLGpu.h @@ -189,7 +189,7 @@ private: GrBuffer* onCreateBuffer(size_t size, GrBufferType intendedType, GrAccessPattern, const void* data) override; - sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, + sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, GrIOType, bool purgeImmediately) override; sk_sp<GrTexture> onWrapRenderableBackendTexture(const GrBackendTexture&, int sampleCnt, diff --git a/src/gpu/gl/GrGLTexture.cpp b/src/gpu/gl/GrGLTexture.cpp index 2d432fec04..06bf6621ad 100644 --- a/src/gpu/gl/GrGLTexture.cpp +++ b/src/gpu/gl/GrGLTexture.cpp @@ -51,12 +51,15 @@ GrGLTexture::GrGLTexture(GrGLGpu* gpu, SkBudgeted budgeted, const GrSurfaceDesc& } GrGLTexture::GrGLTexture(GrGLGpu* gpu, Wrapped, const GrSurfaceDesc& desc, - GrMipMapsStatus mipMapsStatus, const IDDesc& idDesc, + GrMipMapsStatus mipMapsStatus, const IDDesc& idDesc, GrIOType ioType, bool purgeImmediately) : GrSurface(gpu, desc) , INHERITED(gpu, desc, TextureTypeFromTarget(idDesc.fInfo.fTarget), mipMapsStatus) { this->init(desc, idDesc); this->registerWithCacheWrapped(purgeImmediately); + if (ioType == kRead_GrIOType) { + this->setReadOnly(); + } } GrGLTexture::GrGLTexture(GrGLGpu* gpu, const GrSurfaceDesc& desc, const IDDesc& idDesc, @@ -111,9 +114,9 @@ GrBackendFormat GrGLTexture::backendFormat() const { sk_sp<GrGLTexture> GrGLTexture::MakeWrapped(GrGLGpu* gpu, const GrSurfaceDesc& desc, GrMipMapsStatus mipMapsStatus, const IDDesc& idDesc, - bool purgeImmediately) { - return sk_sp<GrGLTexture>(new GrGLTexture(gpu, kWrapped, desc, mipMapsStatus, idDesc, - purgeImmediately)); + GrIOType ioType, bool purgeImmediately) { + return sk_sp<GrGLTexture>( + new GrGLTexture(gpu, kWrapped, desc, mipMapsStatus, idDesc, ioType, purgeImmediately)); } bool GrGLTexture::onStealBackendTexture(GrBackendTexture* backendTexture, diff --git a/src/gpu/gl/GrGLTexture.h b/src/gpu/gl/GrGLTexture.h index a9d7a38c9a..290729bf2c 100644 --- a/src/gpu/gl/GrGLTexture.h +++ b/src/gpu/gl/GrGLTexture.h @@ -100,7 +100,7 @@ public: void baseLevelWasBoundToFBO() { fBaseLevelHasBeenBoundToFBO = true; } static sk_sp<GrGLTexture> MakeWrapped(GrGLGpu*, const GrSurfaceDesc&, GrMipMapsStatus, - const IDDesc&, bool purgeImmediately); + const IDDesc&, GrIOType, bool purgeImmediately); void dumpMemoryStatistics(SkTraceMemoryDump* traceMemoryDump) const override; @@ -110,7 +110,7 @@ protected: enum Wrapped { kWrapped }; // Constructor for instances wrapping backend objects. - GrGLTexture(GrGLGpu*, Wrapped, const GrSurfaceDesc&, GrMipMapsStatus, const IDDesc&, + GrGLTexture(GrGLGpu*, Wrapped, const GrSurfaceDesc&, GrMipMapsStatus, const IDDesc&, GrIOType, bool purgeImmediately); void init(const GrSurfaceDesc&, const IDDesc&); diff --git a/src/gpu/mock/GrMockCaps.h b/src/gpu/mock/GrMockCaps.h index d24afa58ba..e940423650 100644 --- a/src/gpu/mock/GrMockCaps.h +++ b/src/gpu/mock/GrMockCaps.h @@ -66,14 +66,8 @@ public: return 0; } - bool surfaceSupportsWritePixels(const GrSurface*) const override { return true; } bool surfaceSupportsReadPixels(const GrSurface*) const override { return true; } - bool canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, - const SkIRect& srcRect, const SkIPoint& dstPoint) const override { - return true; - } - bool initDescForDstCopy(const GrRenderTargetProxy* src, GrSurfaceDesc* desc, GrSurfaceOrigin*, bool* rectsMustMatch, bool* disallowSubrect) const override { return false; @@ -142,6 +136,11 @@ private: SkAssertResult(backendTex.getMockTextureInfo(&mockInfo)); return GrBackendFormat::MakeMock(mockInfo.fConfig); } + bool onSurfaceSupportsWritePixels(const GrSurface*) const override { return true; } + bool onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const override { + return true; + } static const int kMaxSampleCnt = 16; diff --git a/src/gpu/mock/GrMockGpu.cpp b/src/gpu/mock/GrMockGpu.cpp index 2de25eff9c..4f2c4cd96c 100644 --- a/src/gpu/mock/GrMockGpu.cpp +++ b/src/gpu/mock/GrMockGpu.cpp @@ -103,7 +103,8 @@ sk_sp<GrTexture> GrMockGpu::onCreateTexture(const GrSurfaceDesc& desc, SkBudgete } sk_sp<GrTexture> GrMockGpu::onWrapBackendTexture(const GrBackendTexture& tex, - GrWrapOwnership ownership, bool purgeImmediately) { + GrWrapOwnership ownership, GrIOType ioType, + bool purgeImmediately) { GrSurfaceDesc desc; desc.fWidth = tex.width(); desc.fHeight = tex.height(); @@ -116,7 +117,7 @@ sk_sp<GrTexture> GrMockGpu::onWrapBackendTexture(const GrBackendTexture& tex, : GrMipMapsStatus::kNotAllocated; return sk_sp<GrTexture>(new GrMockTexture(this, GrMockTexture::kWrapped, desc, mipMapsStatus, - info, purgeImmediately)); + info, ioType, purgeImmediately)); } sk_sp<GrTexture> GrMockGpu::onWrapRenderableBackendTexture(const GrBackendTexture& tex, diff --git a/src/gpu/mock/GrMockGpu.h b/src/gpu/mock/GrMockGpu.h index a39a82b220..832877a62e 100644 --- a/src/gpu/mock/GrMockGpu.h +++ b/src/gpu/mock/GrMockGpu.h @@ -59,7 +59,7 @@ private: sk_sp<GrTexture> onCreateTexture(const GrSurfaceDesc&, SkBudgeted, const GrMipLevel[], int mipLevelCount) override; - sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, + sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, GrIOType, bool purgeImmediately) override; sk_sp<GrTexture> onWrapRenderableBackendTexture(const GrBackendTexture&, diff --git a/src/gpu/mock/GrMockTexture.h b/src/gpu/mock/GrMockTexture.h index 0565f81726..ee8780d940 100644 --- a/src/gpu/mock/GrMockTexture.h +++ b/src/gpu/mock/GrMockTexture.h @@ -23,10 +23,12 @@ public: } enum Wrapped { kWrapped }; - GrMockTexture(GrMockGpu* gpu, Wrapped, const GrSurfaceDesc& desc, - GrMipMapsStatus mipMapsStatus, const GrMockTextureInfo& info, - bool purgeImmediately) + GrMockTexture(GrMockGpu* gpu, Wrapped, const GrSurfaceDesc& desc, GrMipMapsStatus mipMapsStatus, + const GrMockTextureInfo& info, GrIOType ioType, bool purgeImmediately) : GrMockTexture(gpu, desc, mipMapsStatus, info) { + if (ioType == kRead_GrIOType) { + this->setReadOnly(); + } this->registerWithCacheWrapped(purgeImmediately); } diff --git a/src/gpu/mtl/GrMtlCaps.h b/src/gpu/mtl/GrMtlCaps.h index 7edfa79d96..9d7b86f95d 100644 --- a/src/gpu/mtl/GrMtlCaps.h +++ b/src/gpu/mtl/GrMtlCaps.h @@ -33,7 +33,6 @@ public: int getRenderTargetSampleCount(int requestedCount, GrPixelConfig) const override; int maxRenderTargetSampleCount(GrPixelConfig) const override; - bool surfaceSupportsWritePixels(const GrSurface*) const override { return true; } bool surfaceSupportsReadPixels(const GrSurface*) const override { return true; } bool isConfigCopyable(GrPixelConfig config) const override { @@ -58,9 +57,6 @@ public: bool canCopyAsDrawThenBlit(GrPixelConfig dstConfig, GrPixelConfig srcConfig, bool srcIsTextureable) const; - bool canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, - const SkIRect& srcRect, const SkIPoint& dstPoint) const override; - bool initDescForDstCopy(const GrRenderTargetProxy* src, GrSurfaceDesc* desc, GrSurfaceOrigin*, bool* rectsMustMatch, bool* disallowSubrect) const override { return false; @@ -109,6 +105,10 @@ private: void initConfigTable(); + bool onSurfaceSupportsWritePixels(const GrSurface*) const override { return true; } + bool onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const override; + struct ConfigInfo { ConfigInfo() : fFlags(0) {} diff --git a/src/gpu/mtl/GrMtlCaps.mm b/src/gpu/mtl/GrMtlCaps.mm index ca3779bdb6..880b0faaca 100644 --- a/src/gpu/mtl/GrMtlCaps.mm +++ b/src/gpu/mtl/GrMtlCaps.mm @@ -166,8 +166,8 @@ bool GrMtlCaps::canCopyAsDrawThenBlit(GrPixelConfig dstConfig, GrPixelConfig src return true; } -bool GrMtlCaps::canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, - const SkIRect& srcRect, const SkIPoint& dstPoint) const { +bool GrMtlCaps::onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const { GrSurfaceOrigin dstOrigin = dst->origin(); GrSurfaceOrigin srcOrigin = src->origin(); diff --git a/src/gpu/mtl/GrMtlGpu.h b/src/gpu/mtl/GrMtlGpu.h index a72778417f..607f70414a 100644 --- a/src/gpu/mtl/GrMtlGpu.h +++ b/src/gpu/mtl/GrMtlGpu.h @@ -132,7 +132,7 @@ private: sk_sp<GrTexture> onCreateTexture(const GrSurfaceDesc& desc, SkBudgeted budgeted, const GrMipLevel texels[], int mipLevelCount) override; - sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, + sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, GrIOType, bool purgeImmediately) override; sk_sp<GrTexture> onWrapRenderableBackendTexture(const GrBackendTexture&, diff --git a/src/gpu/mtl/GrMtlGpu.mm b/src/gpu/mtl/GrMtlGpu.mm index 0661648144..132f455a98 100644 --- a/src/gpu/mtl/GrMtlGpu.mm +++ b/src/gpu/mtl/GrMtlGpu.mm @@ -338,7 +338,8 @@ static inline void init_surface_desc(GrSurfaceDesc* surfaceDesc, id<MTLTexture> } sk_sp<GrTexture> GrMtlGpu::onWrapBackendTexture(const GrBackendTexture& backendTex, - GrWrapOwnership ownership, bool purgeImmediately) { + GrWrapOwnership ownership, GrIOType ioType, + bool purgeImmediately) { id<MTLTexture> mtlTexture = get_texture_from_backend(backendTex, ownership); if (!mtlTexture) { return nullptr; @@ -347,7 +348,7 @@ sk_sp<GrTexture> GrMtlGpu::onWrapBackendTexture(const GrBackendTexture& backendT GrSurfaceDesc surfDesc; init_surface_desc(&surfDesc, mtlTexture, false, backendTex.config()); - return GrMtlTexture::MakeWrappedTexture(this, surfDesc, mtlTexture, purgeImmediately); + return GrMtlTexture::MakeWrappedTexture(this, surfDesc, mtlTexture, ioType, purgeImmediately); } sk_sp<GrTexture> GrMtlGpu::onWrapRenderableBackendTexture(const GrBackendTexture& backendTex, diff --git a/src/gpu/mtl/GrMtlTexture.h b/src/gpu/mtl/GrMtlTexture.h index 5f6234e6d8..7564f94b00 100644 --- a/src/gpu/mtl/GrMtlTexture.h +++ b/src/gpu/mtl/GrMtlTexture.h @@ -21,8 +21,8 @@ public: MTLTextureDescriptor*, GrMipMapsStatus); - static sk_sp<GrMtlTexture> MakeWrappedTexture(GrMtlGpu*, const GrSurfaceDesc&, - id<MTLTexture>, bool purgeImmediately); + static sk_sp<GrMtlTexture> MakeWrappedTexture(GrMtlGpu*, const GrSurfaceDesc&, id<MTLTexture>, + GrIOType, bool purgeImmediately); ~GrMtlTexture() override; @@ -65,7 +65,7 @@ private: GrMipMapsStatus); GrMtlTexture(GrMtlGpu*, Wrapped, const GrSurfaceDesc&, id<MTLTexture>, GrMipMapsStatus, - bool purgeImmediately); + GrIOType, bool purgeImmediately); id<MTLTexture> fTexture; diff --git a/src/gpu/mtl/GrMtlTexture.mm b/src/gpu/mtl/GrMtlTexture.mm index 711d5ae7ab..5e91746f5b 100644 --- a/src/gpu/mtl/GrMtlTexture.mm +++ b/src/gpu/mtl/GrMtlTexture.mm @@ -28,11 +28,15 @@ GrMtlTexture::GrMtlTexture(GrMtlGpu* gpu, const GrSurfaceDesc& desc, id<MTLTexture> texture, GrMipMapsStatus mipMapsStatus, + GrIOType ioType, bool purgeImmediately) : GrSurface(gpu, desc) , INHERITED(gpu, desc, GrTextureType::k2D, mipMapsStatus) , fTexture(texture) { SkASSERT((GrMipMapsStatus::kNotAllocated == mipMapsStatus) == (1 == texture.mipmapLevelCount)); + if (ioType == kRead_GrIOType) { + this->setReadOnly(); + } this->registerWithCacheWrapped(purgeImmediately); } @@ -63,6 +67,7 @@ sk_sp<GrMtlTexture> GrMtlTexture::CreateNewTexture(GrMtlGpu* gpu, SkBudgeted bud sk_sp<GrMtlTexture> GrMtlTexture::MakeWrappedTexture(GrMtlGpu* gpu, const GrSurfaceDesc& desc, id<MTLTexture> texture, + GrIOType ioType, bool purgeImmediately) { if (desc.fSampleCnt > 1) { SkASSERT(false); // Currently we don't support msaa @@ -72,7 +77,7 @@ sk_sp<GrMtlTexture> GrMtlTexture::MakeWrappedTexture(GrMtlGpu* gpu, SkASSERT(MTLTextureUsageShaderRead & texture.usage); GrMipMapsStatus mipMapsStatus = texture.mipmapLevelCount > 1 ? GrMipMapsStatus::kValid : GrMipMapsStatus::kNotAllocated; - return sk_sp<GrMtlTexture>(new GrMtlTexture(gpu, kWrapped, desc, texture, mipMapsStatus, + return sk_sp<GrMtlTexture>(new GrMtlTexture(gpu, kWrapped, desc, texture, mipMapsStatus, ioType, purgeImmediately)); } diff --git a/src/gpu/vk/GrVkCaps.cpp b/src/gpu/vk/GrVkCaps.cpp index fbd381ff8f..75911b6fde 100644 --- a/src/gpu/vk/GrVkCaps.cpp +++ b/src/gpu/vk/GrVkCaps.cpp @@ -158,8 +158,8 @@ bool GrVkCaps::canCopyAsDraw(GrPixelConfig dstConfig, bool dstIsRenderable, return true; } -bool GrVkCaps::canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, - const SkIRect& srcRect, const SkIPoint& dstPoint) const { +bool GrVkCaps::onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const { GrSurfaceOrigin dstOrigin = dst->origin(); GrSurfaceOrigin srcOrigin = src->origin(); @@ -698,7 +698,7 @@ int GrVkCaps::maxRenderTargetSampleCount(GrPixelConfig config) const { return table[table.count() - 1]; } -bool GrVkCaps::surfaceSupportsWritePixels(const GrSurface* surface) const { +bool GrVkCaps::onSurfaceSupportsWritePixels(const GrSurface* surface) const { if (auto rt = surface->asRenderTarget()) { return rt->numColorSamples() <= 1 && SkToBool(surface->asTexture()); } diff --git a/src/gpu/vk/GrVkCaps.h b/src/gpu/vk/GrVkCaps.h index a20a104c11..9514d41a1b 100644 --- a/src/gpu/vk/GrVkCaps.h +++ b/src/gpu/vk/GrVkCaps.h @@ -43,7 +43,6 @@ public: int getRenderTargetSampleCount(int requestedCount, GrPixelConfig config) const override; int maxRenderTargetSampleCount(GrPixelConfig config) const override; - bool surfaceSupportsWritePixels(const GrSurface*) const override; bool surfaceSupportsReadPixels(const GrSurface*) const override { return true; } bool isConfigTexturableLinearly(GrPixelConfig config) const { @@ -151,9 +150,6 @@ public: bool canCopyAsDraw(GrPixelConfig dstConfig, bool dstIsRenderable, GrPixelConfig srcConfig, bool srcIsTextureable) const; - bool canCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, - const SkIRect& srcRect, const SkIPoint& dstPoint) const override; - bool initDescForDstCopy(const GrRenderTargetProxy* src, GrSurfaceDesc* desc, GrSurfaceOrigin*, bool* rectsMustMatch, bool* disallowSubrect) const override; @@ -201,6 +197,10 @@ private: void applyDriverCorrectnessWorkarounds(const VkPhysicalDeviceProperties&); + bool onSurfaceSupportsWritePixels(const GrSurface*) const override; + bool onCanCopySurface(const GrSurfaceProxy* dst, const GrSurfaceProxy* src, + const SkIRect& srcRect, const SkIPoint& dstPoint) const override; + struct ConfigInfo { ConfigInfo() : fOptimalFlags(0), fLinearFlags(0) {} diff --git a/src/gpu/vk/GrVkGpu.cpp b/src/gpu/vk/GrVkGpu.cpp index ca48271e71..1c02e335f2 100644 --- a/src/gpu/vk/GrVkGpu.cpp +++ b/src/gpu/vk/GrVkGpu.cpp @@ -888,7 +888,8 @@ static bool check_image_info(const GrVkCaps& caps, } sk_sp<GrTexture> GrVkGpu::onWrapBackendTexture(const GrBackendTexture& backendTex, - GrWrapOwnership ownership, bool purgeImmediately) { + GrWrapOwnership ownership, GrIOType ioType, + bool purgeImmediately) { GrVkImageInfo imageInfo; if (!backendTex.getVkImageInfo(&imageInfo)) { return nullptr; @@ -907,7 +908,7 @@ sk_sp<GrTexture> GrVkGpu::onWrapBackendTexture(const GrBackendTexture& backendTe sk_sp<GrVkImageLayout> layout = backendTex.getGrVkImageLayout(); SkASSERT(layout); - return GrVkTexture::MakeWrappedTexture(this, surfDesc, ownership, purgeImmediately, + return GrVkTexture::MakeWrappedTexture(this, surfDesc, ownership, ioType, purgeImmediately, imageInfo, std::move(layout)); } diff --git a/src/gpu/vk/GrVkGpu.h b/src/gpu/vk/GrVkGpu.h index c195d3bfb9..32a7c89280 100644 --- a/src/gpu/vk/GrVkGpu.h +++ b/src/gpu/vk/GrVkGpu.h @@ -170,7 +170,7 @@ private: sk_sp<GrTexture> onCreateTexture(const GrSurfaceDesc&, SkBudgeted, const GrMipLevel[], int mipLevelCount) override; - sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, + sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, GrWrapOwnership, GrIOType, bool purgeImmediately) override; sk_sp<GrTexture> onWrapRenderableBackendTexture(const GrBackendTexture&, int sampleCnt, diff --git a/src/gpu/vk/GrVkTexture.cpp b/src/gpu/vk/GrVkTexture.cpp index 8157433717..a295c0409e 100644 --- a/src/gpu/vk/GrVkTexture.cpp +++ b/src/gpu/vk/GrVkTexture.cpp @@ -41,12 +41,16 @@ GrVkTexture::GrVkTexture(GrVkGpu* gpu, const GrVkImageView* view, GrMipMapsStatus mipMapsStatus, GrBackendObjectOwnership ownership, + GrIOType ioType, bool purgeImmediately) : GrSurface(gpu, desc) , GrVkImage(info, std::move(layout), ownership) , INHERITED(gpu, desc, GrTextureType::k2D, mipMapsStatus) , fTextureView(view) { SkASSERT((GrMipMapsStatus::kNotAllocated == mipMapsStatus) == (1 == info.fLevelCount)); + if (ioType == kRead_GrIOType) { + this->setReadOnly(); + } this->registerWithCacheWrapped(purgeImmediately); } @@ -92,6 +96,7 @@ sk_sp<GrVkTexture> GrVkTexture::MakeNewTexture(GrVkGpu* gpu, SkBudgeted budgeted sk_sp<GrVkTexture> GrVkTexture::MakeWrappedTexture(GrVkGpu* gpu, const GrSurfaceDesc& desc, GrWrapOwnership wrapOwnership, + GrIOType ioType, bool purgeImmediately, const GrVkImageInfo& info, sk_sp<GrVkImageLayout> layout) { @@ -111,7 +116,7 @@ sk_sp<GrVkTexture> GrVkTexture::MakeWrappedTexture(GrVkGpu* gpu, GrBackendObjectOwnership ownership = kBorrow_GrWrapOwnership == wrapOwnership ? GrBackendObjectOwnership::kBorrowed : GrBackendObjectOwnership::kOwned; return sk_sp<GrVkTexture>(new GrVkTexture(gpu, kWrapped, desc, info, std::move(layout), - imageView, mipMapsStatus, ownership, + imageView, mipMapsStatus, ownership, ioType, purgeImmediately)); } diff --git a/src/gpu/vk/GrVkTexture.h b/src/gpu/vk/GrVkTexture.h index d841bf3cbd..b85dee04f1 100644 --- a/src/gpu/vk/GrVkTexture.h +++ b/src/gpu/vk/GrVkTexture.h @@ -25,8 +25,8 @@ public: const GrVkImage::ImageDesc&, GrMipMapsStatus); - static sk_sp<GrVkTexture> MakeWrappedTexture(GrVkGpu*, const GrSurfaceDesc&, - GrWrapOwnership, bool purgeImmediatley, + static sk_sp<GrVkTexture> MakeWrappedTexture(GrVkGpu*, const GrSurfaceDesc&, GrWrapOwnership, + GrIOType, bool purgeImmediately, const GrVkImageInfo&, sk_sp<GrVkImageLayout>); ~GrVkTexture() override; @@ -66,7 +66,7 @@ private: GrMipMapsStatus); GrVkTexture(GrVkGpu*, Wrapped, const GrSurfaceDesc&, const GrVkImageInfo&, sk_sp<GrVkImageLayout> layout, const GrVkImageView* imageView, GrMipMapsStatus, - GrBackendObjectOwnership, bool purgeImmediately); + GrBackendObjectOwnership, GrIOType ioType, bool purgeImmediately); const GrVkImageView* fTextureView; diff --git a/src/image/SkImage_Gpu.cpp b/src/image/SkImage_Gpu.cpp index 600ba39b5a..2404f361f7 100644 --- a/src/image/SkImage_Gpu.cpp +++ b/src/image/SkImage_Gpu.cpp @@ -74,8 +74,8 @@ static sk_sp<SkImage> new_wrapped_texture_common(GrContext* ctx, } GrProxyProvider* proxyProvider = ctx->contextPriv().proxyProvider(); - sk_sp<GrTextureProxy> proxy = proxyProvider->wrapBackendTexture(backendTex, origin, ownership, - releaseProc, releaseCtx); + sk_sp<GrTextureProxy> proxy = proxyProvider->wrapBackendTexture( + backendTex, origin, ownership, kRead_GrIOType, releaseProc, releaseCtx); if (!proxy) { return nullptr; } @@ -373,6 +373,7 @@ sk_sp<SkImage> SkImage_Gpu::MakePromiseTexture(GrContext* context, desc.fHeight = height; desc.fConfig = config; + // We pass kReadOnly here since we should treat content of the client's texture as immutable. sk_sp<GrTextureProxy> proxy = proxyProvider->createLazyProxy( [promiseHelper, config](GrResourceProvider* resourceProvider) mutable { if (!resourceProvider) { @@ -382,7 +383,7 @@ sk_sp<SkImage> SkImage_Gpu::MakePromiseTexture(GrContext* context, return promiseHelper.getTexture(resourceProvider, config); }, - backendFormat, desc, origin, mipMapped, GrInternalSurfaceFlags::kNone, + backendFormat, desc, origin, mipMapped, GrInternalSurfaceFlags::kReadOnly, SkBackingFit::kExact, SkBudgeted::kNo, GrSurfaceProxy::LazyInstantiationType::kUninstantiate); @@ -534,7 +535,7 @@ sk_sp<SkImage> SkImage_Gpu::MakePromiseYUVATexture(GrContext* context, }, yuvaFormats[yuvaIndices[SkYUVAIndex::kY_Index].fIndex], desc, imageOrigin, GrMipMapped::kNo, - GrInternalSurfaceFlags::kNone, SkBackingFit::kExact, SkBudgeted::kNo, + GrInternalSurfaceFlags::kReadOnly, SkBackingFit::kExact, SkBudgeted::kNo, GrSurfaceProxy::LazyInstantiationType::kUninstantiate); if (!proxy) { diff --git a/src/image/SkImage_GpuBase.cpp b/src/image/SkImage_GpuBase.cpp index 4dfc483671..b12fee17d4 100644 --- a/src/image/SkImage_GpuBase.cpp +++ b/src/image/SkImage_GpuBase.cpp @@ -320,7 +320,8 @@ bool SkImage_GpuBase::MakeTempTextureProxies(GrContext* ctx, const GrBackendText SkASSERT(yuvaTexturesCopy[textureIndex].isValid()); tempTextureProxies[textureIndex] = - proxyProvider->wrapBackendTexture(yuvaTexturesCopy[textureIndex], imageOrigin); + proxyProvider->wrapBackendTexture(yuvaTexturesCopy[textureIndex], imageOrigin, + kBorrow_GrWrapOwnership, kRead_GrIOType); if (!tempTextureProxies[textureIndex]) { return false; } @@ -400,7 +401,8 @@ sk_sp<GrTexture> SkPromiseImageHelper::getTexture(GrResourceProvider* resourcePr return sk_sp<GrTexture>(); } - tex = resourceProvider->wrapBackendTexture(fBackendTex, kBorrow_GrWrapOwnership); + tex = resourceProvider->wrapBackendTexture(fBackendTex, kBorrow_GrWrapOwnership, + kRead_GrIOType); if (!tex) { // Even though the GrBackendTexture is not valid, we must call the release // proc to keep our contract of always calling Fulfill and Release in pairs. @@ -412,7 +414,8 @@ sk_sp<GrTexture> SkPromiseImageHelper::getTexture(GrResourceProvider* resourcePr fReleaseHelper->weak_ref(); } else { SkASSERT(fBackendTex.isValid()); - tex = resourceProvider->wrapBackendTexture(fBackendTex, kBorrow_GrWrapOwnership); + tex = resourceProvider->wrapBackendTexture(fBackendTex, kBorrow_GrWrapOwnership, + kRead_GrIOType); if (!tex) { // We weren't able to make a texture here, but since we are in this branch // of the calls (promiseHelper.fReleaseHelper is valid) there is already a diff --git a/tests/GrPorterDuffTest.cpp b/tests/GrPorterDuffTest.cpp index 2bbfa4c77e..f94e274089 100644 --- a/tests/GrPorterDuffTest.cpp +++ b/tests/GrPorterDuffTest.cpp @@ -1068,8 +1068,8 @@ DEF_GPUTEST(PorterDuffNoDualSourceBlending, reporter, options) { GrXferProcessor::DstProxy fakeDstProxy; { - sk_sp<GrTextureProxy> proxy = - proxyProvider->wrapBackendTexture(backendTex, kTopLeft_GrSurfaceOrigin); + sk_sp<GrTextureProxy> proxy = proxyProvider->wrapBackendTexture( + backendTex, kTopLeft_GrSurfaceOrigin, kBorrow_GrWrapOwnership, kRead_GrIOType); fakeDstProxy.setProxy(std::move(proxy)); } diff --git a/tests/GrSurfaceTest.cpp b/tests/GrSurfaceTest.cpp index d3cc2f4f23..693fc54f42 100644 --- a/tests/GrSurfaceTest.cpp +++ b/tests/GrSurfaceTest.cpp @@ -5,8 +5,6 @@ * found in the LICENSE file. */ -#include "SkTypes.h" - #include "GrContext.h" #include "GrContextPriv.h" #include "GrGpu.h" @@ -14,7 +12,10 @@ #include "GrRenderTarget.h" #include "GrResourceProvider.h" #include "GrTexture.h" +#include "GrTexturePriv.h" +#include "SkAutoPixmapStorage.h" #include "SkMipMap.h" +#include "SkTypes.h" #include "Test.h" // Tests that GrSurface::asTexture(), GrSurface::asRenderTarget(), and static upcasting of texture @@ -236,3 +237,94 @@ DEF_GPUTEST_FOR_RENDERING_CONTEXTS(InitialTextureClear, reporter, context_info) } } } + +DEF_GPUTEST_FOR_RENDERING_CONTEXTS(ReadOnlyTexture, reporter, context_info) { + auto fillPixels = [](const SkPixmap* p, const std::function<uint32_t(int x, int y)>& f) { + for (int y = 0; y < p->height(); ++y) { + for (int x = 0; x < p->width(); ++x) { + *p->writable_addr32(x, y) = f(x, y); + } + } + }; + + auto comparePixels = [](const SkPixmap& p1, const SkPixmap& p2, skiatest::Reporter* reporter) { + SkASSERT(p1.info() == p2.info()); + for (int y = 0; y < p1.height(); ++y) { + for (int x = 0; x < p1.width(); ++x) { + REPORTER_ASSERT(reporter, p1.getColor(x, y) == p2.getColor(x, y)); + if (p1.getColor(x, y) != p2.getColor(x, y)) { + return; + } + } + } + }; + + static constexpr int kSize = 100; + SkAutoPixmapStorage pixels; + pixels.alloc(SkImageInfo::Make(kSize, kSize, kRGBA_8888_SkColorType, kPremul_SkAlphaType)); + fillPixels(&pixels, + [](int x, int y) { return (0xFFU << 24) | (x << 16) | (y << 8) | uint8_t(x * y); }); + + GrContext* context = context_info.grContext(); + GrProxyProvider* proxyProvider = context->contextPriv().proxyProvider(); + + // We test both kRW in addition to kRead mostly to ensure that the calls are structured such + // that they'd succeed if the texture wasn't kRead. We want to be sure we're failing with + // kRead for the right reason. + for (auto ioType : {kRead_GrIOType, kRW_GrIOType}) { + auto backendTex = context->contextPriv().getGpu()->createTestingOnlyBackendTexture( + pixels.addr(), kSize, kSize, kRGBA_8888_SkColorType, true, GrMipMapped::kNo); + auto proxy = proxyProvider->wrapBackendTexture(backendTex, kTopLeft_GrSurfaceOrigin, + kBorrow_GrWrapOwnership, ioType); + auto surfContext = context->contextPriv().makeWrappedSurfaceContext(proxy); + + // Read pixels should work with a read-only texture. + SkAutoPixmapStorage read; + read.alloc(pixels.info()); + auto readResult = surfContext->readPixels(pixels.info(), read.writable_addr(), 0, 0, 0); + REPORTER_ASSERT(reporter, readResult); + if (readResult) { + comparePixels(pixels, read, reporter); + } + + // Write pixels should not work with a read-only texture. + SkAutoPixmapStorage write; + write.alloc(pixels.info()); + fillPixels(&write, [&pixels](int x, int y) { return ~*pixels.addr32(); }); + auto writeResult = surfContext->writePixels(pixels.info(), pixels.addr(), 0, 0, 0); + REPORTER_ASSERT(reporter, writeResult == (ioType == kRW_GrIOType)); + // Try the low level write. + context->flush(); + auto gpuWriteResult = context->contextPriv().getGpu()->writePixels( + proxy->peekTexture(), 0, 0, kSize, kSize, GrColorType::kRGBA_8888, write.addr32(), + 0); + REPORTER_ASSERT(reporter, gpuWriteResult == (ioType == kRW_GrIOType)); + + // Copies should not work with a read-only texture + auto copySrc = proxyProvider->createTextureProxy( + SkImage::MakeFromRaster(write, nullptr, nullptr), kNone_GrSurfaceFlags, 1, + SkBudgeted::kYes, SkBackingFit::kExact); + REPORTER_ASSERT(reporter, copySrc); + auto copyResult = surfContext->copy(copySrc.get()); + REPORTER_ASSERT(reporter, copyResult == (ioType == kRW_GrIOType)); + // Try the low level copy. + context->flush(); + auto gpuCopyResult = context->contextPriv().getGpu()->copySurface( + proxy->peekTexture(), kTopLeft_GrSurfaceOrigin, copySrc->peekTexture(), + kTopLeft_GrSurfaceOrigin, SkIRect::MakeWH(kSize, kSize), {0, 0}); + REPORTER_ASSERT(reporter, gpuCopyResult == (ioType == kRW_GrIOType)); + + // Mip regen should not work with a read only texture. + if (context->contextPriv().caps()->mipMapSupport()) { + backendTex = context->contextPriv().getGpu()->createTestingOnlyBackendTexture( + nullptr, kSize, kSize, kRGBA_8888_SkColorType, true, GrMipMapped::kYes); + proxy = proxyProvider->wrapBackendTexture(backendTex, kTopLeft_GrSurfaceOrigin, + kBorrow_GrWrapOwnership, ioType); + context->flush(); + proxy->peekTexture()->texturePriv().markMipMapsDirty(); // avoids assert in GrGpu. + auto regenResult = + context->contextPriv().getGpu()->regenerateMipMapLevels(proxy->peekTexture()); + REPORTER_ASSERT(reporter, regenResult == (ioType == kRW_GrIOType)); + } + } +} diff --git a/tests/GrTestingBackendTextureUploadTest.cpp b/tests/GrTestingBackendTextureUploadTest.cpp index 979d05e14c..9ff0e50fd2 100644 --- a/tests/GrTestingBackendTextureUploadTest.cpp +++ b/tests/GrTestingBackendTextureUploadTest.cpp @@ -50,9 +50,8 @@ void testing_only_texture_test(skiatest::Reporter* reporter, GrContext* context, wrappedTex = gpu->wrapRenderableBackendTexture(backendTex, 1, GrWrapOwnership::kAdopt_GrWrapOwnership); } else { - wrappedTex = gpu->wrapBackendTexture(backendTex, - GrWrapOwnership::kAdopt_GrWrapOwnership, - false); + wrappedTex = gpu->wrapBackendTexture(backendTex, GrWrapOwnership::kAdopt_GrWrapOwnership, + kRead_GrIOType, false); } REPORTER_ASSERT(reporter, wrappedTex); diff --git a/tests/LazyProxyTest.cpp b/tests/LazyProxyTest.cpp index 8b106f053b..e3fea66456 100644 --- a/tests/LazyProxyTest.cpp +++ b/tests/LazyProxyTest.cpp @@ -469,7 +469,8 @@ DEF_GPUTEST(LazyProxyUninstantiateTest, reporter, /* options */) { return sk_sp<GrTexture>(); } - sk_sp<GrTexture> texture = rp->wrapBackendTexture(backendTex); + sk_sp<GrTexture> texture = rp->wrapBackendTexture( + backendTex, kBorrow_GrWrapOwnership, kRead_GrIOType); if (!texture) { return sk_sp<GrTexture>(); } @@ -478,7 +479,7 @@ DEF_GPUTEST(LazyProxyUninstantiateTest, reporter, /* options */) { return texture; }, format, desc, kTopLeft_GrSurfaceOrigin, GrMipMapped::kNo, - GrInternalSurfaceFlags::kNone, SkBackingFit::kExact, SkBudgeted::kNo, lazyType); + GrInternalSurfaceFlags::kReadOnly, SkBackingFit::kExact, SkBudgeted::kNo, lazyType); REPORTER_ASSERT(reporter, lazyProxy.get()); diff --git a/tests/ProxyTest.cpp b/tests/ProxyTest.cpp index 9a5a0d14b6..a52ed8e0c0 100644 --- a/tests/ProxyTest.cpp +++ b/tests/ProxyTest.cpp @@ -317,7 +317,7 @@ DEF_GPUTEST_FOR_RENDERING_CONTEXTS(WrappedProxyTest, reporter, ctxInfo) { false, GrMipMapped::kNo); sk_sp<GrSurfaceProxy> sProxy = proxyProvider->wrapBackendTexture( - backendTex, origin, kBorrow_GrWrapOwnership, nullptr, nullptr); + backendTex, origin, kBorrow_GrWrapOwnership, kRead_GrIOType); if (!sProxy) { gpu->deleteTestingOnlyBackendTexture(backendTex); continue; diff --git a/tests/RectangleTextureTest.cpp b/tests/RectangleTextureTest.cpp index 21a9e19747..dc1d3b7dd6 100644 --- a/tests/RectangleTextureTest.cpp +++ b/tests/RectangleTextureTest.cpp @@ -135,7 +135,8 @@ DEF_GPUTEST_FOR_GL_RENDERING_CONTEXTS(RectangleTexture, reporter, ctxInfo) { } } - sk_sp<GrTextureProxy> rectProxy = proxyProvider->wrapBackendTexture(rectangleTex, origin); + sk_sp<GrTextureProxy> rectProxy = proxyProvider->wrapBackendTexture( + rectangleTex, origin, kBorrow_GrWrapOwnership, kRW_GrIOType); if (!rectProxy) { ERRORF(reporter, "Error creating proxy for rectangle texture."); diff --git a/tests/ResourceAllocatorTest.cpp b/tests/ResourceAllocatorTest.cpp index 58af84ea4b..07d82b1109 100644 --- a/tests/ResourceAllocatorTest.cpp +++ b/tests/ResourceAllocatorTest.cpp @@ -69,7 +69,8 @@ static GrSurfaceProxy* make_backend(GrContext* context, const ProxyParams& p, return nullptr; } - auto tmp = proxyProvider->wrapBackendTexture(*backendTex, p.fOrigin); + auto tmp = proxyProvider->wrapBackendTexture(*backendTex, p.fOrigin, kBorrow_GrWrapOwnership, + kRead_GrIOType); if (!tmp) { return nullptr; } diff --git a/tests/ResourceCacheTest.cpp b/tests/ResourceCacheTest.cpp index 03ba4d1b23..17481250f8 100644 --- a/tests/ResourceCacheTest.cpp +++ b/tests/ResourceCacheTest.cpp @@ -223,10 +223,10 @@ DEF_GPUTEST_FOR_RENDERING_CONTEXTS(ResourceCacheWrappedResources, reporter, ctxI context->resetContext(); sk_sp<GrTexture> borrowed(resourceProvider->wrapBackendTexture( - backendTextures[0], kBorrow_GrWrapOwnership)); + backendTextures[0], kBorrow_GrWrapOwnership, kRead_GrIOType)); sk_sp<GrTexture> adopted(resourceProvider->wrapBackendTexture( - backendTextures[1], kAdopt_GrWrapOwnership)); + backendTextures[1], kAdopt_GrWrapOwnership, kRead_GrIOType)); REPORTER_ASSERT(reporter, borrowed != nullptr && adopted != nullptr); if (!borrowed || !adopted) { diff --git a/tests/TextureProxyTest.cpp b/tests/TextureProxyTest.cpp index 03ded09fed..5260a0e987 100644 --- a/tests/TextureProxyTest.cpp +++ b/tests/TextureProxyTest.cpp @@ -112,7 +112,8 @@ static sk_sp<GrTextureProxy> create_wrapped_backend(GrContext* context, SkBackin GrBackendTexture backendTex = (*backingSurface)->getBackendTexture(); backendTex.setPixelConfig(desc.fConfig); - return proxyProvider->wrapBackendTexture(backendTex, kBottomLeft_GrSurfaceOrigin); + return proxyProvider->wrapBackendTexture(backendTex, kBottomLeft_GrSurfaceOrigin, + kBorrow_GrWrapOwnership, kRead_GrIOType); } diff --git a/tests/TraceMemoryDumpTest.cpp b/tests/TraceMemoryDumpTest.cpp index 32eab62b16..c58e915a98 100644 --- a/tests/TraceMemoryDumpTest.cpp +++ b/tests/TraceMemoryDumpTest.cpp @@ -128,7 +128,7 @@ DEF_GPUTEST_FOR_GL_RENDERING_CONTEXTS(SkTraceMemoryDump_unownedGLTexture, report idDesc.fOwnership = GrBackendObjectOwnership::kBorrowed; auto texture = GrGLTexture::MakeWrapped(gpu, desc, GrMipMapsStatus::kNotAllocated, idDesc, - false); + kRead_GrIOType, false); ValidateMemoryDumps(reporter, context, texture->gpuMemorySize(), false /* isOwned */); } diff --git a/tests/VkWrapTests.cpp b/tests/VkWrapTests.cpp index 155333473c..7c846adb7c 100644 --- a/tests/VkWrapTests.cpp +++ b/tests/VkWrapTests.cpp @@ -42,7 +42,8 @@ void wrap_tex_test(skiatest::Reporter* reporter, GrContext* context) { GrVkImageInfo imageInfo; SkAssertResult(origBackendTex.getVkImageInfo(&imageInfo)); - sk_sp<GrTexture> tex = gpu->wrapBackendTexture(origBackendTex, kBorrow_GrWrapOwnership, false); + sk_sp<GrTexture> tex = + gpu->wrapBackendTexture(origBackendTex, kBorrow_GrWrapOwnership, kRead_GrIOType, false); REPORTER_ASSERT(reporter, tex); // image is null @@ -51,9 +52,9 @@ void wrap_tex_test(skiatest::Reporter* reporter, GrContext* context) { backendCopy.fImage = VK_NULL_HANDLE; GrBackendTexture backendTex = GrBackendTexture(kW, kH, backendCopy); backendTex.setPixelConfig(kPixelConfig); - tex = gpu->wrapBackendTexture(backendTex, kBorrow_GrWrapOwnership, false); + tex = gpu->wrapBackendTexture(backendTex, kBorrow_GrWrapOwnership, kRead_GrIOType, false); REPORTER_ASSERT(reporter, !tex); - tex = gpu->wrapBackendTexture(backendTex, kAdopt_GrWrapOwnership, false); + tex = gpu->wrapBackendTexture(backendTex, kAdopt_GrWrapOwnership, kRead_GrIOType, false); REPORTER_ASSERT(reporter, !tex); } @@ -63,9 +64,9 @@ void wrap_tex_test(skiatest::Reporter* reporter, GrContext* context) { backendCopy.fAlloc = GrVkAlloc(); GrBackendTexture backendTex = GrBackendTexture(kW, kH, backendCopy); backendTex.setPixelConfig(kPixelConfig); - tex = gpu->wrapBackendTexture(backendTex, kBorrow_GrWrapOwnership, false); + tex = gpu->wrapBackendTexture(backendTex, kBorrow_GrWrapOwnership, kRead_GrIOType, false); REPORTER_ASSERT(reporter, !tex); - tex = gpu->wrapBackendTexture(backendTex, kAdopt_GrWrapOwnership, false); + tex = gpu->wrapBackendTexture(backendTex, kAdopt_GrWrapOwnership, kRead_GrIOType, false); REPORTER_ASSERT(reporter, !tex); } @@ -74,7 +75,7 @@ void wrap_tex_test(skiatest::Reporter* reporter, GrContext* context) { GrVkImageInfo backendCopy = imageInfo; GrBackendTexture backendTex = GrBackendTexture(kW, kH, backendCopy); backendTex.setPixelConfig(kPixelConfig); - tex = gpu->wrapBackendTexture(backendTex, kAdopt_GrWrapOwnership, false); + tex = gpu->wrapBackendTexture(backendTex, kAdopt_GrWrapOwnership, kRead_GrIOType, false); REPORTER_ASSERT(reporter, tex); } diff --git a/tools/gpu/ProxyUtils.cpp b/tools/gpu/ProxyUtils.cpp index fc167d8685..a1f4df6cdb 100644 --- a/tools/gpu/ProxyUtils.cpp +++ b/tools/gpu/ProxyUtils.cpp @@ -36,7 +36,7 @@ sk_sp<GrTextureProxy> MakeTextureProxyFromData(GrContext* context, bool isRT, in backendTex, origin, 1, kAdopt_GrWrapOwnership); } else { proxy = context->contextPriv().proxyProvider()->wrapBackendTexture( - backendTex, origin, kAdopt_GrWrapOwnership); + backendTex, origin, kAdopt_GrWrapOwnership, kRW_GrIOType); } if (!proxy) { |