summaryrefslogtreecommitdiff
path: root/src/vk/device.cpp
diff options
context:
space:
mode:
authorFrederico Linhares <fred@linhares.blue>2024-05-08 17:56:29 -0300
committerFrederico Linhares <fred@linhares.blue>2024-05-08 17:56:29 -0300
commit43821b0cffc5aa419c0218992f06f8962ae54a13 (patch)
tree97bdbbf710a78e6dcb181d92dd83e98d8b329c6d /src/vk/device.cpp
parent70e156d47346ae3198c623e0af75e5703f894db3 (diff)
refa Rename graphical engine to BluCat
Diffstat (limited to 'src/vk/device.cpp')
-rw-r--r--src/vk/device.cpp392
1 files changed, 0 insertions, 392 deletions
diff --git a/src/vk/device.cpp b/src/vk/device.cpp
deleted file mode 100644
index 78baa53..0000000
--- a/src/vk/device.cpp
+++ /dev/null
@@ -1,392 +0,0 @@
-/*
- * Copyright 2022-2024 Frederico de Oliveira Linhares
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "device.hpp"
-
-#include <fstream>
-#include <new>
-#include <vector>
-#ifdef DEBUG
-#include <sstream>
-#endif
-
-#include "../core.hpp"
-
-namespace
-{
-VkShaderModule
-create_shader_module(VkDevice vk_device, const char *filename)
-{
- std::ifstream file(filename, std::ios::ate | std::ios::binary);
-
- if (!file.is_open())
- {
- throw std::runtime_error("Failed to open shader module file.");
- }
-
- size_t file_size = (size_t) file.tellg();
- std::vector<char> code(file_size);
-
- file.seekg(0);
- file.read(code.data(), file_size);
-
- file.close();
-
- VkShaderModuleCreateInfo create_info = {};
- create_info.sType = VK_STRUCTURE_TYPE_SHADER_MODULE_CREATE_INFO;
- create_info.codeSize = code.size();
- create_info.pCode = reinterpret_cast<const uint32_t*>(code.data());
-
- VkShaderModule shader_module;
- if (vkCreateShaderModule(vk_device, &create_info, nullptr,
- &shader_module) != VK_SUCCESS)
- {
- throw std::runtime_error("Failed to create shader module.");
- }
-
- return shader_module;
-}
-}
-
-namespace VK
-{
-
-Device::Device(VkPhysicalDevice vk_physical_device, bool with_swapchain)
-{
- this->physical_device = vk_physical_device;
-
- std::vector<VkQueueFamilyProperties> queue_family_properties;
-
- // Get queue families.
- {
- vkGetPhysicalDeviceQueueFamilyProperties(
- vk_physical_device, &this->queue_families_count, nullptr);
- queue_family_properties.resize(this->queue_families_count);
- vkGetPhysicalDeviceQueueFamilyProperties(
- vk_physical_device, &this->queue_families_count,
- queue_family_properties.data());
- }
-
- // Get information from physical device.
- {
- VkPhysicalDeviceProperties physical_properties = {};
- vkGetPhysicalDeviceProperties(vk_physical_device, &physical_properties);
- VkPhysicalDeviceFeatures supported_features = {};
- vkGetPhysicalDeviceFeatures(vk_physical_device, &supported_features);
-
-#ifdef DEBUG
- std::stringstream message{};
- message << "Name: " << physical_properties.deviceName << std::endl;
- message << "API version: " << physical_properties.apiVersion <<
- std::endl;
- message << "Driver version: " << physical_properties.driverVersion <<
- std::endl;
- message << "Vendor ID: " << physical_properties.vendorID << std::endl;
- message << "Device ID: " << physical_properties.deviceID << std::endl;
- message << "Device type: " << physical_properties.deviceType <<
- std::endl;
- cg_core.log.message(Log::Level::Trace, message.str());
-#endif
-
- std::vector<VkDeviceQueueCreateInfo> device_queue_create_infos;
- std::vector<std::vector<float>> queue_priorities(
- queue_family_properties.size());
- device_queue_create_infos.resize(queue_family_properties.size());
- for(auto i{0}; i < queue_family_properties.size(); i++)
- {
- // Give different priorities to queues.
- int queue_count = queue_family_properties[i].queueCount;
- queue_priorities[i].resize(queue_count);
- float priority_unity = 1.0f/queue_count;
- for(auto ii{0}; ii < queue_count; ii++)
- queue_priorities[i][ii] = priority_unity * (queue_count - ii);
-
- device_queue_create_infos[i].sType =
- VK_STRUCTURE_TYPE_DEVICE_QUEUE_CREATE_INFO;
- device_queue_create_infos[i].pNext = nullptr;
- device_queue_create_infos[i].flags = 0;
- device_queue_create_infos[i].queueFamilyIndex = i;
- device_queue_create_infos[i].queueCount = queue_priorities[i].size();
- device_queue_create_infos[i].pQueuePriorities =
- queue_priorities[i].data();
- }
-
- VkPhysicalDeviceFeatures required_features = {};
- required_features.multiDrawIndirect = supported_features.multiDrawIndirect;
- required_features.fillModeNonSolid = VK_TRUE;
- required_features.geometryShader = VK_TRUE;
- required_features.tessellationShader = VK_TRUE;
- required_features.samplerAnisotropy = VK_TRUE;
-
- std::vector<const char*> device_extensions;
- if(with_swapchain)
- device_extensions.emplace_back(VK_KHR_SWAPCHAIN_EXTENSION_NAME);
-
- VkDeviceCreateInfo device_create_info = {};
- device_create_info.sType = VK_STRUCTURE_TYPE_DEVICE_CREATE_INFO;
- device_create_info.pNext = nullptr;
- device_create_info.flags = 0;
- device_create_info.queueCreateInfoCount = device_queue_create_infos.size();
- device_create_info.pQueueCreateInfos = device_queue_create_infos.data();
- device_create_info.enabledLayerCount = 0;
- device_create_info.ppEnabledLayerNames = nullptr;
- device_create_info.enabledExtensionCount = device_extensions.size();
- if(device_extensions.size() == 0)
- device_create_info.ppEnabledExtensionNames = nullptr;
- else
- device_create_info.ppEnabledExtensionNames = device_extensions.data();
-
- device_create_info.pEnabledFeatures = &required_features;
-
- if(vkCreateDevice(this->physical_device, &device_create_info, nullptr,
- &this->device) != VK_SUCCESS)
- throw std::runtime_error("Failed to create Vulkan physical device.");
- }
-
- // Load Shaders
- {
- std::string data_dir{""};
-#ifdef _WIN64
- HKEY hKey;
- LPCSTR lpSubKey = "SOFTWARE\\CandyGear";
- LPCSTR lpValueName = "InstallLocation";
- DWORD dwType = REG_SZ;
- DWORD dwSize = 0;
- LPBYTE lpData = NULL;
-
- if(RegOpenKeyEx(HKEY_LOCAL_MACHINE, lpSubKey, 0, KEY_READ, &hKey) ==
- ERROR_SUCCESS)
- {
- if(RegQueryValueEx(hKey, lpValueName, NULL, &dwType, NULL, &dwSize) ==
- ERROR_SUCCESS)
- {
- lpData = new BYTE[dwSize];
- if(RegQueryValueEx(
- hKey, lpValueName, NULL, &dwType, lpData, &dwSize) ==
- ERROR_SUCCESS)
- {
- data_dir = reinterpret_cast<char const*>(lpData);
- }
- delete[] lpData;
- }
- RegCloseKey(hKey);
- }
-
- if(data_dir == "")
- throw std::runtime_error("Failed to read CandyGear registry.");
-
- std::string vert_sprite_3d_shader_module{data_dir};
- vert_sprite_3d_shader_module.append("\\glsl\\shader_sprite_3d.vert.spv");
- this->vert_sprite_3d_shader_module = create_shader_module(
- this->device, vert_sprite_3d_shader_module.c_str());
-
- std::string frag_sprite_3d_shader_module{data_dir};
- frag_sprite_3d_shader_module.append("\\glsl\\shader_sprite_3d.frag.spv");
- this->frag_sprite_3d_shader_module = create_shader_module(
- this->device, frag_sprite_3d_shader_module.c_str());
-
- std::string vert3d_shader_module{data_dir};
- vert3d_shader_module.append("\\glsl\\shader_3d.vert.spv");
- this->vert3d_shader_module = create_shader_module(
- this->device, vert3d_shader_module.c_str());
-
- std::string vert3d_skeletal_shader_module{data_dir};
- vert3d_skeletal_shader_module.append(
- "\\glsl\\shader_3d_skeletal.vert.spv");
- this->vert3d_skeletal_shader_module = create_shader_module(
- this->device, vert3d_skeletal_shader_module.c_str());
-
- std::string frag3d_shader_module{data_dir};
- frag3d_shader_module.append("\\glsl\\shader_3d.frag.spv");
- this->frag3d_shader_module = create_shader_module(
- this->device, frag3d_shader_module.c_str());
-
- std::string vert2d_solid_shader_module{data_dir};
- vert2d_solid_shader_module.append("\\glsl\\shader_2d_solid.vert.spv");
- this->vert2d_solid_shader_module = create_shader_module(
- this->device, vert2d_solid_shader_module.c_str());
-
- std::string frag2d_solid_shader_module{data_dir};
- frag2d_solid_shader_module.append("\\glsl\\shader_2d_solid.frag.spv");
- this->frag2d_solid_shader_module = create_shader_module(
- this->device, frag2d_solid_shader_module.c_str());
-
- std::string vert2d_wired_shader_module{data_dir};
- vert2d_wired_shader_module.append("\\glsl\\shader_2d_wired.vert.spv");
- this->vert2d_wired_shader_module = create_shader_module(
- this->device, vert2d_wired_shader_module.c_str());
-
- std::string frag2d_wired_shader_module{data_dir};
- frag2d_wired_shader_module.append("\\glsl\\shader_2d_wired.frag.spv");
- this->frag2d_wired_shader_module = create_shader_module(
- this->device, frag2d_wired_shader_module.c_str());
-#else
- data_dir = "/usr/local/share/candy_gear";
-
- std::string vert_sprite_3d_shader_module{data_dir};
- vert_sprite_3d_shader_module.append("/glsl/shader_sprite_3d.vert.spv");
- this->vert_sprite_3d_shader_module = create_shader_module(
- this->device, vert_sprite_3d_shader_module.c_str());
-
- std::string frag_sprite_3d_shader_module{data_dir};
- frag_sprite_3d_shader_module.append("/glsl/shader_sprite_3d.frag.spv");
- this->frag_sprite_3d_shader_module = create_shader_module(
- this->device, frag_sprite_3d_shader_module.c_str());
-
- std::string vert3d_shader_module{data_dir};
- vert3d_shader_module.append("/glsl/shader_3d.vert.spv");
- this->vert3d_shader_module = create_shader_module(
- this->device, vert3d_shader_module.c_str());
-
- std::string vert3d_skeletal_shader_module{data_dir};
- vert3d_skeletal_shader_module.append("/glsl/shader_3d_skeletal.vert.spv");
- this->vert3d_skeletal_shader_module = create_shader_module(
- this->device, vert3d_skeletal_shader_module.c_str());
-
- std::string frag3d_shader_module{data_dir};
- frag3d_shader_module.append("/glsl/shader_3d.frag.spv");
- this->frag3d_shader_module = create_shader_module(
- this->device, frag3d_shader_module.c_str());
-
- std::string vert2d_solid_shader_module{data_dir};
- vert2d_solid_shader_module.append("/glsl/shader_2d_solid.vert.spv");
- this->vert2d_solid_shader_module = create_shader_module(
- this->device, vert2d_solid_shader_module.c_str());
-
- std::string frag2d_solid_shader_module{data_dir};
- frag2d_solid_shader_module.append("/glsl/shader_2d_solid.frag.spv");
- this->frag2d_solid_shader_module = create_shader_module(
- this->device, frag2d_solid_shader_module.c_str());
-
- std::string vert2d_wired_shader_module{data_dir};
- vert2d_wired_shader_module.append("/glsl/shader_2d_wired.vert.spv");
- this->vert2d_wired_shader_module = create_shader_module(
- this->device, vert2d_wired_shader_module.c_str());
-
- std::string frag2d_wired_shader_module{data_dir};
- frag2d_wired_shader_module.append("/glsl/shader_2d_wired.frag.spv");
- this->frag2d_wired_shader_module = create_shader_module(
- this->device, frag2d_wired_shader_module.c_str());
-#endif
- }
-
- this->queue_families = static_cast<QueueFamily*>(
- std::malloc(this->queue_families_count * sizeof(QueueFamily)));
- for(auto i{0}; i < this->queue_families_count; i++)
- {
- new(&this->queue_families[i])QueueFamily(
- this, i, queue_family_properties[i]);
-
- // Select families with graphics support.
- auto &family_properties = this->queue_families[i].family_properties;
- if(family_properties.queueCount > 0 &&
- family_properties.queueFlags & VK_QUEUE_GRAPHICS_BIT)
- this->queue_families_with_graphics.push_back(
- &this->queue_families[i]);
-
- // Select families with presentation support.
- VkBool32 present_supported;
- vkGetPhysicalDeviceSurfaceSupportKHR(
- vk_physical_device, i, cg_core.window_surface, &present_supported);
- if(present_supported)
- this->queue_families_with_presentation.push_back(
- &this->queue_families[i]);
- }
-}
-
-Device::~Device()
-{
- for(auto i{0}; i < this->queue_families_count; i++)
- this->queue_families[i].~QueueFamily();
- std::free(this->queue_families);
-
- // Destroy shaders
- vkDestroyShaderModule(
- this->device, this->vert_sprite_3d_shader_module, nullptr);
- vkDestroyShaderModule(
- this->device, this->frag_sprite_3d_shader_module, nullptr);
- vkDestroyShaderModule(this->device, this->vert3d_shader_module, nullptr);
- vkDestroyShaderModule(
- this->device, this->vert3d_skeletal_shader_module, nullptr);
- vkDestroyShaderModule(this->device, this->frag3d_shader_module, nullptr);
- vkDestroyShaderModule(
- this->device, this->vert2d_solid_shader_module, nullptr);
- vkDestroyShaderModule(
- this->device, this->frag2d_solid_shader_module, nullptr);
- vkDestroyShaderModule(
- this->device, this->vert2d_wired_shader_module, nullptr);
- vkDestroyShaderModule(
- this->device, this->frag2d_wired_shader_module, nullptr);
-
- vkDeviceWaitIdle(this->device);
- vkDestroyDevice(this->device, nullptr);
-}
-
-bool
-Device::select_memory_type(
- uint32_t *memory_type_index, VkMemoryRequirements *vk_memory_requirements,
- VkMemoryPropertyFlags vk_property_flags)
-{
- VkPhysicalDeviceMemoryProperties vk_memory_properties;
- vkGetPhysicalDeviceMemoryProperties(
- this->physical_device, &vk_memory_properties);
-
- for (auto i{0}; i < vk_memory_properties.memoryTypeCount; i++)
- {
- if(vk_memory_requirements->memoryTypeBits & (1 << i))
- {
- const VkMemoryType& type = vk_memory_properties.memoryTypes[i];
-
- if ((type.propertyFlags & vk_property_flags) == vk_property_flags)
- {
- *memory_type_index = i;
- return true;
- }
- }
- }
-
- return false;
-}
-
-QueueFamily*
-Device::get_queue_family_with_graphics() const
-{
- /*
- Returns a random queue family, so not all commands in the engine use the
- same queue.
- TODO: There must be a better way of doing this.
- */
- std::uniform_int_distribution<std::size_t> random_distribution{
- 0, this->queue_families_with_graphics.size() -1};
- auto random = random_distribution(random_number_generator);
- return this->queue_families_with_graphics[0];
-}
-
-QueueFamily*
-Device::get_queue_family_with_presentation() const
-{
- /*
- Returns a random queue family, so not all commands in the engine use the
- same queue.
- TODO: There must be a better way of doing this.
- */
- std::uniform_int_distribution<std::size_t> random_distribution{
- 0, this->queue_families_with_presentation.size() -1};
- auto random = random_distribution(random_number_generator);
- return this->queue_families_with_presentation[0];
-}
-
-}