Implemented buffers with cpp headers
This commit is contained in:
parent
e7eba6fab8
commit
1771fa0e7a
2 changed files with 131 additions and 40 deletions
|
|
@ -1 +1,3 @@
|
|||
# Vulkan Compute
|
||||
|
||||
Follows Mozilla C++ Style Guide https://www-archive.mozilla.org/hacking/mozilla-style-guide.html
|
||||
|
|
|
|||
169
src/main.cpp
169
src/main.cpp
|
|
@ -3,17 +3,17 @@
|
|||
#endif
|
||||
|
||||
#include <algorithm>
|
||||
#include <set>
|
||||
#include <assert.h>
|
||||
#include <iostream>
|
||||
#include <set>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <vector>
|
||||
|
||||
#include <spdlog/spdlog.h>
|
||||
#include <vulkan/vulkan.h>
|
||||
#include <vulkan/vulkan.hpp>
|
||||
#include <spdlog/spdlog.h>
|
||||
|
||||
#include "VulkanTools.h"
|
||||
|
||||
|
|
@ -51,13 +51,63 @@ class VulkanCompute
|
|||
|
||||
vk::DebugReportCallbackEXT mDebugReportCallback{};
|
||||
|
||||
void createBuffer(const vk::BufferUsageFlags& aUsageFlags,
|
||||
const vk::MemoryPropertyFlags& aMemoryPropertyFlags,
|
||||
vk::Buffer* aBuffer,
|
||||
vk::DeviceMemory* aMemory,
|
||||
vk::DeviceSize aSize,
|
||||
void* aData = nullptr) const
|
||||
{
|
||||
vk::BufferCreateInfo bufferCreateInfo(vk::BufferCreateFlags(),
|
||||
aSize,
|
||||
aUsageFlags,
|
||||
vk::SharingMode::eExclusive);
|
||||
|
||||
*aBuffer = this->mDevice.createBuffer(bufferCreateInfo);
|
||||
|
||||
vk::PhysicalDeviceMemoryProperties deviceMemoryProperties =
|
||||
this->mPhysicalDevice.getMemoryProperties();
|
||||
|
||||
vk::MemoryRequirements memReqs =
|
||||
this->mDevice.getBufferMemoryRequirements(*aBuffer);
|
||||
|
||||
uint32_t memoryTypeIndex = -1;
|
||||
for (uint32_t i = 0; i < 32; i++) {
|
||||
if (memReqs.memoryTypeBits & (1 << i)) {
|
||||
if ((deviceMemoryProperties.memoryTypes[i].propertyFlags &
|
||||
aMemoryPropertyFlags) == aMemoryPropertyFlags) {
|
||||
memoryTypeIndex = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (memoryTypeIndex < 0) {
|
||||
throw std::runtime_error(
|
||||
"Memory type index for buffer creation not found");
|
||||
}
|
||||
|
||||
vk::MemoryAllocateInfo memoryAllocateInfo(memReqs.size,
|
||||
memoryTypeIndex);
|
||||
|
||||
*aMemory = this->mDevice.allocateMemory(memoryAllocateInfo);
|
||||
this->mDevice.bindBufferMemory(*aBuffer, *aMemory, 0);
|
||||
|
||||
if (aData != nullptr) {
|
||||
vk::DeviceSize offset = 0;
|
||||
void* mapped = this->mDevice.mapMemory(
|
||||
*aMemory, offset, aSize, vk::MemoryMapFlags());
|
||||
memcpy(mapped, aData, aSize);
|
||||
this->mDevice.unmapMemory(*aMemory);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* C API
|
||||
*/
|
||||
VkInstance instance;
|
||||
VkPhysicalDevice physicalDevice;
|
||||
VkDevice device;
|
||||
//uint32_t queueFamilyIndex;
|
||||
// uint32_t queueFamilyIndex;
|
||||
VkPipelineCache pipelineCache;
|
||||
VkQueue queue;
|
||||
VkCommandPool commandPool;
|
||||
|
|
@ -72,6 +122,7 @@ class VulkanCompute
|
|||
|
||||
// VkDebugReportCallbackEXT debugReportCallback{};
|
||||
|
||||
// C API Function
|
||||
VkResult createBuffer(VkBufferUsageFlags usageFlags,
|
||||
VkMemoryPropertyFlags memoryPropertyFlags,
|
||||
VkBuffer* buffer,
|
||||
|
|
@ -140,13 +191,15 @@ class VulkanCompute
|
|||
vk::InstanceCreateInfo computeInstanceCreateInfo;
|
||||
computeInstanceCreateInfo.pApplicationInfo = &applicationInfo;
|
||||
if (!applicationExtensions.empty()) {
|
||||
computeInstanceCreateInfo.enabledExtensionCount = (uint32_t)applicationExtensions.size();
|
||||
computeInstanceCreateInfo.ppEnabledExtensionNames = applicationExtensions.data();
|
||||
computeInstanceCreateInfo.enabledExtensionCount =
|
||||
(uint32_t)applicationExtensions.size();
|
||||
computeInstanceCreateInfo.ppEnabledExtensionNames =
|
||||
applicationExtensions.data();
|
||||
}
|
||||
|
||||
#if DEBUG
|
||||
// We'll identify the layers that are supported
|
||||
std::vector<const char*> validLayerNames;
|
||||
// We'll identify the layers that are supported
|
||||
std::vector<const char*> validLayerNames;
|
||||
std::vector<const char*> desiredLayerNames = {
|
||||
"VK_LAYER_LUNARG_assistant_layer",
|
||||
"VK_LAYER_LUNARG_standard_validation"
|
||||
|
|
@ -154,8 +207,10 @@ class VulkanCompute
|
|||
// Identify the valid layer names based on the desiredLayerNames
|
||||
{
|
||||
std::set<std::string> uniqueLayerNames;
|
||||
std::vector<vk::LayerProperties> availableLayerProperties = vk::enumerateInstanceLayerProperties();
|
||||
for (vk::LayerProperties layerProperties : availableLayerProperties) {
|
||||
std::vector<vk::LayerProperties> availableLayerProperties =
|
||||
vk::enumerateInstanceLayerProperties();
|
||||
for (vk::LayerProperties layerProperties :
|
||||
availableLayerProperties) {
|
||||
std::string layerName(layerProperties.layerName);
|
||||
uniqueLayerNames.insert(layerName);
|
||||
}
|
||||
|
|
@ -167,8 +222,10 @@ class VulkanCompute
|
|||
}
|
||||
|
||||
if (validLayerNames.size() > 0) {
|
||||
computeInstanceCreateInfo.enabledLayerCount = (uint32_t)validLayerNames.size();
|
||||
computeInstanceCreateInfo.ppEnabledLayerNames = validLayerNames.data();
|
||||
computeInstanceCreateInfo.enabledLayerCount =
|
||||
(uint32_t)validLayerNames.size();
|
||||
computeInstanceCreateInfo.ppEnabledLayerNames =
|
||||
validLayerNames.data();
|
||||
}
|
||||
#endif
|
||||
|
||||
|
|
@ -176,71 +233,78 @@ class VulkanCompute
|
|||
|
||||
#if DEBUG
|
||||
if (validLayerNames.size() > 0) {
|
||||
vk::DebugReportFlagsEXT debugFlags =
|
||||
vk::DebugReportFlagBitsEXT::eError | vk::DebugReportFlagBitsEXT::eWarning;
|
||||
vk::DebugReportFlagsEXT debugFlags =
|
||||
vk::DebugReportFlagBitsEXT::eError |
|
||||
vk::DebugReportFlagBitsEXT::eWarning;
|
||||
vk::DebugReportCallbackCreateInfoEXT debugCreateInfo = {};
|
||||
debugCreateInfo.pfnCallback = (PFN_vkDebugReportCallbackEXT)debugMessageCallback;
|
||||
debugCreateInfo.pfnCallback =
|
||||
(PFN_vkDebugReportCallbackEXT)debugMessageCallback;
|
||||
debugCreateInfo.flags = debugFlags;
|
||||
|
||||
vk::DispatchLoaderDynamic dispatcher;
|
||||
dispatcher.init(this->mInstance, &vkGetInstanceProcAddr);
|
||||
this->mDebugReportCallback = this->mInstance.createDebugReportCallbackEXT(debugCreateInfo, nullptr, dispatcher);
|
||||
this->mDebugReportCallback =
|
||||
this->mInstance.createDebugReportCallbackEXT(
|
||||
debugCreateInfo, nullptr, dispatcher);
|
||||
}
|
||||
#endif
|
||||
|
||||
// Find device (currently only pick first device)
|
||||
{
|
||||
std::vector<vk::PhysicalDevice> physicalDevices =
|
||||
this->mInstance.enumeratePhysicalDevices();
|
||||
std::vector<vk::PhysicalDevice> physicalDevices =
|
||||
this->mInstance.enumeratePhysicalDevices();
|
||||
|
||||
this->mPhysicalDevice = physicalDevices[0];
|
||||
|
||||
vk::PhysicalDeviceProperties physicalDeviceProperties =
|
||||
this->mPhysicalDevice.getProperties();
|
||||
this->mPhysicalDevice.getProperties();
|
||||
|
||||
spdlog::info("Device {}", physicalDeviceProperties.deviceName);
|
||||
}
|
||||
|
||||
{
|
||||
// Find compute queue
|
||||
std::vector<vk::QueueFamilyProperties> allQueueFamilyProperties =
|
||||
this->mPhysicalDevice.getQueueFamilyProperties();
|
||||
std::vector<vk::QueueFamilyProperties> allQueueFamilyProperties =
|
||||
this->mPhysicalDevice.getQueueFamilyProperties();
|
||||
|
||||
this->mComputeQueueFamilyIndex = 0;
|
||||
for (; this->mComputeQueueFamilyIndex < allQueueFamilyProperties.size(); this->mComputeQueueFamilyIndex++) {
|
||||
vk::QueueFamilyProperties queueFamilyProperties =
|
||||
allQueueFamilyProperties[this->mComputeQueueFamilyIndex];
|
||||
if (queueFamilyProperties.queueFlags & vk::QueueFlagBits::eCompute) {
|
||||
this->mComputeQueueFamilyIndex = -1;
|
||||
for (uint32_t i = 0; i < allQueueFamilyProperties.size(); i++) {
|
||||
vk::QueueFamilyProperties queueFamilyProperties =
|
||||
allQueueFamilyProperties[this->mComputeQueueFamilyIndex];
|
||||
|
||||
if (queueFamilyProperties.queueFlags &
|
||||
vk::QueueFlagBits::eCompute) {
|
||||
this->mComputeQueueFamilyIndex = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
spdlog::info("ComputeQueueFamilyIndex: {}, Size: {}", this->mComputeQueueFamilyIndex, allQueueFamilyProperties.size());
|
||||
if (this->mComputeQueueFamilyIndex == allQueueFamilyProperties.size() - 1) {
|
||||
if (this->mComputeQueueFamilyIndex < 0) {
|
||||
spdlog::critical("Compute queue is not supported");
|
||||
}
|
||||
spdlog::info("Running after critical");
|
||||
|
||||
const float defaultQueuePriority(0.0f);
|
||||
const uint32_t defaultQueueCount(1);
|
||||
vk::DeviceQueueCreateInfo deviceQueueCreateInfo(
|
||||
vk::DeviceQueueCreateFlags(),
|
||||
this->mComputeQueueFamilyIndex,
|
||||
defaultQueueCount,
|
||||
&defaultQueuePriority);
|
||||
vk::DeviceQueueCreateFlags(),
|
||||
this->mComputeQueueFamilyIndex,
|
||||
defaultQueueCount,
|
||||
&defaultQueuePriority);
|
||||
|
||||
vk::DeviceCreateInfo deviceCreateInfo(
|
||||
vk::DeviceCreateFlags(),
|
||||
1, // Number of deviceQueueCreateInfo
|
||||
&deviceQueueCreateInfo);
|
||||
vk::DeviceCreateFlags(),
|
||||
1, // Number of deviceQueueCreateInfo
|
||||
&deviceQueueCreateInfo);
|
||||
|
||||
this->mDevice = this->mPhysicalDevice.createDevice(deviceCreateInfo);
|
||||
this->mComputeQueue = this->mDevice.getQueue(this->mComputeQueueFamilyIndex, 0);
|
||||
this->mDevice =
|
||||
this->mPhysicalDevice.createDevice(deviceCreateInfo);
|
||||
this->mComputeQueue =
|
||||
this->mDevice.getQueue(this->mComputeQueueFamilyIndex, 0);
|
||||
}
|
||||
|
||||
// /*
|
||||
// C API Vulkan
|
||||
// */
|
||||
// /*
|
||||
// C API Vulkan
|
||||
// */
|
||||
|
||||
this->instance = static_cast<VkInstance>(this->mInstance);
|
||||
this->physicalDevice = this->mPhysicalDevice;
|
||||
|
|
@ -260,6 +324,8 @@ class VulkanCompute
|
|||
|
||||
const VkDeviceSize bufferSize = BUFFER_ELEMENTS * sizeof(uint32_t);
|
||||
|
||||
/*
|
||||
|
||||
VkBuffer deviceBuffer, hostBuffer;
|
||||
VkDeviceMemory deviceMemory, hostMemory;
|
||||
|
||||
|
|
@ -282,6 +348,29 @@ class VulkanCompute
|
|||
bufferSize);
|
||||
}
|
||||
|
||||
*/
|
||||
|
||||
vk::Buffer hostBuffer, deviceBuffer;
|
||||
vk::DeviceMemory hostMemory, deviceMemory;
|
||||
|
||||
{
|
||||
createBuffer(vk::BufferUsageFlagBits::eTransferSrc |
|
||||
vk::BufferUsageFlagBits::eTransferDst,
|
||||
vk::MemoryPropertyFlagBits::eHostVisible,
|
||||
&hostBuffer,
|
||||
&hostMemory,
|
||||
bufferSize,
|
||||
computeInput.data());
|
||||
|
||||
createBuffer(vk::BufferUsageFlagBits::eStorageBuffer |
|
||||
vk::BufferUsageFlagBits::eTransferSrc |
|
||||
vk::BufferUsageFlagBits::eTransferDst,
|
||||
vk::MemoryPropertyFlagBits::eDeviceLocal,
|
||||
&deviceBuffer,
|
||||
&deviceMemory,
|
||||
bufferSize);
|
||||
}
|
||||
|
||||
/*
|
||||
Prepare compute this->pipeline
|
||||
*/
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue