OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2015 Google Inc. | 2 * Copyright 2015 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #include "GrVkGpu.h" | 8 #include "GrVkGpu.h" |
9 | 9 |
10 #include "GrContextOptions.h" | 10 #include "GrContextOptions.h" |
(...skipping 451 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
462 } | 462 } |
463 | 463 |
464 VkImageUsageFlags usageFlags = VK_IMAGE_USAGE_SAMPLED_BIT; | 464 VkImageUsageFlags usageFlags = VK_IMAGE_USAGE_SAMPLED_BIT; |
465 if (renderTarget) { | 465 if (renderTarget) { |
466 usageFlags |= VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT; | 466 usageFlags |= VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT; |
467 } | 467 } |
468 | 468 |
469 // For now we will set the VK_IMAGE_USAGE_TRANSFER_DESTINATION_BIT and | 469 // For now we will set the VK_IMAGE_USAGE_TRANSFER_DESTINATION_BIT and |
470 // VK_IMAGE_USAGE_TRANSFER_SOURCE_BIT on every texture since we do not know
whether or not we | 470 // VK_IMAGE_USAGE_TRANSFER_SOURCE_BIT on every texture since we do not know
whether or not we |
471 // will be using this texture in some copy or not. Also this assumes, as is
the current case, | 471 // will be using this texture in some copy or not. Also this assumes, as is
the current case, |
472 // that all render targets in vulkan are also texutres. If we change this pr
actice of setting | 472 // that all render targets in vulkan are also textures. If we change this pr
actice of setting |
473 // both bits, we must make sure to set the destination bit if we are uploadi
ng srcData to the | 473 // both bits, we must make sure to set the destination bit if we are uploadi
ng srcData to the |
474 // texture. | 474 // texture. |
475 usageFlags |= VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_
BIT; | 475 usageFlags |= VK_IMAGE_USAGE_TRANSFER_SRC_BIT | VK_IMAGE_USAGE_TRANSFER_DST_
BIT; |
476 | 476 |
477 VkFlags memProps = (!texels.empty() && linearTiling) ? VK_MEMORY_PROPERTY_HO
ST_VISIBLE_BIT : | 477 VkFlags memProps = (!texels.empty() && linearTiling) ? VK_MEMORY_PROPERTY_HO
ST_VISIBLE_BIT : |
478 VK_MEMORY_PROPERTY_DE
VICE_LOCAL_BIT; | 478 VK_MEMORY_PROPERTY_DE
VICE_LOCAL_BIT; |
479 | 479 |
480 // This ImageDesc refers to the texture that will be read by the client. Thu
s even if msaa is | 480 // This ImageDesc refers to the texture that will be read by the client. Thu
s even if msaa is |
481 // requested, this ImageDesc describes the resolved texutre. Therefore we al
ways have samples set | 481 // requested, this ImageDesc describes the resolved texture. Therefore we al
ways have samples set |
482 // to 1. | 482 // to 1. |
483 GrVkImage::ImageDesc imageDesc; | 483 GrVkImage::ImageDesc imageDesc; |
484 imageDesc.fImageType = VK_IMAGE_TYPE_2D; | 484 imageDesc.fImageType = VK_IMAGE_TYPE_2D; |
485 imageDesc.fFormat = pixelFormat; | 485 imageDesc.fFormat = pixelFormat; |
486 imageDesc.fWidth = desc.fWidth; | 486 imageDesc.fWidth = desc.fWidth; |
487 imageDesc.fHeight = desc.fHeight; | 487 imageDesc.fHeight = desc.fHeight; |
488 imageDesc.fLevels = 1; | 488 imageDesc.fLevels = 1; // TODO: support miplevels for optimal tiling |
489 imageDesc.fSamples = 1; | 489 imageDesc.fSamples = 1; |
490 imageDesc.fImageTiling = linearTiling ? VK_IMAGE_TILING_LINEAR : VK_IMAGE_TI
LING_OPTIMAL; | 490 imageDesc.fImageTiling = linearTiling ? VK_IMAGE_TILING_LINEAR : VK_IMAGE_TI
LING_OPTIMAL; |
491 imageDesc.fUsageFlags = usageFlags; | 491 imageDesc.fUsageFlags = usageFlags; |
492 imageDesc.fMemProps = memProps; | 492 imageDesc.fMemProps = memProps; |
493 | 493 |
494 GrVkTexture* tex; | 494 GrVkTexture* tex; |
495 if (renderTarget) { | 495 if (renderTarget) { |
496 tex = GrVkTextureRenderTarget::CreateNewTextureRenderTarget(this, budget
ed, desc, | 496 tex = GrVkTextureRenderTarget::CreateNewTextureRenderTarget(this, budget
ed, desc, |
497 imageDesc); | 497 imageDesc); |
498 } else { | 498 } else { |
(...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
599 info); | 599 info); |
600 if (tgt && wrapDesc.fStencilBits) { | 600 if (tgt && wrapDesc.fStencilBits) { |
601 if (!createStencilAttachmentForRenderTarget(tgt, desc.fWidth, desc.fHeig
ht)) { | 601 if (!createStencilAttachmentForRenderTarget(tgt, desc.fWidth, desc.fHeig
ht)) { |
602 tgt->unref(); | 602 tgt->unref(); |
603 return nullptr; | 603 return nullptr; |
604 } | 604 } |
605 } | 605 } |
606 return tgt; | 606 return tgt; |
607 } | 607 } |
608 | 608 |
| 609 void GrVkGpu::generateMipmap(GrVkTexture* tex) const { |
| 610 // don't need to do anything for linearly tiled textures (can't have mipmaps
) |
| 611 if (tex->isLinearTiled()) { |
| 612 return; |
| 613 } |
| 614 |
| 615 // We cannot generate mipmaps for images that are multisampled. |
| 616 // TODO: does it even make sense for rendertargets in general? |
| 617 if (tex->asRenderTarget() && tex->asRenderTarget()->numColorSamples() > 1) { |
| 618 return; |
| 619 } |
| 620 |
| 621 // determine if we can blit to and from this format |
| 622 const GrVkCaps& caps = this->vkCaps(); |
| 623 if (!caps.configCanBeDstofBlit(tex->config(), false) || |
| 624 !caps.configCanBeSrcofBlit(tex->config(), false)) { |
| 625 return; |
| 626 } |
| 627 |
| 628 // change the original image's layout |
| 629 VkImageLayout origSrcLayout = tex->currentLayout(); |
| 630 VkPipelineStageFlags srcStageMask = GrVkMemory::LayoutToPipelineStageFlags(o
rigSrcLayout); |
| 631 VkPipelineStageFlags dstStageMask = VK_PIPELINE_STAGE_TRANSFER_BIT; |
| 632 |
| 633 VkAccessFlags srcAccessMask = GrVkMemory::LayoutToSrcAccessMask(origSrcLayou
t); |
| 634 VkAccessFlags dstAccessMask = VK_ACCESS_TRANSFER_READ_BIT; |
| 635 |
| 636 tex->setImageLayout(this, VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, |
| 637 srcAccessMask, dstAccessMask, srcStageMask, dstStageMask
, false); |
| 638 |
| 639 // grab handle to the original image resource |
| 640 const GrVkImage::Resource* oldResource = tex->resource(); |
| 641 oldResource->ref(); |
| 642 |
| 643 if (!tex->reallocForMipmap(this)) { |
| 644 oldResource->unref(this); |
| 645 return; |
| 646 } |
| 647 |
| 648 // change the new image's layout |
| 649 VkImageLayout origDstLayout = tex->currentLayout(); |
| 650 |
| 651 srcStageMask = GrVkMemory::LayoutToPipelineStageFlags(origDstLayout); |
| 652 dstStageMask = VK_PIPELINE_STAGE_TRANSFER_BIT; |
| 653 |
| 654 srcAccessMask = GrVkMemory::LayoutToSrcAccessMask(origDstLayout); |
| 655 dstAccessMask = VK_ACCESS_TRANSFER_WRITE_BIT; |
| 656 |
| 657 tex->setImageLayout(this, |
| 658 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, |
| 659 srcAccessMask, |
| 660 dstAccessMask, |
| 661 srcStageMask, |
| 662 dstStageMask, |
| 663 false); |
| 664 |
| 665 // Blit original image |
| 666 int width = tex->width(); |
| 667 int height = tex->height(); |
| 668 uint32_t mipLevel = 0; |
| 669 |
| 670 VkImageBlit blitRegion; |
| 671 memset(&blitRegion, 0, sizeof(VkImageBlit)); |
| 672 blitRegion.srcSubresource = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 0, 1 }; |
| 673 blitRegion.srcOffsets[0] = { 0, 0, 0 }; |
| 674 blitRegion.srcOffsets[1] = { width, height, 0 }; |
| 675 blitRegion.dstSubresource = { VK_IMAGE_ASPECT_COLOR_BIT, mipLevel, 0, 1 }; |
| 676 blitRegion.dstOffsets[0] = { 0, 0, 0 }; |
| 677 blitRegion.dstOffsets[1] = { width, height, 0 }; |
| 678 |
| 679 fCurrentCmdBuffer->blitImage(this, |
| 680 oldResource, |
| 681 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, |
| 682 tex->resource(), |
| 683 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, |
| 684 1, |
| 685 &blitRegion, |
| 686 VK_FILTER_LINEAR); |
| 687 // Blit the miplevels |
| 688 while (width/2 > 0 && height/2 > 0) { |
| 689 blitRegion.srcSubresource = { VK_IMAGE_ASPECT_COLOR_BIT, mipLevel, 0, 1
}; |
| 690 blitRegion.srcOffsets[0] = { 0, 0, 0 }; |
| 691 blitRegion.srcOffsets[1] = { width, height, 0 }; |
| 692 blitRegion.dstSubresource = { VK_IMAGE_ASPECT_COLOR_BIT, mipLevel+1, 0,
1 }; |
| 693 blitRegion.dstOffsets[0] = { 0, 0, 0 }; |
| 694 blitRegion.dstOffsets[1] = { width/2, height/2, 0 }; |
| 695 |
| 696 fCurrentCmdBuffer->blitImage(this, |
| 697 tex->resource(), |
| 698 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, |
| 699 tex->resource(), |
| 700 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, |
| 701 1, |
| 702 &blitRegion, |
| 703 VK_FILTER_LINEAR); |
| 704 |
| 705 width /= 2; |
| 706 height /= 2; |
| 707 mipLevel++; |
| 708 } |
| 709 |
| 710 oldResource->unref(this); |
| 711 } |
| 712 |
| 713 |
| 714 |
609 //////////////////////////////////////////////////////////////////////////////// | 715 //////////////////////////////////////////////////////////////////////////////// |
610 | 716 |
611 void GrVkGpu::bindGeometry(const GrPrimitiveProcessor& primProc, | 717 void GrVkGpu::bindGeometry(const GrPrimitiveProcessor& primProc, |
612 const GrNonInstancedMesh& mesh) { | 718 const GrNonInstancedMesh& mesh) { |
613 // There is no need to put any memory barriers to make sure host writes have
finished here. | 719 // There is no need to put any memory barriers to make sure host writes have
finished here. |
614 // When a command buffer is submitted to a queue, there is an implicit memor
y barrier that | 720 // When a command buffer is submitted to a queue, there is an implicit memor
y barrier that |
615 // occurs for all host writes. Additionally, BufferMemoryBarriers are not al
lowed inside of | 721 // occurs for all host writes. Additionally, BufferMemoryBarriers are not al
lowed inside of |
616 // an active RenderPass. | 722 // an active RenderPass. |
617 GrVkVertexBuffer* vbuf; | 723 GrVkVertexBuffer* vbuf; |
618 vbuf = (GrVkVertexBuffer*)mesh.vertexBuffer(); | 724 vbuf = (GrVkVertexBuffer*)mesh.vertexBuffer(); |
(...skipping 642 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1261 VkImageBlit blitRegion; | 1367 VkImageBlit blitRegion; |
1262 memset(&blitRegion, 0, sizeof(VkImageBlit)); | 1368 memset(&blitRegion, 0, sizeof(VkImageBlit)); |
1263 blitRegion.srcSubresource = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 0, 1 }; | 1369 blitRegion.srcSubresource = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 0, 1 }; |
1264 blitRegion.srcOffsets[0] = { srcVkRect.fLeft, srcVkRect.fTop, 0 }; | 1370 blitRegion.srcOffsets[0] = { srcVkRect.fLeft, srcVkRect.fTop, 0 }; |
1265 blitRegion.srcOffsets[1] = { srcVkRect.fRight, srcVkRect.fBottom, 0 }; | 1371 blitRegion.srcOffsets[1] = { srcVkRect.fRight, srcVkRect.fBottom, 0 }; |
1266 blitRegion.dstSubresource = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 0, 1 }; | 1372 blitRegion.dstSubresource = { VK_IMAGE_ASPECT_COLOR_BIT, 0, 0, 1 }; |
1267 blitRegion.dstOffsets[0] = { dstRect.fLeft, dstRect.fTop, 0 }; | 1373 blitRegion.dstOffsets[0] = { dstRect.fLeft, dstRect.fTop, 0 }; |
1268 blitRegion.dstOffsets[1] = { dstRect.fRight, dstRect.fBottom, 0 }; | 1374 blitRegion.dstOffsets[1] = { dstRect.fRight, dstRect.fBottom, 0 }; |
1269 | 1375 |
1270 fCurrentCmdBuffer->blitImage(this, | 1376 fCurrentCmdBuffer->blitImage(this, |
1271 srcImage, | 1377 srcImage->resource(), |
1272 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, | 1378 VK_IMAGE_LAYOUT_TRANSFER_SRC_OPTIMAL, |
1273 dstImage, | 1379 dstImage->resource(), |
1274 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, | 1380 VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, |
1275 1, | 1381 1, |
1276 &blitRegion, | 1382 &blitRegion, |
1277 VK_FILTER_NEAREST); // We never scale so any fi
lter works here | 1383 VK_FILTER_NEAREST); // We never scale so any fi
lter works here |
1278 } | 1384 } |
1279 | 1385 |
1280 inline bool can_copy_as_draw(const GrSurface* dst, | 1386 inline bool can_copy_as_draw(const GrSurface* dst, |
1281 const GrSurface* src, | 1387 const GrSurface* src, |
1282 const GrVkGpu* gpu) { | 1388 const GrVkGpu* gpu) { |
1283 return false; | 1389 return false; |
(...skipping 317 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1601 aglSwapBuffers(aglGetCurrentContext()); | 1707 aglSwapBuffers(aglGetCurrentContext()); |
1602 int set_a_break_pt_here = 9; | 1708 int set_a_break_pt_here = 9; |
1603 aglSwapBuffers(aglGetCurrentContext()); | 1709 aglSwapBuffers(aglGetCurrentContext()); |
1604 #elif defined(SK_BUILD_FOR_WIN32) | 1710 #elif defined(SK_BUILD_FOR_WIN32) |
1605 SwapBuf(); | 1711 SwapBuf(); |
1606 int set_a_break_pt_here = 9; | 1712 int set_a_break_pt_here = 9; |
1607 SwapBuf(); | 1713 SwapBuf(); |
1608 #endif | 1714 #endif |
1609 #endif | 1715 #endif |
1610 } | 1716 } |
OLD | NEW |