1 // Copyright 2018 The Amber Authors. 2 // Copyright (C) 2024 Advanced Micro Devices, Inc. All rights reserved. 3 // 4 // Licensed under the Apache License, Version 2.0 (the "License"); 5 // you may not use this file except in compliance with the License. 6 // You may obtain a copy of the License at 7 // 8 // http://www.apache.org/licenses/LICENSE-2.0 9 // 10 // Unless required by applicable law or agreed to in writing, software 11 // distributed under the License is distributed on an "AS IS" BASIS, 12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 // See the License for the specific language governing permissions and 14 // limitations under the License. 15 16 #ifndef SRC_VULKAN_DEVICE_H_ 17 #define SRC_VULKAN_DEVICE_H_ 18 19 #include <functional> 20 #include <memory> 21 #include <string> 22 #include <vector> 23 24 #include "amber/amber.h" 25 #include "amber/result.h" 26 #include "amber/vulkan_header.h" 27 #include "src/buffer.h" 28 #include "src/format.h" 29 30 namespace amber { 31 namespace vulkan { 32 33 struct VulkanPtrs { 34 #include "vk-wrappers-1-0.h" // NOLINT(build/include_subdir) 35 #include "vk-wrappers-1-1.h" // NOLINT(build/include_subdir) 36 }; 37 38 /// Wrapper around a Vulkan Device object. 39 class Device { 40 public: 41 Device(VkInstance instance, 42 VkPhysicalDevice physical_device, 43 uint32_t queue_family_index, 44 VkDevice device, 45 VkQueue queue, 46 Delegate* delegate); 47 virtual ~Device(); 48 49 Result Initialize(PFN_vkGetInstanceProcAddr getInstanceProcAddr, 50 const std::vector<std::string>& required_features, 51 const std::vector<std::string>& required_properties, 52 const std::vector<std::string>& required_device_extensions, 53 const VkPhysicalDeviceFeatures& available_features, 54 const VkPhysicalDeviceFeatures2KHR& available_features2, 55 const VkPhysicalDeviceProperties2KHR& available_properties2, 56 const std::vector<std::string>& available_extensions); 57 58 /// Returns true if |format| and the |buffer|s buffer type combination is 59 /// supported by the physical device. 60 bool IsFormatSupportedByPhysicalDevice(const Format& format, BufferType type); 61 GetVkDevice()62 VkDevice GetVkDevice() const { return device_; } GetVkQueue()63 VkQueue GetVkQueue() const { return queue_; } 64 VkFormat GetVkFormat(const Format& format) const; 65 GetQueueFamilyIndex()66 uint32_t GetQueueFamilyIndex() const { return queue_family_index_; } 67 uint32_t GetMaxPushConstants() const; 68 69 /// Returns true if the given |descriptor_set| is within the bounds of 70 /// this device. 71 bool IsDescriptorSetInBounds(uint32_t descriptor_set) const; 72 73 /// Returns true if the memory at |memory_type_index| has |flags| set. 74 virtual bool HasMemoryFlags(uint32_t memory_type_index, 75 const VkMemoryPropertyFlags flags) const; 76 /// Returns true if the memory at |memory_type_index| is host accessible. 77 bool IsMemoryHostAccessible(uint32_t memory_type_index) const; 78 /// Returns true if the memory at |memory_type_index| is host coherent. 79 bool IsMemoryHostCoherent(uint32_t memory_type_index) const; 80 81 /// Returns the pointers to the Vulkan API methods. GetPtrs()82 virtual const VulkanPtrs* GetPtrs() const { return &ptrs_; } 83 84 /// Returns true if the required subgroup size is supported for given stage 85 bool IsRequiredSubgroupSizeSupported( 86 const ShaderType type, 87 const uint32_t required_subgroup_size) const; 88 /// Returns the minimum required subgroup size or 0 if subgroup size control 89 /// is not supported. 90 uint32_t GetMinSubgroupSize() const; 91 /// Returns the maximum required subgroup size or 0 if subgroup size control 92 /// is not supported. 93 uint32_t GetMaxSubgroupSize() const; 94 /// Returns ray tracing shader group handle size. 95 uint32_t GetRayTracingShaderGroupHandleSize() const; 96 97 // Returns true if we have support for timestamps. 98 bool IsTimestampComputeAndGraphicsSupported() const; 99 100 // Returns a float used to convert between timestamps and actual elapsed time. 101 float GetTimestampPeriod() const; 102 103 // Each timed execution reports timing to the device and on to the delegate. 104 void ReportExecutionTiming(double time_in_ns); 105 106 private: 107 Result LoadVulkanPointers(PFN_vkGetInstanceProcAddr, Delegate* delegate); 108 bool SupportsApiVersion(uint32_t major, uint32_t minor, uint32_t patch); 109 110 VkInstance instance_ = VK_NULL_HANDLE; 111 VkPhysicalDevice physical_device_ = VK_NULL_HANDLE; 112 VkPhysicalDeviceProperties physical_device_properties_; 113 VkPhysicalDeviceMemoryProperties physical_memory_properties_; 114 VkPhysicalDeviceSubgroupSizeControlPropertiesEXT 115 subgroup_size_control_properties_; 116 VkDevice device_ = VK_NULL_HANDLE; 117 VkQueue queue_ = VK_NULL_HANDLE; 118 uint32_t queue_family_index_ = 0; 119 uint32_t shader_group_handle_size_ = 0; 120 121 VulkanPtrs ptrs_; 122 123 Delegate* delegate_ = nullptr; 124 }; 125 126 } // namespace vulkan 127 } // namespace amber 128 129 #endif // SRC_VULKAN_DEVICE_H_ 130