public void Submit(VkSemaphore waitSemaphore, VkPipelineStageFlags waitDstStageMask, VkCommandBuffer commandBuffer, VkSemaphore signalSemaphore, VkFence fence = default) { VkCommandBuffer commandBufferHandle = commandBuffer; var nativeSubmit = new VkSubmitInfo { sType = VkStructureType.SubmitInfo }; if (waitSemaphore != default) { nativeSubmit.waitSemaphoreCount = 1; nativeSubmit.pWaitSemaphores = &waitSemaphore; nativeSubmit.pWaitDstStageMask = &waitDstStageMask; } if (commandBuffer != null) { nativeSubmit.commandBufferCount = 1; nativeSubmit.pCommandBuffers = &commandBufferHandle; } if (signalSemaphore != default) { nativeSubmit.signalSemaphoreCount = 1; nativeSubmit.pSignalSemaphores = &signalSemaphore; } VulkanUtil.CheckResult(vkQueueSubmit(this, 1, &nativeSubmit, fence)); }
public Graphics(Settings settings) { #if DEBUG //settings.Validation = true; #else settings.Validation = false; #endif Settings = settings; enabledFeatures.samplerAnisotropy = true; enabledFeatures.depthClamp = true; enabledFeatures.shaderStorageImageExtendedFormats = true; Device.Create(settings, enabledFeatures, EnabledExtensions); // Get a graphics queue from the Device GraphicsQueue = new VkQueue(Device.QFGraphics, 0); WorkQueue = new VkQueue(Device.QFGraphics, 0); ComputeQueue = new VkQueue(Device.QFCompute, 0); TransferQueue = new VkQueue(Device.QFTransfer, 0); DepthFormat = Device.GetSupportedDepthFormat(); primaryCmdPool = new CommandBufferPool(Device.QFGraphics, VkCommandPoolCreateFlags.ResetCommandBuffer); DescriptorPoolManager = new DescriptorPoolManager(); acquireSemaphore = new VkSemaphore(VkSemaphoreCreateFlags.None); }
public static VkResult vkCreateSemaphore(VkDevice device, out VkSemaphore semaphore) { VkSemaphoreCreateInfo createInfo = new VkSemaphoreCreateInfo { sType = VkStructureType.SemaphoreCreateInfo, pNext = null, flags = VkSemaphoreCreateFlags.None }; return(vkCreateSemaphore(device, &createInfo, null, out semaphore)); }
public RenderContext(int id = -1) { this.id = id; acquireSemaphore = new VkSemaphore(VkSemaphoreCreateFlags.None); for (int i = 0; i < (int)SubmitQueue.MaxCount; i++) { submitQueue[i] = new SubmitQueueData { cmdBuffer = pools[i].AllocateCommandBuffer(VkCommandBufferLevel.Primary), submitFence = new VkFence(VkFenceCreateFlags.Signaled), semaphore = new VkSemaphore(VkSemaphoreCreateFlags.None), pipelineStageFlags = (i == (int)SubmitQueue.Compute ? VkPipelineStageFlags.ComputeShader : VkPipelineStageFlags.FragmentShader) }; } }
private VkResult AcquireNextImage(out uint imageIndex) { VkSemaphore acquireSemaphore; if (_recycledSemaphores.Count == 0) { vkCreateSemaphore(VkDevice, out acquireSemaphore).CheckResult(); } else { acquireSemaphore = _recycledSemaphores[_recycledSemaphores.Count - 1]; _recycledSemaphores.RemoveAt(_recycledSemaphores.Count - 1); } VkResult result = vkAcquireNextImageKHR(VkDevice, Swapchain.Handle, ulong.MaxValue, acquireSemaphore, VkFence.Null, out imageIndex); if (result != VkResult.Success) { _recycledSemaphores.Add(acquireSemaphore); return(result); } if (_perFrame[imageIndex].QueueSubmitFence != VkFence.Null) { vkWaitForFences(VkDevice, _perFrame[imageIndex].QueueSubmitFence, true, ulong.MaxValue); vkResetFences(VkDevice, _perFrame[imageIndex].QueueSubmitFence); } if (_perFrame[imageIndex].PrimaryCommandPool != VkCommandPool.Null) { vkResetCommandPool(VkDevice, _perFrame[imageIndex].PrimaryCommandPool, VkCommandPoolResetFlags.None); } // Recycle the old semaphore back into the semaphore manager. VkSemaphore old_semaphore = _perFrame[imageIndex].SwapchainAcquireSemaphore; if (old_semaphore != VkSemaphore.Null) { _recycledSemaphores.Add(old_semaphore); } _perFrame[imageIndex].SwapchainAcquireSemaphore = acquireSemaphore; return(VkResult.Success); }
public unsafe void QueuePresent(VkQueue queue, uint imageIndex, VkSemaphore waitSemaphore = default) { var sc = swapchain; var presentInfo = new VkPresentInfoKHR { sType = VkStructureType.PresentInfoKHR, pNext = null, swapchainCount = 1, pSwapchains = &sc, pImageIndices = &imageIndex }; // Check if a wait semaphore has been specified to wait for before presenting the image if (waitSemaphore != VkSampler.Null) { presentInfo.pWaitSemaphores = (VkSemaphore *)Unsafe.AsPointer(ref waitSemaphore); presentInfo.waitSemaphoreCount = 1; } VulkanUtil.CheckResult(vkQueuePresentKHR(queue, &presentInfo)); }
public static VkResult vkQueuePresentKHR(VkQueue queue, VkSemaphore waitSemaphore, VkSwapchainKHR swapchain, uint imageIndex) { var presentInfo = new VkPresentInfoKHR { sType = VkStructureType.PresentInfoKHR, pNext = null }; if (waitSemaphore != VkSemaphore.Null) { presentInfo.waitSemaphoreCount = 1u; presentInfo.pWaitSemaphores = &waitSemaphore; } if (swapchain != VkSwapchainKHR.Null) { presentInfo.swapchainCount = 1u; presentInfo.pSwapchains = &swapchain; presentInfo.pImageIndices = &imageIndex; } return(vkQueuePresentKHR(queue, &presentInfo)); }
public bool AcquireNextImage(VkSemaphore presentCompleteSemaphore, out int imageIndex) { VkResult res = Device.AcquireNextImageKHR(swapchain, ulong.MaxValue, presentCompleteSemaphore, new VkFence(), out uint nextImageIndex); if (res == VkResult.ErrorOutOfDateKHR) { Log.Error(res.ToString()); //uint w = 0, h = 0; //Create(ref w, ref h, false); } else if (res == VkResult.SuboptimalKHR) { Log.Info(res.ToString()); } else if (res != VkResult.Success) { Log.Info(res.ToString()); imageIndex = 0; return(false); } imageIndex = (int)nextImageIndex; return(true); }
public static VkResult AcquireNextImageKHR(VkSwapchainKHR swapchain, ulong timeout, VkSemaphore semaphore, VkFence fence, out uint pImageIndex) { return(vkAcquireNextImageKHR(device, swapchain, timeout, semaphore, fence, out pImageIndex)); }
public static VkResult vkCreateTypedSemaphore(VkDevice device, VkSemaphoreType type, ulong initialValue, out VkSemaphore semaphore) { VkSemaphoreTypeCreateInfo typeCreateiInfo = new VkSemaphoreTypeCreateInfo { sType = VkStructureType.SemaphoreTypeCreateInfo, pNext = null, semaphoreType = type, initialValue = initialValue }; VkSemaphoreCreateInfo createInfo = new VkSemaphoreCreateInfo { sType = VkStructureType.SemaphoreCreateInfo, pNext = &typeCreateiInfo, flags = VkSemaphoreCreateFlags.None }; return(vkCreateSemaphore(device, &createInfo, null, out semaphore)); }
public void RenderFrame(Action <VkCommandBuffer, VkFramebuffer, VkExtent2D> draw, [CallerMemberName] string?frameName = null) { VkResult result = AcquireNextImage(out uint swapchainIndex); // Handle outdated error in acquire. if (result == VkResult.SuboptimalKHR || result == VkResult.ErrorOutOfDateKHR) { //Resize(context.swapchain_dimensions.width, context.swapchain_dimensions.height); result = AcquireNextImage(out swapchainIndex); } if (result != VkResult.Success) { vkDeviceWaitIdle(VkDevice); return; } // Begin command recording VkCommandBuffer cmd = _perFrame[swapchainIndex].PrimaryCommandBuffer; VkCommandBufferBeginInfo beginInfo = new VkCommandBufferBeginInfo { sType = VkStructureType.CommandBufferBeginInfo, flags = VkCommandBufferUsageFlags.OneTimeSubmit }; vkBeginCommandBuffer(cmd, &beginInfo).CheckResult(); draw(cmd, Swapchain.Framebuffers[swapchainIndex], Swapchain.Extent); // Complete the command buffer. vkEndCommandBuffer(cmd).CheckResult(); if (_perFrame[swapchainIndex].SwapchainReleaseSemaphore == VkSemaphore.Null) { vkCreateSemaphore(VkDevice, out _perFrame[swapchainIndex].SwapchainReleaseSemaphore).CheckResult(); } VkPipelineStageFlags wait_stage = VkPipelineStageFlags.ColorAttachmentOutput; VkSemaphore waitSemaphore = _perFrame[swapchainIndex].SwapchainAcquireSemaphore; VkSemaphore signalSemaphore = _perFrame[swapchainIndex].SwapchainReleaseSemaphore; VkSubmitInfo submitInfo = new VkSubmitInfo { sType = VkStructureType.SubmitInfo, commandBufferCount = 1u, pCommandBuffers = &cmd, waitSemaphoreCount = 1u, pWaitSemaphores = &waitSemaphore, pWaitDstStageMask = &wait_stage, signalSemaphoreCount = 1u, pSignalSemaphores = &signalSemaphore }; // Submit command buffer to graphics queue vkQueueSubmit(GraphicsQueue, submitInfo, _perFrame[swapchainIndex].QueueSubmitFence); result = PresentImage(swapchainIndex); // Handle Outdated error in present. if (result == VkResult.SuboptimalKHR || result == VkResult.ErrorOutOfDateKHR) { //Resize(context.swapchain_dimensions.width, context.swapchain_dimensions.height); } else if (result != VkResult.Success) { Log.Error("Failed to present swapchain image."); } }