adding base for intel backend
This commit is contained in:
@@ -38,6 +38,13 @@ const implementations = [_]ImplementationDesc{
|
||||
.custom = customSoft,
|
||||
.options = optionsSoft,
|
||||
},
|
||||
.{
|
||||
.name = "intel",
|
||||
.root_source_file = "src/intel/lib.zig",
|
||||
.vulkan_version = .{ .major = 1, .minor = 0, .patch = 0 },
|
||||
.custom = customIntel,
|
||||
.options = optionsIntel,
|
||||
},
|
||||
};
|
||||
|
||||
const RunningMode = enum {
|
||||
@@ -270,6 +277,25 @@ fn optionsSoft(b: *std.Build, options: *Step.Options) !void {
|
||||
options.addOption(bool, "soft_approximates_rgb", approxiamte_rgb_option);
|
||||
}
|
||||
|
||||
fn customIntel(
|
||||
_: *std.Build,
|
||||
_: *Step.Compile,
|
||||
lib_mod: *std.Build.Module,
|
||||
_: *std.Build.Module,
|
||||
_: *std.Build.Module,
|
||||
base_c_mod: *std.Build.Module,
|
||||
_: std.Build.ResolvedTarget,
|
||||
_: std.builtin.OptimizeMode,
|
||||
_: bool,
|
||||
) !void {
|
||||
lib_mod.addImport("intel_c", base_c_mod);
|
||||
}
|
||||
|
||||
fn optionsIntel(b: *std.Build, options: *Step.Options) !void {
|
||||
_ = b;
|
||||
_ = options;
|
||||
}
|
||||
|
||||
fn addCTS(b: *std.Build, target: std.Build.ResolvedTarget, impl: *const ImplementationDesc, impl_lib: *Step.Compile, comptime mode: RunningMode) !*Step {
|
||||
const cts = b.dependency("cts_bin", .{});
|
||||
|
||||
|
||||
@@ -0,0 +1,44 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.BinarySemaphore;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.SemaphoreCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
.signal = signal,
|
||||
.wait = wait,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn signal(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
|
||||
pub fn wait(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
@@ -0,0 +1,40 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const lib = @import("lib.zig");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Buffer;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.BufferCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
.getMemoryRequirements = getMemoryRequirements,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn getMemoryRequirements(interface: *Interface, requirements: *vk.MemoryRequirements) void {
|
||||
_ = interface;
|
||||
_ = requirements;
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.BufferView;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.BufferViewCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,392 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.CommandBuffer;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.CommandBufferAllocateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
interface.vtable = &.{ .destroy = destroy };
|
||||
interface.dispatch_table = &.{
|
||||
.begin = begin,
|
||||
.beginQuery = beginQuery,
|
||||
.beginRenderPass = beginRenderPass,
|
||||
.bindDescriptorSets = bindDescriptorSets,
|
||||
.bindPipeline = bindPipeline,
|
||||
.bindIndexBuffer = bindIndexBuffer,
|
||||
.bindVertexBuffer = bindVertexBuffer,
|
||||
.blitImage = blitImage,
|
||||
.clearAttachment = clearAttachment,
|
||||
.clearColorImage = clearColorImage,
|
||||
.clearDepthStencilImage = clearDepthStencilImage,
|
||||
.copyBuffer = copyBuffer,
|
||||
.copyBufferToImage = copyBufferToImage,
|
||||
.copyImage = copyImage,
|
||||
.copyImageToBuffer = copyImageToBuffer,
|
||||
.copyQueryPoolResults = copyQueryPoolResults,
|
||||
.dispatch = dispatch,
|
||||
.dispatchBase = dispatchBase,
|
||||
.dispatchIndirect = dispatchIndirect,
|
||||
.draw = draw,
|
||||
.drawIndexed = drawIndexed,
|
||||
.drawIndexedIndirect = drawIndexedIndirect,
|
||||
.drawIndirect = drawIndirect,
|
||||
.end = end,
|
||||
.endQuery = endQuery,
|
||||
.endRenderPass = endRenderPass,
|
||||
.executeCommands = executeCommands,
|
||||
.fillBuffer = fillBuffer,
|
||||
.nextSubpass = nextSubpass,
|
||||
.pipelineBarrier = pipelineBarrier,
|
||||
.pushConstants = pushConstants,
|
||||
.reset = reset,
|
||||
.resetQueryPool = resetQueryPool,
|
||||
.resetEvent = resetEvent,
|
||||
.resolveImage = resolveImage,
|
||||
.setEvent = setEvent,
|
||||
.setBlendConstants = setBlendConstants,
|
||||
.setDeviceMask = setDeviceMask,
|
||||
.setScissor = setScissor,
|
||||
.setStencilCompareMask = setStencilCompareMask,
|
||||
.setStencilReference = setStencilReference,
|
||||
.setStencilWriteMask = setStencilWriteMask,
|
||||
.setViewport = setViewport,
|
||||
.updateBuffer = updateBuffer,
|
||||
.waitEvent = waitEvent,
|
||||
};
|
||||
|
||||
self.* = .{ .interface = interface };
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn execute(self: *Self) VkError!void {
|
||||
try self.interface.submit();
|
||||
self.interface.finish() catch {};
|
||||
}
|
||||
|
||||
pub fn begin(interface: *Interface, info: *const vk.CommandBufferBeginInfo) VkError!void {
|
||||
_ = interface;
|
||||
_ = info;
|
||||
}
|
||||
|
||||
pub fn end(interface: *Interface) VkError!void {
|
||||
_ = interface;
|
||||
}
|
||||
|
||||
pub fn reset(interface: *Interface, flags: vk.CommandBufferResetFlags) VkError!void {
|
||||
_ = interface;
|
||||
_ = flags;
|
||||
}
|
||||
|
||||
pub fn beginQuery(interface: *Interface, pool: *base.QueryPool, query: u32, flags: vk.QueryControlFlags) VkError!void {
|
||||
_ = interface;
|
||||
_ = flags;
|
||||
try pool.begin(query);
|
||||
}
|
||||
|
||||
pub fn endQuery(interface: *Interface, pool: *base.QueryPool, query: u32) VkError!void {
|
||||
_ = interface;
|
||||
try pool.end(query);
|
||||
}
|
||||
|
||||
pub fn resetQueryPool(interface: *Interface, pool: *base.QueryPool, first: u32, count: u32) VkError!void {
|
||||
_ = interface;
|
||||
try pool.reset(first, count);
|
||||
}
|
||||
|
||||
pub fn beginRenderPass(interface: *Interface, render_pass: *base.RenderPass, framebuffer: *base.Framebuffer, render_area: vk.Rect2D, clear_values: ?[]const vk.ClearValue) VkError!void {
|
||||
_ = interface;
|
||||
_ = render_pass;
|
||||
_ = framebuffer;
|
||||
_ = render_area;
|
||||
_ = clear_values;
|
||||
}
|
||||
|
||||
pub fn bindDescriptorSets(interface: *Interface, bind_point: vk.PipelineBindPoint, first_set: u32, sets: [base.VULKAN_MAX_DESCRIPTOR_SETS]?*base.DescriptorSet, dynamic_offsets: []const u32) VkError!void {
|
||||
_ = interface;
|
||||
_ = bind_point;
|
||||
_ = first_set;
|
||||
_ = sets;
|
||||
_ = dynamic_offsets;
|
||||
}
|
||||
|
||||
pub fn bindPipeline(interface: *Interface, bind_point: vk.PipelineBindPoint, pipeline: *base.Pipeline) VkError!void {
|
||||
_ = interface;
|
||||
_ = bind_point;
|
||||
_ = pipeline;
|
||||
}
|
||||
|
||||
pub fn bindIndexBuffer(interface: *Interface, buffer: *base.Buffer, offset: usize, index_type: vk.IndexType) VkError!void {
|
||||
_ = interface;
|
||||
_ = buffer;
|
||||
_ = offset;
|
||||
_ = index_type;
|
||||
}
|
||||
|
||||
pub fn bindVertexBuffer(interface: *Interface, index: usize, buffer: *base.Buffer, offset: usize) VkError!void {
|
||||
_ = interface;
|
||||
_ = index;
|
||||
_ = buffer;
|
||||
_ = offset;
|
||||
}
|
||||
|
||||
pub fn blitImage(interface: *Interface, src: *base.Image, src_layout: vk.ImageLayout, dst: *base.Image, dst_layout: vk.ImageLayout, regions: []const vk.ImageBlit, filter: vk.Filter) VkError!void {
|
||||
_ = interface;
|
||||
_ = src;
|
||||
_ = src_layout;
|
||||
_ = dst;
|
||||
_ = dst_layout;
|
||||
_ = regions;
|
||||
_ = filter;
|
||||
}
|
||||
|
||||
pub fn clearAttachment(interface: *Interface, attachment: vk.ClearAttachment, rect: vk.ClearRect) VkError!void {
|
||||
_ = interface;
|
||||
_ = attachment;
|
||||
_ = rect;
|
||||
}
|
||||
|
||||
pub fn clearColorImage(interface: *Interface, image: *base.Image, layout: vk.ImageLayout, color: *const vk.ClearColorValue, range: vk.ImageSubresourceRange) VkError!void {
|
||||
_ = interface;
|
||||
_ = image;
|
||||
_ = layout;
|
||||
_ = color;
|
||||
_ = range;
|
||||
}
|
||||
|
||||
pub fn clearDepthStencilImage(interface: *Interface, image: *base.Image, layout: vk.ImageLayout, value: *const vk.ClearDepthStencilValue, range: vk.ImageSubresourceRange) VkError!void {
|
||||
_ = interface;
|
||||
_ = image;
|
||||
_ = layout;
|
||||
_ = value;
|
||||
_ = range;
|
||||
}
|
||||
|
||||
pub fn copyBuffer(interface: *Interface, src: *base.Buffer, dst: *base.Buffer, regions: []const vk.BufferCopy) VkError!void {
|
||||
_ = interface;
|
||||
_ = src;
|
||||
_ = dst;
|
||||
_ = regions;
|
||||
}
|
||||
|
||||
pub fn copyBufferToImage(interface: *Interface, src: *base.Buffer, dst: *base.Image, dst_layout: vk.ImageLayout, regions: []const vk.BufferImageCopy) VkError!void {
|
||||
_ = interface;
|
||||
_ = src;
|
||||
_ = dst;
|
||||
_ = dst_layout;
|
||||
_ = regions;
|
||||
}
|
||||
|
||||
pub fn copyImage(interface: *Interface, src: *base.Image, src_layout: vk.ImageLayout, dst: *base.Image, dst_layout: vk.ImageLayout, regions: []const vk.ImageCopy) VkError!void {
|
||||
_ = interface;
|
||||
_ = src;
|
||||
_ = src_layout;
|
||||
_ = dst;
|
||||
_ = dst_layout;
|
||||
_ = regions;
|
||||
}
|
||||
|
||||
pub fn copyImageToBuffer(interface: *Interface, src: *base.Image, src_layout: vk.ImageLayout, dst: *base.Buffer, regions: []const vk.BufferImageCopy) VkError!void {
|
||||
_ = interface;
|
||||
_ = src;
|
||||
_ = src_layout;
|
||||
_ = dst;
|
||||
_ = regions;
|
||||
}
|
||||
|
||||
pub fn copyQueryPoolResults(interface: *Interface, pool: *base.QueryPool, first: u32, count: u32, dst: *base.Buffer, offset: vk.DeviceSize, stride: vk.DeviceSize, flags: vk.QueryResultFlags) VkError!void {
|
||||
_ = interface;
|
||||
_ = pool;
|
||||
_ = first;
|
||||
_ = count;
|
||||
_ = dst;
|
||||
_ = offset;
|
||||
_ = stride;
|
||||
_ = flags;
|
||||
}
|
||||
|
||||
pub fn dispatch(interface: *Interface, group_count_x: u32, group_count_y: u32, group_count_z: u32) VkError!void {
|
||||
_ = interface;
|
||||
_ = group_count_x;
|
||||
_ = group_count_y;
|
||||
_ = group_count_z;
|
||||
}
|
||||
|
||||
pub fn dispatchBase(interface: *Interface, base_group_x: u32, base_group_y: u32, base_group_z: u32, group_count_x: u32, group_count_y: u32, group_count_z: u32) VkError!void {
|
||||
_ = interface;
|
||||
_ = base_group_x;
|
||||
_ = base_group_y;
|
||||
_ = base_group_z;
|
||||
_ = group_count_x;
|
||||
_ = group_count_y;
|
||||
_ = group_count_z;
|
||||
}
|
||||
|
||||
pub fn setDeviceMask(interface: *Interface, device_mask: u32) VkError!void {
|
||||
_ = interface;
|
||||
_ = device_mask;
|
||||
}
|
||||
|
||||
pub fn dispatchIndirect(interface: *Interface, buffer: *base.Buffer, offset: vk.DeviceSize) VkError!void {
|
||||
_ = interface;
|
||||
_ = buffer;
|
||||
_ = offset;
|
||||
}
|
||||
|
||||
pub fn draw(interface: *Interface, vertex_count: usize, instance_count: usize, first_vertex: usize, first_instance: usize) VkError!void {
|
||||
_ = interface;
|
||||
_ = vertex_count;
|
||||
_ = instance_count;
|
||||
_ = first_vertex;
|
||||
_ = first_instance;
|
||||
}
|
||||
|
||||
pub fn drawIndexed(interface: *Interface, index_count: usize, instance_count: usize, first_index: usize, vertex_offset: i32, first_instance: usize) VkError!void {
|
||||
_ = interface;
|
||||
_ = index_count;
|
||||
_ = instance_count;
|
||||
_ = first_index;
|
||||
_ = vertex_offset;
|
||||
_ = first_instance;
|
||||
}
|
||||
|
||||
pub fn drawIndexedIndirect(interface: *Interface, buffer: *base.Buffer, offset: usize, count: usize, stride: usize) VkError!void {
|
||||
_ = interface;
|
||||
_ = buffer;
|
||||
_ = offset;
|
||||
_ = count;
|
||||
_ = stride;
|
||||
}
|
||||
|
||||
pub fn drawIndirect(interface: *Interface, buffer: *base.Buffer, offset: usize, count: usize, stride: usize) VkError!void {
|
||||
_ = interface;
|
||||
_ = buffer;
|
||||
_ = offset;
|
||||
_ = count;
|
||||
_ = stride;
|
||||
}
|
||||
|
||||
pub fn endRenderPass(interface: *Interface) VkError!void {
|
||||
_ = interface;
|
||||
}
|
||||
|
||||
pub fn executeCommands(interface: *Interface, commands: *Interface) VkError!void {
|
||||
_ = interface;
|
||||
_ = commands;
|
||||
}
|
||||
|
||||
pub fn fillBuffer(interface: *Interface, buffer: *base.Buffer, offset: vk.DeviceSize, size: vk.DeviceSize, data: u32) VkError!void {
|
||||
_ = interface;
|
||||
_ = buffer;
|
||||
_ = offset;
|
||||
_ = size;
|
||||
_ = data;
|
||||
}
|
||||
|
||||
pub fn updateBuffer(interface: *Interface, buffer: *base.Buffer, offset: vk.DeviceSize, data: []const u8) VkError!void {
|
||||
_ = interface;
|
||||
_ = buffer;
|
||||
_ = offset;
|
||||
_ = data;
|
||||
}
|
||||
|
||||
pub fn nextSubpass(interface: *Interface, contents: vk.SubpassContents) VkError!void {
|
||||
_ = interface;
|
||||
_ = contents;
|
||||
}
|
||||
|
||||
pub fn pipelineBarrier(interface: *Interface, src_stage: vk.PipelineStageFlags, dst_stage: vk.PipelineStageFlags, dependency: vk.DependencyFlags, memory: []const vk.MemoryBarrier, buffers: []const vk.BufferMemoryBarrier, images: []const vk.ImageMemoryBarrier) VkError!void {
|
||||
_ = interface;
|
||||
_ = src_stage;
|
||||
_ = dst_stage;
|
||||
_ = dependency;
|
||||
_ = memory;
|
||||
_ = buffers;
|
||||
_ = images;
|
||||
}
|
||||
|
||||
pub fn pushConstants(interface: *Interface, stages: vk.ShaderStageFlags, offset: u32, blob: []const u8) VkError!void {
|
||||
_ = interface;
|
||||
_ = stages;
|
||||
_ = offset;
|
||||
_ = blob;
|
||||
}
|
||||
|
||||
pub fn resetEvent(interface: *Interface, event: *base.Event, stage: vk.PipelineStageFlags) VkError!void {
|
||||
_ = interface;
|
||||
_ = stage;
|
||||
try event.reset();
|
||||
}
|
||||
|
||||
pub fn resolveImage(interface: *Interface, src: *base.Image, src_layout: vk.ImageLayout, dst: *base.Image, dst_layout: vk.ImageLayout, region: vk.ImageResolve) VkError!void {
|
||||
_ = interface;
|
||||
_ = src;
|
||||
_ = src_layout;
|
||||
_ = dst;
|
||||
_ = dst_layout;
|
||||
_ = region;
|
||||
}
|
||||
|
||||
pub fn setEvent(interface: *Interface, event: *base.Event, stage: vk.PipelineStageFlags) VkError!void {
|
||||
_ = interface;
|
||||
_ = stage;
|
||||
try event.signal();
|
||||
}
|
||||
|
||||
pub fn setScissor(interface: *Interface, first: u32, scissor: []const vk.Rect2D) VkError!void {
|
||||
_ = interface;
|
||||
_ = first;
|
||||
_ = scissor;
|
||||
}
|
||||
|
||||
pub fn setViewport(interface: *Interface, first: u32, viewports: []const vk.Viewport) VkError!void {
|
||||
_ = interface;
|
||||
_ = first;
|
||||
_ = viewports;
|
||||
}
|
||||
|
||||
pub fn setBlendConstants(interface: *Interface, constants: [4]f32) VkError!void {
|
||||
_ = interface;
|
||||
_ = constants;
|
||||
}
|
||||
|
||||
pub fn setStencilCompareMask(interface: *Interface, face_mask: vk.StencilFaceFlags, compare_mask: u32) VkError!void {
|
||||
_ = interface;
|
||||
_ = face_mask;
|
||||
_ = compare_mask;
|
||||
}
|
||||
|
||||
pub fn setStencilReference(interface: *Interface, face_mask: vk.StencilFaceFlags, reference: u32) VkError!void {
|
||||
_ = interface;
|
||||
_ = face_mask;
|
||||
_ = reference;
|
||||
}
|
||||
|
||||
pub fn setStencilWriteMask(interface: *Interface, face_mask: vk.StencilFaceFlags, write_mask: u32) VkError!void {
|
||||
_ = interface;
|
||||
_ = face_mask;
|
||||
_ = write_mask;
|
||||
}
|
||||
|
||||
pub fn waitEvent(interface: *Interface, event: *base.Event, src_stage: vk.PipelineStageFlags, dst_stage: vk.PipelineStageFlags, memory_barriers: []const vk.MemoryBarrier, buffer_barriers: []const vk.BufferMemoryBarrier, image_barriers: []const vk.ImageMemoryBarrier) VkError!void {
|
||||
_ = interface;
|
||||
_ = event;
|
||||
_ = src_stage;
|
||||
_ = dst_stage;
|
||||
_ = memory_barriers;
|
||||
_ = buffer_barriers;
|
||||
_ = image_barriers;
|
||||
}
|
||||
@@ -0,0 +1,48 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const NonDispatchable = base.NonDispatchable;
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const IntelCommandBuffer = @import("IntelCommandBuffer.zig");
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.CommandPool;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.CommandPoolCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.createCommandBuffer = createCommandBuffer,
|
||||
.destroy = destroy,
|
||||
.reset = reset,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn createCommandBuffer(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.CommandBufferAllocateInfo) VkError!*base.CommandBuffer {
|
||||
const cmd = try IntelCommandBuffer.create(interface.owner, allocator, info);
|
||||
return &cmd.interface;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn reset(interface: *Interface, flags: vk.CommandPoolResetFlags) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
_ = flags;
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const VulkanAllocator = base.VulkanAllocator;
|
||||
|
||||
const Device = base.Device;
|
||||
|
||||
const IntelDescriptorSet = @import("IntelDescriptorSet.zig");
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.DescriptorPool;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.DescriptorPoolCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.allocateDescriptorSet = allocateDescriptorSet,
|
||||
.destroy = destroy,
|
||||
.freeDescriptorSet = freeDescriptorSet,
|
||||
.reset = reset,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn allocateDescriptorSet(interface: *Interface, layout: *base.DescriptorSetLayout) VkError!*base.DescriptorSet {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
_ = layout;
|
||||
return VkError.Unknown;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn freeDescriptorSet(interface: *Interface, set: *base.DescriptorSet) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
_ = set;
|
||||
}
|
||||
|
||||
pub fn reset(interface: *Interface, _: vk.DescriptorPoolResetFlags) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.DescriptorSet;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, layout: *base.DescriptorSetLayout) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, layout);
|
||||
|
||||
interface.vtable = &.{
|
||||
.copy = copy,
|
||||
.destroy = destroy,
|
||||
.write = write,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.free(self.heap);
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn copy(interface: *Interface, src_interface: *const Interface, data: vk.CopyDescriptorSet) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
_ = src_interface;
|
||||
_ = data;
|
||||
}
|
||||
|
||||
pub fn write(interface: *Interface, write_data: vk.WriteDescriptorSet) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
_ = write_data;
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.DescriptorSetLayout;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.DescriptorSetLayoutCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,208 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const IntelQueue = @import("IntelQueue.zig");
|
||||
|
||||
pub const IntelBinarySemaphore = @import("IntelBinarySemaphore.zig");
|
||||
pub const IntelBuffer = @import("IntelBuffer.zig");
|
||||
pub const IntelBufferView = @import("IntelBufferView.zig");
|
||||
pub const IntelCommandBuffer = @import("IntelCommandBuffer.zig");
|
||||
pub const IntelCommandPool = @import("IntelCommandPool.zig");
|
||||
pub const IntelDescriptorPool = @import("IntelDescriptorPool.zig");
|
||||
pub const IntelDescriptorSetLayout = @import("IntelDescriptorSetLayout.zig");
|
||||
pub const IntelDeviceMemory = @import("IntelDeviceMemory.zig");
|
||||
pub const IntelEvent = @import("IntelEvent.zig");
|
||||
pub const IntelFence = @import("IntelFence.zig");
|
||||
pub const IntelFramebuffer = @import("IntelFramebuffer.zig");
|
||||
pub const IntelImage = @import("IntelImage.zig");
|
||||
pub const IntelInstance = @import("IntelInstance.zig");
|
||||
pub const IntelImageView = @import("IntelImageView.zig");
|
||||
pub const IntelPipeline = @import("IntelPipeline.zig");
|
||||
pub const IntelPipelineCache = @import("IntelPipelineCache.zig");
|
||||
pub const IntelPipelineLayout = @import("IntelPipelineLayout.zig");
|
||||
pub const IntelQueryPool = @import("IntelQueryPool.zig");
|
||||
pub const IntelRenderPass = @import("IntelRenderPass.zig");
|
||||
pub const IntelSampler = @import("IntelSampler.zig");
|
||||
pub const IntelShaderModule = @import("IntelShaderModule.zig");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Device;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(instance: *base.Instance, physical_device: *base.PhysicalDevice, allocator: std.mem.Allocator, info: *const vk.DeviceCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(allocator, instance, physical_device, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.createQueue = IntelQueue.create,
|
||||
.destroyQueue = IntelQueue.destroy,
|
||||
};
|
||||
|
||||
interface.dispatch_table = &.{
|
||||
.allocateMemory = allocateMemory,
|
||||
.createBuffer = createBuffer,
|
||||
.createBufferView = createBufferView,
|
||||
.createCommandPool = createCommandPool,
|
||||
.createComputePipeline = createComputePipeline,
|
||||
.createDescriptorPool = createDescriptorPool,
|
||||
.createDescriptorSetLayout = createDescriptorSetLayout,
|
||||
.createEvent = createEvent,
|
||||
.createFence = createFence,
|
||||
.createFramebuffer = createFramebuffer,
|
||||
.createGraphicsPipeline = createGraphicsPipeline,
|
||||
.createImage = createImage,
|
||||
.createImageView = createImageView,
|
||||
.createPipelineCache = createPipelineCache,
|
||||
.createPipelineLayout = createPipelineLayout,
|
||||
.createQueryPool = createQueryPool,
|
||||
.createRenderPass = createRenderPass,
|
||||
.createSampler = createSampler,
|
||||
.createSemaphore = createSemaphore,
|
||||
.createShaderModule = createShaderModule,
|
||||
.destroy = destroy,
|
||||
.getDeviceGroupPeerMemoryFeatures = getDeviceGroupPeerMemoryFeatures,
|
||||
.getDeviceGroupPresentCapabilitiesKHR = getDeviceGroupPresentCapabilitiesKHR,
|
||||
.getDeviceGroupSurfacePresentModesKHR = getDeviceGroupSurfacePresentModesKHR,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
|
||||
try self.interface.createQueues(allocator, info);
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn allocateMemory(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.MemoryAllocateInfo) VkError!*base.DeviceMemory {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
const device_memory = try IntelDeviceMemory.create(self, allocator, info.allocation_size, info.memory_type_index);
|
||||
return &device_memory.interface;
|
||||
}
|
||||
|
||||
pub fn createBuffer(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.BufferCreateInfo) VkError!*base.Buffer {
|
||||
const buffer = try IntelBuffer.create(interface, allocator, info);
|
||||
return &buffer.interface;
|
||||
}
|
||||
|
||||
pub fn createDescriptorPool(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.DescriptorPoolCreateInfo) VkError!*base.DescriptorPool {
|
||||
const pool = try IntelDescriptorPool.create(interface, allocator, info);
|
||||
return &pool.interface;
|
||||
}
|
||||
|
||||
pub fn createDescriptorSetLayout(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.DescriptorSetLayoutCreateInfo) VkError!*base.DescriptorSetLayout {
|
||||
const layout = try IntelDescriptorSetLayout.create(interface, allocator, info);
|
||||
return &layout.interface;
|
||||
}
|
||||
|
||||
pub fn createFence(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.FenceCreateInfo) VkError!*base.Fence {
|
||||
const fence = try IntelFence.create(interface, allocator, info);
|
||||
return &fence.interface;
|
||||
}
|
||||
|
||||
pub fn createCommandPool(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.CommandPoolCreateInfo) VkError!*base.CommandPool {
|
||||
const pool = try IntelCommandPool.create(interface, allocator, info);
|
||||
return &pool.interface;
|
||||
}
|
||||
|
||||
pub fn createImage(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.ImageCreateInfo) VkError!*base.Image {
|
||||
const image = try IntelImage.create(interface, allocator, info);
|
||||
return &image.interface;
|
||||
}
|
||||
|
||||
pub fn createImageView(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.ImageViewCreateInfo) VkError!*base.ImageView {
|
||||
const view = try IntelImageView.create(interface, allocator, info);
|
||||
return &view.interface;
|
||||
}
|
||||
|
||||
pub fn createBufferView(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.BufferViewCreateInfo) VkError!*base.BufferView {
|
||||
const view = try IntelBufferView.create(interface, allocator, info);
|
||||
return &view.interface;
|
||||
}
|
||||
|
||||
pub fn createComputePipeline(interface: *Interface, allocator: std.mem.Allocator, cache: ?*base.PipelineCache, info: *const vk.ComputePipelineCreateInfo) VkError!*base.Pipeline {
|
||||
const pipeline = try IntelPipeline.createCompute(interface, allocator, cache, info);
|
||||
return &pipeline.interface;
|
||||
}
|
||||
|
||||
pub fn createEvent(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.EventCreateInfo) VkError!*base.Event {
|
||||
const event = try IntelEvent.create(interface, allocator, info);
|
||||
return &event.interface;
|
||||
}
|
||||
|
||||
pub fn createFramebuffer(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.FramebufferCreateInfo) VkError!*base.Framebuffer {
|
||||
const framebuffer = try IntelFramebuffer.create(interface, allocator, info);
|
||||
return &framebuffer.interface;
|
||||
}
|
||||
|
||||
pub fn createGraphicsPipeline(interface: *Interface, allocator: std.mem.Allocator, cache: ?*base.PipelineCache, info: *const vk.GraphicsPipelineCreateInfo) VkError!*base.Pipeline {
|
||||
const pipeline = try IntelPipeline.createGraphics(interface, allocator, cache, info);
|
||||
return &pipeline.interface;
|
||||
}
|
||||
|
||||
pub fn createPipelineCache(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.PipelineCacheCreateInfo) VkError!*base.PipelineCache {
|
||||
const cache = try IntelPipelineCache.create(interface, allocator, info);
|
||||
return &cache.interface;
|
||||
}
|
||||
|
||||
pub fn createPipelineLayout(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.PipelineLayoutCreateInfo) VkError!*base.PipelineLayout {
|
||||
const layout = try IntelPipelineLayout.create(interface, allocator, info);
|
||||
return &layout.interface;
|
||||
}
|
||||
|
||||
pub fn createQueryPool(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.QueryPoolCreateInfo) VkError!*base.QueryPool {
|
||||
const pool = try IntelQueryPool.create(interface, allocator, info);
|
||||
return &pool.interface;
|
||||
}
|
||||
|
||||
pub fn createRenderPass(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.RenderPassCreateInfo) VkError!*base.RenderPass {
|
||||
const pass = try IntelRenderPass.create(interface, allocator, info);
|
||||
return &pass.interface;
|
||||
}
|
||||
|
||||
pub fn createSampler(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.SamplerCreateInfo) VkError!*base.Sampler {
|
||||
const sampler = try IntelSampler.create(interface, allocator, info);
|
||||
return &sampler.interface;
|
||||
}
|
||||
|
||||
pub fn createSemaphore(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.SemaphoreCreateInfo) VkError!*base.BinarySemaphore {
|
||||
const semaphore = try IntelBinarySemaphore.create(interface, allocator, info);
|
||||
return &semaphore.interface;
|
||||
}
|
||||
|
||||
pub fn createShaderModule(interface: *Interface, allocator: std.mem.Allocator, info: *const vk.ShaderModuleCreateInfo) VkError!*base.ShaderModule {
|
||||
const module = try IntelShaderModule.create(interface, allocator, info);
|
||||
return &module.interface;
|
||||
}
|
||||
|
||||
pub fn getDeviceGroupPeerMemoryFeatures(interface: *Interface, heap_index: u32, local_device_index: u32, remote_device_index: u32) VkError!vk.PeerMemoryFeatureFlags {
|
||||
if (heap_index >= interface.physical_device.mem_props.memory_heap_count) return VkError.ValidationFailed;
|
||||
if (local_device_index != 0 or remote_device_index != 0) return VkError.ValidationFailed;
|
||||
|
||||
return .{
|
||||
.copy_src_bit = true,
|
||||
.copy_dst_bit = true,
|
||||
.generic_src_bit = true,
|
||||
.generic_dst_bit = true,
|
||||
};
|
||||
}
|
||||
|
||||
pub fn getDeviceGroupPresentCapabilitiesKHR(_: *Interface, capabilities: *vk.DeviceGroupPresentCapabilitiesKHR) VkError!void {
|
||||
capabilities.present_mask = @splat(0);
|
||||
capabilities.present_mask[0] = 1;
|
||||
capabilities.modes = .{ .local_bit_khr = true };
|
||||
}
|
||||
|
||||
pub fn getDeviceGroupSurfacePresentModesKHR(_: *Interface, _: *base.SurfaceKHR) VkError!vk.DeviceGroupPresentModeFlagsKHR {
|
||||
return .{ .local_bit_khr = true };
|
||||
}
|
||||
@@ -0,0 +1,59 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const IntelDevice = @import("IntelDevice.zig");
|
||||
const base = @import("base");
|
||||
const lib = @import("lib.zig");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.DeviceMemory;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *IntelDevice, allocator: std.mem.Allocator, size: vk.DeviceSize, memory_type_index: u32) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(&device.interface, size, memory_type_index);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
.map = map,
|
||||
.unmap = unmap,
|
||||
.flushRange = flushRange,
|
||||
.invalidateRange = invalidateRange,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn flushRange(interface: *Interface, offset: vk.DeviceSize, size: vk.DeviceSize) VkError!void {
|
||||
_ = interface;
|
||||
_ = offset;
|
||||
_ = size;
|
||||
}
|
||||
|
||||
pub fn invalidateRange(interface: *Interface, offset: vk.DeviceSize, size: vk.DeviceSize) VkError!void {
|
||||
_ = interface;
|
||||
_ = offset;
|
||||
_ = size;
|
||||
}
|
||||
|
||||
pub fn map(interface: *Interface, offset: vk.DeviceSize, size: vk.DeviceSize) VkError![]u8 {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
_ = offset;
|
||||
_ = size;
|
||||
return VkError.Unknown;
|
||||
}
|
||||
|
||||
pub fn unmap(_: *Interface) void {}
|
||||
@@ -0,0 +1,56 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Event;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.EventCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
.getStatus = getStatus,
|
||||
.reset = reset,
|
||||
.signal = signal,
|
||||
.wait = wait,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn getStatus(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
|
||||
pub fn reset(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
|
||||
pub fn signal(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
|
||||
pub fn wait(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Fence;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *Device, allocator: std.mem.Allocator, info: *const vk.FenceCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
.getStatus = getStatus,
|
||||
.reset = reset,
|
||||
.signal = signal,
|
||||
.wait = wait,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn getStatus(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
|
||||
pub fn reset(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
|
||||
pub fn signal(interface: *Interface) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
}
|
||||
|
||||
pub fn wait(interface: *Interface, timeout: u64) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
_ = self;
|
||||
_ = timeout;
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const IntelRenderPass = @import("IntelRenderPass.zig");
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Framebuffer;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.FramebufferCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
interface.vtable = &.{ .destroy = destroy };
|
||||
|
||||
self.* = .{ .interface = interface };
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,79 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
const lib = @import("lib.zig");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const IntelBuffer = @import("IntelBuffer.zig");
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Image;
|
||||
|
||||
pub const F32x4 = @Vector(4, f32);
|
||||
pub const U32x4 = @Vector(4, u32);
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.ImageCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
.getMemoryRequirements = getMemoryRequirements,
|
||||
.getSubresourceLayout = getSubresourceLayout,
|
||||
.getTotalSizeForAspect = getTotalSizeForAspect,
|
||||
.getSliceMemSizeForMipLevel = getSliceMemSizeForMipLevel,
|
||||
.getRowPitchMemSizeForMipLevel = getRowPitchMemSizeForMipLevel,
|
||||
.copyToMemory = copyToMemory,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn getMemoryRequirements(_: *Interface, requirements: *vk.MemoryRequirements) VkError!void {
|
||||
requirements.alignment = lib.MEMORY_REQUIREMENTS_IMAGE_ALIGNMENT;
|
||||
}
|
||||
|
||||
pub fn copyToMemory(interface: *const Interface, memory: []u8, subresource: vk.ImageSubresourceLayers) VkError!void {
|
||||
_ = interface;
|
||||
_ = subresource;
|
||||
@memset(memory, 0);
|
||||
}
|
||||
|
||||
pub fn getTotalSizeForAspect(interface: *const Interface, aspect_mask: vk.ImageAspectFlags) VkError!usize {
|
||||
_ = aspect_mask;
|
||||
return interface.extent.width * interface.extent.height * interface.extent.depth * base.format.texelSize(interface.format);
|
||||
}
|
||||
|
||||
pub fn getSubresourceLayout(interface: *const Interface, subresource: vk.ImageSubresource) VkError!vk.SubresourceLayout {
|
||||
_ = subresource;
|
||||
return .{
|
||||
.offset = 0,
|
||||
.size = try getTotalSizeForAspect(interface, base.format.toAspect(interface.format)),
|
||||
.row_pitch = getRowPitchMemSizeForMipLevel(interface, base.format.toAspect(interface.format), 0),
|
||||
.array_pitch = getSliceMemSizeForMipLevel(interface, base.format.toAspect(interface.format), 0),
|
||||
.depth_pitch = getSliceMemSizeForMipLevel(interface, base.format.toAspect(interface.format), 0),
|
||||
};
|
||||
}
|
||||
|
||||
pub fn getSliceMemSizeForMipLevel(interface: *const Interface, aspect_mask: vk.ImageAspectFlags, mip_level: u32) usize {
|
||||
_ = aspect_mask;
|
||||
_ = mip_level;
|
||||
return interface.extent.width * interface.extent.height * base.format.texelSize(interface.format);
|
||||
}
|
||||
|
||||
pub fn getRowPitchMemSizeForMipLevel(interface: *const Interface, aspect_mask: vk.ImageAspectFlags, mip_level: u32) usize {
|
||||
_ = aspect_mask;
|
||||
_ = mip_level;
|
||||
return interface.extent.width * base.format.texelSize(interface.format);
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.ImageView;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.ImageViewCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,75 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
const IntelPhysicalDevice = @import("IntelPhysicalDevice.zig");
|
||||
|
||||
const Dispatchable = base.Dispatchable;
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Instance;
|
||||
|
||||
interface: Interface,
|
||||
threaded: std.Io.Threaded,
|
||||
io_impl: std.Io,
|
||||
allocator: std.mem.Allocator,
|
||||
|
||||
fn castExtension(comptime ext: vk.ApiInfo) vk.ExtensionProperties {
|
||||
var props: vk.ExtensionProperties = .{
|
||||
.extension_name = @splat(0),
|
||||
.spec_version = @bitCast(ext.version),
|
||||
};
|
||||
@memcpy(props.extension_name[0..ext.name.len], ext.name);
|
||||
return props;
|
||||
}
|
||||
|
||||
pub const EXTENSIONS = [_]vk.ExtensionProperties{
|
||||
castExtension(vk.extensions.khr_device_group_creation),
|
||||
castExtension(vk.extensions.khr_get_physical_device_properties_2),
|
||||
castExtension(vk.extensions.khr_surface),
|
||||
castExtension(vk.extensions.khr_wayland_surface),
|
||||
};
|
||||
|
||||
pub fn create(allocator: std.mem.Allocator, infos: *const vk.InstanceCreateInfo) VkError!*Interface {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
self.allocator = std.heap.smp_allocator;
|
||||
self.threaded = if (comptime base.config.intel_single_threaded) .init_single_threaded else std.Io.Threaded.init(self.allocator, .{});
|
||||
self.io_impl = self.threaded.io();
|
||||
|
||||
self.interface = try base.Instance.init(allocator, infos);
|
||||
self.interface.dispatch_table = &.{
|
||||
.destroy = destroy,
|
||||
};
|
||||
|
||||
self.interface.vtable = &.{
|
||||
.requestPhysicalDevices = requestPhysicalDevices,
|
||||
.releasePhysicalDevices = releasePhysicalDevices,
|
||||
.io = io,
|
||||
};
|
||||
|
||||
return &self.interface;
|
||||
}
|
||||
|
||||
fn destroy(interface: *Interface, allocator: std.mem.Allocator) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
self.threaded.deinit();
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
fn requestPhysicalDevices(interface: *Interface, allocator: std.mem.Allocator) VkError!void {
|
||||
_ = interface;
|
||||
_ = allocator;
|
||||
}
|
||||
|
||||
fn releasePhysicalDevices(interface: *Interface, allocator: std.mem.Allocator) VkError!void {
|
||||
_ = interface;
|
||||
_ = allocator;
|
||||
}
|
||||
|
||||
fn io(interface: *Interface) std.Io {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
return self.io_impl;
|
||||
}
|
||||
@@ -0,0 +1,873 @@
|
||||
const std = @import("std");
|
||||
const builtin = @import("builtin");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
const lib = @import("lib.zig");
|
||||
|
||||
const IntelDevice = @import("IntelDevice.zig");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const VulkanAllocator = base.VulkanAllocator;
|
||||
const SurfaceKHR = base.SurfaceKHR;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.PhysicalDevice;
|
||||
|
||||
fn castExtension(comptime ext: vk.ApiInfo) vk.ExtensionProperties {
|
||||
var props: vk.ExtensionProperties = .{
|
||||
.extension_name = @splat(0),
|
||||
.spec_version = @bitCast(ext.version),
|
||||
};
|
||||
@memcpy(props.extension_name[0..ext.name.len], ext.name);
|
||||
return props;
|
||||
}
|
||||
|
||||
pub const EXTENSIONS = [_]vk.ExtensionProperties{
|
||||
castExtension(vk.extensions.khr_device_group),
|
||||
castExtension(vk.extensions.khr_swapchain),
|
||||
};
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(allocator: std.mem.Allocator, instance: *base.Instance) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(allocator, instance);
|
||||
|
||||
interface.dispatch_table = &.{
|
||||
.createDevice = createDevice,
|
||||
.getFormatProperties = getFormatProperties,
|
||||
.getImageFormatProperties = getImageFormatProperties,
|
||||
.getSparseImageFormatProperties = getSparseImageFormatProperties,
|
||||
.enumerateLayerProperties = enumerateLayerProperties,
|
||||
.enumerateExtensionProperties = enumerateExtensionProperties,
|
||||
.release = destroy,
|
||||
|
||||
// VK_KHR_get_physical_device_properties_2
|
||||
.getSparseImageFormatProperties2 = getSparseImageFormatProperties2,
|
||||
|
||||
// VK_KHR_surface
|
||||
.getSurfaceSupportKHR = getSurfaceSupportKHR,
|
||||
};
|
||||
|
||||
interface.props.api_version = @bitCast(lib.VULKAN_VERSION);
|
||||
interface.props.driver_version = @bitCast(base.DRIVER_VERSION);
|
||||
interface.props.device_id = lib.DEVICE_ID;
|
||||
interface.props.device_type = .cpu;
|
||||
interface.props.pipeline_cache_uuid = lib.PIPELINE_CACHE_UUID;
|
||||
interface.props.limits = .{
|
||||
.max_image_dimension_1d = 4096,
|
||||
.max_image_dimension_2d = 4096,
|
||||
.max_image_dimension_3d = 256,
|
||||
.max_image_dimension_cube = 4096,
|
||||
.max_image_array_layers = 256,
|
||||
.max_texel_buffer_elements = 65536,
|
||||
.max_uniform_buffer_range = 16384,
|
||||
.max_storage_buffer_range = 134217728,
|
||||
.max_push_constants_size = 256,
|
||||
.max_memory_allocation_count = 1024,
|
||||
.max_sampler_allocation_count = 4096,
|
||||
.buffer_image_granularity = 131072,
|
||||
.sparse_address_space_size = 0,
|
||||
.max_bound_descriptor_sets = 8,
|
||||
.max_per_stage_descriptor_samplers = 16,
|
||||
.max_per_stage_descriptor_uniform_buffers = 12,
|
||||
.max_per_stage_descriptor_storage_buffers = 4,
|
||||
.max_per_stage_descriptor_sampled_images = 16,
|
||||
.max_per_stage_descriptor_storage_images = 4,
|
||||
.max_per_stage_descriptor_input_attachments = 4,
|
||||
.max_per_stage_resources = 128,
|
||||
.max_descriptor_set_samplers = 96,
|
||||
.max_descriptor_set_uniform_buffers = 72,
|
||||
.max_descriptor_set_uniform_buffers_dynamic = 8,
|
||||
.max_descriptor_set_storage_buffers = 24,
|
||||
.max_descriptor_set_storage_buffers_dynamic = 4,
|
||||
.max_descriptor_set_sampled_images = 96,
|
||||
.max_descriptor_set_storage_images = 24,
|
||||
.max_descriptor_set_input_attachments = 4,
|
||||
.max_vertex_input_attributes = 32,
|
||||
.max_vertex_input_bindings = 32,
|
||||
.max_vertex_input_attribute_offset = 2047,
|
||||
.max_vertex_input_binding_stride = 2048,
|
||||
.max_vertex_output_components = 64,
|
||||
.max_tessellation_generation_level = 0,
|
||||
.max_tessellation_patch_size = 0,
|
||||
.max_tessellation_control_per_vertex_input_components = 0,
|
||||
.max_tessellation_control_per_vertex_output_components = 0,
|
||||
.max_tessellation_control_per_patch_output_components = 0,
|
||||
.max_tessellation_control_total_output_components = 0,
|
||||
.max_tessellation_evaluation_input_components = 0,
|
||||
.max_tessellation_evaluation_output_components = 0,
|
||||
.max_geometry_shader_invocations = 0,
|
||||
.max_geometry_input_components = 0,
|
||||
.max_geometry_output_components = 0,
|
||||
.max_geometry_output_vertices = 0,
|
||||
.max_geometry_total_output_components = 0,
|
||||
.max_fragment_input_components = 64,
|
||||
.max_fragment_output_attachments = 4,
|
||||
.max_fragment_dual_src_attachments = 0,
|
||||
.max_fragment_combined_output_resources = 4,
|
||||
.max_compute_shared_memory_size = 16384,
|
||||
.max_compute_work_group_count = .{ 65535, 65535, 65535 },
|
||||
.max_compute_work_group_invocations = 128,
|
||||
.max_compute_work_group_size = .{ 128, 128, 64 },
|
||||
.sub_pixel_precision_bits = 4,
|
||||
.sub_texel_precision_bits = 4,
|
||||
.mipmap_precision_bits = 4,
|
||||
.max_draw_indexed_index_value = 4294967295,
|
||||
.max_draw_indirect_count = 65535,
|
||||
.max_sampler_lod_bias = 2.0,
|
||||
.max_sampler_anisotropy = 1.0,
|
||||
.max_viewports = 1,
|
||||
.max_viewport_dimensions = .{ 4096, 4096 },
|
||||
.viewport_bounds_range = .{ -8192.0, 8191.0 },
|
||||
.viewport_sub_pixel_bits = 0,
|
||||
.min_memory_map_alignment = 64,
|
||||
.min_texel_buffer_offset_alignment = 256,
|
||||
.min_uniform_buffer_offset_alignment = 256,
|
||||
.min_storage_buffer_offset_alignment = 256,
|
||||
.min_texel_offset = -8,
|
||||
.max_texel_offset = 7,
|
||||
.min_texel_gather_offset = 0,
|
||||
.max_texel_gather_offset = 0,
|
||||
.min_interpolation_offset = 0.0,
|
||||
.max_interpolation_offset = 0.0,
|
||||
.sub_pixel_interpolation_offset_bits = 0,
|
||||
.max_framebuffer_width = 4096,
|
||||
.max_framebuffer_height = 4096,
|
||||
.max_framebuffer_layers = 256,
|
||||
.framebuffer_color_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.framebuffer_depth_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.framebuffer_stencil_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.framebuffer_no_attachments_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.max_color_attachments = 4,
|
||||
.sampled_image_color_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.sampled_image_integer_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.sampled_image_depth_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.sampled_image_stencil_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.storage_image_sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true },
|
||||
.max_sample_mask_words = 1,
|
||||
.timestamp_compute_and_graphics = .false,
|
||||
.timestamp_period = 1.0,
|
||||
.max_clip_distances = 0,
|
||||
.max_cull_distances = 0,
|
||||
.max_combined_clip_and_cull_distances = 0,
|
||||
.discrete_queue_priorities = 2,
|
||||
.point_size_range = .{ 1.0, 1.0 },
|
||||
.line_width_range = .{ 1.0, 1.0 },
|
||||
.point_size_granularity = 0.0,
|
||||
.line_width_granularity = 0.0,
|
||||
.strict_lines = .false,
|
||||
.standard_sample_locations = .true,
|
||||
.optimal_buffer_copy_offset_alignment = 1,
|
||||
.optimal_buffer_copy_row_pitch_alignment = 1,
|
||||
.non_coherent_atom_size = 256,
|
||||
};
|
||||
|
||||
interface.mem_props.memory_type_count = 1;
|
||||
interface.mem_props.memory_types[0] = .{
|
||||
.heap_index = 0,
|
||||
.property_flags = .{
|
||||
.device_local_bit = true,
|
||||
.host_visible_bit = true,
|
||||
.host_coherent_bit = true,
|
||||
.host_cached_bit = true,
|
||||
},
|
||||
};
|
||||
interface.mem_props.memory_heap_count = 1;
|
||||
interface.mem_props.memory_heaps[0] = .{
|
||||
.size = std.process.totalSystemMemory() catch 0,
|
||||
.flags = .{ .device_local_bit = true },
|
||||
};
|
||||
|
||||
interface.features = .{
|
||||
.robust_buffer_access = .true,
|
||||
.shader_float_64 = .true,
|
||||
.shader_int_64 = .true,
|
||||
.shader_int_16 = .true,
|
||||
};
|
||||
|
||||
var queue_family_props = [_]vk.QueueFamilyProperties{
|
||||
.{
|
||||
.queue_flags = .{ .graphics_bit = true, .compute_bit = true, .transfer_bit = true },
|
||||
.queue_count = 1,
|
||||
.timestamp_valid_bits = 0,
|
||||
.min_image_transfer_granularity = .{ .width = 1, .height = 1, .depth = 1 },
|
||||
},
|
||||
};
|
||||
interface.queue_family_props.appendSlice(allocator, queue_family_props[0..]) catch return VkError.OutOfHostMemory;
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn createDevice(interface: *Interface, allocator: std.mem.Allocator, infos: *const vk.DeviceCreateInfo) VkError!*base.Device {
|
||||
const device = try IntelDevice.create(interface.instance, interface, allocator, infos);
|
||||
return &device.interface;
|
||||
}
|
||||
|
||||
pub fn enumerateLayerProperties(_: *const Interface, count: *u32, p_properties: ?[*]vk.LayerProperties) VkError!void {
|
||||
count.* = 0;
|
||||
_ = p_properties;
|
||||
}
|
||||
|
||||
pub fn enumerateExtensionProperties(_: *const Interface, layer_name: ?[]const u8, count: *u32, p_properties: ?[*]vk.ExtensionProperties) VkError!void {
|
||||
if (layer_name) |_| {
|
||||
return VkError.LayerNotPresent;
|
||||
}
|
||||
|
||||
const available = EXTENSIONS.len;
|
||||
if (p_properties) |properties| {
|
||||
const write_count = @min(count.*, available);
|
||||
for (EXTENSIONS[0..write_count], properties[0..write_count]) |ext, *prop| {
|
||||
prop.* = ext;
|
||||
}
|
||||
count.* = @intCast(write_count);
|
||||
if (write_count < available) return VkError.Incomplete;
|
||||
} else {
|
||||
count.* = @intCast(available);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn getFormatProperties(interface: *Interface, format: vk.Format) VkError!vk.FormatProperties {
|
||||
_ = interface;
|
||||
var properties: vk.FormatProperties = .{};
|
||||
|
||||
switch (format) {
|
||||
// Formats which can be sampled *and* filtered
|
||||
.r4g4b4a4_unorm_pack16,
|
||||
.b4g4r4a4_unorm_pack16,
|
||||
.a4r4g4b4_unorm_pack16,
|
||||
.a4b4g4r4_unorm_pack16,
|
||||
.r5g6b5_unorm_pack16,
|
||||
.b5g6r5_unorm_pack16,
|
||||
.r5g5b5a1_unorm_pack16,
|
||||
.b5g5r5a1_unorm_pack16,
|
||||
.a1r5g5b5_unorm_pack16,
|
||||
.r8_unorm,
|
||||
.r8_srgb,
|
||||
.r8_snorm,
|
||||
.r8g8_unorm,
|
||||
.r8g8_srgb,
|
||||
.r8g8_snorm,
|
||||
.r8g8b8a8_unorm,
|
||||
.r8g8b8a8_snorm,
|
||||
.r8g8b8a8_srgb,
|
||||
.b8g8r8a8_unorm,
|
||||
.b8g8r8a8_srgb,
|
||||
.a8b8g8r8_unorm_pack32,
|
||||
.a8b8g8r8_snorm_pack32,
|
||||
.a8b8g8r8_srgb_pack32,
|
||||
.a2b10g10r10_unorm_pack32,
|
||||
.a2r10g10b10_unorm_pack32,
|
||||
.r16_unorm,
|
||||
.r16_snorm,
|
||||
.r16_sfloat,
|
||||
.r16g16_unorm,
|
||||
.r16g16_snorm,
|
||||
.r16g16_sfloat,
|
||||
.r16g16b16a16_unorm,
|
||||
.r16g16b16a16_snorm,
|
||||
.r16g16b16a16_sfloat,
|
||||
.r32_sfloat,
|
||||
.r32g32_sfloat,
|
||||
.r32g32b32a32_sfloat,
|
||||
.b10g11r11_ufloat_pack32,
|
||||
.e5b9g9r9_ufloat_pack32,
|
||||
//.bc1_rgb_unorm_block,
|
||||
//.bc1_rgb_srgb_block,
|
||||
//.bc1_rgba_unorm_block,
|
||||
//.bc1_rgba_srgb_block,
|
||||
//.bc2_unorm_block,
|
||||
//.bc2_srgb_block,
|
||||
//.bc3_unorm_block,
|
||||
//.bc3_srgb_block,
|
||||
//.bc4_unorm_block,
|
||||
//.bc4_snorm_block,
|
||||
//.bc5_unorm_block,
|
||||
//.bc5_snorm_block,
|
||||
//.bc6h_ufloat_block,
|
||||
//.bc6h_sfloat_block,
|
||||
//.bc7_unorm_block,
|
||||
//.bc7_srgb_block,
|
||||
//.etc2_r8g8b8_unorm_block,
|
||||
//.etc2_r8g8b8_srgb_block,
|
||||
//.etc2_r8g8b8a1_unorm_block,
|
||||
//.etc2_r8g8b8a1_srgb_block,
|
||||
//.etc2_r8g8b8a8_unorm_block,
|
||||
//.etc2_r8g8b8a8_srgb_block,
|
||||
//.eac_r11_unorm_block,
|
||||
//.eac_r11_snorm_block,
|
||||
//.eac_r11g11_unorm_block,
|
||||
//.eac_r11g11_snorm_block,
|
||||
//.astc_4x_4_unorm_block,
|
||||
//.astc_5x_4_unorm_block,
|
||||
//.astc_5x_5_unorm_block,
|
||||
//.astc_6x_5_unorm_block,
|
||||
//.astc_6x_6_unorm_block,
|
||||
//.astc_8x_5_unorm_block,
|
||||
//.astc_8x_6_unorm_block,
|
||||
//.astc_8x_8_unorm_block,
|
||||
//.astc_1_0x_5_unorm_block,
|
||||
//.astc_1_0x_6_unorm_block,
|
||||
//.astc_1_0x_8_unorm_block,
|
||||
//.astc_1_0x_10_unorm_block,
|
||||
//.astc_1_2x_10_unorm_block,
|
||||
//.astc_1_2x_12_unorm_block,
|
||||
//.astc_4x_4_srgb_block,
|
||||
//.astc_5x_4_srgb_block,
|
||||
//.astc_5x_5_srgb_block,
|
||||
//.astc_6x_5_srgb_block,
|
||||
//.astc_6x_6_srgb_block,
|
||||
//.astc_8x_5_srgb_block,
|
||||
//.astc_8x_6_srgb_block,
|
||||
//.astc_8x_8_srgb_block,
|
||||
//.astc_1_0x_5_srgb_block,
|
||||
//.astc_1_0x_6_srgb_block,
|
||||
//.astc_1_0x_8_srgb_block,
|
||||
//.astc_1_0x_10_srgb_block,
|
||||
//.astc_1_2x_10_srgb_block,
|
||||
//.astc_1_2x_12_srgb_block,
|
||||
.d16_unorm,
|
||||
.d32_sfloat,
|
||||
.d32_sfloat_s8_uint,
|
||||
=> {
|
||||
properties.optimal_tiling_features.blit_src_bit = true;
|
||||
properties.optimal_tiling_features.sampled_image_bit = true;
|
||||
properties.optimal_tiling_features.transfer_dst_bit = true;
|
||||
properties.optimal_tiling_features.transfer_src_bit = true;
|
||||
properties.optimal_tiling_features.sampled_image_filter_linear_bit = true;
|
||||
},
|
||||
|
||||
// Formats which can be sampled, but don't support filtering
|
||||
.r8_uint,
|
||||
.r8_sint,
|
||||
.r8g8_uint,
|
||||
.r8g8_sint,
|
||||
.r8g8b8a8_uint,
|
||||
.r8g8b8a8_sint,
|
||||
.a8b8g8r8_uint_pack32,
|
||||
.a8b8g8r8_sint_pack32,
|
||||
.a2b10g10r10_uint_pack32,
|
||||
.a2r10g10b10_uint_pack32,
|
||||
.r16_uint,
|
||||
.r16_sint,
|
||||
.r16g16_uint,
|
||||
.r16g16_sint,
|
||||
.r16g16b16a16_uint,
|
||||
.r16g16b16a16_sint,
|
||||
.r32_uint,
|
||||
.r32_sint,
|
||||
.r32g32_uint,
|
||||
.r32g32_sint,
|
||||
.r32g32b32a32_uint,
|
||||
.r32g32b32a32_sint,
|
||||
.s8_uint,
|
||||
=> {
|
||||
properties.optimal_tiling_features.blit_src_bit = true;
|
||||
properties.optimal_tiling_features.sampled_image_bit = true;
|
||||
properties.optimal_tiling_features.transfer_dst_bit = true;
|
||||
properties.optimal_tiling_features.transfer_src_bit = true;
|
||||
},
|
||||
|
||||
// YCbCr formats
|
||||
.g8_b8_r8_3plane_420_unorm,
|
||||
.g8_b8r8_2plane_420_unorm,
|
||||
.g10x6_b10x6r10x6_2plane_420_unorm_3pack16,
|
||||
=> {
|
||||
properties.optimal_tiling_features.sampled_image_bit = true;
|
||||
properties.optimal_tiling_features.sampled_image_filter_linear_bit = true;
|
||||
properties.optimal_tiling_features.sampled_image_ycbcr_conversion_linear_filter_bit = true;
|
||||
properties.optimal_tiling_features.transfer_src_bit = true;
|
||||
properties.optimal_tiling_features.transfer_dst_bit = true;
|
||||
properties.optimal_tiling_features.cosited_chroma_samples_bit = true;
|
||||
},
|
||||
else => {},
|
||||
}
|
||||
|
||||
switch (format) {
|
||||
// Vulkan 1.0 mandatory storage image formats supporting atomic operations
|
||||
.r32_uint,
|
||||
.r32_sint,
|
||||
=> {
|
||||
properties.buffer_features.storage_texel_buffer_bit = true;
|
||||
properties.buffer_features.storage_texel_buffer_atomic_bit = true;
|
||||
properties.optimal_tiling_features.storage_image_bit = true;
|
||||
properties.optimal_tiling_features.storage_image_atomic_bit = true;
|
||||
},
|
||||
// vulkan 1.0 mandatory storage image formats
|
||||
.r8g8b8a8_unorm,
|
||||
.r8g8b8a8_snorm,
|
||||
.r8g8b8a8_uint,
|
||||
.r8g8b8a8_sint,
|
||||
.r16g16b16a16_uint,
|
||||
.r16g16b16a16_sint,
|
||||
.r16g16b16a16_sfloat,
|
||||
.r32_sfloat,
|
||||
.r32g32_uint,
|
||||
.r32g32_sint,
|
||||
.r32g32_sfloat,
|
||||
.r32g32b32a32_uint,
|
||||
.r32g32b32a32_sint,
|
||||
.r32g32b32a32_sfloat,
|
||||
.a2b10g10r10_unorm_pack32,
|
||||
.a2b10g10r10_uint_pack32,
|
||||
// vulkan 1.0 shaderstorageimageextendedformats
|
||||
.r16g16_sfloat,
|
||||
.b10g11r11_ufloat_pack32,
|
||||
.r16_sfloat,
|
||||
.r16g16b16a16_unorm,
|
||||
.r16g16_unorm,
|
||||
.r8g8_unorm,
|
||||
.r16_unorm,
|
||||
.r8_unorm,
|
||||
.r16g16b16a16_snorm,
|
||||
.r16g16_snorm,
|
||||
.r8g8_snorm,
|
||||
.r16_snorm,
|
||||
.r8_snorm,
|
||||
.r16g16_sint,
|
||||
.r8g8_sint,
|
||||
.r16_sint,
|
||||
.r8_sint,
|
||||
.r16g16_uint,
|
||||
.r8g8_uint,
|
||||
.r16_uint,
|
||||
.r8_uint,
|
||||
// additional formats not listed under "formats without shader storage format"
|
||||
.a8b8g8r8_unorm_pack32,
|
||||
.a8b8g8r8_snorm_pack32,
|
||||
.a8b8g8r8_uint_pack32,
|
||||
.a8b8g8r8_sint_pack32,
|
||||
.b8g8r8a8_unorm,
|
||||
.b8g8r8a8_srgb,
|
||||
=> {
|
||||
properties.optimal_tiling_features.storage_image_bit = true;
|
||||
properties.buffer_features.storage_texel_buffer_bit = true;
|
||||
},
|
||||
|
||||
else => {},
|
||||
}
|
||||
|
||||
switch (format) {
|
||||
.r5g6b5_unorm_pack16,
|
||||
.a1r5g5b5_unorm_pack16,
|
||||
.r4g4b4a4_unorm_pack16,
|
||||
.b4g4r4a4_unorm_pack16,
|
||||
.a4r4g4b4_unorm_pack16,
|
||||
.a4b4g4r4_unorm_pack16,
|
||||
.b5g6r5_unorm_pack16,
|
||||
.r5g5b5a1_unorm_pack16,
|
||||
.b5g5r5a1_unorm_pack16,
|
||||
.r8_unorm,
|
||||
.r8g8_unorm,
|
||||
.r8g8b8a8_unorm,
|
||||
.r8g8b8a8_srgb,
|
||||
.b8g8r8a8_unorm,
|
||||
.b8g8r8a8_srgb,
|
||||
.a8b8g8r8_unorm_pack32,
|
||||
.a8b8g8r8_srgb_pack32,
|
||||
.a2b10g10r10_unorm_pack32,
|
||||
.a2r10g10b10_unorm_pack32,
|
||||
.r16_sfloat,
|
||||
.r16g16_sfloat,
|
||||
.r16g16b16a16_sfloat,
|
||||
.r32_sfloat,
|
||||
.r32g32_sfloat,
|
||||
.r32g32b32a32_sfloat,
|
||||
.b10g11r11_ufloat_pack32,
|
||||
.r8_uint,
|
||||
.r8_sint,
|
||||
.r8g8_uint,
|
||||
.r8g8_sint,
|
||||
.r8g8b8a8_uint,
|
||||
.r8g8b8a8_sint,
|
||||
.a8b8g8r8_uint_pack32,
|
||||
.a8b8g8r8_sint_pack32,
|
||||
.a2b10g10r10_uint_pack32,
|
||||
.a2r10g10b10_uint_pack32,
|
||||
.r16_unorm,
|
||||
.r16_uint,
|
||||
.r16_sint,
|
||||
.r16g16_unorm,
|
||||
.r16g16_uint,
|
||||
.r16g16_sint,
|
||||
.r16g16b16a16_unorm,
|
||||
.r16g16b16a16_uint,
|
||||
.r16g16b16a16_sint,
|
||||
.r32_uint,
|
||||
.r32_sint,
|
||||
.r32g32_uint,
|
||||
.r32g32_sint,
|
||||
.r32g32b32a32_uint,
|
||||
.r32g32b32a32_sint,
|
||||
=> {
|
||||
properties.optimal_tiling_features.color_attachment_bit = true;
|
||||
properties.optimal_tiling_features.blit_dst_bit = true;
|
||||
},
|
||||
.s8_uint,
|
||||
.d16_unorm,
|
||||
.d32_sfloat, // note: either vk_format_d32_sfloat or vk_format_x8_d24_unorm_pack32 must be supported
|
||||
.d32_sfloat_s8_uint,
|
||||
=> { // note: either vk_format_d24_unorm_s8_uint or vk_format_d32_sfloat_s8_uint must be supported
|
||||
properties.optimal_tiling_features.depth_stencil_attachment_bit = true;
|
||||
},
|
||||
|
||||
else => {},
|
||||
}
|
||||
|
||||
if (base.format.supportsColorAttachemendBlend(format)) {
|
||||
properties.optimal_tiling_features.color_attachment_blend_bit = true;
|
||||
}
|
||||
|
||||
switch (format) {
|
||||
.r8_unorm,
|
||||
.r8_snorm,
|
||||
.r8_uscaled,
|
||||
.r8_sscaled,
|
||||
.r8_uint,
|
||||
.r8_sint,
|
||||
.r8g8_unorm,
|
||||
.r8g8_snorm,
|
||||
.r8g8_uscaled,
|
||||
.r8g8_sscaled,
|
||||
.r8g8_uint,
|
||||
.r8g8_sint,
|
||||
.r8g8b8a8_unorm,
|
||||
.r8g8b8a8_snorm,
|
||||
.r8g8b8a8_uscaled,
|
||||
.r8g8b8a8_sscaled,
|
||||
.r8g8b8a8_uint,
|
||||
.r8g8b8a8_sint,
|
||||
.b8g8r8a8_unorm,
|
||||
.a8b8g8r8_unorm_pack32,
|
||||
.a8b8g8r8_snorm_pack32,
|
||||
.a8b8g8r8_uscaled_pack32,
|
||||
.a8b8g8r8_sscaled_pack32,
|
||||
.a8b8g8r8_uint_pack32,
|
||||
.a8b8g8r8_sint_pack32,
|
||||
.a2r10g10b10_unorm_pack32,
|
||||
.a2r10g10b10_snorm_pack32,
|
||||
.a2r10g10b10_uint_pack32,
|
||||
.a2r10g10b10_sint_pack32,
|
||||
.a2b10g10r10_unorm_pack32,
|
||||
.a2b10g10r10_snorm_pack32,
|
||||
.a2b10g10r10_uint_pack32,
|
||||
.a2b10g10r10_sint_pack32,
|
||||
.r16_unorm,
|
||||
.r16_snorm,
|
||||
.r16_uscaled,
|
||||
.r16_sscaled,
|
||||
.r16_uint,
|
||||
.r16_sint,
|
||||
.r16_sfloat,
|
||||
.r16g16_unorm,
|
||||
.r16g16_snorm,
|
||||
.r16g16_uscaled,
|
||||
.r16g16_sscaled,
|
||||
.r16g16_uint,
|
||||
.r16g16_sint,
|
||||
.r16g16_sfloat,
|
||||
.r16g16b16a16_unorm,
|
||||
.r16g16b16a16_snorm,
|
||||
.r16g16b16a16_uscaled,
|
||||
.r16g16b16a16_sscaled,
|
||||
.r16g16b16a16_uint,
|
||||
.r16g16b16a16_sint,
|
||||
.r16g16b16a16_sfloat,
|
||||
.r32_uint,
|
||||
.r32_sint,
|
||||
.r32_sfloat,
|
||||
.r32g32_uint,
|
||||
.r32g32_sint,
|
||||
.r32g32_sfloat,
|
||||
.r32g32b32_uint,
|
||||
.r32g32b32_sint,
|
||||
.r32g32b32_sfloat,
|
||||
.r32g32b32a32_uint,
|
||||
.r32g32b32a32_sint,
|
||||
.r32g32b32a32_sfloat,
|
||||
=> properties.buffer_features.vertex_buffer_bit = true,
|
||||
else => {},
|
||||
}
|
||||
|
||||
switch (format) {
|
||||
// Vulkan 1.1 mandatory
|
||||
.r8_unorm,
|
||||
.r8_snorm,
|
||||
.r8_uint,
|
||||
.r8_sint,
|
||||
.r8g8_unorm,
|
||||
.r8g8_snorm,
|
||||
.r8g8_uint,
|
||||
.r8g8_sint,
|
||||
.r8g8b8a8_unorm,
|
||||
.r8g8b8a8_snorm,
|
||||
.r8g8b8a8_uint,
|
||||
.r8g8b8a8_sint,
|
||||
.b8g8r8a8_unorm,
|
||||
.a8b8g8r8_unorm_pack32,
|
||||
.a8b8g8r8_snorm_pack32,
|
||||
.a8b8g8r8_uint_pack32,
|
||||
.a8b8g8r8_sint_pack32,
|
||||
.a2b10g10r10_unorm_pack32,
|
||||
.a2b10g10r10_uint_pack32,
|
||||
.r16_uint,
|
||||
.r16_sint,
|
||||
.r16_sfloat,
|
||||
.r16g16_uint,
|
||||
.r16g16_sint,
|
||||
.r16g16_sfloat,
|
||||
.r16g16b16a16_uint,
|
||||
.r16g16b16a16_sint,
|
||||
.r16g16b16a16_sfloat,
|
||||
.r32_uint,
|
||||
.r32_sint,
|
||||
.r32_sfloat,
|
||||
.r32g32_uint,
|
||||
.r32g32_sint,
|
||||
.r32g32_sfloat,
|
||||
.r32g32b32a32_uint,
|
||||
.r32g32b32a32_sint,
|
||||
.r32g32b32a32_sfloat,
|
||||
.b10g11r11_ufloat_pack32,
|
||||
// optional
|
||||
.a2r10g10b10_unorm_pack32,
|
||||
.a2r10g10b10_uint_pack32,
|
||||
=> properties.buffer_features.uniform_texel_buffer_bit = true,
|
||||
else => {},
|
||||
}
|
||||
|
||||
if (properties.optimal_tiling_features.toInt() != 0) {
|
||||
// "Formats that are required to support VK_FORMAT_FEATURE_SAMPLED_IMAGE_BIT must also support
|
||||
// VK_FORMAT_FEATURE_TRANSFER_SRC_BIT and VK_FORMAT_FEATURE_TRANSFER_DST_BIT."
|
||||
|
||||
properties.linear_tiling_features.transfer_src_bit = true;
|
||||
properties.linear_tiling_features.transfer_dst_bit = true;
|
||||
}
|
||||
|
||||
return properties;
|
||||
}
|
||||
|
||||
pub fn getImageFormatProperties(
|
||||
interface: *Interface,
|
||||
format: vk.Format,
|
||||
image_type: vk.ImageType,
|
||||
tiling: vk.ImageTiling,
|
||||
usage: vk.ImageUsageFlags,
|
||||
flags: vk.ImageCreateFlags,
|
||||
) VkError!vk.ImageFormatProperties {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
if (!try self.isFormatSupported(format, image_type, tiling, usage))
|
||||
return VkError.FormatNotSupported;
|
||||
|
||||
var properties: vk.ImageFormatProperties = .{
|
||||
.max_extent = .{ .width = 0, .height = 0, .depth = 1 },
|
||||
.max_mip_levels = 1,
|
||||
.max_array_layers = lib.MAX_IMAGE_ARRAY_LAYERS,
|
||||
.sample_counts = .{ .@"1_bit" = true },
|
||||
.max_resource_size = std.math.maxInt(u32),
|
||||
};
|
||||
|
||||
switch (image_type) {
|
||||
.@"1d" => {
|
||||
properties.max_mip_levels = lib.MAX_IMAGE_LEVELS_1D;
|
||||
properties.max_extent.width = 1 << (lib.MAX_IMAGE_LEVELS_1D - 1);
|
||||
properties.max_extent.height = 1;
|
||||
},
|
||||
.@"2d" => {
|
||||
if (flags.cube_compatible_bit) {
|
||||
properties.max_mip_levels = lib.MAX_IMAGE_LEVELS_CUBE;
|
||||
properties.max_extent.width = 1 << (lib.MAX_IMAGE_LEVELS_CUBE - 1);
|
||||
properties.max_extent.height = 1 << (lib.MAX_IMAGE_LEVELS_CUBE - 1);
|
||||
} else {
|
||||
properties.max_mip_levels = lib.MAX_IMAGE_LEVELS_2D;
|
||||
properties.max_extent.width = 1 << (lib.MAX_IMAGE_LEVELS_2D - 1);
|
||||
properties.max_extent.height = 1 << (lib.MAX_IMAGE_LEVELS_2D - 1);
|
||||
|
||||
const format_properties = try interface.getFormatProperties(format);
|
||||
const format_features = if (tiling == .linear) format_properties.linear_tiling_features else format_properties.optimal_tiling_features;
|
||||
if (format_features.color_attachment_bit or format_features.depth_stencil_attachment_bit) {
|
||||
properties.sample_counts = .{ .@"1_bit" = true, .@"4_bit" = true };
|
||||
}
|
||||
}
|
||||
},
|
||||
.@"3d" => {
|
||||
properties.max_mip_levels = lib.MAX_IMAGE_LEVELS_3D;
|
||||
properties.max_extent.width = 1 << (lib.MAX_IMAGE_LEVELS_3D - 1);
|
||||
properties.max_extent.height = 1 << (lib.MAX_IMAGE_LEVELS_3D - 1);
|
||||
properties.max_extent.depth = 1 << (lib.MAX_IMAGE_LEVELS_3D - 1);
|
||||
properties.max_array_layers = 1;
|
||||
},
|
||||
else => return VkError.FormatNotSupported,
|
||||
}
|
||||
|
||||
if (tiling == .linear) {
|
||||
properties.max_mip_levels = 1;
|
||||
properties.max_array_layers = 1;
|
||||
properties.sample_counts = .{ .@"1_bit" = true };
|
||||
}
|
||||
|
||||
return properties;
|
||||
}
|
||||
|
||||
/// Intel does not support sparse images.
|
||||
pub fn getSparseImageFormatProperties(
|
||||
interface: *Interface,
|
||||
format: vk.Format,
|
||||
image_type: vk.ImageType,
|
||||
samples: vk.SampleCountFlags,
|
||||
tiling: vk.ImageTiling,
|
||||
usage: vk.ImageUsageFlags,
|
||||
properties: ?[*]vk.SparseImageFormatProperties,
|
||||
) VkError!u32 {
|
||||
_ = interface;
|
||||
_ = format;
|
||||
_ = image_type;
|
||||
_ = samples;
|
||||
_ = tiling;
|
||||
_ = usage;
|
||||
_ = properties;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/// Intel does not support sparse images.
|
||||
pub fn getSparseImageFormatProperties2(
|
||||
interface: *Interface,
|
||||
format: vk.Format,
|
||||
image_type: vk.ImageType,
|
||||
samples: vk.SampleCountFlags,
|
||||
tiling: vk.ImageTiling,
|
||||
usage: vk.ImageUsageFlags,
|
||||
properties: ?[*]vk.SparseImageFormatProperties2,
|
||||
) VkError!u32 {
|
||||
_ = interface;
|
||||
_ = format;
|
||||
_ = image_type;
|
||||
_ = samples;
|
||||
_ = tiling;
|
||||
_ = usage;
|
||||
_ = properties;
|
||||
return 0;
|
||||
}
|
||||
|
||||
fn isFormatSupported(
|
||||
self: *Self,
|
||||
format: vk.Format,
|
||||
image_type: vk.ImageType,
|
||||
tiling: vk.ImageTiling,
|
||||
usage: vk.ImageUsageFlags,
|
||||
) VkError!bool {
|
||||
const format_properties = try self.interface.getFormatProperties(format);
|
||||
const format_features = switch (tiling) {
|
||||
.linear => format_properties.linear_tiling_features,
|
||||
.optimal => format_properties.optimal_tiling_features,
|
||||
else => return false,
|
||||
};
|
||||
|
||||
if (!checkFormatUsage(usage, format_features))
|
||||
return false;
|
||||
|
||||
const all_recognized_usages: vk.ImageUsageFlags = .{
|
||||
.sampled_bit = true,
|
||||
.storage_bit = true,
|
||||
.color_attachment_bit = true,
|
||||
.depth_stencil_attachment_bit = true,
|
||||
.input_attachment_bit = true,
|
||||
.transfer_src_bit = true,
|
||||
.transfer_dst_bit = true,
|
||||
.transient_attachment_bit = true,
|
||||
};
|
||||
|
||||
if (usage.subtract(all_recognized_usages).toInt() != 0)
|
||||
return false;
|
||||
|
||||
if (usage.sampled_bit) {
|
||||
if (tiling != .linear and !format_features.sampled_image_bit)
|
||||
return false;
|
||||
}
|
||||
|
||||
if (tiling == .linear) {
|
||||
if (image_type != .@"2d")
|
||||
return false;
|
||||
if (base.format.isDepth(format) or base.format.isStencil(format))
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
fn checkFormatUsage(usage: vk.ImageUsageFlags, features: vk.FormatFeatureFlags) bool {
|
||||
if (usage.sampled_bit and !features.sampled_image_bit)
|
||||
return false;
|
||||
if (usage.storage_bit and !features.storage_image_bit)
|
||||
return false;
|
||||
if (usage.color_attachment_bit and !features.color_attachment_bit)
|
||||
return false;
|
||||
if (usage.depth_stencil_attachment_bit and !features.depth_stencil_attachment_bit)
|
||||
return false;
|
||||
if (usage.input_attachment_bit and !(features.color_attachment_bit or features.depth_stencil_attachment_bit))
|
||||
return false;
|
||||
if (usage.transfer_src_bit and !features.transfer_src_bit)
|
||||
return false;
|
||||
if (usage.transfer_dst_bit and !features.transfer_dst_bit)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
pub fn getSurfaceSupportKHR(_: *Interface, _: u32, _: *SurfaceKHR) VkError!bool {
|
||||
return true;
|
||||
}
|
||||
|
||||
const CpuidRegs = packed struct {
|
||||
eax: u32,
|
||||
ebx: u32,
|
||||
ecx: u32,
|
||||
edx: u32,
|
||||
};
|
||||
|
||||
fn cpuid(leaf_id: u32, subleaf_id: u32) CpuidRegs {
|
||||
comptime {
|
||||
switch (builtin.cpu.arch) {
|
||||
.x86, .x86_64 => {},
|
||||
else => @compileError("cpuid is only available on x86/x86_64"),
|
||||
}
|
||||
}
|
||||
|
||||
var eax: u32 = undefined;
|
||||
var ebx: u32 = undefined;
|
||||
var ecx: u32 = undefined;
|
||||
var edx: u32 = undefined;
|
||||
|
||||
asm volatile ("cpuid"
|
||||
: [_] "={eax}" (eax),
|
||||
[_] "={ebx}" (ebx),
|
||||
[_] "={ecx}" (ecx),
|
||||
[_] "={edx}" (edx),
|
||||
: [_] "{eax}" (leaf_id),
|
||||
[_] "{ecx}" (subleaf_id),
|
||||
);
|
||||
|
||||
return .{
|
||||
.eax = eax,
|
||||
.ebx = ebx,
|
||||
.ecx = ecx,
|
||||
.edx = edx,
|
||||
};
|
||||
}
|
||||
|
||||
fn writeU32Le(dst: []u8, offset: usize, value: u32) void {
|
||||
dst[offset + 0] = @truncate(value);
|
||||
dst[offset + 1] = @truncate(value >> 8);
|
||||
dst[offset + 2] = @truncate(value >> 16);
|
||||
dst[offset + 3] = @truncate(value >> 24);
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Pipeline;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn createCompute(device: *base.Device, allocator: std.mem.Allocator, cache: ?*base.PipelineCache, info: *const vk.ComputePipelineCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.initCompute(device, allocator, cache, info);
|
||||
interface.vtable = &.{ .destroy = destroy };
|
||||
|
||||
self.* = .{ .interface = interface };
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn createGraphics(device: *base.Device, allocator: std.mem.Allocator, cache: ?*base.PipelineCache, info: *const vk.GraphicsPipelineCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.initGraphics(device, allocator, cache, info);
|
||||
interface.vtable = &.{ .destroy = destroy };
|
||||
|
||||
self.* = .{ .interface = interface };
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.PipelineCache;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.PipelineCacheCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
interface.vtable = &.{ .destroy = destroy };
|
||||
|
||||
self.* = .{ .interface = interface };
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.PipelineLayout;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.PipelineLayoutCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.QueryPool;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.QueryPoolCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.free(interface.queries);
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,64 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const IntelCommandBuffer = @import("IntelCommandBuffer.zig");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Queue;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(allocator: std.mem.Allocator, device: *base.Device, index: u32, family_index: u32, flags: vk.DeviceQueueCreateFlags) VkError!*Interface {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(allocator, device, index, family_index, flags);
|
||||
interface.dispatch_table = &.{
|
||||
.bindSparse = bindSparse,
|
||||
.submit = submit,
|
||||
.waitIdle = waitIdle,
|
||||
};
|
||||
|
||||
self.* = .{ .interface = interface };
|
||||
return &self.interface;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) VkError!void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn bindSparse(interface: *Interface, info: []const vk.BindSparseInfo, fence: ?*base.Fence) VkError!void {
|
||||
_ = interface;
|
||||
_ = info;
|
||||
_ = fence;
|
||||
return VkError.FeatureNotPresent;
|
||||
}
|
||||
|
||||
pub fn submit(interface: *Interface, infos: []Interface.SubmitInfo, fence: ?*base.Fence) VkError!void {
|
||||
_ = interface;
|
||||
for (infos) |info| {
|
||||
for (info.wait_semaphores.items) |semaphore| {
|
||||
try semaphore.wait();
|
||||
}
|
||||
|
||||
for (info.command_buffers.items) |command_buffer| {
|
||||
const intel_command_buffer: *IntelCommandBuffer = @alignCast(@fieldParentPtr("interface", command_buffer));
|
||||
_ = intel_command_buffer;
|
||||
}
|
||||
|
||||
for (info.signal_semaphores.items) |semaphore| {
|
||||
try semaphore.signal();
|
||||
}
|
||||
}
|
||||
if (fence) |value| {
|
||||
try value.signal();
|
||||
}
|
||||
}
|
||||
|
||||
pub fn waitIdle(interface: *Interface) VkError!void {
|
||||
_ = interface;
|
||||
}
|
||||
@@ -0,0 +1,40 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
const Device = base.Device;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.RenderPass;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.RenderPassCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
|
||||
interface.vtable = &.{
|
||||
.destroy = destroy,
|
||||
.getRenderAreaGranularity = getRenderAreaGranularity,
|
||||
};
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn getRenderAreaGranularity(_: *Interface) vk.Extent2D {
|
||||
return .{
|
||||
.width = 1,
|
||||
.height = 1,
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.Sampler;
|
||||
|
||||
interface: Interface,
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.SamplerCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
interface.vtable = &.{ .destroy = destroy };
|
||||
|
||||
self.* = .{ .interface = interface };
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
allocator.destroy(self);
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
const base = @import("base");
|
||||
|
||||
const VkError = base.VkError;
|
||||
|
||||
const Self = @This();
|
||||
pub const Interface = base.ShaderModule;
|
||||
|
||||
interface: Interface,
|
||||
ref_count: std.atomic.Value(usize),
|
||||
|
||||
pub fn create(device: *base.Device, allocator: std.mem.Allocator, info: *const vk.ShaderModuleCreateInfo) VkError!*Self {
|
||||
const self = allocator.create(Self) catch return VkError.OutOfHostMemory;
|
||||
errdefer allocator.destroy(self);
|
||||
|
||||
var interface = try Interface.init(device, allocator, info);
|
||||
interface.vtable = &.{ .destroy = destroy };
|
||||
|
||||
self.* = .{
|
||||
.interface = interface,
|
||||
.ref_count = std.atomic.Value(usize).init(1),
|
||||
};
|
||||
return self;
|
||||
}
|
||||
|
||||
pub fn destroy(interface: *Interface, allocator: std.mem.Allocator) void {
|
||||
const self: *Self = @alignCast(@fieldParentPtr("interface", interface));
|
||||
self.unref(allocator);
|
||||
}
|
||||
|
||||
pub fn drop(self: *Self, allocator: std.mem.Allocator) void {
|
||||
allocator.destroy(self);
|
||||
}
|
||||
|
||||
pub fn ref(self: *Self) void {
|
||||
_ = self.ref_count.fetchAdd(1, .monotonic);
|
||||
}
|
||||
|
||||
pub fn unref(self: *Self, allocator: std.mem.Allocator) void {
|
||||
if (self.ref_count.fetchSub(1, .release) == 1) {
|
||||
self.drop(allocator);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,84 @@
|
||||
const std = @import("std");
|
||||
const vk = @import("vulkan");
|
||||
pub const base = @import("base");
|
||||
|
||||
pub const c = @import("intel_c");
|
||||
pub const config = base.config;
|
||||
|
||||
pub const IntelInstance = @import("IntelInstance.zig");
|
||||
pub const IntelDevice = @import("IntelDevice.zig");
|
||||
pub const IntelPhysicalDevice = @import("IntelPhysicalDevice.zig");
|
||||
pub const IntelQueue = @import("IntelQueue.zig");
|
||||
|
||||
pub const IntelBinarySemaphore = @import("IntelBinarySemaphore.zig");
|
||||
pub const IntelBuffer = @import("IntelBuffer.zig");
|
||||
pub const IntelBufferView = @import("IntelBufferView.zig");
|
||||
pub const IntelCommandBuffer = @import("IntelCommandBuffer.zig");
|
||||
pub const IntelCommandPool = @import("IntelCommandPool.zig");
|
||||
pub const IntelDescriptorPool = @import("IntelDescriptorPool.zig");
|
||||
pub const IntelDescriptorSet = @import("IntelDescriptorSet.zig");
|
||||
pub const IntelDescriptorSetLayout = @import("IntelDescriptorSetLayout.zig");
|
||||
pub const IntelDeviceMemory = @import("IntelDeviceMemory.zig");
|
||||
pub const IntelEvent = @import("IntelEvent.zig");
|
||||
pub const IntelFence = @import("IntelFence.zig");
|
||||
pub const IntelFramebuffer = @import("IntelFramebuffer.zig");
|
||||
pub const IntelImage = @import("IntelImage.zig");
|
||||
pub const IntelImageView = @import("IntelImageView.zig");
|
||||
pub const IntelPipeline = @import("IntelPipeline.zig");
|
||||
pub const IntelPipelineCache = @import("IntelPipelineCache.zig");
|
||||
pub const IntelPipelineLayout = @import("IntelPipelineLayout.zig");
|
||||
pub const IntelQueryPool = @import("IntelQueryPool.zig");
|
||||
pub const IntelRenderPass = @import("IntelRenderPass.zig");
|
||||
pub const IntelSampler = @import("IntelSampler.zig");
|
||||
pub const IntelShaderModule = @import("IntelShaderModule.zig");
|
||||
|
||||
pub const Instance = IntelInstance;
|
||||
|
||||
pub const DRIVER_NAME = "Intel";
|
||||
|
||||
pub const VULKAN_VERSION = vk.makeApiVersion(
|
||||
0,
|
||||
config.intel_vulkan_version.major,
|
||||
config.intel_vulkan_version.minor,
|
||||
config.intel_vulkan_version.patch,
|
||||
);
|
||||
|
||||
pub const DEVICE_ID = 0x00000000;
|
||||
pub const PIPELINE_CACHE_UUID: [vk.UUID_SIZE]u8 = "ApeIntelCacheUUI".*;
|
||||
|
||||
pub const PHYSICAL_DEVICE_DEFAULT_NAME = "Ape Intel device";
|
||||
|
||||
pub const std_options = base.std_options;
|
||||
|
||||
comptime {
|
||||
_ = base;
|
||||
}
|
||||
|
||||
test {
|
||||
std.testing.refAllDecls(IntelBinarySemaphore);
|
||||
std.testing.refAllDecls(IntelBuffer);
|
||||
std.testing.refAllDecls(IntelBufferView);
|
||||
std.testing.refAllDecls(IntelCommandBuffer);
|
||||
std.testing.refAllDecls(IntelCommandPool);
|
||||
std.testing.refAllDecls(IntelDescriptorPool);
|
||||
std.testing.refAllDecls(IntelDescriptorSet);
|
||||
std.testing.refAllDecls(IntelDescriptorSetLayout);
|
||||
std.testing.refAllDecls(IntelDevice);
|
||||
std.testing.refAllDecls(IntelDeviceMemory);
|
||||
std.testing.refAllDecls(IntelEvent);
|
||||
std.testing.refAllDecls(IntelFence);
|
||||
std.testing.refAllDecls(IntelFramebuffer);
|
||||
std.testing.refAllDecls(IntelImage);
|
||||
std.testing.refAllDecls(IntelImageView);
|
||||
std.testing.refAllDecls(IntelInstance);
|
||||
std.testing.refAllDecls(IntelPhysicalDevice);
|
||||
std.testing.refAllDecls(IntelPipeline);
|
||||
std.testing.refAllDecls(IntelPipelineCache);
|
||||
std.testing.refAllDecls(IntelPipelineLayout);
|
||||
std.testing.refAllDecls(IntelQueryPool);
|
||||
std.testing.refAllDecls(IntelQueue);
|
||||
std.testing.refAllDecls(IntelRenderPass);
|
||||
std.testing.refAllDecls(IntelSampler);
|
||||
std.testing.refAllDecls(IntelShaderModule);
|
||||
std.testing.refAllDecls(base);
|
||||
}
|
||||
Reference in New Issue
Block a user