debugging swapchain create with hardcoded values seems to work?
This commit is contained in:
@@ -97,6 +97,11 @@ pub fn build(b: *std.Build) void {
|
|||||||
.needed = true,
|
.needed = true,
|
||||||
.preferred_link_mode = .dynamic,
|
.preferred_link_mode = .dynamic,
|
||||||
});
|
});
|
||||||
|
inspect.linkSystemLibrary2("glfw3", .{
|
||||||
|
.needed = true,
|
||||||
|
.preferred_link_mode = .static,
|
||||||
|
.use_pkg_config = .force,
|
||||||
|
});
|
||||||
exe_unit_tests.linkLibC();
|
exe_unit_tests.linkLibC();
|
||||||
inspect.root_module.addImport("vk", vkmod);
|
inspect.root_module.addImport("vk", vkmod);
|
||||||
inspect.linkLibC();
|
inspect.linkLibC();
|
||||||
|
@@ -85,15 +85,6 @@ pub const Queue = struct {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
fn createSurface(instance: vk.Instance, window: *c.GLFWwindow) !vk.SurfaceKHR {
|
|
||||||
var surface: vk.SurfaceKHR = undefined;
|
|
||||||
if (c.glfwCreateWindowSurface(instance, window, null, &surface) != .success) {
|
|
||||||
return error.SurfaceInitFailed;
|
|
||||||
}
|
|
||||||
|
|
||||||
return surface;
|
|
||||||
}
|
|
||||||
|
|
||||||
fn initializeCandidate(vki: InstanceDispatch, candidate: DeviceCandidate) !vk.Device {
|
fn initializeCandidate(vki: InstanceDispatch, candidate: DeviceCandidate) !vk.Device {
|
||||||
const priority = [_]f32{1};
|
const priority = [_]f32{1};
|
||||||
const qci = [_]vk.DeviceQueueCreateInfo{
|
const qci = [_]vk.DeviceQueueCreateInfo{
|
||||||
@@ -164,6 +155,8 @@ fn checkSuitable(
|
|||||||
) !?DeviceCandidate {
|
) !?DeviceCandidate {
|
||||||
const props = vki.getPhysicalDeviceProperties(pdev);
|
const props = vki.getPhysicalDeviceProperties(pdev);
|
||||||
|
|
||||||
|
if (props.device_type != .discrete_gpu) return null;
|
||||||
|
|
||||||
if (!try checkExtensionSupport(vki, pdev, allocator)) {
|
if (!try checkExtensionSupport(vki, pdev, allocator)) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
@@ -1,6 +1,11 @@
|
|||||||
const std = @import("std");
|
const std = @import("std");
|
||||||
const vk = @import("vk");
|
const vk = @import("vk");
|
||||||
|
|
||||||
|
const c = @cImport({
|
||||||
|
@cDefine("GLFW_INCLUDE_NONE", {});
|
||||||
|
@cInclude("GLFW/glfw3.h");
|
||||||
|
});
|
||||||
|
|
||||||
const BaseWrapper = vk.BaseWrapper(.{
|
const BaseWrapper = vk.BaseWrapper(.{
|
||||||
.getInstanceProcAddr = true,
|
.getInstanceProcAddr = true,
|
||||||
.createInstance = true,
|
.createInstance = true,
|
||||||
@@ -11,17 +16,44 @@ const InstanceWrapper = vk.InstanceWrapper(.{
|
|||||||
.enumeratePhysicalDevices = true,
|
.enumeratePhysicalDevices = true,
|
||||||
.getPhysicalDeviceProperties = true,
|
.getPhysicalDeviceProperties = true,
|
||||||
.getPhysicalDeviceQueueFamilyProperties = true,
|
.getPhysicalDeviceQueueFamilyProperties = true,
|
||||||
|
.getPhysicalDeviceSurfaceFormatsKHR = true,
|
||||||
|
.getPhysicalDeviceSurfacePresentModesKHR = true,
|
||||||
|
.getPhysicalDeviceSurfaceSupportKHR = true,
|
||||||
|
.getPhysicalDeviceSurfaceCapabilitiesKHR = true,
|
||||||
|
.destroySurfaceKHR = true,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
extern fn glfwGetRequiredInstanceExtensions(count: *u32) [*]const [*:0]const u8;
|
||||||
|
|
||||||
|
extern fn glfwCreateWindowSurface(
|
||||||
|
instance: vk.Instance,
|
||||||
|
window: *c.GLFWwindow,
|
||||||
|
allocation_callbacks: ?*const vk.AllocationCallbacks,
|
||||||
|
surface: *vk.SurfaceKHR,
|
||||||
|
) vk.Result;
|
||||||
|
|
||||||
extern fn vkGetInstanceProcAddr(instance: vk.Instance, procname: [*:0]const u8) vk.PfnVoidFunction;
|
extern fn vkGetInstanceProcAddr(instance: vk.Instance, procname: [*:0]const u8) vk.PfnVoidFunction;
|
||||||
extern fn vkGetDeviceProcAddr(device: vk.Device, procname: [*:0]const u8) vk.PfnVoidFunction;
|
extern fn vkGetDeviceProcAddr(device: vk.Device, procname: [*:0]const u8) vk.PfnVoidFunction;
|
||||||
|
|
||||||
pub fn main() !void {
|
pub fn main() !void {
|
||||||
|
if (c.glfwInit() == c.GLFW_FALSE) return error.glfwInitFailed;
|
||||||
|
defer c.glfwTerminate();
|
||||||
|
|
||||||
|
c.glfwWindowHint(c.GLFW_CLIENT_API, c.GLFW_NO_API);
|
||||||
|
c.glfwWindowHintString(c.GLFW_X11_CLASS_NAME, "floating_window");
|
||||||
|
c.glfwWindowHintString(c.GLFW_X11_INSTANCE_NAME, "floating_window");
|
||||||
|
const window = c.glfwCreateWindow(400, 300, "vkinspect", null, null) orelse
|
||||||
|
return error.glfwWindowCreateFailed;
|
||||||
|
defer c.glfwDestroyWindow(window);
|
||||||
|
|
||||||
var gpa = std.heap.GeneralPurposeAllocator(.{}){};
|
var gpa = std.heap.GeneralPurposeAllocator(.{}){};
|
||||||
const ally = gpa.allocator();
|
const ally = gpa.allocator();
|
||||||
|
|
||||||
const vkb = try BaseWrapper.load(vkGetInstanceProcAddr);
|
const vkb = try BaseWrapper.load(vkGetInstanceProcAddr);
|
||||||
|
|
||||||
|
var ext_count: u32 = undefined;
|
||||||
|
const exts = glfwGetRequiredInstanceExtensions(&ext_count);
|
||||||
|
|
||||||
const instance = try vkb.createInstance(&.{
|
const instance = try vkb.createInstance(&.{
|
||||||
.p_application_info = &.{
|
.p_application_info = &.{
|
||||||
.p_application_name = "vkinspect",
|
.p_application_name = "vkinspect",
|
||||||
@@ -30,12 +62,20 @@ pub fn main() !void {
|
|||||||
.engine_version = 0,
|
.engine_version = 0,
|
||||||
.api_version = vk.API_VERSION_1_3,
|
.api_version = vk.API_VERSION_1_3,
|
||||||
},
|
},
|
||||||
.enabled_extension_count = 0,
|
.enabled_extension_count = ext_count,
|
||||||
|
.pp_enabled_extension_names = exts,
|
||||||
.enabled_layer_count = 0,
|
.enabled_layer_count = 0,
|
||||||
}, null);
|
}, null);
|
||||||
const vki = try InstanceWrapper.load(instance, vkGetInstanceProcAddr);
|
const vki = try InstanceWrapper.load(instance, vkGetInstanceProcAddr);
|
||||||
defer vki.destroyInstance(instance, null);
|
defer vki.destroyInstance(instance, null);
|
||||||
|
|
||||||
|
var surface: vk.SurfaceKHR = undefined;
|
||||||
|
switch (glfwCreateWindowSurface(instance, window, null, &surface)) {
|
||||||
|
.success => {},
|
||||||
|
else => return error.Unknown,
|
||||||
|
}
|
||||||
|
defer vki.destroySurfaceKHR(instance, surface, null);
|
||||||
|
|
||||||
var pdev_count: u32 = undefined;
|
var pdev_count: u32 = undefined;
|
||||||
_ = try vki.enumeratePhysicalDevices(instance, &pdev_count, null);
|
_ = try vki.enumeratePhysicalDevices(instance, &pdev_count, null);
|
||||||
const pdevs = try ally.alloc(vk.PhysicalDevice, pdev_count);
|
const pdevs = try ally.alloc(vk.PhysicalDevice, pdev_count);
|
||||||
@@ -46,7 +86,12 @@ pub fn main() !void {
|
|||||||
for (pdevs) |pdev| {
|
for (pdevs) |pdev| {
|
||||||
const props = vki.getPhysicalDeviceProperties(pdev);
|
const props = vki.getPhysicalDeviceProperties(pdev);
|
||||||
const name = std.mem.sliceTo(&props.device_name, 0);
|
const name = std.mem.sliceTo(&props.device_name, 0);
|
||||||
std.debug.print("- {s}\n", .{name});
|
std.debug.print("=" ** 30 ++ "\n", .{});
|
||||||
|
std.debug.print("= {s}\n", .{name});
|
||||||
|
std.debug.print("=" ** 30 ++ "\n", .{});
|
||||||
|
|
||||||
|
std.debug.print("type: {any}\n", .{props.device_type});
|
||||||
|
// props.device_type
|
||||||
|
|
||||||
var family_count: u32 = undefined;
|
var family_count: u32 = undefined;
|
||||||
vki.getPhysicalDeviceQueueFamilyProperties(pdev, &family_count, null);
|
vki.getPhysicalDeviceQueueFamilyProperties(pdev, &family_count, null);
|
||||||
@@ -55,9 +100,45 @@ pub fn main() !void {
|
|||||||
vki.getPhysicalDeviceQueueFamilyProperties(pdev, &family_count, families.ptr);
|
vki.getPhysicalDeviceQueueFamilyProperties(pdev, &family_count, families.ptr);
|
||||||
|
|
||||||
std.debug.print(" {d} queue families:\n", .{family_count});
|
std.debug.print(" {d} queue families:\n", .{family_count});
|
||||||
for (families) |family| {
|
for (families, 0..) |family, idx| {
|
||||||
|
const support = try vki.getPhysicalDeviceSurfaceSupportKHR(pdev, @intCast(idx), surface);
|
||||||
std.debug.print(" - {any}\n", .{family.queue_flags});
|
std.debug.print(" - {any}\n", .{family.queue_flags});
|
||||||
std.debug.print(" (max {d})\n", .{family.queue_count});
|
std.debug.print(" (max {d}, surface {any})\n", .{
|
||||||
}
|
family.queue_count,
|
||||||
|
support != 0,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
var format_count: u32 = undefined;
|
||||||
|
_ = try vki.getPhysicalDeviceSurfaceFormatsKHR(pdev, surface, &format_count, null);
|
||||||
|
const formats = try ally.alloc(vk.SurfaceFormatKHR, format_count);
|
||||||
|
defer ally.free(formats);
|
||||||
|
_ = try vki.getPhysicalDeviceSurfaceFormatsKHR(pdev, surface, &format_count, formats.ptr);
|
||||||
|
|
||||||
|
var mode_count: u32 = undefined;
|
||||||
|
_ = try vki.getPhysicalDeviceSurfacePresentModesKHR(pdev, surface, &mode_count, null);
|
||||||
|
const modes = try ally.alloc(vk.PresentModeKHR, mode_count);
|
||||||
|
defer ally.free(modes);
|
||||||
|
_ = try vki.getPhysicalDeviceSurfacePresentModesKHR(pdev, surface, &mode_count, modes.ptr);
|
||||||
|
|
||||||
|
std.debug.print(" {d} formats\n", .{format_count});
|
||||||
|
for (formats) |format| {
|
||||||
|
std.debug.print(" - {any}\n", .{format});
|
||||||
|
}
|
||||||
|
std.debug.print(" {d} present modes\n", .{mode_count});
|
||||||
|
for (modes) |mode| {
|
||||||
|
std.debug.print(" - {any}\n", .{mode});
|
||||||
|
}
|
||||||
|
|
||||||
|
const caps = try vki.getPhysicalDeviceSurfaceCapabilitiesKHR(pdev, surface);
|
||||||
|
std.debug.print(" surface capabilities:\n", .{});
|
||||||
|
std.debug.print(" {any}\n", .{caps.current_extent});
|
||||||
|
std.debug.print(" current: {any}\n", .{caps.current_transform});
|
||||||
|
std.debug.print(" supported: {any}\n", .{caps.supported_transforms});
|
||||||
|
std.debug.print(" {any}\n", .{caps.supported_usage_flags});
|
||||||
|
std.debug.print(" {} - {} images\n", .{ caps.min_image_count, caps.max_image_count });
|
||||||
|
std.debug.print(" {} - {} extent\n", .{ caps.min_image_extent, caps.max_image_extent });
|
||||||
|
std.debug.print(" 1 - {} arrays\n", .{caps.max_image_array_layers});
|
||||||
|
std.debug.print(" {}\n", .{caps.supported_composite_alpha});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
375
src/main.zig
375
src/main.zig
@@ -100,40 +100,51 @@ fn create_window(extent: vk.Extent2D, title: [*:0]const u8) !*c.GLFWwindow {
|
|||||||
) orelse error.WindowInitFailed;
|
) orelse error.WindowInitFailed;
|
||||||
}
|
}
|
||||||
|
|
||||||
const DevicePair = struct {
|
const DevicePair = std.meta.Tuple(&.{ vk.PhysicalDevice, vk.Device, gfx.DeviceDispatch, vk.Queue });
|
||||||
pdev: vk.PhysicalDevice,
|
|
||||||
dev: vk.Device,
|
|
||||||
graphics: vk.Queue,
|
|
||||||
present: vk.Queue,
|
|
||||||
present_sharing_mode: vk.SharingMode,
|
|
||||||
};
|
|
||||||
|
|
||||||
fn create_device(ally: std.mem.Allocator, instance: vk.Instance, vki: gfx.InstanceDispatch, surface: vk.SurfaceKHR) !DevicePair {
|
/// note: destroy with vkd.destroyDevice(dev, null)
|
||||||
const required_device_extensions = [_][*:0]const u8{
|
fn create_device(
|
||||||
|
ally: std.mem.Allocator,
|
||||||
|
instance: vk.Instance,
|
||||||
|
surface: vk.SurfaceKHR,
|
||||||
|
vki: gfx.InstanceDispatch,
|
||||||
|
) !DevicePair {
|
||||||
|
const required_device_extensions: []const [*:0]const u8 = &.{
|
||||||
vk.extension_info.khr_swapchain.name,
|
vk.extension_info.khr_swapchain.name,
|
||||||
vk.extension_info.khr_dynamic_rendering.name,
|
vk.extension_info.khr_dynamic_rendering.name,
|
||||||
};
|
};
|
||||||
|
|
||||||
var pdev_count: u32 = undefined;
|
var pdev_count: u32 = undefined;
|
||||||
|
|
||||||
_ = try vki.enumeratePhysicalDevices(instance, &pdev_count, null);
|
_ = try vki.enumeratePhysicalDevices(instance, &pdev_count, null);
|
||||||
const pdevs = try ally.alloc(vk.PhysicalDevice, pdev_count);
|
const pdevs = try ally.alloc(vk.PhysicalDevice, pdev_count);
|
||||||
defer ally.free(pdevs);
|
defer ally.free(pdevs);
|
||||||
_ = try vki.enumeratePhysicalDevices(instance, &pdev_count, pdevs);
|
_ = try vki.enumeratePhysicalDevices(instance, &pdev_count, pdevs.ptr);
|
||||||
|
|
||||||
pdev_search: for (pdevs[0..pdev_count]) |pdev| {
|
pdev_search: for (pdevs) |pdev| {
|
||||||
// const props = vki.getPhysicalDeviceProperties(pdev);
|
const props = vki.getPhysicalDeviceProperties(pdev);
|
||||||
// const feats = vki.getPhysicalDeviceFeatures(pdev);
|
if (props.device_type != .discrete_gpu) continue :pdev_search;
|
||||||
|
|
||||||
var ext_prop_count: u32 = undefined;
|
var format_count: u32 = undefined;
|
||||||
_ = try vki.enumerateDeviceExtensionProperties(pdev, null, &ext_prop_count, null);
|
_ = try vki.getPhysicalDeviceSurfaceFormatsKHR(pdev, surface, &format_count, null);
|
||||||
const ext_props = try ally.alloc(vk.ExtensionProperties, ext_prop_count);
|
if (format_count == 0) continue :pdev_search;
|
||||||
defer ally.free(ext_props);
|
|
||||||
_ = try vki.enumerateDeviceExtensionProperties(pdev, null, &ext_prop_count, ext_props);
|
|
||||||
|
|
||||||
for (required_device_extensions) |required| {
|
var mode_count: u32 = undefined;
|
||||||
for (ext_props) |prop| {
|
_ = try vki.getPhysicalDeviceSurfacePresentModesKHR(pdev, surface, &mode_count, null);
|
||||||
if (std.mem.eql(u8, std.mem.span(required), std.mem.sliceTo(&prop.extension_name, 0))) {
|
if (mode_count == 0) continue :pdev_search;
|
||||||
|
|
||||||
|
var ext_count: u32 = undefined;
|
||||||
|
_ = try vki.enumerateDeviceExtensionProperties(pdev, null, &ext_count, null);
|
||||||
|
const exts = try ally.alloc(vk.ExtensionProperties, ext_count);
|
||||||
|
defer ally.free(exts);
|
||||||
|
_ = try vki.enumerateDeviceExtensionProperties(pdev, null, &ext_count, exts.ptr);
|
||||||
|
|
||||||
|
for (required_device_extensions) |name| {
|
||||||
|
for (exts) |ext| {
|
||||||
|
if (std.mem.eql(
|
||||||
|
u8,
|
||||||
|
std.mem.span(name),
|
||||||
|
std.mem.sliceTo(&ext.extension_name, 0),
|
||||||
|
)) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@@ -141,80 +152,61 @@ fn create_device(ally: std.mem.Allocator, instance: vk.Instance, vki: gfx.Instan
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var format_count: u32 = undefined;
|
var family_count: u32 = undefined;
|
||||||
_ = try vki.getPhysicalDeviceSurfaceFormatsKHR(pdev, surface, &format_count, null);
|
vki.getPhysicalDeviceQueueFamilyProperties(pdev, &family_count, null);
|
||||||
if (format_count == 0) continue :pdev_search;
|
const families = try ally.alloc(vk.QueueFamilyProperties, family_count);
|
||||||
|
defer ally.free(families);
|
||||||
|
vki.getPhysicalDeviceQueueFamilyProperties(pdev, &family_count, families.ptr);
|
||||||
|
|
||||||
var present_mode_count: u32 = undefined;
|
// just find one family that does graphics and present, so we can use exclusive sharing
|
||||||
_ = try vki.getPhysicalDeviceSurfacePresentModesKHR(pdev, surface, &present_mode_count, null);
|
// on the swapchain. apparently most hardware supports this. logic for queue allocation
|
||||||
if (present_mode_count == 0) continue :pdev_search;
|
// and swapchain creation is so much simpler this way. swapchain creation needs to know
|
||||||
|
// the list of queue family indices which will have access to the images, and there's a
|
||||||
|
// performance penalty to allow concurrent access to multiple queue families.
|
||||||
|
//
|
||||||
|
// multiple _queues_ may have exclusive access, but only if they're in the smae family.
|
||||||
|
|
||||||
var fam_prop_count: u32 = undefined;
|
const graphics_family: u32 = for (families, 0..) |family, idx| {
|
||||||
vki.getPhysicalDeviceQueueFamilyProperties(pdev, &fam_prop_count, null);
|
const graphics = family.queue_flags.graphics_bit;
|
||||||
const fam_props = try ally.alloc(vk.QueueFamilyProperties, fam_prop_count);
|
const present = try vki.getPhysicalDeviceSurfaceSupportKHR(pdev, @intCast(idx), surface) == vk.TRUE;
|
||||||
defer ally.free(fam_props);
|
if (graphics and present) {
|
||||||
vki.getPhysicalDeviceQueueFamilyProperties(pdev, &fam_prop_count, fam_props);
|
break @intCast(idx);
|
||||||
|
|
||||||
var graphics_families = std.ArrayList(u32).init(ally);
|
|
||||||
var present_families = std.ArrayList(u32).init(ally);
|
|
||||||
|
|
||||||
for (fam_props, 0..) |fam, idx| {
|
|
||||||
if (fam.queue_flags.graphics_bit) {
|
|
||||||
graphics_families.append(idx);
|
|
||||||
}
|
|
||||||
if (try vki.getPhysicalDeviceSurfaceSupportKHR(pdev, idx, surface)) {
|
|
||||||
present_families.append(idx);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
continue :pdev_search;
|
||||||
|
};
|
||||||
|
|
||||||
// only choose the same family if we really have to.
|
std.log.debug("selecting device {s}", .{std.mem.sliceTo(&props.device_name, 0)});
|
||||||
|
|
||||||
// at this point, we know this pdev can support _a_ swap chain and has required extensions. try to make a
|
const qci: []const vk.DeviceQueueCreateInfo = &.{
|
||||||
// logical device and queues out of it.
|
vk.DeviceQueueCreateInfo{
|
||||||
|
.queue_family_index = graphics_family,
|
||||||
|
.queue_count = 1,
|
||||||
|
.p_queue_priorities = &[_]f32{1.0},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
|
||||||
|
const dev = try vki.createDevice(pdev, &.{
|
||||||
|
.queue_create_info_count = @intCast(qci.len),
|
||||||
|
.p_queue_create_infos = qci.ptr,
|
||||||
|
.enabled_extension_count = @intCast(required_device_extensions.len),
|
||||||
|
.pp_enabled_extension_names = required_device_extensions.ptr,
|
||||||
|
}, null);
|
||||||
|
const vkd = try gfx.DeviceDispatch.load(dev, vki.dispatch.vkGetDeviceProcAddr);
|
||||||
|
errdefer vkd.destroyDevice(dev, null);
|
||||||
|
|
||||||
|
const queue = vkd.getDeviceQueue(dev, graphics_family, 0);
|
||||||
|
|
||||||
|
return .{ pdev, dev, vkd, queue };
|
||||||
}
|
}
|
||||||
|
|
||||||
return error.NoSuitableDevice;
|
return error.NoSuitableDevice;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn includes(comptime T: type, us: []const T, vs: []const T) bool {
|
|
||||||
var vidx: usize = 0;
|
|
||||||
var uidx: usize = 0;
|
|
||||||
while (uidx < us.len) {
|
|
||||||
while (vidx < vs.len) : (vidx += 1) {
|
|
||||||
if (us[uidx] == vs[vidx]) break;
|
|
||||||
vidx += 1;
|
|
||||||
} else {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
uidx += 1;
|
|
||||||
vidx += 1;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
test "includes" {
|
|
||||||
const u = &.{ 0, 1, 7 };
|
|
||||||
const v = &.{11};
|
|
||||||
const w = &.{};
|
|
||||||
const x = &.{ 0, 1, 3, 5, 7, 9, 11 };
|
|
||||||
const y = &.{2};
|
|
||||||
const z = &.{ 0, 1, 3, 5, 7, 9, 11, 12 };
|
|
||||||
|
|
||||||
const full = &.{ 0, 1, 3, 5, 7, 9, 11 };
|
|
||||||
|
|
||||||
try std.testing.expectEqual(true, includes(usize, u, full));
|
|
||||||
try std.testing.expectEqual(true, includes(usize, v, full));
|
|
||||||
try std.testing.expectEqual(true, includes(usize, w, full));
|
|
||||||
try std.testing.expectEqual(true, includes(usize, x, full));
|
|
||||||
try std.testing.expectEqual(false, includes(usize, y, full));
|
|
||||||
try std.testing.expectEqual(false, includes(usize, z, full));
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn main() !void {
|
pub fn main() !void {
|
||||||
var gpa = std.heap.GeneralPurposeAllocator(.{}){};
|
var gpa = std.heap.GeneralPurposeAllocator(.{}){};
|
||||||
defer _ = gpa.deinit();
|
defer _ = gpa.deinit();
|
||||||
const allocator = gpa.allocator();
|
const ally = gpa.allocator();
|
||||||
|
|
||||||
if (c.glfwInit() != c.GLFW_TRUE) return error.GlfwInitFailed;
|
if (c.glfwInit() != c.GLFW_TRUE) return error.GlfwInitFailed;
|
||||||
defer c.glfwTerminate();
|
defer c.glfwTerminate();
|
||||||
@@ -237,108 +229,139 @@ pub fn main() !void {
|
|||||||
const surface = try create_surface(instance, window);
|
const surface = try create_surface(instance, window);
|
||||||
defer vki.destroySurfaceKHR(instance, surface, null);
|
defer vki.destroySurfaceKHR(instance, surface, null);
|
||||||
|
|
||||||
const gc = try GraphicsContext.init(allocator, instance, surface, vki);
|
const pdev: vk.PhysicalDevice, const dev: vk.Device, const vkd: gfx.DeviceDispatch, const queue: vk.Queue =
|
||||||
defer gc.deinit();
|
try create_device(ally, instance, surface, vki);
|
||||||
|
defer vkd.destroyDevice(dev, null);
|
||||||
|
|
||||||
std.log.debug("Using device: {s}", .{gc.deviceName()});
|
var swapchain: vk.SwapchainKHR = .null_handle;
|
||||||
|
defer vkd.destroySwapchainKHR(dev, swapchain, null);
|
||||||
|
|
||||||
var swapchain = try Swapchain.init(&gc, allocator, extent);
|
swapchain = try vkd.createSwapchainKHR(dev, &.{
|
||||||
defer swapchain.deinit();
|
.surface = surface,
|
||||||
|
.min_image_count = 3, // todo compute
|
||||||
const pipeline_layout = try gc.vkd.createPipelineLayout(gc.dev, &.{
|
.image_format = .r8g8b8a8_sint, // todo compute
|
||||||
.flags = .{},
|
// .image_format = .r8g8b8a8_sint, // todo compute
|
||||||
.set_layout_count = 0,
|
.image_color_space = .srgb_nonlinear_khr, // todo compute
|
||||||
.p_set_layouts = undefined,
|
.image_extent = extent, // todo compute
|
||||||
.push_constant_range_count = 0,
|
.image_array_layers = 1,
|
||||||
.p_push_constant_ranges = undefined,
|
.image_usage = .{ .color_attachment_bit = true, .transfer_dst_bit = true },
|
||||||
|
.image_sharing_mode = .exclusive, // since we only choose one queue family
|
||||||
|
.pre_transform = .{ .identity_bit_khr = true }, // todo compute
|
||||||
|
.composite_alpha = .{ .opaque_bit_khr = true },
|
||||||
|
.present_mode = .mailbox_khr, // todo compute
|
||||||
|
.clipped = vk.TRUE,
|
||||||
|
.old_swapchain = swapchain,
|
||||||
}, null);
|
}, null);
|
||||||
defer gc.vkd.destroyPipelineLayout(gc.dev, pipeline_layout, null);
|
|
||||||
|
|
||||||
const pipeline = try createPipeline(&gc, pipeline_layout, swapchain);
|
_ = try vkd.queuePresentKHR(queue, &.{
|
||||||
defer gc.vkd.destroyPipeline(gc.dev, pipeline, null);
|
.wait_semaphore_count = 0,
|
||||||
|
.swapchain_count = 1,
|
||||||
|
.p_swapchains = &[_]vk.SwapchainKHR{swapchain},
|
||||||
|
.p_image_indices = &[_]u32{0},
|
||||||
|
});
|
||||||
|
|
||||||
const pool = try gc.vkd.createCommandPool(gc.dev, &.{
|
try vkd.deviceWaitIdle(dev);
|
||||||
.queue_family_index = gc.graphics_queue.family,
|
|
||||||
}, null);
|
|
||||||
defer gc.vkd.destroyCommandPool(gc.dev, pool, null);
|
|
||||||
|
|
||||||
const vertex_buffer = try gc.vkd.createBuffer(gc.dev, &.{
|
_ = pdev;
|
||||||
.size = @sizeOf(@TypeOf(vertices)),
|
extent = undefined;
|
||||||
.usage = .{ .transfer_dst_bit = true, .vertex_buffer_bit = true },
|
|
||||||
.sharing_mode = .exclusive,
|
|
||||||
}, null);
|
|
||||||
defer gc.vkd.destroyBuffer(gc.dev, vertex_buffer, null);
|
|
||||||
const vertex_mem_reqs = gc.vkd.getBufferMemoryRequirements(gc.dev, vertex_buffer);
|
|
||||||
const vertex_memory = try gc.allocate(vertex_mem_reqs, .{ .device_local_bit = true });
|
|
||||||
defer gc.vkd.freeMemory(gc.dev, vertex_memory, null);
|
|
||||||
try gc.vkd.bindBufferMemory(gc.dev, vertex_buffer, vertex_memory, 0);
|
|
||||||
|
|
||||||
try uploadData(Vertex, &gc, pool, vertex_buffer, &vertices);
|
// var swapchain = try Swapchain.init(&gc, ally, extent);
|
||||||
|
// defer swapchain.deinit();
|
||||||
|
|
||||||
const index_buffer = try gc.vkd.createBuffer(gc.dev, &.{
|
// const pipeline_layout = try gc.vkd.createPipelineLayout(gc.dev, &.{
|
||||||
.size = @sizeOf(@TypeOf(indices)),
|
// .flags = .{},
|
||||||
.usage = .{ .transfer_dst_bit = true, .index_buffer_bit = true },
|
// .set_layout_count = 0,
|
||||||
.sharing_mode = .exclusive,
|
// .p_set_layouts = undefined,
|
||||||
}, null);
|
// .push_constant_range_count = 0,
|
||||||
defer gc.vkd.destroyBuffer(gc.dev, index_buffer, null);
|
// .p_push_constant_ranges = undefined,
|
||||||
const index_mem_reqs = gc.vkd.getBufferMemoryRequirements(gc.dev, index_buffer);
|
// }, null);
|
||||||
const index_memory = try gc.allocate(index_mem_reqs, .{ .device_local_bit = true });
|
// defer gc.vkd.destroyPipelineLayout(gc.dev, pipeline_layout, null);
|
||||||
defer gc.vkd.freeMemory(gc.dev, index_memory, null);
|
//
|
||||||
try gc.vkd.bindBufferMemory(gc.dev, index_buffer, index_memory, 0);
|
// const pipeline = try createPipeline(&gc, pipeline_layout, swapchain);
|
||||||
|
// defer gc.vkd.destroyPipeline(gc.dev, pipeline, null);
|
||||||
try uploadData(Index, &gc, pool, index_buffer, &indices);
|
//
|
||||||
|
// const pool = try gc.vkd.createCommandPool(gc.dev, &.{
|
||||||
var cmdbufs = try createCommandBuffers(
|
// .queue_family_index = gc.graphics_queue.family,
|
||||||
&gc,
|
// }, null);
|
||||||
pool,
|
// defer gc.vkd.destroyCommandPool(gc.dev, pool, null);
|
||||||
allocator,
|
//
|
||||||
vertex_buffer,
|
// const vertex_buffer = try gc.vkd.createBuffer(gc.dev, &.{
|
||||||
index_buffer,
|
// .size = @sizeOf(@TypeOf(vertices)),
|
||||||
pipeline,
|
// .usage = .{ .transfer_dst_bit = true, .vertex_buffer_bit = true },
|
||||||
swapchain,
|
// .sharing_mode = .exclusive,
|
||||||
);
|
// }, null);
|
||||||
defer destroyCommandBuffers(&gc, pool, allocator, cmdbufs);
|
// defer gc.vkd.destroyBuffer(gc.dev, vertex_buffer, null);
|
||||||
|
// const vertex_mem_reqs = gc.vkd.getBufferMemoryRequirements(gc.dev, vertex_buffer);
|
||||||
while (c.glfwWindowShouldClose(window) == c.GLFW_FALSE) {
|
// const vertex_memory = try gc.allocate(vertex_mem_reqs, .{ .device_local_bit = true });
|
||||||
var w: c_int = undefined;
|
// defer gc.vkd.freeMemory(gc.dev, vertex_memory, null);
|
||||||
var h: c_int = undefined;
|
// try gc.vkd.bindBufferMemory(gc.dev, vertex_buffer, vertex_memory, 0);
|
||||||
c.glfwGetFramebufferSize(window, &w, &h);
|
//
|
||||||
|
// try uploadData(Vertex, &gc, pool, vertex_buffer, &vertices);
|
||||||
// Don't present or resize swapchain while the window is minimized
|
//
|
||||||
if (w == 0 or h == 0) {
|
// const index_buffer = try gc.vkd.createBuffer(gc.dev, &.{
|
||||||
c.glfwPollEvents();
|
// .size = @sizeOf(@TypeOf(indices)),
|
||||||
continue;
|
// .usage = .{ .transfer_dst_bit = true, .index_buffer_bit = true },
|
||||||
}
|
// .sharing_mode = .exclusive,
|
||||||
|
// }, null);
|
||||||
const cmdbuf = cmdbufs[swapchain.image_index];
|
// defer gc.vkd.destroyBuffer(gc.dev, index_buffer, null);
|
||||||
|
// const index_mem_reqs = gc.vkd.getBufferMemoryRequirements(gc.dev, index_buffer);
|
||||||
const state = swapchain.present(cmdbuf) catch |err| switch (err) {
|
// const index_memory = try gc.allocate(index_mem_reqs, .{ .device_local_bit = true });
|
||||||
error.OutOfDateKHR => Swapchain.PresentState.suboptimal,
|
// defer gc.vkd.freeMemory(gc.dev, index_memory, null);
|
||||||
else => |narrow| return narrow,
|
// try gc.vkd.bindBufferMemory(gc.dev, index_buffer, index_memory, 0);
|
||||||
};
|
//
|
||||||
|
// try uploadData(Index, &gc, pool, index_buffer, &indices);
|
||||||
if (state == .suboptimal or extent.width != @as(u32, @intCast(w)) or extent.height != @as(u32, @intCast(h))) {
|
//
|
||||||
extent.width = @intCast(w);
|
// var cmdbufs = try createCommandBuffers(
|
||||||
extent.height = @intCast(h);
|
// &gc,
|
||||||
try swapchain.recreate(extent);
|
// pool,
|
||||||
|
// ally,
|
||||||
destroyCommandBuffers(&gc, pool, allocator, cmdbufs);
|
// vertex_buffer,
|
||||||
cmdbufs = try createCommandBuffers(
|
// index_buffer,
|
||||||
&gc,
|
// pipeline,
|
||||||
pool,
|
// swapchain,
|
||||||
allocator,
|
// );
|
||||||
vertex_buffer,
|
// defer destroyCommandBuffers(&gc, pool, ally, cmdbufs);
|
||||||
index_buffer,
|
//
|
||||||
pipeline,
|
// while (c.glfwWindowShouldClose(window) == c.GLFW_FALSE) {
|
||||||
swapchain,
|
// var w: c_int = undefined;
|
||||||
);
|
// var h: c_int = undefined;
|
||||||
}
|
// c.glfwGetFramebufferSize(window, &w, &h);
|
||||||
|
//
|
||||||
c.glfwPollEvents();
|
// // Don't present or resize swapchain while the window is minimized
|
||||||
}
|
// if (w == 0 or h == 0) {
|
||||||
|
// c.glfwPollEvents();
|
||||||
try swapchain.waitForAllFences();
|
// continue;
|
||||||
try gc.vkd.deviceWaitIdle(gc.dev);
|
// }
|
||||||
|
//
|
||||||
|
// const cmdbuf = cmdbufs[swapchain.image_index];
|
||||||
|
//
|
||||||
|
// const state = swapchain.present(cmdbuf) catch |err| switch (err) {
|
||||||
|
// error.OutOfDateKHR => Swapchain.PresentState.suboptimal,
|
||||||
|
// else => |narrow| return narrow,
|
||||||
|
// };
|
||||||
|
//
|
||||||
|
// if (state == .suboptimal or extent.width != @as(u32, @intCast(w)) or extent.height != @as(u32, @intCast(h))) {
|
||||||
|
// extent.width = @intCast(w);
|
||||||
|
// extent.height = @intCast(h);
|
||||||
|
// try swapchain.recreate(extent);
|
||||||
|
//
|
||||||
|
// destroyCommandBuffers(&gc, pool, ally, cmdbufs);
|
||||||
|
// cmdbufs = try createCommandBuffers(
|
||||||
|
// &gc,
|
||||||
|
// pool,
|
||||||
|
// ally,
|
||||||
|
// vertex_buffer,
|
||||||
|
// index_buffer,
|
||||||
|
// pipeline,
|
||||||
|
// swapchain,
|
||||||
|
// );
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// c.glfwPollEvents();
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// try swapchain.waitForAllFences();
|
||||||
|
// try gc.vkd.deviceWaitIdle(gc.dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn uploadData(comptime T: type, gc: *const GraphicsContext, pool: vk.CommandPool, buffer: vk.Buffer, source: []const T) !void {
|
fn uploadData(comptime T: type, gc: *const GraphicsContext, pool: vk.CommandPool, buffer: vk.Buffer, source: []const T) !void {
|
||||||
|
Reference in New Issue
Block a user