OLD | NEW |
1 | 1 |
2 /* | 2 /* |
3 * Copyright 2011 Google Inc. | 3 * Copyright 2011 Google Inc. |
4 * | 4 * |
5 * Use of this source code is governed by a BSD-style license that can be | 5 * Use of this source code is governed by a BSD-style license that can be |
6 * found in the LICENSE file. | 6 * found in the LICENSE file. |
7 */ | 7 */ |
8 | 8 |
9 | 9 |
10 #include "GrContext.h" | 10 #include "GrContext.h" |
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
108 GrAssert(NULL == fGpu); | 108 GrAssert(NULL == fGpu); |
109 | 109 |
110 fGpu = GrGpu::Create(backend, backendContext, this); | 110 fGpu = GrGpu::Create(backend, backendContext, this); |
111 if (NULL == fGpu) { | 111 if (NULL == fGpu) { |
112 return false; | 112 return false; |
113 } | 113 } |
114 | 114 |
115 fDrawState = SkNEW(GrDrawState); | 115 fDrawState = SkNEW(GrDrawState); |
116 fGpu->setDrawState(fDrawState); | 116 fGpu->setDrawState(fDrawState); |
117 | 117 |
118 | |
119 fTextureCache = SkNEW_ARGS(GrResourceCache, | 118 fTextureCache = SkNEW_ARGS(GrResourceCache, |
120 (MAX_TEXTURE_CACHE_COUNT, | 119 (MAX_TEXTURE_CACHE_COUNT, |
121 MAX_TEXTURE_CACHE_BYTES)); | 120 MAX_TEXTURE_CACHE_BYTES)); |
122 fTextureCache->setOverbudgetCallback(OverbudgetCB, this); | 121 fTextureCache->setOverbudgetCallback(OverbudgetCB, this); |
123 | 122 |
124 fFontCache = SkNEW_ARGS(GrFontCache, (fGpu)); | 123 fFontCache = SkNEW_ARGS(GrFontCache, (fGpu)); |
125 | 124 |
126 fLastDrawWasBuffered = kNo_BufferedDraw; | 125 fLastDrawWasBuffered = kNo_BufferedDraw; |
127 | 126 |
128 fAARectRenderer = SkNEW(GrAARectRenderer); | 127 fAARectRenderer = SkNEW(GrAARectRenderer); |
(...skipping 263 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
392 if (NULL != texture) { | 391 if (NULL != texture) { |
393 // Adding a resource could put us overbudget. Try to free up the | 392 // Adding a resource could put us overbudget. Try to free up the |
394 // necessary space before adding it. | 393 // necessary space before adding it. |
395 fTextureCache->purgeAsNeeded(1, texture->sizeInBytes()); | 394 fTextureCache->purgeAsNeeded(1, texture->sizeInBytes()); |
396 fTextureCache->addResource(resourceKey, texture); | 395 fTextureCache->addResource(resourceKey, texture); |
397 } | 396 } |
398 | 397 |
399 return texture; | 398 return texture; |
400 } | 399 } |
401 | 400 |
| 401 static GrTexture* create_scratch_texture(GrGpu* gpu, |
| 402 GrResourceCache* textureCache, |
| 403 const GrTextureDesc& desc) { |
| 404 GrTexture* texture = gpu->createTexture(desc, NULL, 0); |
| 405 if (NULL != texture) { |
| 406 GrResourceKey key = GrTexture::ComputeScratchKey(texture->desc()); |
| 407 // Adding a resource could put us overbudget. Try to free up the |
| 408 // necessary space before adding it. |
| 409 textureCache->purgeAsNeeded(1, texture->sizeInBytes()); |
| 410 // Make the resource exclusive so future 'find' calls don't return it |
| 411 textureCache->addResource(key, texture, GrResourceCache::kHide_Ownership
Flag); |
| 412 } |
| 413 return texture; |
| 414 } |
| 415 |
402 GrTexture* GrContext::lockAndRefScratchTexture(const GrTextureDesc& inDesc, Scra
tchTexMatch match) { | 416 GrTexture* GrContext::lockAndRefScratchTexture(const GrTextureDesc& inDesc, Scra
tchTexMatch match) { |
| 417 |
| 418 GrAssert((inDesc.fFlags & kRenderTarget_GrTextureFlagBit) || |
| 419 !(inDesc.fFlags & kNoStencil_GrTextureFlagBit)); |
| 420 |
| 421 // Renderable A8 targets are not universally supported (e.g., not on ANGLE) |
| 422 GrAssert(this->isConfigRenderable(kAlpha_8_GrPixelConfig) || |
| 423 !(inDesc.fFlags & kRenderTarget_GrTextureFlagBit) || |
| 424 (inDesc.fConfig != kAlpha_8_GrPixelConfig)); |
| 425 |
| 426 if (!fGpu->caps()->reuseScratchTextures()) { |
| 427 // If we're never recycling scratch textures we can |
| 428 // always make them the right size |
| 429 return create_scratch_texture(fGpu, fTextureCache, inDesc); |
| 430 } |
| 431 |
403 GrTextureDesc desc = inDesc; | 432 GrTextureDesc desc = inDesc; |
404 | 433 |
405 GrAssert((desc.fFlags & kRenderTarget_GrTextureFlagBit) || | |
406 !(desc.fFlags & kNoStencil_GrTextureFlagBit)); | |
407 | |
408 if (kApprox_ScratchTexMatch == match) { | 434 if (kApprox_ScratchTexMatch == match) { |
409 // bin by pow2 with a reasonable min | 435 // bin by pow2 with a reasonable min |
410 static const int MIN_SIZE = 16; | 436 static const int MIN_SIZE = 16; |
411 desc.fWidth = GrMax(MIN_SIZE, GrNextPow2(desc.fWidth)); | 437 desc.fWidth = GrMax(MIN_SIZE, GrNextPow2(desc.fWidth)); |
412 desc.fHeight = GrMax(MIN_SIZE, GrNextPow2(desc.fHeight)); | 438 desc.fHeight = GrMax(MIN_SIZE, GrNextPow2(desc.fHeight)); |
413 } | 439 } |
414 | 440 |
415 // Renderable A8 targets are not universally supported (e.g., not on ANGLE) | |
416 GrAssert(this->isConfigRenderable(kAlpha_8_GrPixelConfig) || | |
417 !(desc.fFlags & kRenderTarget_GrTextureFlagBit) || | |
418 (desc.fConfig != kAlpha_8_GrPixelConfig)); | |
419 | |
420 GrResource* resource = NULL; | 441 GrResource* resource = NULL; |
421 int origWidth = desc.fWidth; | 442 int origWidth = desc.fWidth; |
422 int origHeight = desc.fHeight; | 443 int origHeight = desc.fHeight; |
423 | 444 |
424 do { | 445 do { |
425 GrResourceKey key = GrTexture::ComputeScratchKey(desc); | 446 GrResourceKey key = GrTexture::ComputeScratchKey(desc); |
426 // Ensure we have exclusive access to the texture so future 'find' calls
don't return it | 447 // Ensure we have exclusive access to the texture so future 'find' calls
don't return it |
427 resource = fTextureCache->find(key, GrResourceCache::kHide_OwnershipFlag
); | 448 resource = fTextureCache->find(key, GrResourceCache::kHide_OwnershipFlag
); |
428 if (NULL != resource) { | 449 if (NULL != resource) { |
429 resource->ref(); | 450 resource->ref(); |
(...skipping 12 matching lines...) Expand all Loading... |
442 } else { | 463 } else { |
443 break; | 464 break; |
444 } | 465 } |
445 | 466 |
446 } while (true); | 467 } while (true); |
447 | 468 |
448 if (NULL == resource) { | 469 if (NULL == resource) { |
449 desc.fFlags = inDesc.fFlags; | 470 desc.fFlags = inDesc.fFlags; |
450 desc.fWidth = origWidth; | 471 desc.fWidth = origWidth; |
451 desc.fHeight = origHeight; | 472 desc.fHeight = origHeight; |
452 GrTexture* texture = fGpu->createTexture(desc, NULL, 0); | 473 resource = create_scratch_texture(fGpu, fTextureCache, desc); |
453 if (NULL != texture) { | |
454 GrResourceKey key = GrTexture::ComputeScratchKey(texture->desc()); | |
455 // Adding a resource could put us overbudget. Try to free up the | |
456 // necessary space before adding it. | |
457 fTextureCache->purgeAsNeeded(1, texture->sizeInBytes()); | |
458 // Make the resource exclusive so future 'find' calls don't return i
t | |
459 fTextureCache->addResource(key, texture, GrResourceCache::kHide_Owne
rshipFlag); | |
460 resource = texture; | |
461 } | |
462 } | 474 } |
463 | 475 |
464 return static_cast<GrTexture*>(resource); | 476 return static_cast<GrTexture*>(resource); |
465 } | 477 } |
466 | 478 |
467 void GrContext::addExistingTextureToCache(GrTexture* texture) { | 479 void GrContext::addExistingTextureToCache(GrTexture* texture) { |
468 | 480 |
469 if (NULL == texture) { | 481 if (NULL == texture) { |
470 return; | 482 return; |
471 } | 483 } |
472 | 484 |
473 // This texture should already have a cache entry since it was once | 485 // This texture should already have a cache entry since it was once |
474 // attached | 486 // attached |
475 GrAssert(NULL != texture->getCacheEntry()); | 487 GrAssert(NULL != texture->getCacheEntry()); |
476 | 488 |
477 // Conceptually, the cache entry is going to assume responsibility | 489 // Conceptually, the cache entry is going to assume responsibility |
478 // for the creation ref. | 490 // for the creation ref. |
479 GrAssert(1 == texture->getRefCnt()); | 491 GrAssert(1 == texture->getRefCnt()); |
480 | 492 |
481 // Since this texture came from an AutoScratchTexture it should | 493 // Since this texture came from an AutoScratchTexture it should |
482 // still be in the exclusive pile | 494 // still be in the exclusive pile |
483 fTextureCache->makeNonExclusive(texture->getCacheEntry()); | 495 fTextureCache->makeNonExclusive(texture->getCacheEntry()); |
484 | 496 |
485 this->purgeCache(); | 497 if (fGpu->caps()->reuseScratchTextures()) { |
| 498 this->purgeCache(); |
| 499 } else { |
| 500 // When we aren't reusing textures we know this scratch texture |
| 501 // will never be reused and would be just wasting time in the cache |
| 502 fTextureCache->deleteResource(texture->getCacheEntry()); |
| 503 } |
486 } | 504 } |
487 | 505 |
488 | 506 |
489 void GrContext::unlockScratchTexture(GrTexture* texture) { | 507 void GrContext::unlockScratchTexture(GrTexture* texture) { |
490 ASSERT_OWNED_RESOURCE(texture); | 508 ASSERT_OWNED_RESOURCE(texture); |
491 GrAssert(NULL != texture->getCacheEntry()); | 509 GrAssert(NULL != texture->getCacheEntry()); |
492 | 510 |
493 // If this is a scratch texture we detached it from the cache | 511 // If this is a scratch texture we detached it from the cache |
494 // while it was locked (to avoid two callers simultaneously getting | 512 // while it was locked (to avoid two callers simultaneously getting |
495 // the same texture). | 513 // the same texture). |
496 if (texture->getCacheEntry()->key().isScratch()) { | 514 if (texture->getCacheEntry()->key().isScratch()) { |
497 fTextureCache->makeNonExclusive(texture->getCacheEntry()); | 515 fTextureCache->makeNonExclusive(texture->getCacheEntry()); |
498 this->purgeCache(); | 516 this->purgeCache(); |
499 } | 517 } |
500 | |
501 } | 518 } |
502 | 519 |
503 void GrContext::purgeCache() { | 520 void GrContext::purgeCache() { |
504 if (NULL != fTextureCache) { | 521 if (NULL != fTextureCache) { |
505 fTextureCache->purgeAsNeeded(); | 522 fTextureCache->purgeAsNeeded(); |
506 } | 523 } |
507 } | 524 } |
508 | 525 |
509 bool GrContext::OverbudgetCB(void* data) { | 526 bool GrContext::OverbudgetCB(void* data) { |
510 GrAssert(NULL != data); | 527 GrAssert(NULL != data); |
(...skipping 1175 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1686 return NULL; | 1703 return NULL; |
1687 } | 1704 } |
1688 } | 1705 } |
1689 | 1706 |
1690 /////////////////////////////////////////////////////////////////////////////// | 1707 /////////////////////////////////////////////////////////////////////////////// |
1691 #if GR_CACHE_STATS | 1708 #if GR_CACHE_STATS |
1692 void GrContext::printCacheStats() const { | 1709 void GrContext::printCacheStats() const { |
1693 fTextureCache->printStats(); | 1710 fTextureCache->printStats(); |
1694 } | 1711 } |
1695 #endif | 1712 #endif |
OLD | NEW |