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" |
11 #include "GrGeometryProcessor.h" | 11 #include "GrGeometryProcessor.h" |
12 #include "GrGpuResourceCacheAccess.h" | 12 #include "GrGpuResourceCacheAccess.h" |
13 #include "GrMesh.h" | 13 #include "GrMesh.h" |
14 #include "GrPipeline.h" | 14 #include "GrPipeline.h" |
15 #include "GrRenderTargetPriv.h" | 15 #include "GrRenderTargetPriv.h" |
16 #include "GrSurfacePriv.h" | 16 #include "GrSurfacePriv.h" |
17 #include "GrTexturePriv.h" | 17 #include "GrTexturePriv.h" |
18 | 18 |
19 #include "GrVkCommandBuffer.h" | 19 #include "GrVkCommandBuffer.h" |
20 #include "GrVkImage.h" | 20 #include "GrVkImage.h" |
21 #include "GrVkIndexBuffer.h" | 21 #include "GrVkIndexBuffer.h" |
22 #include "GrVkMemory.h" | 22 #include "GrVkMemory.h" |
23 #include "GrVkPipeline.h" | 23 #include "GrVkPipeline.h" |
24 #include "GrVkProgram.h" | 24 #include "GrVkPipelineState.h" |
25 #include "GrVkProgramBuilder.h" | |
26 #include "GrVkProgramDesc.h" | |
27 #include "GrVkRenderPass.h" | 25 #include "GrVkRenderPass.h" |
28 #include "GrVkResourceProvider.h" | 26 #include "GrVkResourceProvider.h" |
29 #include "GrVkTexture.h" | 27 #include "GrVkTexture.h" |
30 #include "GrVkTextureRenderTarget.h" | 28 #include "GrVkTextureRenderTarget.h" |
31 #include "GrVkTransferBuffer.h" | 29 #include "GrVkTransferBuffer.h" |
32 #include "GrVkVertexBuffer.h" | 30 #include "GrVkVertexBuffer.h" |
33 | 31 |
34 #include "SkConfig8888.h" | 32 #include "SkConfig8888.h" |
35 | 33 |
36 #include "vk/GrVkInterface.h" | 34 #include "vk/GrVkInterface.h" |
(...skipping 320 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
357 | 355 |
358 // wait for all commands to finish | 356 // wait for all commands to finish |
359 fResourceProvider.checkCommandBuffers(); | 357 fResourceProvider.checkCommandBuffers(); |
360 SkDEBUGCODE(VkResult res =) VK_CALL(QueueWaitIdle(fQueue)); | 358 SkDEBUGCODE(VkResult res =) VK_CALL(QueueWaitIdle(fQueue)); |
361 // VK_ERROR_DEVICE_LOST is acceptable when tearing down (see 4.2.4 in spec) | 359 // VK_ERROR_DEVICE_LOST is acceptable when tearing down (see 4.2.4 in spec) |
362 SkASSERT(VK_SUCCESS == res || VK_ERROR_DEVICE_LOST == res); | 360 SkASSERT(VK_SUCCESS == res || VK_ERROR_DEVICE_LOST == res); |
363 | 361 |
364 // must call this just before we destroy the VkDevice | 362 // must call this just before we destroy the VkDevice |
365 fResourceProvider.destroyResources(); | 363 fResourceProvider.destroyResources(); |
366 | 364 |
367 #ifdef SK_DEBUG | 365 #ifdef ENABLE_VK_LAYERS |
368 VK_CALL(DestroyDebugReportCallbackEXT(fVkInstance, fCallback, nullptr)); | 366 VK_CALL(DestroyDebugReportCallbackEXT(fVkInstance, fCallback, nullptr)); |
369 #endif | 367 #endif |
370 | 368 |
371 VK_CALL(DestroyCommandPool(fDevice, fCmdPool, nullptr)); | 369 VK_CALL(DestroyCommandPool(fDevice, fCmdPool, nullptr)); |
372 VK_CALL(DestroyDevice(fDevice, nullptr)); | 370 VK_CALL(DestroyDevice(fDevice, nullptr)); |
373 VK_CALL(DestroyInstance(fVkInstance, nullptr)); | 371 VK_CALL(DestroyInstance(fVkInstance, nullptr)); |
374 } | 372 } |
375 | 373 |
376 /////////////////////////////////////////////////////////////////////////////// | 374 /////////////////////////////////////////////////////////////////////////////// |
377 | 375 |
(...skipping 311 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
689 imageDesc.fLevels = 1; | 687 imageDesc.fLevels = 1; |
690 imageDesc.fSamples = 1; | 688 imageDesc.fSamples = 1; |
691 imageDesc.fImageTiling = linearTiling ? VK_IMAGE_TILING_LINEAR : VK_IMAGE_TI
LING_OPTIMAL; | 689 imageDesc.fImageTiling = linearTiling ? VK_IMAGE_TILING_LINEAR : VK_IMAGE_TI
LING_OPTIMAL; |
692 imageDesc.fUsageFlags = usageFlags; | 690 imageDesc.fUsageFlags = usageFlags; |
693 imageDesc.fMemProps = memProps; | 691 imageDesc.fMemProps = memProps; |
694 | 692 |
695 GrVkTexture* tex; | 693 GrVkTexture* tex; |
696 if (renderTarget) { | 694 if (renderTarget) { |
697 tex = GrVkTextureRenderTarget::CreateNewTextureRenderTarget(this, desc,
lifeCycle, | 695 tex = GrVkTextureRenderTarget::CreateNewTextureRenderTarget(this, desc,
lifeCycle, |
698 imageDesc); | 696 imageDesc); |
699 #if 0 | |
700 // This clear can be included to fix warning described in htttps://bugs.
skia.org/5045 | |
701 // Obviously we do not want to be clearling needlessly every time we cre
ate a render target. | |
702 SkIRect rect = SkIRect::MakeWH(tex->width(), tex->height()); | |
703 this->clear(rect, GrColor_TRANSPARENT_BLACK, tex->asRenderTarget()); | |
704 #endif | |
705 } else { | 697 } else { |
706 tex = GrVkTexture::CreateNewTexture(this, desc, lifeCycle, imageDesc); | 698 tex = GrVkTexture::CreateNewTexture(this, desc, lifeCycle, imageDesc); |
707 } | 699 } |
708 | 700 |
709 if (!tex) { | 701 if (!tex) { |
710 return nullptr; | 702 return nullptr; |
711 } | 703 } |
712 | 704 |
713 // TODO: We're ignoring MIP levels here. | 705 // TODO: We're ignoring MIP levels here. |
714 if (!texels.empty()) { | 706 if (!texels.empty()) { |
(...skipping 787 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1502 memcpy(tmpRow, top, tightRowBytes); | 1494 memcpy(tmpRow, top, tightRowBytes); |
1503 memcpy(top, bottom, tightRowBytes); | 1495 memcpy(top, bottom, tightRowBytes); |
1504 memcpy(bottom, tmpRow, tightRowBytes); | 1496 memcpy(bottom, tmpRow, tightRowBytes); |
1505 top += rowBytes; | 1497 top += rowBytes; |
1506 bottom -= rowBytes; | 1498 bottom -= rowBytes; |
1507 } | 1499 } |
1508 } | 1500 } |
1509 | 1501 |
1510 return true; | 1502 return true; |
1511 } | 1503 } |
1512 | |
1513 bool GrVkGpu::prepareDrawState(const GrPipeline& pipeline, | 1504 bool GrVkGpu::prepareDrawState(const GrPipeline& pipeline, |
1514 const GrPrimitiveProcessor& primProc, | 1505 const GrPrimitiveProcessor& primProc, |
1515 GrPrimitiveType primitiveType, | 1506 GrPrimitiveType primitiveType, |
1516 const GrVkRenderPass& renderPass, | 1507 const GrVkRenderPass& renderPass, |
1517 GrVkProgram** program) { | 1508 GrVkPipelineState** pipelineState) { |
1518 // Get GrVkProgramDesc | 1509 *pipelineState = fResourceProvider.findOrCreateCompatiblePipelineState(pipel
ine, |
1519 GrVkProgramDesc desc; | 1510 primP
roc, |
1520 if (!GrVkProgramDescBuilder::Build(&desc, primProc, pipeline, *this->vkCaps(
).glslCaps())) { | 1511 primi
tiveType, |
1521 GrCapsDebugf(this->caps(), "Failed to vk program descriptor!\n"); | 1512 rende
rPass); |
| 1513 if (!pipelineState) { |
1522 return false; | 1514 return false; |
1523 } | 1515 } |
1524 | 1516 |
1525 *program = GrVkProgramBuilder::CreateProgram(this, | 1517 (*pipelineState)->setData(this, primProc, pipeline); |
1526 pipeline, | |
1527 primProc, | |
1528 primitiveType, | |
1529 desc, | |
1530 renderPass); | |
1531 if (!program) { | |
1532 return false; | |
1533 } | |
1534 | 1518 |
1535 (*program)->setData(this, primProc, pipeline); | 1519 (*pipelineState)->bind(this, fCurrentCmdBuffer); |
1536 | |
1537 (*program)->bind(this, fCurrentCmdBuffer); | |
1538 | 1520 |
1539 GrVkPipeline::SetDynamicState(this, fCurrentCmdBuffer, pipeline); | 1521 GrVkPipeline::SetDynamicState(this, fCurrentCmdBuffer, pipeline); |
1540 | 1522 |
1541 return true; | 1523 return true; |
1542 } | 1524 } |
1543 | 1525 |
1544 void GrVkGpu::onDraw(const GrPipeline& pipeline, | 1526 void GrVkGpu::onDraw(const GrPipeline& pipeline, |
1545 const GrPrimitiveProcessor& primProc, | 1527 const GrPrimitiveProcessor& primProc, |
1546 const GrMesh* meshes, | 1528 const GrMesh* meshes, |
1547 int meshCount) { | 1529 int meshCount) { |
1548 if (!meshCount) { | 1530 if (!meshCount) { |
1549 return; | 1531 return; |
1550 } | 1532 } |
1551 GrRenderTarget* rt = pipeline.getRenderTarget(); | 1533 GrRenderTarget* rt = pipeline.getRenderTarget(); |
1552 GrVkRenderTarget* vkRT = static_cast<GrVkRenderTarget*>(rt); | 1534 GrVkRenderTarget* vkRT = static_cast<GrVkRenderTarget*>(rt); |
1553 const GrVkRenderPass* renderPass = vkRT->simpleRenderPass(); | 1535 const GrVkRenderPass* renderPass = vkRT->simpleRenderPass(); |
1554 SkASSERT(renderPass); | 1536 SkASSERT(renderPass); |
1555 | 1537 |
1556 fCurrentCmdBuffer->beginRenderPass(this, renderPass, *vkRT); | 1538 fCurrentCmdBuffer->beginRenderPass(this, renderPass, *vkRT); |
1557 | 1539 |
1558 GrVkProgram* program = nullptr; | 1540 GrVkPipelineState* pipelineState = nullptr; |
1559 GrPrimitiveType primitiveType = meshes[0].primitiveType(); | 1541 GrPrimitiveType primitiveType = meshes[0].primitiveType(); |
1560 if (!this->prepareDrawState(pipeline, primProc, primitiveType, *renderPass,
&program)) { | 1542 if (!this->prepareDrawState(pipeline, primProc, primitiveType, *renderPass,
&pipelineState)) { |
1561 return; | 1543 return; |
1562 } | 1544 } |
1563 | 1545 |
1564 // Change layout of our render target so it can be used as the color attachm
ent | 1546 // Change layout of our render target so it can be used as the color attachm
ent |
1565 VkImageLayout layout = vkRT->currentLayout(); | 1547 VkImageLayout layout = vkRT->currentLayout(); |
1566 // Our color attachment is purely a destination and won't be read so don't n
eed to flush or | 1548 // Our color attachment is purely a destination and won't be read so don't n
eed to flush or |
1567 // invalidate any caches | 1549 // invalidate any caches |
1568 VkPipelineStageFlags srcStageMask = GrVkMemory::LayoutToPipelineStageFlags(l
ayout); | 1550 VkPipelineStageFlags srcStageMask = GrVkMemory::LayoutToPipelineStageFlags(l
ayout); |
1569 VkPipelineStageFlags dstStageMask = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT; | 1551 VkPipelineStageFlags dstStageMask = VK_PIPELINE_STAGE_TOP_OF_PIPE_BIT; |
1570 VkAccessFlags srcAccessMask = GrVkMemory::LayoutToSrcAccessMask(layout); | 1552 VkAccessFlags srcAccessMask = GrVkMemory::LayoutToSrcAccessMask(layout); |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1602 if (GrXferBarrierType barrierType = pipeline.xferBarrierType(*this->caps
())) { | 1584 if (GrXferBarrierType barrierType = pipeline.xferBarrierType(*this->caps
())) { |
1603 this->xferBarrier(pipeline.getRenderTarget(), barrierType); | 1585 this->xferBarrier(pipeline.getRenderTarget(), barrierType); |
1604 } | 1586 } |
1605 | 1587 |
1606 const GrMesh& mesh = meshes[i]; | 1588 const GrMesh& mesh = meshes[i]; |
1607 GrMesh::Iterator iter; | 1589 GrMesh::Iterator iter; |
1608 const GrNonInstancedMesh* nonIdxMesh = iter.init(mesh); | 1590 const GrNonInstancedMesh* nonIdxMesh = iter.init(mesh); |
1609 do { | 1591 do { |
1610 if (nonIdxMesh->primitiveType() != primitiveType) { | 1592 if (nonIdxMesh->primitiveType() != primitiveType) { |
1611 // Technically we don't have to call this here (since there is a
safety check in | 1593 // Technically we don't have to call this here (since there is a
safety check in |
1612 // program:setData but this will allow for quicker freeing of re
sources if the | 1594 // pipelineState:setData but this will allow for quicker freeing
of resources if the |
1613 // program sits in a cache for a while. | 1595 // pipelineState sits in a cache for a while. |
1614 program->freeTempResources(this); | 1596 pipelineState->freeTempResources(this); |
1615 // This free will go away once we setup a program cache, and the
n the cache will be | 1597 pipelineState->unref(); |
1616 // responsible for call freeGpuResources. | 1598 SkDEBUGCODE(pipelineState = nullptr); |
1617 program->freeGPUResources(this); | |
1618 program->unref(); | |
1619 SkDEBUGCODE(program = nullptr); | |
1620 primitiveType = nonIdxMesh->primitiveType(); | 1599 primitiveType = nonIdxMesh->primitiveType(); |
1621 if (!this->prepareDrawState(pipeline, primProc, primitiveType, *
renderPass, | 1600 if (!this->prepareDrawState(pipeline, primProc, primitiveType, *
renderPass, |
1622 &program)) { | 1601 &pipelineState)) { |
1623 return; | 1602 return; |
1624 } | 1603 } |
1625 } | 1604 } |
1626 SkASSERT(program); | 1605 SkASSERT(pipelineState); |
1627 this->bindGeometry(primProc, *nonIdxMesh); | 1606 this->bindGeometry(primProc, *nonIdxMesh); |
1628 | 1607 |
1629 if (nonIdxMesh->isIndexed()) { | 1608 if (nonIdxMesh->isIndexed()) { |
1630 fCurrentCmdBuffer->drawIndexed(this, | 1609 fCurrentCmdBuffer->drawIndexed(this, |
1631 nonIdxMesh->indexCount(), | 1610 nonIdxMesh->indexCount(), |
1632 1, | 1611 1, |
1633 nonIdxMesh->startIndex(), | 1612 nonIdxMesh->startIndex(), |
1634 nonIdxMesh->startVertex(), | 1613 nonIdxMesh->startVertex(), |
1635 0); | 1614 0); |
1636 } else { | 1615 } else { |
1637 fCurrentCmdBuffer->draw(this, | 1616 fCurrentCmdBuffer->draw(this, |
1638 nonIdxMesh->vertexCount(), | 1617 nonIdxMesh->vertexCount(), |
1639 1, | 1618 1, |
1640 nonIdxMesh->startVertex(), | 1619 nonIdxMesh->startVertex(), |
1641 0); | 1620 0); |
1642 } | 1621 } |
1643 | 1622 |
1644 fStats.incNumDraws(); | 1623 fStats.incNumDraws(); |
1645 } while ((nonIdxMesh = iter.next())); | 1624 } while ((nonIdxMesh = iter.next())); |
1646 } | 1625 } |
1647 | 1626 |
1648 fCurrentCmdBuffer->endRenderPass(this); | 1627 fCurrentCmdBuffer->endRenderPass(this); |
1649 | 1628 |
1650 // Technically we don't have to call this here (since there is a safety chec
k in program:setData | 1629 // Technically we don't have to call this here (since there is a safety chec
k in |
1651 // but this will allow for quicker freeing of resources if the program sits
in a cache for a | 1630 // pipelineState:setData but this will allow for quicker freeing of resource
s if the |
1652 // while. | 1631 // pipelineState sits in a cache for a while. |
1653 program->freeTempResources(this); | 1632 pipelineState->freeTempResources(this); |
1654 // This free will go away once we setup a program cache, and then the cache
will be responsible | 1633 pipelineState->unref(); |
1655 // for call freeGpuResources. | |
1656 program->freeGPUResources(this); | |
1657 program->unref(); | |
1658 | 1634 |
1659 #if SWAP_PER_DRAW | 1635 #if SWAP_PER_DRAW |
1660 glFlush(); | 1636 glFlush(); |
1661 #if defined(SK_BUILD_FOR_MAC) | 1637 #if defined(SK_BUILD_FOR_MAC) |
1662 aglSwapBuffers(aglGetCurrentContext()); | 1638 aglSwapBuffers(aglGetCurrentContext()); |
1663 int set_a_break_pt_here = 9; | 1639 int set_a_break_pt_here = 9; |
1664 aglSwapBuffers(aglGetCurrentContext()); | 1640 aglSwapBuffers(aglGetCurrentContext()); |
1665 #elif defined(SK_BUILD_FOR_WIN32) | 1641 #elif defined(SK_BUILD_FOR_WIN32) |
1666 SwapBuf(); | 1642 SwapBuf(); |
1667 int set_a_break_pt_here = 9; | 1643 int set_a_break_pt_here = 9; |
1668 SwapBuf(); | 1644 SwapBuf(); |
1669 #endif | 1645 #endif |
1670 #endif | 1646 #endif |
1671 } | 1647 } |
1672 | 1648 |
OLD | NEW |