diff --git a/src/main/java/net/vulkanmod/render/chunk/buffer/UploadManager.java b/src/main/java/net/vulkanmod/render/chunk/buffer/UploadManager.java index 9f14e3ccd..05d45429d 100644 --- a/src/main/java/net/vulkanmod/render/chunk/buffer/UploadManager.java +++ b/src/main/java/net/vulkanmod/render/chunk/buffer/UploadManager.java @@ -8,7 +8,6 @@ import net.vulkanmod.vulkan.memory.StagingBuffer; import net.vulkanmod.vulkan.queue.CommandPool; import net.vulkanmod.vulkan.queue.Queue; -import net.vulkanmod.vulkan.queue.TransferQueue; import org.lwjgl.system.MemoryStack; import org.lwjgl.vulkan.VkBufferMemoryBarrier; import org.lwjgl.vulkan.VkCommandBuffer; @@ -16,6 +15,7 @@ import java.nio.ByteBuffer; +import static net.vulkanmod.vulkan.queue.Queue.TransferQueue; import static org.lwjgl.vulkan.VK10.*; public class UploadManager { diff --git a/src/main/java/net/vulkanmod/vulkan/Vulkan.java b/src/main/java/net/vulkanmod/vulkan/Vulkan.java index 33c75fcea..3261dd442 100644 --- a/src/main/java/net/vulkanmod/vulkan/Vulkan.java +++ b/src/main/java/net/vulkanmod/vulkan/Vulkan.java @@ -8,6 +8,7 @@ import net.vulkanmod.vulkan.memory.MemoryTypes; import net.vulkanmod.vulkan.memory.StagingBuffer; import net.vulkanmod.vulkan.queue.Queue; +import net.vulkanmod.vulkan.queue.QueueFamilyIndices; import net.vulkanmod.vulkan.shader.Pipeline; import net.vulkanmod.vulkan.util.VUtil; import net.vulkanmod.vulkan.util.VkResult; @@ -22,7 +23,6 @@ import java.util.*; import static java.util.stream.Collectors.toSet; -import static net.vulkanmod.vulkan.queue.Queue.getQueueFamilies; import static net.vulkanmod.vulkan.util.VUtil.asPointerBuffer; import static org.lwjgl.glfw.GLFWVulkan.glfwCreateWindowSurface; import static org.lwjgl.glfw.GLFWVulkan.glfwGetRequiredInstanceExtensions; @@ -345,11 +345,11 @@ private static void createCommandPool() { try (MemoryStack stack = stackPush()) { - Queue.QueueFamilyIndices queueFamilyIndices = getQueueFamilies(); + VkCommandPoolCreateInfo poolInfo = VkCommandPoolCreateInfo.calloc(stack); poolInfo.sType(VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO); - poolInfo.queueFamilyIndex(queueFamilyIndices.graphicsFamily); + poolInfo.queueFamilyIndex(QueueFamilyIndices.graphicsFamily); poolInfo.flags(VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT); LongBuffer pCommandPool = stack.mallocLong(1); diff --git a/src/main/java/net/vulkanmod/vulkan/device/DeviceManager.java b/src/main/java/net/vulkanmod/vulkan/device/DeviceManager.java index 18fd202a0..8f047c9bc 100644 --- a/src/main/java/net/vulkanmod/vulkan/device/DeviceManager.java +++ b/src/main/java/net/vulkanmod/vulkan/device/DeviceManager.java @@ -14,7 +14,6 @@ import java.util.List; import static java.util.stream.Collectors.toSet; -import static net.vulkanmod.vulkan.queue.Queue.findQueueFamilies; import static net.vulkanmod.vulkan.util.VUtil.asPointerBuffer; import static org.lwjgl.glfw.GLFWVulkan.glfwGetRequiredInstanceExtensions; import static org.lwjgl.system.MemoryStack.stackGet; @@ -38,11 +37,6 @@ public abstract class DeviceManager { public static SurfaceProperties surfaceProperties; - static GraphicsQueue graphicsQueue; - static PresentQueue presentQueue; - static TransferQueue transferQueue; - static ComputeQueue computeQueue; - public static void init(VkInstance instance) { try { DeviceManager.getSuitableDevices(instance); @@ -106,7 +100,7 @@ public static void pickPhysicalDevice() { Initializer.CONFIG.device = -1; } - physicalDevice = DeviceManager.device.physicalDevice; + QueueFamilyIndices.findQueueFamilies(physicalDevice = DeviceManager.device.physicalDevice); // Get device properties deviceProperties = device.properties; @@ -154,9 +148,7 @@ else if (!otherDevices.isEmpty()) public static void createLogicalDevice() { try (MemoryStack stack = stackPush()) { - net.vulkanmod.vulkan.queue.Queue.QueueFamilyIndices indices = findQueueFamilies(physicalDevice); - - int[] uniqueQueueFamilies = indices.unique(); + int[] uniqueQueueFamilies = QueueFamilyIndices.unique(); VkDeviceQueueCreateInfo.Buffer queueCreateInfos = VkDeviceQueueCreateInfo.calloc(uniqueQueueFamilies.length, stack); @@ -221,11 +213,6 @@ public static void createLogicalDevice() { Vulkan.checkResult(res, "Failed to create logical device"); vkDevice = new VkDevice(pDevice.get(0), physicalDevice, createInfo, VK_API_VERSION_1_2); - - graphicsQueue = new GraphicsQueue(stack, indices.graphicsFamily); - transferQueue = new TransferQueue(stack, indices.transferFamily); - presentQueue = new PresentQueue(stack, indices.presentFamily); - computeQueue = new ComputeQueue(stack, indices.computeFamily); } } @@ -250,7 +237,7 @@ private static PointerBuffer getRequiredExtensions() { private static boolean isDeviceSuitable(VkPhysicalDevice device) { try (MemoryStack stack = stackPush()) { - Queue.QueueFamilyIndices indices = findQueueFamilies(device); + VkExtensionProperties.Buffer availableExtensions = getAvailableExtension(stack, device); boolean extensionsSupported = availableExtensions.stream() @@ -269,7 +256,7 @@ private static boolean isDeviceSuitable(VkPhysicalDevice device) { vkGetPhysicalDeviceFeatures(device, supportedFeatures); boolean anisotropicFilterSupported = supportedFeatures.samplerAnisotropy(); - return indices.isSuitable() && extensionsSupported && swapChainAdequate; + return extensionsSupported && swapChainAdequate; } } @@ -348,27 +335,22 @@ public static String getAvailableDevicesInfo() { } public static void destroy() { - graphicsQueue.cleanUp(); - transferQueue.cleanUp(); - computeQueue.cleanUp(); + Queue.GraphicsQueue.cleanUp(); + Queue.TransferQueue.cleanUp(); vkDestroyDevice(vkDevice, null); } - public static GraphicsQueue getGraphicsQueue() { - return graphicsQueue; - } - - public static PresentQueue getPresentQueue() { - return presentQueue; + public static Queue getGraphicsQueue() { + return Queue.GraphicsQueue; } - public static TransferQueue getTransferQueue() { - return transferQueue; + public static Queue getPresentQueue() { + return Queue.PresentQueue; } - public static ComputeQueue getComputeQueue() { - return computeQueue; + public static Queue getTransferQueue() { + return Queue.TransferQueue; } public static SurfaceProperties querySurfaceProperties(VkPhysicalDevice device, MemoryStack stack) { diff --git a/src/main/java/net/vulkanmod/vulkan/framebuffer/SwapChain.java b/src/main/java/net/vulkanmod/vulkan/framebuffer/SwapChain.java index 44b8bf7e5..0ebd24b42 100644 --- a/src/main/java/net/vulkanmod/vulkan/framebuffer/SwapChain.java +++ b/src/main/java/net/vulkanmod/vulkan/framebuffer/SwapChain.java @@ -8,6 +8,7 @@ import net.vulkanmod.vulkan.Vulkan; import net.vulkanmod.vulkan.device.DeviceManager; import net.vulkanmod.vulkan.queue.Queue; +import net.vulkanmod.vulkan.queue.QueueFamilyIndices; import net.vulkanmod.vulkan.texture.VulkanImage; import org.lwjgl.system.MemoryStack; import org.lwjgl.vulkan.*; @@ -112,11 +113,11 @@ private void createSwapChain() { createInfo.imageArrayLayers(1); createInfo.imageUsage(VK_IMAGE_USAGE_COLOR_ATTACHMENT_BIT | VK_IMAGE_USAGE_SAMPLED_BIT); - Queue.QueueFamilyIndices indices = Queue.getQueueFamilies(); - if (indices.graphicsFamily != indices.presentFamily) { + + if (QueueFamilyIndices.graphicsFamily != QueueFamilyIndices.presentFamily) { createInfo.imageSharingMode(VK_SHARING_MODE_CONCURRENT); - createInfo.pQueueFamilyIndices(stack.ints(indices.graphicsFamily, indices.presentFamily)); + createInfo.pQueueFamilyIndices(stack.ints(QueueFamilyIndices.graphicsFamily, QueueFamilyIndices.presentFamily)); } else { createInfo.imageSharingMode(VK_SHARING_MODE_EXCLUSIVE); } diff --git a/src/main/java/net/vulkanmod/vulkan/memory/IndirectBuffer.java b/src/main/java/net/vulkanmod/vulkan/memory/IndirectBuffer.java index 811bddfb1..eeac07c73 100644 --- a/src/main/java/net/vulkanmod/vulkan/memory/IndirectBuffer.java +++ b/src/main/java/net/vulkanmod/vulkan/memory/IndirectBuffer.java @@ -4,10 +4,10 @@ import net.vulkanmod.vulkan.Vulkan; import net.vulkanmod.vulkan.device.DeviceManager; import net.vulkanmod.vulkan.queue.CommandPool; -import net.vulkanmod.vulkan.queue.TransferQueue; import java.nio.ByteBuffer; +import static net.vulkanmod.vulkan.queue.Queue.TransferQueue; import static org.lwjgl.vulkan.VK10.VK_BUFFER_USAGE_INDIRECT_BUFFER_BIT; public class IndirectBuffer extends Buffer { diff --git a/src/main/java/net/vulkanmod/vulkan/queue/CommandPool.java b/src/main/java/net/vulkanmod/vulkan/queue/CommandPool.java index eff323b7f..c3f060dc3 100644 --- a/src/main/java/net/vulkanmod/vulkan/queue/CommandPool.java +++ b/src/main/java/net/vulkanmod/vulkan/queue/CommandPool.java @@ -14,22 +14,18 @@ import static org.lwjgl.vulkan.VK10.*; public class CommandPool { - long id; + final long id; private final List commandBuffers = new ObjectArrayList<>(); private final java.util.Queue availableCmdBuffers = new ArrayDeque<>(); CommandPool(int queueFamilyIndex) { - this.createCommandPool(queueFamilyIndex); - } - - public void createCommandPool(int familyIndex) { try (MemoryStack stack = stackPush()) { VkCommandPoolCreateInfo poolInfo = VkCommandPoolCreateInfo.calloc(stack); poolInfo.sType(VK_STRUCTURE_TYPE_COMMAND_POOL_CREATE_INFO); - poolInfo.queueFamilyIndex(familyIndex); + poolInfo.queueFamilyIndex(queueFamilyIndex); poolInfo.flags(VK_COMMAND_POOL_CREATE_RESET_COMMAND_BUFFER_BIT); LongBuffer pCommandPool = stack.mallocLong(1); @@ -67,7 +63,6 @@ public CommandBuffer beginCommands() { vkCreateFence(Vulkan.getVkDevice(), fenceInfo, null, pFence); CommandBuffer commandBuffer = new CommandBuffer(new VkCommandBuffer(pCommandBuffer.get(i), Vulkan.getVkDevice()), pFence.get(0)); - commandBuffer.handle = new VkCommandBuffer(pCommandBuffer.get(i), Vulkan.getVkDevice()); commandBuffers.add(commandBuffer); availableCmdBuffers.add(commandBuffer); } @@ -120,8 +115,8 @@ public void cleanUp() { } public class CommandBuffer { - VkCommandBuffer handle; - long fence; + final VkCommandBuffer handle; + final long fence; boolean submitted; boolean recording; diff --git a/src/main/java/net/vulkanmod/vulkan/queue/ComputeQueue.java b/src/main/java/net/vulkanmod/vulkan/queue/ComputeQueue.java deleted file mode 100644 index 1c0d7c025..000000000 --- a/src/main/java/net/vulkanmod/vulkan/queue/ComputeQueue.java +++ /dev/null @@ -1,10 +0,0 @@ -package net.vulkanmod.vulkan.queue; - -import org.lwjgl.system.MemoryStack; - -public class ComputeQueue extends Queue { - - public ComputeQueue(MemoryStack stack, int familyIndex) { - super(stack, familyIndex); - } -} diff --git a/src/main/java/net/vulkanmod/vulkan/queue/GraphicsQueue.java b/src/main/java/net/vulkanmod/vulkan/queue/GraphicsQueue.java deleted file mode 100644 index e449f617b..000000000 --- a/src/main/java/net/vulkanmod/vulkan/queue/GraphicsQueue.java +++ /dev/null @@ -1,48 +0,0 @@ -package net.vulkanmod.vulkan.queue; - -import net.vulkanmod.vulkan.Synchronization; -import net.vulkanmod.vulkan.Vulkan; -import net.vulkanmod.vulkan.memory.MemoryManager; -import net.vulkanmod.vulkan.util.VUtil; -import org.lwjgl.system.MemoryStack; -import org.lwjgl.vulkan.*; - -import static org.lwjgl.vulkan.VK10.*; - -public class GraphicsQueue extends Queue { - public static GraphicsQueue INSTANCE; - - private static CommandPool.CommandBuffer currentCmdBuffer; - - public GraphicsQueue(MemoryStack stack, int familyIndex) { - super(stack, familyIndex); - } - - public void startRecording() { - currentCmdBuffer = beginCommands(); - } - - public void endRecordingAndSubmit() { - long fence = submitCommands(currentCmdBuffer); - Synchronization.INSTANCE.addCommandBuffer(currentCmdBuffer); - - currentCmdBuffer = null; - } - - public CommandPool.CommandBuffer getCommandBuffer() { - if (currentCmdBuffer != null) { - return currentCmdBuffer; - } else { - return beginCommands(); - } - } - - public long endIfNeeded(CommandPool.CommandBuffer commandBuffer) { - if (currentCmdBuffer != null) { - return VK_NULL_HANDLE; - } else { - return submitCommands(commandBuffer); - } - } - -} diff --git a/src/main/java/net/vulkanmod/vulkan/queue/PresentQueue.java b/src/main/java/net/vulkanmod/vulkan/queue/PresentQueue.java deleted file mode 100644 index 0997e72a4..000000000 --- a/src/main/java/net/vulkanmod/vulkan/queue/PresentQueue.java +++ /dev/null @@ -1,10 +0,0 @@ -package net.vulkanmod.vulkan.queue; - -import org.lwjgl.system.MemoryStack; - -public class PresentQueue extends Queue { - - public PresentQueue(MemoryStack stack, int familyIndex) { - super(stack, familyIndex, false); - } -} diff --git a/src/main/java/net/vulkanmod/vulkan/queue/Queue.java b/src/main/java/net/vulkanmod/vulkan/queue/Queue.java index 4f68e0778..cc44ca8e8 100644 --- a/src/main/java/net/vulkanmod/vulkan/queue/Queue.java +++ b/src/main/java/net/vulkanmod/vulkan/queue/Queue.java @@ -1,57 +1,49 @@ package net.vulkanmod.vulkan.queue; -import net.vulkanmod.Initializer; -import net.vulkanmod.vulkan.Vulkan; +import it.unimi.dsi.fastutil.longs.LongSet; import net.vulkanmod.vulkan.device.DeviceManager; +import net.vulkanmod.vulkan.Synchronization; +import net.vulkanmod.vulkan.util.VUtil; import org.lwjgl.PointerBuffer; import org.lwjgl.system.MemoryStack; -import org.lwjgl.vulkan.VkDevice; -import org.lwjgl.vulkan.VkPhysicalDevice; -import org.lwjgl.vulkan.VkQueue; -import org.lwjgl.vulkan.VkQueueFamilyProperties; - -import java.nio.IntBuffer; -import java.util.stream.IntStream; +import org.lwjgl.vulkan.*; import static org.lwjgl.system.MemoryStack.stackPush; -import static org.lwjgl.vulkan.KHRSurface.vkGetPhysicalDeviceSurfaceSupportKHR; import static org.lwjgl.vulkan.VK10.*; -public abstract class Queue { - private static VkDevice DEVICE; - - private static QueueFamilyIndices queueFamilyIndices; - protected CommandPool commandPool; - +public enum Queue { + GraphicsQueue(QueueFamilyIndices.graphicsFamily, true), + TransferQueue(QueueFamilyIndices.transferFamily, true), + PresentQueue(QueueFamilyIndices.presentFamily, false); + private final int familyIndex; + private CommandPool.CommandBuffer currentCmdBuffer; + private final CommandPool commandPool; private final VkQueue queue; - public synchronized CommandPool.CommandBuffer beginCommands() { + public CommandPool.CommandBuffer beginCommands() { return this.commandPool.beginCommands(); } - - Queue(MemoryStack stack, int familyIndex) { - this(stack, familyIndex, true); - } - - Queue(MemoryStack stack, int familyIndex, boolean initCommandPool) { - PointerBuffer pQueue = stack.mallocPointer(1); - vkGetDeviceQueue(DeviceManager.vkDevice, familyIndex, 0, pQueue); - this.queue = new VkQueue(pQueue.get(0), DeviceManager.vkDevice); - - if (initCommandPool) - this.commandPool = new CommandPool(familyIndex); + //We don't use the Compute Queue: will skip creating it to save driver resources + Queue(int familyIndex, boolean initCommandPool) { + try (MemoryStack stack = MemoryStack.stackPush()) + { + PointerBuffer pQueue = stack.mallocPointer(1); + this.familyIndex = familyIndex; + vkGetDeviceQueue(DeviceManager.vkDevice, this.familyIndex, 0, pQueue); + this.queue = new VkQueue(pQueue.get(0), DeviceManager.vkDevice); + + this.commandPool = initCommandPool ? new CommandPool(this.familyIndex) : null; + } } - public synchronized long submitCommands(CommandPool.CommandBuffer commandBuffer) { + public long submitCommands(CommandPool.CommandBuffer commandBuffer) { return this.commandPool.submitCommands(commandBuffer, queue); } - public VkQueue queue() { - return this.queue; - } + public VkQueue queue() { return this.queue; } public void cleanUp() { - if (commandPool != null) + if(commandPool != null) commandPool.cleanUp(); } @@ -59,145 +51,187 @@ public void waitIdle() { vkQueueWaitIdle(queue); } - public enum Family { - Graphics, - Transfer, - Compute - } - public static QueueFamilyIndices getQueueFamilies() { - if (DEVICE == null) - DEVICE = Vulkan.getVkDevice(); + public long copyBufferCmd(long srcBuffer, long srcOffset, long dstBuffer, long dstOffset, long size) { - if (queueFamilyIndices == null) { - queueFamilyIndices = findQueueFamilies(DEVICE.getPhysicalDevice()); - } - return queueFamilyIndices; - } + try(MemoryStack stack = stackPush()) { - public static QueueFamilyIndices findQueueFamilies(VkPhysicalDevice device) { + CommandPool.CommandBuffer commandBuffer = beginCommands(); - QueueFamilyIndices indices = new QueueFamilyIndices(); + VkBufferCopy.Buffer copyRegion = VkBufferCopy.malloc(1, stack); + copyRegion.size(size); + copyRegion.srcOffset(srcOffset); + copyRegion.dstOffset(dstOffset); - try (MemoryStack stack = stackPush()) { + vkCmdCopyBuffer(commandBuffer.getHandle(), srcBuffer, dstBuffer, copyRegion); - IntBuffer queueFamilyCount = stack.ints(0); + long a = this.submitCommands(commandBuffer); + Synchronization.INSTANCE.addCommandBuffer(commandBuffer); + return a; - vkGetPhysicalDeviceQueueFamilyProperties(device, queueFamilyCount, null); + } + } - VkQueueFamilyProperties.Buffer queueFamilies = VkQueueFamilyProperties.mallocStack(queueFamilyCount.get(0), stack); + public void uploadBufferImmediate(long srcBuffer, long srcOffset, long dstBuffer, long dstOffset, long size) { - vkGetPhysicalDeviceQueueFamilyProperties(device, queueFamilyCount, queueFamilies); + try(MemoryStack stack = stackPush()) { + CommandPool.CommandBuffer commandBuffer = this.beginCommands(); - IntBuffer presentSupport = stack.ints(VK_FALSE); +// if(Initializer.CONFIG.useGigaBarriers) this.GigaBarrier(commandBuffer.getHandle()); + VkBufferCopy.Buffer copyRegion = VkBufferCopy.malloc(1, stack); + copyRegion.size(size); + copyRegion.srcOffset(srcOffset); + copyRegion.dstOffset(dstOffset); +// this.BufferBarrier(commandBuffer.getHandle(), srcBuffer, ~0,VK_ACCESS_VERTEX_ATTRIBUTE_READ_BIT/*|VK_ACCESS_TRANSFER_WRITE_BIT*/, VK_ACCESS_TRANSFER_READ_BIT, VK_PIPELINE_STAGE_VERTEX_INPUT_BIT/*|VK_PIPELINE_STAGE_TRANSFER_BIT*/, VK_PIPELINE_STAGE_TRANSFER_BIT); + vkCmdCopyBuffer(commandBuffer.getHandle(), srcBuffer, dstBuffer, copyRegion); + + this.submitCommands(commandBuffer); + vkWaitForFences(DeviceManager.vkDevice, commandBuffer.fence, true, VUtil.UINT64_MAX); + commandBuffer.reset(); + } + } - for (int i = 0; i < queueFamilies.capacity(); i++) { - int queueFlags = queueFamilies.get(i).queueFlags(); + public void uploadBufferCmd(VkCommandBuffer commandBuffer, long srcBuffer, long srcOffset, long dstBuffer, long dstOffset, long size) { - if ((queueFlags & VK_QUEUE_GRAPHICS_BIT) != 0) { - indices.graphicsFamily = i; + try(MemoryStack stack = stackPush()) { - vkGetPhysicalDeviceSurfaceSupportKHR(device, i, Vulkan.getSurface(), presentSupport); + VkBufferCopy.Buffer copyRegion = VkBufferCopy.malloc(1, stack); + copyRegion.size(size); + copyRegion.srcOffset(srcOffset); + copyRegion.dstOffset(dstOffset); - if (presentSupport.get(0) == VK_TRUE) { - indices.presentFamily = i; - } - } else if ((queueFlags & (VK_QUEUE_GRAPHICS_BIT)) == 0 - && (queueFlags & VK_QUEUE_COMPUTE_BIT) != 0) { - indices.computeFamily = i; - } else if ((queueFlags & (VK_QUEUE_COMPUTE_BIT | VK_QUEUE_GRAPHICS_BIT)) == 0 - && (queueFlags & VK_QUEUE_TRANSFER_BIT) != 0) { - indices.transferFamily = i; - } + vkCmdCopyBuffer(commandBuffer, srcBuffer, dstBuffer, copyRegion); + } + } - if (indices.presentFamily == -1) { - vkGetPhysicalDeviceSurfaceSupportKHR(device, i, Vulkan.getSurface(), presentSupport); + public void startRecording() { + currentCmdBuffer = beginCommands(); + } - if (presentSupport.get(0) == VK_TRUE) { - indices.presentFamily = i; - } - } + public void endRecordingAndSubmit() { + long fence = submitCommands(currentCmdBuffer); + Synchronization.INSTANCE.addCommandBuffer(currentCmdBuffer); - if (indices.isComplete()) - break; - } + currentCmdBuffer = null; + } - if (indices.presentFamily == -1) { - // Some drivers will not show present support even if some queue supports it - // Use compute queue as fallback + public CommandPool.CommandBuffer getCommandBuffer() { + return currentCmdBuffer != null ? currentCmdBuffer : beginCommands(); + } - indices.presentFamily = indices.computeFamily; - Initializer.LOGGER.warn("Using compute queue as present fallback"); - } + public long endIfNeeded(CommandPool.CommandBuffer commandBuffer) { + return currentCmdBuffer != null ? VK_NULL_HANDLE : submitCommands(commandBuffer); + } - if (indices.transferFamily == -1) { + public void trimCmdPool() + { + if(commandPool==null) return; + VK11.vkTrimCommandPool(DeviceManager.vkDevice, this.commandPool.id, 0); + } - int fallback = -1; - for (int i = 0; i < queueFamilies.capacity(); i++) { - int queueFlags = queueFamilies.get(i).queueFlags(); + public static void trimCmdPools() + { + for(var queue : Queue.values()) { + queue.trimCmdPool(); + } + } - if ((queueFlags & VK_QUEUE_TRANSFER_BIT) != 0) { - if (fallback == -1) - fallback = i; + public void fillBuffer(long id, int bufferSize, int qNaN) { + vkCmdFillBuffer(this.getCommandBuffer().getHandle(), id, 0, bufferSize, qNaN); + } - if ((queueFlags & (VK_QUEUE_GRAPHICS_BIT)) == 0) { - indices.transferFamily = i; + public void BufferBarrier(VkCommandBuffer commandBuffer, long bufferhdle, int size_t, int srcAccess, int dstAccess, int srcStage, int dstStage) { + + try(MemoryStack stack = MemoryStack.stackPush()) { + VkBufferMemoryBarrier.Buffer memBarrier = VkBufferMemoryBarrier.calloc(1, stack) + .sType$Default() + .buffer(bufferhdle) + .srcQueueFamilyIndex(this.familyIndex) + .dstQueueFamilyIndex(this.familyIndex) + .srcAccessMask(srcAccess) + .dstAccessMask(dstAccess) + .size(size_t); + + vkCmdPipelineBarrier(commandBuffer, + srcStage, dstStage, + 0, + null, + memBarrier, + null); - if (i != indices.computeFamily) - break; - fallback = i; - } - } + } + } - if (fallback == -1) - throw new RuntimeException("Failed to find queue family with transfer support"); + public void MemoryBarrier(VkCommandBuffer commandBuffer, int srcAccess, int dstAccess, int srcStage, int dstStage) { - indices.transferFamily = fallback; - } - } + try(MemoryStack stack = MemoryStack.stackPush()) { + VkMemoryBarrier.Buffer memBarrier = VkMemoryBarrier.calloc(1, stack) + .sType$Default() + .srcAccessMask(srcAccess) + .dstAccessMask(dstAccess); - if (indices.computeFamily == -1) { - for (int i = 0; i < queueFamilies.capacity(); i++) { - int queueFlags = queueFamilies.get(i).queueFlags(); + vkCmdPipelineBarrier(commandBuffer, + srcStage, dstStage, + 0, + memBarrier, + null, + null); - if ((queueFlags & VK_QUEUE_COMPUTE_BIT) != 0) { - indices.computeFamily = i; - break; - } - } + } + } + + + //Using barrier batching to allow Driver optimisations + public void MultiBufferBarriers(VkCommandBuffer commandBuffer, LongSet bufferhdles, int srcAccess, int dstAccess, int srcStage, int dstStage) { + + try(MemoryStack stack = MemoryStack.stackPush()) { + VkBufferMemoryBarrier.Buffer memBarriers = VkBufferMemoryBarrier.malloc(bufferhdles.size(), stack); + int i = 0; + for (var a : bufferhdles) { + + memBarriers.get(i).sType$Default() + .buffer(a) + .pNext(0) + .offset(0) + .srcQueueFamilyIndex(this.familyIndex) + .dstQueueFamilyIndex(this.familyIndex) + .srcAccessMask(srcAccess) //Not sure if VK_ACCESS_VERTEX_ATTRIBUTE_READ_BIT or VK_ACCESS_INDEX_READ_BIT is Faster + .dstAccessMask(dstAccess) + .size(~0 /*VK_WHOLE_SIZE*/); + i++; } - if (indices.graphicsFamily == VK_QUEUE_FAMILY_IGNORED) - throw new RuntimeException("Unable to find queue family with graphics support."); - if (indices.presentFamily == VK_QUEUE_FAMILY_IGNORED) - throw new RuntimeException("Unable to find queue family with present support."); - if (indices.computeFamily == VK_QUEUE_FAMILY_IGNORED) - throw new RuntimeException("Unable to find queue family with compute support."); + vkCmdPipelineBarrier(commandBuffer, + srcStage, dstStage, + 0, + null, + memBarriers, + null); - return indices; } } - public static class QueueFamilyIndices { - public int graphicsFamily = VK_QUEUE_FAMILY_IGNORED; - public int presentFamily = VK_QUEUE_FAMILY_IGNORED; - public int transferFamily = VK_QUEUE_FAMILY_IGNORED; - public int computeFamily = VK_QUEUE_FAMILY_IGNORED; + public void GigaBarrier(VkCommandBuffer commandBuffer, int srcStage, int dstStage, boolean flushReads) { - public boolean isComplete() { - return graphicsFamily != -1 && presentFamily != -1 && transferFamily != -1 && computeFamily != -1; - } + try(MemoryStack stack = MemoryStack.stackPush()) { + VkMemoryBarrier.Buffer memBarrier = VkMemoryBarrier.calloc(1, stack); + memBarrier.sType$Default(); + memBarrier.srcAccessMask(flushReads ? VK_ACCESS_MEMORY_WRITE_BIT|VK_ACCESS_MEMORY_READ_BIT : 0); + memBarrier.dstAccessMask(flushReads ? VK_ACCESS_MEMORY_WRITE_BIT|VK_ACCESS_MEMORY_READ_BIT : VK_ACCESS_MEMORY_WRITE_BIT); - public boolean isSuitable() { - return graphicsFamily != -1 && presentFamily != -1; + vkCmdPipelineBarrier(commandBuffer, + srcStage, dstStage, + 0, + memBarrier, + null, + null); } + } - public int[] unique() { - return IntStream.of(graphicsFamily, presentFamily, transferFamily, computeFamily).distinct().toArray(); - } + public void updateBuffer(CommandPool.CommandBuffer commandBuffer, long id, int baseOffset, long bufferPtr, int sizeT) { + + nvkCmdUpdateBuffer(commandBuffer.getHandle(), id, baseOffset, sizeT, bufferPtr); - public int[] array() { - return new int[]{graphicsFamily, presentFamily}; - } } } + diff --git a/src/main/java/net/vulkanmod/vulkan/queue/QueueFamilyIndices.java b/src/main/java/net/vulkanmod/vulkan/queue/QueueFamilyIndices.java new file mode 100644 index 000000000..23728d2f3 --- /dev/null +++ b/src/main/java/net/vulkanmod/vulkan/queue/QueueFamilyIndices.java @@ -0,0 +1,129 @@ +package net.vulkanmod.vulkan.queue; + +import org.lwjgl.system.MemoryStack; +import org.lwjgl.vulkan.VkPhysicalDevice; +import org.lwjgl.vulkan.VkQueueFamilyProperties; + +import java.nio.IntBuffer; +import java.util.stream.IntStream; + +import static org.lwjgl.system.MemoryStack.stackPush; +import static org.lwjgl.vulkan.VK10.*; + +public class QueueFamilyIndices { + + + public static boolean findQueueFamilies(VkPhysicalDevice device) { + + try (MemoryStack stack = stackPush()) { + + IntBuffer queueFamilyCount = stack.ints(0); + + vkGetPhysicalDeviceQueueFamilyProperties(device, queueFamilyCount, null); + + + + VkQueueFamilyProperties.Buffer queueFamilies = VkQueueFamilyProperties.malloc(queueFamilyCount.get(0), stack); + + vkGetPhysicalDeviceQueueFamilyProperties(device, queueFamilyCount, queueFamilies); + + if(queueFamilies.capacity()==1) + { + graphicsFamily = transferFamily = presentFamily = 0; + return true; + } + + + //Instead using VK_QUEUE_COMPUTE_BIT to check for Present Support + for (int i = 0; i < queueFamilies.capacity(); i++) { + int queueFlags = queueFamilies.get(i).queueFlags(); + + if ((queueFlags & VK_QUEUE_GRAPHICS_BIT) != 0) { + graphicsFamily = i; + + + if ((queueFlags & VK_QUEUE_COMPUTE_BIT) != 0) { + presentFamily = i; + } + } if ((queueFlags & (VK_QUEUE_COMPUTE_BIT | VK_QUEUE_GRAPHICS_BIT)) == 0 + && (queueFlags & VK_QUEUE_TRANSFER_BIT) != 0) { + transferFamily = i; + } + + if (presentFamily == VK_QUEUE_FAMILY_IGNORED) { + + if ((queueFlags & VK_QUEUE_COMPUTE_BIT) != 0) { + presentFamily = i; + } + } + + if (isComplete()) break; + } + + if (transferFamily == VK_QUEUE_FAMILY_IGNORED) { + + int fallback = VK_QUEUE_FAMILY_IGNORED; + for (int i = 0; i < queueFamilies.capacity(); i++) { + int queueFlags = queueFamilies.get(i).queueFlags(); + + if ((queueFlags & VK_QUEUE_TRANSFER_BIT) != 0) { + if (fallback == VK_QUEUE_FAMILY_IGNORED) + fallback = i; + + if ((queueFlags & (VK_QUEUE_GRAPHICS_BIT)) == 0) { + transferFamily = i; + + + fallback = i; + } + } + + if (fallback == VK_QUEUE_FAMILY_IGNORED) + throw new RuntimeException("Failed to find queue family with transfer support"); + + transferFamily = fallback; + } + } + + + + hasDedicatedTransferQueue = graphicsFamily != transferFamily; + + + if (graphicsFamily == VK_QUEUE_FAMILY_IGNORED) + throw new RuntimeException("Unable to find queue family with graphics support."); + if (presentFamily == VK_QUEUE_FAMILY_IGNORED) + throw new RuntimeException("Unable to find queue family with present support."); + + } + return true; + } + + public static boolean hasQueues(VkPhysicalDevice device, MemoryStack stack) { + IntBuffer queueFamilyCount = stack.ints(0); + + vkGetPhysicalDeviceQueueFamilyProperties(device, queueFamilyCount, null); + return queueFamilyCount.get()!=0; + } + + public static int graphicsFamily = VK_QUEUE_FAMILY_IGNORED, presentFamily = VK_QUEUE_FAMILY_IGNORED, transferFamily = VK_QUEUE_FAMILY_IGNORED; + + public static boolean hasDedicatedTransferQueue = false; + + public static boolean isComplete() { + return graphicsFamily != VK_QUEUE_FAMILY_IGNORED && presentFamily != VK_QUEUE_FAMILY_IGNORED && transferFamily != VK_QUEUE_FAMILY_IGNORED; + } + + public static boolean isSuitable() { + return graphicsFamily != VK_QUEUE_FAMILY_IGNORED && presentFamily != VK_QUEUE_FAMILY_IGNORED; + } + + public static int[] unique() { + return IntStream.of(graphicsFamily, presentFamily, transferFamily).distinct().toArray(); + } + + public static int[] array() { + return new int[]{graphicsFamily, presentFamily}; + } + +} diff --git a/src/main/java/net/vulkanmod/vulkan/queue/TransferQueue.java b/src/main/java/net/vulkanmod/vulkan/queue/TransferQueue.java deleted file mode 100644 index 4cd17c4d6..000000000 --- a/src/main/java/net/vulkanmod/vulkan/queue/TransferQueue.java +++ /dev/null @@ -1,73 +0,0 @@ -package net.vulkanmod.vulkan.queue; - -import net.vulkanmod.vulkan.Synchronization; -import net.vulkanmod.vulkan.Vulkan; -import net.vulkanmod.vulkan.util.VUtil; -import org.lwjgl.system.MemoryStack; -import org.lwjgl.vulkan.VkBufferCopy; -import org.lwjgl.vulkan.VkCommandBuffer; -import org.lwjgl.vulkan.VkDevice; - -import static org.lwjgl.system.MemoryStack.stackPush; -import static org.lwjgl.vulkan.VK10.vkCmdCopyBuffer; -import static org.lwjgl.vulkan.VK10.vkWaitForFences; - -public class TransferQueue extends Queue { - private static final VkDevice DEVICE = Vulkan.getVkDevice(); - - public TransferQueue(MemoryStack stack, int familyIndex) { - super(stack, familyIndex); - } - - public long copyBufferCmd(long srcBuffer, long srcOffset, long dstBuffer, long dstOffset, long size) { - - try (MemoryStack stack = stackPush()) { - - CommandPool.CommandBuffer commandBuffer = beginCommands(); - - VkBufferCopy.Buffer copyRegion = VkBufferCopy.calloc(1, stack); - copyRegion.size(size); - copyRegion.srcOffset(srcOffset); - copyRegion.dstOffset(dstOffset); - - vkCmdCopyBuffer(commandBuffer.getHandle(), srcBuffer, dstBuffer, copyRegion); - - this.submitCommands(commandBuffer); - Synchronization.INSTANCE.addCommandBuffer(commandBuffer); - - return commandBuffer.fence; - } - } - - public void uploadBufferImmediate(long srcBuffer, long srcOffset, long dstBuffer, long dstOffset, long size) { - - try (MemoryStack stack = stackPush()) { - CommandPool.CommandBuffer commandBuffer = this.beginCommands(); - - VkBufferCopy.Buffer copyRegion = VkBufferCopy.calloc(1, stack); - copyRegion.size(size); - copyRegion.srcOffset(srcOffset); - copyRegion.dstOffset(dstOffset); - - vkCmdCopyBuffer(commandBuffer.getHandle(), srcBuffer, dstBuffer, copyRegion); - - this.submitCommands(commandBuffer); - vkWaitForFences(DEVICE, commandBuffer.fence, true, VUtil.UINT64_MAX); - commandBuffer.reset(); - } - } - - public static void uploadBufferCmd(VkCommandBuffer commandBuffer, long srcBuffer, long srcOffset, long dstBuffer, long dstOffset, long size) { - - try (MemoryStack stack = stackPush()) { - - VkBufferCopy.Buffer copyRegion = VkBufferCopy.calloc(1, stack); - copyRegion.size(size); - copyRegion.srcOffset(srcOffset); - copyRegion.dstOffset(dstOffset); - - vkCmdCopyBuffer(commandBuffer, srcBuffer, dstBuffer, copyRegion); - } - } - -}