1 /* 2 * Copyright 2011 Google Inc. 3 * 4 * Use of this source code is governed by a BSD-style license that can be 5 * found in the LICENSE file. 6 */ 7 8 #ifndef GrGLGpu_DEFINED 9 #define GrGLGpu_DEFINED 10 11 #include "GrGLContext.h" 12 #include "GrGLIRect.h" 13 #include "GrGLPathRendering.h" 14 #include "GrGLProgram.h" 15 #include "GrGLRenderTarget.h" 16 #include "GrGLStencilAttachment.h" 17 #include "GrGLTexture.h" 18 #include "GrGLVertexArray.h" 19 #include "GrGpu.h" 20 #include "GrMesh.h" 21 #include "GrWindowRectsState.h" 22 #include "GrXferProcessor.h" 23 #include "SkLRUCache.h" 24 #include "SkTArray.h" 25 #include "SkTypes.h" 26 27 class GrGLBuffer; 28 class GrPipeline; 29 class GrSwizzle; 30 31 namespace gr_instanced { class GLInstancedRendering; } 32 33 #ifdef SK_DEBUG 34 #define PROGRAM_CACHE_STATS 35 #endif 36 37 class GrGLGpu final : public GrGpu, private GrMesh::SendToGpuImpl { 38 public: 39 static GrGpu* Create(GrBackendContext backendContext, const GrContextOptions& options, 40 GrContext* context); 41 ~GrGLGpu() override; 42 43 void disconnect(DisconnectType) override; 44 glContext()45 const GrGLContext& glContext() const { return *fGLContext; } 46 glInterface()47 const GrGLInterface* glInterface() const { return fGLContext->interface(); } ctxInfo()48 const GrGLContextInfo& ctxInfo() const { return *fGLContext; } glStandard()49 GrGLStandard glStandard() const { return fGLContext->standard(); } glVersion()50 GrGLVersion glVersion() const { return fGLContext->version(); } glslGeneration()51 GrGLSLGeneration glslGeneration() const { return fGLContext->glslGeneration(); } glCaps()52 const GrGLCaps& glCaps() const { return *fGLContext->caps(); } 53 glPathRendering()54 GrGLPathRendering* glPathRendering() { 55 SkASSERT(glCaps().shaderCaps()->pathRenderingSupport()); 56 return static_cast<GrGLPathRendering*>(pathRendering()); 57 } 58 59 // Used by GrGLProgram to configure OpenGL state. 60 void bindTexture(int unitIdx, const GrSamplerParams& params, bool allowSRGBInputs, 61 GrGLTexture* texture); 62 63 void bindTexelBuffer(int unitIdx, GrPixelConfig, GrGLBuffer*); 64 65 void bindImageStorage(int unitIdx, GrIOType, GrGLTexture *); 66 67 void generateMipmaps(const GrSamplerParams& params, bool allowSRGBInputs, GrGLTexture* texture); 68 69 bool onGetReadPixelsInfo(GrSurface* srcSurface, int readWidth, int readHeight, size_t rowBytes, 70 GrPixelConfig readConfig, DrawPreference*, 71 ReadPixelTempDrawInfo*) override; 72 73 bool onGetWritePixelsInfo(GrSurface* dstSurface, int width, int height, 74 GrPixelConfig srcConfig, DrawPreference*, 75 WritePixelTempDrawInfo*) override; 76 77 // These functions should be used to bind GL objects. They track the GL state and skip redundant 78 // bindings. Making the equivalent glBind calls directly will confuse the state tracking. bindVertexArray(GrGLuint id)79 void bindVertexArray(GrGLuint id) { 80 fHWVertexArrayState.setVertexArrayID(this, id); 81 } 82 83 // These callbacks update state tracking when GL objects are deleted. They are called from 84 // GrGLResource onRelease functions. notifyVertexArrayDelete(GrGLuint id)85 void notifyVertexArrayDelete(GrGLuint id) { 86 fHWVertexArrayState.notifyVertexArrayDelete(id); 87 } 88 89 // Binds a buffer to the GL target corresponding to 'type', updates internal state tracking, and 90 // returns the GL target the buffer was bound to. 91 // When 'type' is kIndex_GrBufferType, this function will also implicitly bind the default VAO. 92 // If the caller wishes to bind an index buffer to a specific VAO, it can call glBind directly. 93 GrGLenum bindBuffer(GrBufferType type, const GrBuffer*); 94 95 // Called by GrGLBuffer after its buffer object has been destroyed. 96 void notifyBufferReleased(const GrGLBuffer*); 97 98 // The GrGLGpuCommandBuffer does not buffer up draws before submitting them to the gpu. 99 // Thus this is the implementation of the draw call for the corresponding passthrough function 100 // on GrGLGpuCommandBuffer. 101 void draw(const GrPipeline&, 102 const GrPrimitiveProcessor&, 103 const GrMesh[], 104 const GrPipeline::DynamicState[], 105 int meshCount); 106 107 108 // GrMesh::SendToGpuImpl methods. These issue the actual GL draw calls. 109 // Marked final as a hint to the compiler to not use virtual dispatch. 110 void sendMeshToGpu(const GrPrimitiveProcessor&, GrPrimitiveType, 111 const GrBuffer* vertexBuffer, int vertexCount, int baseVertex) final; 112 113 void sendIndexedMeshToGpu(const GrPrimitiveProcessor&, GrPrimitiveType, 114 const GrBuffer* indexBuffer, int indexCount, int baseIndex, 115 uint16_t minIndexValue, uint16_t maxIndexValue, 116 const GrBuffer* vertexBuffer, int baseVertex) final; 117 118 void sendInstancedMeshToGpu(const GrPrimitiveProcessor&, GrPrimitiveType, 119 const GrBuffer* vertexBuffer, int vertexCount, int baseVertex, 120 const GrBuffer* instanceBuffer, int instanceCount, 121 int baseInstance) final; 122 123 void sendIndexedInstancedMeshToGpu(const GrPrimitiveProcessor&, GrPrimitiveType, 124 const GrBuffer* indexBuffer, int indexCount, int baseIndex, 125 const GrBuffer* vertexBuffer, int baseVertex, 126 const GrBuffer* instanceBuffer, int instanceCount, 127 int baseInstance) final; 128 129 // The GrGLGpuCommandBuffer does not buffer up draws before submitting them to the gpu. 130 // Thus this is the implementation of the clear call for the corresponding passthrough function 131 // on GrGLGpuCommandBuffer. 132 void clear(const GrFixedClip&, GrColor, GrRenderTarget*); 133 134 // The GrGLGpuCommandBuffer does not buffer up draws before submitting them to the gpu. 135 // Thus this is the implementation of the clearStencil call for the corresponding passthrough 136 // function on GrGLGpuCommandBuffer. 137 void clearStencilClip(const GrFixedClip&, bool insideStencilMask, GrRenderTarget*); 138 glContextForTesting()139 const GrGLContext* glContextForTesting() const override { 140 return &this->glContext(); 141 } 142 143 void clearStencil(GrRenderTarget*) override; 144 145 GrGpuCommandBuffer* createCommandBuffer( 146 const GrGpuCommandBuffer::LoadAndStoreInfo& colorInfo, 147 const GrGpuCommandBuffer::LoadAndStoreInfo& stencilInfo) override; 148 invalidateBoundRenderTarget()149 void invalidateBoundRenderTarget() { 150 fHWBoundRenderTargetUniqueID.makeInvalid(); 151 } 152 153 GrStencilAttachment* createStencilAttachmentForRenderTarget(const GrRenderTarget* rt, 154 int width, 155 int height) override; 156 157 GrBackendObject createTestingOnlyBackendTexture(void* pixels, int w, int h, 158 GrPixelConfig config, 159 bool isRenderTarget = false) override; 160 bool isTestingOnlyBackendTexture(GrBackendObject) const override; 161 void deleteTestingOnlyBackendTexture(GrBackendObject, bool abandonTexture) override; 162 163 void resetShaderCacheForTesting() const override; 164 165 GrFence SK_WARN_UNUSED_RESULT insertFence() override; 166 bool waitFence(GrFence, uint64_t timeout) override; 167 void deleteFence(GrFence) const override; 168 169 sk_sp<GrSemaphore> SK_WARN_UNUSED_RESULT makeSemaphore(bool isOwned) override; 170 sk_sp<GrSemaphore> wrapBackendSemaphore(const GrBackendSemaphore& semaphore, 171 GrWrapOwnership ownership) override; 172 void insertSemaphore(sk_sp<GrSemaphore> semaphore, bool flush) override; 173 void waitSemaphore(sk_sp<GrSemaphore> semaphore) override; 174 175 sk_sp<GrSemaphore> prepareTextureForCrossContextUsage(GrTexture*) override; 176 177 void deleteSync(GrGLsync) const; 178 179 private: 180 GrGLGpu(GrGLContext* ctx, GrContext* context); 181 182 // GrGpu overrides 183 void onResetContext(uint32_t resetBits) override; 184 185 void xferBarrier(GrRenderTarget*, GrXferBarrierType) override; 186 187 sk_sp<GrTexture> onCreateTexture(const GrSurfaceDesc& desc, SkBudgeted budgeted, 188 const GrMipLevel texels[], 189 int mipLevelCount) override; 190 191 GrBuffer* onCreateBuffer(size_t size, GrBufferType intendedType, GrAccessPattern, 192 const void* data) override; 193 194 sk_sp<GrTexture> onWrapBackendTexture(const GrBackendTexture&, 195 GrSurfaceOrigin, 196 GrBackendTextureFlags, 197 int sampleCnt, 198 GrWrapOwnership) override; 199 sk_sp<GrRenderTarget> onWrapBackendRenderTarget(const GrBackendRenderTarget&, 200 GrSurfaceOrigin origin) override; 201 sk_sp<GrRenderTarget> onWrapBackendTextureAsRenderTarget(const GrBackendTexture&, 202 GrSurfaceOrigin, 203 int sampleCnt) override; 204 205 std::unique_ptr<gr_instanced::OpAllocator> onCreateInstancedRenderingAllocator() override; 206 gr_instanced::InstancedRendering* onCreateInstancedRendering() override; 207 208 // Given a GrPixelConfig return the index into the stencil format array on GrGLCaps to a 209 // compatible stencil format, or negative if there is no compatible stencil format. 210 int getCompatibleStencilIndex(GrPixelConfig config); 211 212 213 // Returns whether the texture is successfully created. On success, the 214 // result is stored in |info|. 215 // The texture is populated with |texels|, if it exists. 216 // The texture parameters are cached in |initialTexParams|. 217 bool createTextureImpl(const GrSurfaceDesc& desc, GrGLTextureInfo* info, 218 bool renderTarget, GrGLTexture::TexParams* initialTexParams, 219 const GrMipLevel texels[], int mipLevelCount); 220 221 bool onIsACopyNeededForTextureParams(GrTextureProxy*, const GrSamplerParams&, 222 GrTextureProducer::CopyParams*, 223 SkScalar scaleAdjust[2]) const override; 224 225 // Checks whether glReadPixels can be called to get pixel values in readConfig from the 226 // render target. 227 bool readPixelsSupported(GrRenderTarget* target, GrPixelConfig readConfig); 228 229 // Checks whether glReadPixels can be called to get pixel values in readConfig from a 230 // render target that has renderTargetConfig. This may have to create a temporary 231 // render target and thus is less preferable than the variant that takes a render target. 232 bool readPixelsSupported(GrPixelConfig renderTargetConfig, GrPixelConfig readConfig); 233 234 // Checks whether glReadPixels can be called to get pixel values in readConfig from a 235 // render target that has the same config as surfaceForConfig. Calls one of the the two 236 // variations above, depending on whether the surface is a render target or not. 237 bool readPixelsSupported(GrSurface* surfaceForConfig, GrPixelConfig readConfig); 238 239 bool onReadPixels(GrSurface*, 240 int left, int top, 241 int width, int height, 242 GrPixelConfig, 243 void* buffer, 244 size_t rowBytes) override; 245 246 bool onWritePixels(GrSurface*, 247 int left, int top, int width, int height, 248 GrPixelConfig config, 249 const GrMipLevel texels[], int mipLevelCount) override; 250 251 bool onTransferPixels(GrTexture*, 252 int left, int top, int width, int height, 253 GrPixelConfig config, GrBuffer* transferBuffer, 254 size_t offset, size_t rowBytes) override; 255 256 void onResolveRenderTarget(GrRenderTarget* target) override; 257 258 bool onCopySurface(GrSurface* dst, 259 GrSurface* src, 260 const SkIRect& srcRect, 261 const SkIPoint& dstPoint) override; 262 263 void onQueryMultisampleSpecs(GrRenderTarget*, const GrStencilSettings&, 264 int* effectiveSampleCnt, SamplePattern*) override; 265 266 // binds texture unit in GL 267 void setTextureUnit(int unitIdx); 268 269 void setTextureSwizzle(int unitIdx, GrGLenum target, const GrGLenum swizzle[]); 270 271 // Flushes state from GrPipeline to GL. Returns false if the state couldn't be set. 272 // willDrawPoints must be true if point primitives will be rendered after setting the GL state. 273 bool flushGLState(const GrPipeline&, const GrPrimitiveProcessor&, bool willDrawPoints); 274 275 // Sets up vertex/instance attribute pointers and strides. 276 void setupGeometry(const GrPrimitiveProcessor&, 277 const GrBuffer* indexBuffer, 278 const GrBuffer* vertexBuffer, 279 int baseVertex, 280 const GrBuffer* instanceBuffer, 281 int baseInstance); 282 283 void flushBlend(const GrXferProcessor::BlendInfo& blendInfo, const GrSwizzle&); 284 hasExtension(const char * ext)285 bool hasExtension(const char* ext) const { return fGLContext->hasExtension(ext); } 286 287 bool copySurfaceAsDraw(GrSurface* dst, 288 GrSurface* src, 289 const SkIRect& srcRect, 290 const SkIPoint& dstPoint); 291 void copySurfaceAsCopyTexSubImage(GrSurface* dst, 292 GrSurface* src, 293 const SkIRect& srcRect, 294 const SkIPoint& dstPoint); 295 bool copySurfaceAsBlitFramebuffer(GrSurface* dst, 296 GrSurface* src, 297 const SkIRect& srcRect, 298 const SkIPoint& dstPoint); 299 bool generateMipmap(GrGLTexture* texture, bool gammaCorrect); 300 void clearStencilClipAsDraw(const GrFixedClip&, bool insideStencilMask, GrRenderTarget*); 301 302 static bool BlendCoeffReferencesConstant(GrBlendCoeff coeff); 303 304 class ProgramCache : public ::SkNoncopyable { 305 public: 306 ProgramCache(GrGLGpu* gpu); 307 ~ProgramCache(); 308 309 void abandon(); 310 GrGLProgram* refProgram(const GrGLGpu*, const GrPipeline&, const GrPrimitiveProcessor&, 311 bool hasPointSize); 312 313 private: 314 // We may actually have kMaxEntries+1 shaders in the GL context because we create a new 315 // shader before evicting from the cache. 316 static const int kMaxEntries = 128; 317 318 struct Entry; 319 320 // binary search for entry matching desc. returns index into fEntries that matches desc or ~ 321 // of the index of where it should be inserted. 322 int search(const GrProgramDesc& desc) const; 323 324 struct DescHash { operatorDescHash325 uint32_t operator()(const GrProgramDesc& desc) const { 326 return SkOpts::hash_fn(desc.asKey(), desc.keyLength(), 0); 327 } 328 }; 329 330 SkLRUCache<GrProgramDesc, std::unique_ptr<Entry>, DescHash> fMap; 331 332 GrGLGpu* fGpu; 333 #ifdef PROGRAM_CACHE_STATS 334 int fTotalRequests; 335 int fCacheMisses; 336 int fHashMisses; // cache hit but hash table missed 337 #endif 338 }; 339 340 void flushColorWrite(bool writeColor); 341 342 // flushes the scissor. see the note on flushBoundTextureAndParams about 343 // flushing the scissor after that function is called. 344 void flushScissor(const GrScissorState&, 345 const GrGLIRect& rtViewport, 346 GrSurfaceOrigin rtOrigin); 347 348 // disables the scissor 349 void disableScissor(); 350 351 void flushWindowRectangles(const GrWindowRectsState&, const GrGLRenderTarget*); 352 void disableWindowRectangles(); 353 354 // sets a texture unit to use for texture operations other than binding a texture to a program. 355 // ensures that such operations don't negatively interact with tracking bound textures. 356 void setScratchTextureUnit(); 357 358 // bounds is region that may be modified. 359 // nullptr means whole target. Can be an empty rect. 360 void flushRenderTarget(GrGLRenderTarget*, const SkIRect* bounds, bool disableSRGB = false); 361 362 // Need not be called if flushRenderTarget is used. 363 void flushViewport(const GrGLIRect&); 364 365 void flushStencil(const GrStencilSettings&); 366 void disableStencil(); 367 368 // rt is used only if useHWAA is true. 369 void flushHWAAState(GrRenderTarget* rt, bool useHWAA, bool stencilEnabled); 370 371 void flushMinSampleShading(float minSampleShading); 372 373 void flushFramebufferSRGB(bool enable); 374 375 // helper for onCreateTexture and writeTexturePixels 376 enum UploadType { 377 kNewTexture_UploadType, // we are creating a new texture 378 kWrite_UploadType, // we are using TexSubImage2D to copy data to an existing texture 379 }; 380 bool uploadTexData(GrPixelConfig texConfig, int texWidth, int texHeight, 381 GrSurfaceOrigin texOrigin, GrGLenum target, UploadType uploadType, int left, 382 int top, int width, int height, GrPixelConfig dataConfig, 383 const GrMipLevel texels[], int mipLevelCount); 384 385 bool createRenderTargetObjects(const GrSurfaceDesc&, const GrGLTextureInfo& texInfo, 386 GrGLRenderTarget::IDDesc*); 387 388 enum TempFBOTarget { 389 kSrc_TempFBOTarget, 390 kDst_TempFBOTarget 391 }; 392 393 // Binds a surface as a FBO for copying, reading, or clearing. If the surface already owns an 394 // FBO ID then that ID is bound. If not the surface is temporarily bound to a FBO and that FBO 395 // is bound. This must be paired with a call to unbindSurfaceFBOForPixelOps(). 396 void bindSurfaceFBOForPixelOps(GrSurface* surface, GrGLenum fboTarget, GrGLIRect* viewport, 397 TempFBOTarget tempFBOTarget); 398 399 // Must be called if bindSurfaceFBOForPixelOps was used to bind a surface for copying. 400 void unbindTextureFBOForPixelOps(GrGLenum fboTarget, GrSurface* surface); 401 402 sk_sp<GrGLContext> fGLContext; 403 404 bool createCopyProgram(GrTexture* srcTexture); 405 bool createMipmapProgram(int progIdx); 406 bool createStencilClipClearProgram(); 407 408 // GL program-related state 409 ProgramCache* fProgramCache; 410 411 /////////////////////////////////////////////////////////////////////////// 412 ///@name Caching of GL State 413 ///@{ 414 int fHWActiveTextureUnitIdx; 415 GrGLuint fHWProgramID; 416 417 enum TriState { 418 kNo_TriState, 419 kYes_TriState, 420 kUnknown_TriState 421 }; 422 423 GrGLuint fTempSrcFBOID; 424 GrGLuint fTempDstFBOID; 425 426 GrGLuint fStencilClearFBOID; 427 428 // last scissor / viewport scissor state seen by the GL. 429 struct { 430 TriState fEnabled; 431 GrGLIRect fRect; invalidate__anon660999490108432 void invalidate() { 433 fEnabled = kUnknown_TriState; 434 fRect.invalidate(); 435 } 436 } fHWScissorSettings; 437 438 class { 439 public: valid()440 bool valid() const { return kInvalidSurfaceOrigin != fRTOrigin; } invalidate()441 void invalidate() { fRTOrigin = kInvalidSurfaceOrigin; } knownDisabled()442 bool knownDisabled() const { return this->valid() && !fWindowState.enabled(); } setDisabled()443 void setDisabled() { 444 fRTOrigin = kDefault_GrSurfaceOrigin; 445 fWindowState.setDisabled(); 446 } 447 set(GrSurfaceOrigin rtOrigin,const GrGLIRect & viewport,const GrWindowRectsState & windowState)448 void set(GrSurfaceOrigin rtOrigin, const GrGLIRect& viewport, 449 const GrWindowRectsState& windowState) { 450 fRTOrigin = rtOrigin; 451 fViewport = viewport; 452 fWindowState = windowState; 453 } 454 knownEqualTo(GrSurfaceOrigin rtOrigin,const GrGLIRect & viewport,const GrWindowRectsState & windowState)455 bool knownEqualTo(GrSurfaceOrigin rtOrigin, const GrGLIRect& viewport, 456 const GrWindowRectsState& windowState) const { 457 if (!this->valid()) { 458 return false; 459 } 460 if (fWindowState.numWindows() && (fRTOrigin != rtOrigin || fViewport != viewport)) { 461 return false; 462 } 463 return fWindowState == windowState; 464 } 465 466 private: 467 enum { kInvalidSurfaceOrigin = -1 }; 468 469 int fRTOrigin; 470 GrGLIRect fViewport; 471 GrWindowRectsState fWindowState; 472 } fHWWindowRectsState; 473 474 GrGLIRect fHWViewport; 475 476 /** 477 * Tracks vertex attrib array state. 478 */ 479 class HWVertexArrayState { 480 public: HWVertexArrayState()481 HWVertexArrayState() : fCoreProfileVertexArray(nullptr) { this->invalidate(); } 482 ~HWVertexArrayState()483 ~HWVertexArrayState() { delete fCoreProfileVertexArray; } 484 invalidate()485 void invalidate() { 486 fBoundVertexArrayIDIsValid = false; 487 fDefaultVertexArrayAttribState.invalidate(); 488 if (fCoreProfileVertexArray) { 489 fCoreProfileVertexArray->invalidateCachedState(); 490 } 491 } 492 notifyVertexArrayDelete(GrGLuint id)493 void notifyVertexArrayDelete(GrGLuint id) { 494 if (fBoundVertexArrayIDIsValid && fBoundVertexArrayID == id) { 495 // Does implicit bind to 0 496 fBoundVertexArrayID = 0; 497 } 498 } 499 setVertexArrayID(GrGLGpu * gpu,GrGLuint arrayID)500 void setVertexArrayID(GrGLGpu* gpu, GrGLuint arrayID) { 501 if (!gpu->glCaps().vertexArrayObjectSupport()) { 502 SkASSERT(0 == arrayID); 503 return; 504 } 505 if (!fBoundVertexArrayIDIsValid || arrayID != fBoundVertexArrayID) { 506 GR_GL_CALL(gpu->glInterface(), BindVertexArray(arrayID)); 507 fBoundVertexArrayIDIsValid = true; 508 fBoundVertexArrayID = arrayID; 509 } 510 } 511 512 /** 513 * Binds the vertex array that should be used for internal draws, and returns its attrib 514 * state. This binds the default VAO (ID=zero) unless we are on a core profile, in which 515 * case we use a dummy array instead. 516 * 517 * If an index buffer is privided, it will be bound to the vertex array. Otherwise the 518 * index buffer binding will be left unchanged. 519 * 520 * The returned GrGLAttribArrayState should be used to set vertex attribute arrays. 521 */ 522 GrGLAttribArrayState* bindInternalVertexArray(GrGLGpu*, const GrBuffer* ibuff = nullptr); 523 524 private: 525 GrGLuint fBoundVertexArrayID; 526 bool fBoundVertexArrayIDIsValid; 527 528 // We return a non-const pointer to this from bindArrayAndBuffersToDraw when vertex array 0 529 // is bound. However, this class is internal to GrGLGpu and this object never leaks out of 530 // GrGLGpu. 531 GrGLAttribArrayState fDefaultVertexArrayAttribState; 532 533 // This is used when we're using a core profile. 534 GrGLVertexArray* fCoreProfileVertexArray; 535 } fHWVertexArrayState; 536 537 struct { 538 GrGLenum fGLTarget; 539 GrGpuResource::UniqueID fBoundBufferUniqueID; 540 bool fBufferZeroKnownBound; 541 invalidate__anon660999490308542 void invalidate() { 543 fBoundBufferUniqueID.makeInvalid(); 544 fBufferZeroKnownBound = false; 545 } 546 } fHWBufferState[kGrBufferTypeCount]; 547 548 struct { 549 GrBlendEquation fEquation; 550 GrBlendCoeff fSrcCoeff; 551 GrBlendCoeff fDstCoeff; 552 GrColor fConstColor; 553 bool fConstColorValid; 554 TriState fEnabled; 555 invalidate__anon660999490408556 void invalidate() { 557 fEquation = static_cast<GrBlendEquation>(-1); 558 fSrcCoeff = static_cast<GrBlendCoeff>(-1); 559 fDstCoeff = static_cast<GrBlendCoeff>(-1); 560 fConstColorValid = false; 561 fEnabled = kUnknown_TriState; 562 } 563 } fHWBlendState; 564 565 TriState fMSAAEnabled; 566 567 GrStencilSettings fHWStencilSettings; 568 TriState fHWStencilTestEnabled; 569 570 571 TriState fHWWriteToColor; 572 GrGpuResource::UniqueID fHWBoundRenderTargetUniqueID; 573 TriState fHWSRGBFramebuffer; 574 SkTArray<GrGpuResource::UniqueID, true> fHWBoundTextureUniqueIDs; 575 576 struct Image { 577 GrGpuResource::UniqueID fTextureUniqueID; 578 GrIOType fIOType; 579 }; 580 SkTArray<Image, true> fHWBoundImageStorages; 581 582 struct BufferTexture { BufferTextureBufferTexture583 BufferTexture() : fTextureID(0), fKnownBound(false), 584 fAttachedBufferUniqueID(SK_InvalidUniqueID), 585 fSwizzle(GrSwizzle::RGBA()) {} 586 587 GrGLuint fTextureID; 588 bool fKnownBound; 589 GrPixelConfig fTexelConfig; 590 GrGpuResource::UniqueID fAttachedBufferUniqueID; 591 GrSwizzle fSwizzle; 592 }; 593 594 SkTArray<BufferTexture, true> fHWBufferTextures; 595 int fHWMaxUsedBufferTextureUnit; 596 597 // EXT_raster_multisample. 598 TriState fHWRasterMultisampleEnabled; 599 int fHWNumRasterSamples; 600 ///@} 601 602 /** IDs for copy surface program. (4 sampler types) */ 603 struct { 604 GrGLuint fProgram; 605 GrGLint fTextureUniform; 606 GrGLint fTexCoordXformUniform; 607 GrGLint fPosXformUniform; 608 } fCopyPrograms[4]; 609 sk_sp<GrGLBuffer> fCopyProgramArrayBuffer; 610 611 /** IDs for texture mipmap program. (4 filter configurations) */ 612 struct { 613 GrGLuint fProgram; 614 GrGLint fTextureUniform; 615 GrGLint fTexCoordXformUniform; 616 } fMipmapPrograms[4]; 617 sk_sp<GrGLBuffer> fMipmapProgramArrayBuffer; 618 619 GrGLuint fStencilClipClearProgram; 620 sk_sp<GrGLBuffer> fStencilClipClearArrayBuffer; 621 622 static int TextureToCopyProgramIdx(GrTexture* texture); 623 TextureSizeToMipmapProgramIdx(int width,int height)624 static int TextureSizeToMipmapProgramIdx(int width, int height) { 625 const bool wide = (width > 1) && SkToBool(width & 0x1); 626 const bool tall = (height > 1) && SkToBool(height & 0x1); 627 return (wide ? 0x2 : 0x0) | (tall ? 0x1 : 0x0); 628 } 629 630 float fHWMinSampleShading; 631 GrPrimitiveType fLastPrimitiveType; 632 633 typedef GrGpu INHERITED; 634 friend class GrGLPathRendering; // For accessing setTextureUnit. 635 friend class gr_instanced::GLInstancedRendering; // For accessing flushGLState. 636 }; 637 638 #endif 639