diff options
Diffstat (limited to 'vulkan/Utils.cs')
| -rw-r--r-- | vulkan/Utils.cs | 63 |
1 files changed, 42 insertions, 21 deletions
diff --git a/vulkan/Utils.cs b/vulkan/Utils.cs index b91a47b..bf629ed 100644 --- a/vulkan/Utils.cs +++ b/vulkan/Utils.cs @@ -3,30 +3,51 @@ // This code is licensed under the MIT license (MIT) (http://opensource.org/licenses/MIT) using System; using System.Runtime.InteropServices; +using System.Runtime.CompilerServices; +using Vulkan; +using static Vulkan.Vk; namespace Vulkan { - internal static class LoadingUtils { - public static IntPtr GetDelegate (VkInstance inst, string name) { - byte[] n = System.Text.Encoding.UTF8.GetBytes (name + '\0'); - GCHandle hnd = GCHandle.Alloc (n, GCHandleType.Pinned); - IntPtr del = Vk.vkGetInstanceProcAddr (inst, hnd.AddrOfPinnedObject ()); - if (del == IntPtr.Zero) - System.Diagnostics.Debug.WriteLine ("instance function pointer not found for " + name); - hnd.Free (); - return del; + public static class Utils { + public static void CheckResult (VkResult result, string msg = "Call failed", + [CallerMemberName] string caller = null, + [CallerFilePath] string sourceFilePath = "", + [CallerLineNumber] int sourceLineNumber = 0) { + if (result != VkResult.Success) + throw new InvalidOperationException ($"[{sourceFilePath}:{sourceLineNumber}->{caller}]{msg}: {result}"); } - /// <summary> - /// try to get device function handle if available - /// </summary> - public static void GetDelegate (VkDevice dev, string name, ref IntPtr ptr) { - byte[] n = System.Text.Encoding.UTF8.GetBytes (name + '\0'); - GCHandle hnd = GCHandle.Alloc (n, GCHandleType.Pinned); - IntPtr del = Vk.vkGetDeviceProcAddr (dev, hnd.AddrOfPinnedObject ()); - if (del == IntPtr.Zero) - System.Diagnostics.Debug.WriteLine ("device function pointer not found for " + name); - else - ptr = del; - hnd.Free (); + public static bool TryGetPhysicalDevice (VkInstance inst, VkPhysicalDeviceType deviceType, out VkPhysicalDevice phy) { + CheckResult (vkEnumeratePhysicalDevices (inst, out uint phyCount, IntPtr.Zero)); + + VkPhysicalDevice[] phys = new VkPhysicalDevice[phyCount]; + + CheckResult (vkEnumeratePhysicalDevices (inst, out phyCount, phys.Pin())); + + for (int i = 0; i < phys.Length; i++) + { + phy = phys[i]; + vkGetPhysicalDeviceProperties (phy, out VkPhysicalDeviceProperties props); + if (props.deviceType == deviceType) + return true; + } + phy = default; + return false; + } + public static VkPhysicalDeviceToolPropertiesEXT[] GetToolProperties (VkPhysicalDevice phy) { + CheckResult (vkGetPhysicalDeviceToolPropertiesEXT (phy , out uint count, IntPtr.Zero)); + int sizeStruct = Marshal.SizeOf<VkPhysicalDeviceToolPropertiesEXT> (); + IntPtr ptrTools = Marshal.AllocHGlobal (sizeStruct * (int)count); + CheckResult (vkGetPhysicalDeviceToolPropertiesEXT (phy , out count, ptrTools)); + + VkPhysicalDeviceToolPropertiesEXT[] result = new VkPhysicalDeviceToolPropertiesEXT[count]; + IntPtr tmp = ptrTools; + for (int i = 0; i < count; i++) { + result[i] = Marshal.PtrToStructure<VkPhysicalDeviceToolPropertiesEXT> (tmp); + tmp += sizeStruct; + } + + Marshal.FreeHGlobal (ptrTools); + return result; } } } |