diff --git a/driver/ConsecutivePoolAllocator.c b/driver/ConsecutivePoolAllocator.c index 062cc45..876506d 100644 --- a/driver/ConsecutivePoolAllocator.c +++ b/driver/ConsecutivePoolAllocator.c @@ -201,49 +201,52 @@ void consecutivePoolFree(ConsecutivePoolAllocator* pa, void* p, uint32_t numBloc pa->numFreeBlocks += numBlocks; } -uint32_t consecutivePoolReAllocate(ConsecutivePoolAllocator* pa, void* currentMem, uint32_t currNumBlocks) +uint32_t consecutivePoolReAllocate(ConsecutivePoolAllocator* pa, void* currentMem, uint32_t currNumBlocks, uint32_t newNumBlocks) { assert(pa); assert(pa->buf); assert(currentMem); assert(currNumBlocks); - uint32_t* nextCandidate = (char*)currentMem + pa->blockSize * currNumBlocks; - - uint32_t* prevPtr = 0; - for(uint32_t* listPtr = pa->nextFreeBlock; listPtr; listPtr = *listPtr) + //TODO hack + if(newNumBlocks - currNumBlocks < 2) { - if(listPtr == nextCandidate) + uint32_t* nextCandidate = (char*)currentMem + pa->blockSize * currNumBlocks; + uint32_t* prevPtr = 0; + for(uint32_t* listPtr = pa->nextFreeBlock; listPtr; listPtr = *listPtr) { - //update next free block to be the one after our current candidate - if(prevPtr) + if(listPtr == nextCandidate) { - *prevPtr = *listPtr; - pa->nextFreeBlock = prevPtr; - } - else if(*listPtr) - { - pa->nextFreeBlock = *listPtr; + //update next free block to be the one after our current candidate + if(prevPtr) + { + *prevPtr = *listPtr; + pa->nextFreeBlock = prevPtr; + } + else if(*listPtr) + { + pa->nextFreeBlock = *listPtr; + } + + pa->numFreeBlocks -= 1; + + return (char*)currentMem - (char*)pa->buf; } - pa->numFreeBlocks -= 1; - - return (char*)currentMem - (char*)pa->buf; + prevPtr = listPtr; } - - prevPtr = listPtr; } { //try to allocate one more block - uint32_t newMemOffset = consecutivePoolAllocate(pa, currNumBlocks + 1); + uint32_t newMemOffset = consecutivePoolAllocate(pa, newNumBlocks); if(newMemOffset == -1) { return -1; } - pa->numFreeBlocks -= 1; + pa->numFreeBlocks -= newNumBlocks - currNumBlocks; //copy over old content memcpy(pa->buf + newMemOffset, currentMem, currNumBlocks * pa->blockSize); diff --git a/driver/ConsecutivePoolAllocator.h b/driver/ConsecutivePoolAllocator.h index b0b3a59..9393801 100644 --- a/driver/ConsecutivePoolAllocator.h +++ b/driver/ConsecutivePoolAllocator.h @@ -21,7 +21,7 @@ ConsecutivePoolAllocator createConsecutivePoolAllocator(void* b, unsigned bs, un void destroyConsecutivePoolAllocator(ConsecutivePoolAllocator* pa); uint32_t consecutivePoolAllocate(ConsecutivePoolAllocator* pa, uint32_t numBlocks); void consecutivePoolFree(ConsecutivePoolAllocator* pa, void* p, uint32_t numBlocks); -uint32_t consecutivePoolReAllocate(ConsecutivePoolAllocator* pa, void* currentMem, uint32_t currNumBlocks); +uint32_t consecutivePoolReAllocate(ConsecutivePoolAllocator* pa, void* currentMem, uint32_t currNumBlocks, uint32_t newNumBlocks); void CPAdebugPrint(ConsecutivePoolAllocator* pa); void* getCPAptrFromOffset(ConsecutivePoolAllocator* pa, uint32_t offset); diff --git a/driver/ControlListUtil.c b/driver/ControlListUtil.c index b7d0d80..08b2538 100644 --- a/driver/ControlListUtil.c +++ b/driver/ControlListUtil.c @@ -19,7 +19,8 @@ uint32_t clHasEnoughSpace(ControlList* cl, uint32_t size) assert(cl); assert(cl->CPA); uint32_t currSize = cl->nextFreeByteOffset - cl->offset; - if(currSize + size < cl->numBlocks * cl->blockSize - 4) + + if((currSize + size) <= (cl->numBlocks * cl->blockSize)) { return 1; //fits! } diff --git a/driver/command.c b/driver/command.c index bbdfdb8..a0d59e3 100644 --- a/driver/command.c +++ b/driver/command.c @@ -120,6 +120,8 @@ VKAPI_ATTR VkResult VKAPI_CALL RPIFUNC(vkAllocateCommandBuffers)( pCommandBuffers[c]->dev = device; + pCommandBuffers[c]->level = pAllocateInfo[c].level; + pCommandBuffers[c]->shaderRecCount = 0; pCommandBuffers[c]->usageFlags = 0; pCommandBuffers[c]->state = CMDBUF_STATE_INITIAL; @@ -212,16 +214,12 @@ VKAPI_ATTR VkResult VKAPI_CALL RPIFUNC(vkBeginCommandBuffer)( assert(commandBuffer); assert(pBeginInfo); - //TODO secondary command buffers - //TODO VK_COMMAND_BUFFER_USAGE_RENDER_PASS_CONTINUE_BIT //specifies that a secondary command buffer is considered to be entirely inside a render pass. If this is a primary command buffer, then this bit is ignored //TODO VK_COMMAND_BUFFER_USAGE_SIMULTANEOUS_USE_BIT //specifies that a command buffer can be resubmitted to a queue while it is in the pending state, and recorded into multiple primary command buffers - //TODO inheritance info - //When a command buffer begins recording, all state in that command buffer is undefined commandBuffer->usageFlags = pBeginInfo->flags; @@ -233,6 +231,16 @@ VKAPI_ATTR VkResult VKAPI_CALL RPIFUNC(vkBeginCommandBuffer)( RPIFUNC(vkResetCommandBuffer)(commandBuffer, 0); } + if(pBeginInfo->pInheritanceInfo && commandBuffer->level == VK_COMMAND_BUFFER_LEVEL_SECONDARY) + { + VkRenderPassBeginInfo rpbi = {0}; + rpbi.sType = VK_STRUCTURE_TYPE_RENDER_PASS_BEGIN_INFO; + rpbi.framebuffer = pBeginInfo->pInheritanceInfo->framebuffer; + rpbi.renderPass = pBeginInfo->pInheritanceInfo->renderPass; + //TODO query stuff + RPIFUNC(vkCmdBeginRenderPass)(commandBuffer, &rpbi, VK_SUBPASS_CONTENTS_SECONDARY_COMMAND_BUFFERS); + } + PROFILEEND(RPIFUNC(vkBeginCommandBuffer)); return VK_SUCCESS; } @@ -930,7 +938,42 @@ VKAPI_ATTR void VKAPI_CALL RPIFUNC(vkCmdExecuteCommands)( const VkCommandBuffer* pCommandBuffers) { PROFILESTART(RPIFUNC(vkCmdExecuteCommands)); - //TODO + + assert(commandBuffer); + assert(commandBufferCount > 0); + assert(pCommandBuffers); + + //just copy bincl etc. over until there's a better solution + + _commandBuffer* primary = commandBuffer; + + for(uint32_t c = 0; c < commandBufferCount; ++c) + { + _commandBuffer* secondary = pCommandBuffers[c]; + + CLMarker* secondaryMarker = getCPAptrFromOffset(secondary->binCl.CPA, secondary->binCl.currMarkerOffset); + + if(!secondaryMarker->size) + { + clCloseCurrentMarker(&secondary->binCl, &secondary->handlesCl, &secondary->shaderRecCl, secondary->shaderRecCount, &secondary->uniformsCl); + } + + clFit(&primary->binCl, secondaryMarker->size); + clInsertData(&primary->binCl, secondaryMarker->size, ((uint8_t*)secondaryMarker) + sizeof(CLMarker)); + + ((CLMarker*)getCPAptrFromOffset(primary->binCl.CPA, primary->binCl.currMarkerOffset))->numDrawCallsSubmitted += secondaryMarker->numDrawCallsSubmitted; + + //TODO handles/handle indices might be grabled up like this... + clFit(&primary->handlesCl, secondaryMarker->handlesSize); + clInsertData(&primary->handlesCl, secondaryMarker->handlesSize, getCPAptrFromOffset(secondary->handlesCl.CPA, secondaryMarker->handlesBufOffset)); + clFit(&primary->uniformsCl, secondaryMarker->uniformsSize); + clInsertData(&primary->uniformsCl, secondaryMarker->uniformsSize, getCPAptrFromOffset(secondary->uniformsCl.CPA, secondaryMarker->uniformsBufOffset)); + clFit(&primary->shaderRecCl, secondaryMarker->shaderRecSize); + clInsertData(&primary->shaderRecCl, secondaryMarker->shaderRecSize, getCPAptrFromOffset(secondary->shaderRecCl.CPA, secondaryMarker->shaderRecBufOffset)); + + primary->shaderRecCount += secondary->shaderRecCount; + } + PROFILEEND(RPIFUNC(vkCmdExecuteCommands)); } diff --git a/driver/common.c b/driver/common.c index 488914e..b329ff5 100644 --- a/driver/common.c +++ b/driver/common.c @@ -537,9 +537,10 @@ void clFit(ControlList* cl, uint32_t commandSize) { uint32_t currSize = cl->nextFreeByteOffset - cl->offset; uint32_t currMarkerOffset = cl->currMarkerOffset - cl->offset; - cl->offset = consecutivePoolReAllocate(cl->CPA, getCPAptrFromOffset(cl->CPA, cl->offset), cl->numBlocks); assert(cl->offset != ~0u); + uint32_t newNumBlocks = ((currSize + commandSize) / (((ConsecutivePoolAllocator*)cl->CPA)->blockSize)) + 1; + cl->offset = consecutivePoolReAllocate(cl->CPA, getCPAptrFromOffset(cl->CPA, cl->offset), cl->numBlocks, newNumBlocks); assert(cl->offset != ~0u); cl->nextFreeByteOffset = cl->offset + currSize; - cl->numBlocks++; + cl->numBlocks = newNumBlocks; cl->currMarkerOffset = cl->currMarkerOffset == ~0u ? ~0u : cl->offset + currMarkerOffset; if(cl->currMarkerOffset != ~0u) { diff --git a/driver/common.h b/driver/common.h index 6e3390f..dac7d42 100644 --- a/driver/common.h +++ b/driver/common.h @@ -359,6 +359,8 @@ typedef struct VkCommandBuffer_T _device* dev; //device from which it was created + VkCommandBufferLevel level; + //Recorded commands include commands to bind pipelines and descriptor sets to the command buffer, commands to modify dynamic state, commands to draw (for graphics rendering), //commands to dispatch (for compute), commands to execute secondary command buffers (for primary command buffers only), commands to copy buffers and images, and other commands diff --git a/driver/renderpass.c b/driver/renderpass.c index 503230d..34e3ee9 100644 --- a/driver/renderpass.c +++ b/driver/renderpass.c @@ -150,140 +150,152 @@ void RPIFUNC(vkCmdBeginRenderPass)(VkCommandBuffer commandBuffer, const VkRender currMarker->readMSAAimage = readMSAAimage; currMarker->readMSAAdepthStencilImage = readMSAAdepthStencilImage; - if(rp->subpasses[0].colorAttachmentCount > 0) + if(commandBuffer->level == VK_COMMAND_BUFFER_LEVEL_PRIMARY) { - if(rp->subpasses[0].pColorAttachments) + if(rp->subpasses[0].colorAttachmentCount > 0) { - if(rp->attachments[rp->subpasses[0].pColorAttachments[0].attachment].loadOp == VK_ATTACHMENT_LOAD_OP_CLEAR) + if(rp->subpasses[0].pColorAttachments) { - flags |= VC4_SUBMIT_CL_USE_CLEAR_COLOR; + if(rp->attachments[rp->subpasses[0].pColorAttachments[0].attachment].loadOp == VK_ATTACHMENT_LOAD_OP_CLEAR) + { + flags |= VC4_SUBMIT_CL_USE_CLEAR_COLOR; - if(!rp->subpasses[0].pResolveAttachments) - { - currMarker->clearColor[0] = - currMarker->clearColor[1] = - packVec4IntoABGR8(pRenderPassBegin->pClearValues[rp->subpasses[0].pColorAttachments[0].attachment].color.float32); - } - else - { - currMarker->clearColor[0] = - currMarker->clearColor[1] = - packVec4IntoABGR8(pRenderPassBegin->pClearValues[rp->subpasses[0].pColorAttachments[0].attachment].color.float32); + if(!rp->subpasses[0].pResolveAttachments) + { + currMarker->clearColor[0] = + currMarker->clearColor[1] = + packVec4IntoABGR8(pRenderPassBegin->pClearValues[rp->subpasses[0].pColorAttachments[0].attachment].color.float32); + } + else + { + currMarker->clearColor[0] = + currMarker->clearColor[1] = + packVec4IntoABGR8(pRenderPassBegin->pClearValues[rp->subpasses[0].pColorAttachments[0].attachment].color.float32); + } } } } - } - if(rp->subpasses[0].pDepthStencilAttachment) - { - if(rp->attachments[rp->subpasses[0].pDepthStencilAttachment->attachment].loadOp == VK_ATTACHMENT_LOAD_OP_CLEAR) + if(rp->subpasses[0].pDepthStencilAttachment) { - flags |= VC4_SUBMIT_CL_USE_CLEAR_COLOR; + if(rp->attachments[rp->subpasses[0].pDepthStencilAttachment->attachment].loadOp == VK_ATTACHMENT_LOAD_OP_CLEAR) + { + flags |= VC4_SUBMIT_CL_USE_CLEAR_COLOR; - currMarker->clearDepth = - (uint32_t)(pRenderPassBegin->pClearValues[rp->subpasses[0].pDepthStencilAttachment->attachment].depthStencil.depth * 0xffffff) & 0xffffff; + currMarker->clearDepth = + (uint32_t)(pRenderPassBegin->pClearValues[rp->subpasses[0].pDepthStencilAttachment->attachment].depthStencil.depth * 0xffffff) & 0xffffff; + } + + if(rp->attachments[rp->subpasses[0].pDepthStencilAttachment->attachment].stencilLoadOp == VK_ATTACHMENT_LOAD_OP_CLEAR) + { + flags |= VC4_SUBMIT_CL_USE_CLEAR_COLOR; + + currMarker->clearStencil = + pRenderPassBegin->pClearValues[rp->subpasses[0].pDepthStencilAttachment->attachment].depthStencil.stencil & 0xff; + } } - if(rp->attachments[rp->subpasses[0].pDepthStencilAttachment->attachment].stencilLoadOp == VK_ATTACHMENT_LOAD_OP_CLEAR) - { - flags |= VC4_SUBMIT_CL_USE_CLEAR_COLOR; - - currMarker->clearStencil = - pRenderPassBegin->pClearValues[rp->subpasses[0].pDepthStencilAttachment->attachment].depthStencil.stencil & 0xff; - } + currMarker->flags = flags; } - currMarker->flags = flags; - //insert relocs - - if(writeImage) + //only add image stuff if we're in a primary level + //secondary level can't begin a renderpass + //but still will need a marker + if(commandBuffer->level == VK_COMMAND_BUFFER_LEVEL_PRIMARY) { - clFit(&commandBuffer->handlesCl, 4); - clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, writeImage->boundMem->bo); + if(writeImage) + { + clFit(&commandBuffer->handlesCl, 4); + clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, writeImage->boundMem->bo); + } + + if(readImage) + { + clFit(&commandBuffer->handlesCl, 4); + clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, readImage->boundMem->bo); + } + + if(writeDepthStencilImage) + { + clFit(&commandBuffer->handlesCl, 4); + clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, writeDepthStencilImage->boundMem->bo); + } + + if(readDepthStencilImage) + { + clFit(&commandBuffer->handlesCl, 4); + clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, readDepthStencilImage->boundMem->bo); + } + + if(writeMSAAimage) + { + clFit(&commandBuffer->handlesCl, 4); + clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, writeMSAAimage->boundMem->bo); + } + + if(writeMSAAdepthStencilImage) + { + clFit(&commandBuffer->handlesCl, 4); + clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, writeMSAAdepthStencilImage->boundMem->bo); + } } - if(readImage) + if(commandBuffer->level == VK_COMMAND_BUFFER_LEVEL_PRIMARY) { - clFit(&commandBuffer->handlesCl, 4); - clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, readImage->boundMem->bo); + uint32_t bpp = 0; + + ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->width = fb->width; + ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->height = fb->height; + + if(writeImage) + { + bpp = getFormatBpp(writeImage->format); + } + else if(writeMSAAimage) + { + bpp = getFormatBpp(writeMSAAimage->format); + } + + uint32_t biggestMip = 0; + for(uint32_t c = 0; c < fb->numAttachmentViews; ++c) + { + biggestMip = max(biggestMip, fb->attachmentViews[c].subresourceRange.baseMipLevel); + } + + //pad render size if we are rendering to a mip level + ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->mipLevel = biggestMip; + + uint32_t width = ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->width; + + if(((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->mipLevel > 0) + { + width = getPow2Pad(width); + width = width < 4 ? 4 : width; + } + + + clFit(&commandBuffer->binCl, V3D21_TILE_BINNING_MODE_CONFIGURATION_length); + clInsertTileBinningModeConfiguration(&commandBuffer->binCl, + 0, //double buffer in non ms mode + 0, //tile allocation block size + 0, //tile allocation initial block size + 0, //auto initialize tile state data array + bpp == 64, //64 bit color mode + writeMSAAimage || writeMSAAdepthStencilImage || performResolve ? 1 : 0, //msaa + width, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->height, + 0, //tile state data array address + 0, //tile allocation memory size + 0); //tile allocation memory address + + //START_TILE_BINNING resets the statechange counters in the hardware, + //which are what is used when a primitive is binned to a tile to + //figure out what new state packets need to be written to that tile's + //command list. + clFit(&commandBuffer->binCl, V3D21_START_TILE_BINNING_length); + clInsertStartTileBinning(&commandBuffer->binCl); } - if(writeDepthStencilImage) - { - clFit(&commandBuffer->handlesCl, 4); - clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, writeDepthStencilImage->boundMem->bo); - } - - if(readDepthStencilImage) - { - clFit(&commandBuffer->handlesCl, 4); - clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, readDepthStencilImage->boundMem->bo); - } - - if(writeMSAAimage) - { - clFit(&commandBuffer->handlesCl, 4); - clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, writeMSAAimage->boundMem->bo); - } - - if(writeMSAAdepthStencilImage) - { - clFit(&commandBuffer->handlesCl, 4); - clGetHandleIndex(&commandBuffer->handlesCl, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesBufOffset + cb->handlesCl.offset, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->handlesSize, writeMSAAdepthStencilImage->boundMem->bo); - } - - uint32_t bpp = 0; - - ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->width = fb->width; - ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->height = fb->height; - - if(writeImage) - { - bpp = getFormatBpp(writeImage->format); - } - else if(writeMSAAimage) - { - bpp = getFormatBpp(writeMSAAimage->format); - } - - uint32_t biggestMip = 0; - for(uint32_t c = 0; c < fb->numAttachmentViews; ++c) - { - biggestMip = max(biggestMip, fb->attachmentViews[c].subresourceRange.baseMipLevel); - } - - //pad render size if we are rendering to a mip level - ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->mipLevel = biggestMip; - - uint32_t width = ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->width; - - if(((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->mipLevel > 0) - { - width = getPow2Pad(width); - width = width < 4 ? 4 : width; - } - - clFit(&commandBuffer->binCl, V3D21_TILE_BINNING_MODE_CONFIGURATION_length); - clInsertTileBinningModeConfiguration(&commandBuffer->binCl, - 0, //double buffer in non ms mode - 0, //tile allocation block size - 0, //tile allocation initial block size - 0, //auto initialize tile state data array - bpp == 64, //64 bit color mode - writeMSAAimage || writeMSAAdepthStencilImage || performResolve ? 1 : 0, //msaa - width, ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->height, - 0, //tile state data array address - 0, //tile allocation memory size - 0); //tile allocation memory address - - //START_TILE_BINNING resets the statechange counters in the hardware, - //which are what is used when a primitive is binned to a tile to - //figure out what new state packets need to be written to that tile's - //command list. - clFit(&commandBuffer->binCl, V3D21_START_TILE_BINNING_length); - clInsertStartTileBinning(&commandBuffer->binCl); - ((CLMarker*)getCPAptrFromOffset(cb->binCl.CPA, cb->binCl.currMarkerOffset))->perfmonID = cb->perfmonID; cb->currRenderPass = rp; @@ -306,15 +318,18 @@ void RPIFUNC(vkCmdEndRenderPass)(VkCommandBuffer commandBuffer) //Ending a render pass instance performs any multisample resolve operations on the final subpass - //Increment the semaphore indicating that binning is done and - //unblocking the render thread. Note that this doesn't act - //until the FLUSH completes. - //The FLUSH caps all of our bin lists with a - //VC4_PACKET_RETURN. - clFit(&cb->binCl, V3D21_INCREMENT_SEMAPHORE_length); - clInsertIncrementSemaphore(&cb->binCl); - clFit(&cb->binCl, V3D21_FLUSH_length); - clInsertFlush(&cb->binCl); + if(commandBuffer->level == VK_COMMAND_BUFFER_LEVEL_PRIMARY) + { + //Increment the semaphore indicating that binning is done and + //unblocking the render thread. Note that this doesn't act + //until the FLUSH completes. + //The FLUSH caps all of our bin lists with a + //VC4_PACKET_RETURN. + clFit(&cb->binCl, V3D21_INCREMENT_SEMAPHORE_length); + clInsertIncrementSemaphore(&cb->binCl); + clFit(&cb->binCl, V3D21_FLUSH_length); + clInsertFlush(&cb->binCl); + } cb->currRenderPass = 0; diff --git a/test/multithreading/multithreading.cpp b/test/multithreading/multithreading.cpp index bbca75a..19d58bb 100644 --- a/test/multithreading/multithreading.cpp +++ b/test/multithreading/multithreading.cpp @@ -1333,8 +1333,8 @@ void CreateVertexBuffer() float w = 2.0; float h = 2.0; - float stepH = 6.0*h/1080.0; - float stepW = 8.0*w/1920.0; + float stepH = 90*6.0*h/1080.0; + float stepW = 90*8.0*w/1920.0; vertices.reserve(3 * 2 * 960 * 540);