kronos_compute/sys/
mod.rs

1//! System types and handles for Kronos
2//! 
3//! Type-safe handle system with zero overhead
4
5use std::marker::PhantomData;
6use std::fmt;
7
8/// Opaque handle type with phantom data for type safety
9#[repr(transparent)]
10#[derive(Clone, Copy, PartialEq, Eq, Hash)]
11pub struct Handle<T> {
12    pub(crate) raw: u64,
13    pub(crate) _marker: PhantomData<*const T>,
14}
15
16impl<T> Handle<T> {
17    pub const NULL: Self = Self {
18        raw: 0,
19        _marker: PhantomData,
20    };
21    
22    #[inline]
23    pub const fn from_raw(raw: u64) -> Self {
24        Self {
25            raw,
26            _marker: PhantomData,
27        }
28    }
29    
30    #[inline]
31    pub const fn as_raw(&self) -> u64 {
32        self.raw
33    }
34    
35    #[inline]
36    pub const fn is_null(&self) -> bool {
37        self.raw == 0
38    }
39}
40
41impl<T> fmt::Debug for Handle<T> {
42    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
43        f.debug_struct("Handle")
44            .field("raw", &self.raw)
45            .field("_marker", &self._marker)
46            .finish()
47    }
48}
49
50// SAFETY: Handle<T> is safe to send between threads because:
51// 1. It contains only a u64 value (no references or pointers)
52// 2. The phantom data doesn't affect thread safety
53// 3. Vulkan handles are designed to be thread-safe at the API level
54unsafe impl<T> Send for Handle<T> {}
55unsafe impl<T> Sync for Handle<T> {}
56
57// Define opaque types
58#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
59pub enum InstanceT {}
60#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
61pub enum PhysicalDeviceT {}
62#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
63pub enum DeviceT {}
64#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
65pub enum QueueT {}
66#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
67pub enum CommandBufferT {}
68#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
69pub enum BufferT {}
70#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
71pub enum DeviceMemoryT {}
72#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
73pub enum PipelineT {}
74#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
75pub enum PipelineLayoutT {}
76#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
77pub enum ShaderModuleT {}
78#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
79pub enum DescriptorSetT {}
80#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
81pub enum DescriptorSetLayoutT {}
82#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
83pub enum DescriptorPoolT {}
84#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
85pub enum CommandPoolT {}
86#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
87pub enum FenceT {}
88#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
89pub enum SemaphoreT {}
90#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
91pub enum EventT {}
92#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
93pub enum PipelineCacheT {}
94#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
95pub enum SamplerT {}
96#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)]
97pub enum ImageViewT {}
98
99// Type aliases for handles
100pub type VkInstance = Handle<InstanceT>;
101pub type VkPhysicalDevice = Handle<PhysicalDeviceT>;
102pub type VkDevice = Handle<DeviceT>;
103pub type VkQueue = Handle<QueueT>;
104pub type VkCommandBuffer = Handle<CommandBufferT>;
105pub type VkBuffer = Handle<BufferT>;
106pub type VkDeviceMemory = Handle<DeviceMemoryT>;
107pub type VkPipeline = Handle<PipelineT>;
108pub type VkPipelineLayout = Handle<PipelineLayoutT>;
109pub type VkShaderModule = Handle<ShaderModuleT>;
110pub type VkDescriptorSet = Handle<DescriptorSetT>;
111pub type VkDescriptorSetLayout = Handle<DescriptorSetLayoutT>;
112pub type VkDescriptorPool = Handle<DescriptorPoolT>;
113pub type VkCommandPool = Handle<CommandPoolT>;
114pub type VkFence = Handle<FenceT>;
115pub type VkSemaphore = Handle<SemaphoreT>;
116pub type VkEvent = Handle<EventT>;
117pub type VkPipelineCache = Handle<PipelineCacheT>;
118pub type VkSampler = Handle<SamplerT>;
119pub type VkImageView = Handle<ImageViewT>;
120
121// Basic types
122pub type VkBool32 = u32;
123pub type VkFlags = u32;
124pub type VkDeviceSize = u64;
125
126// Constants
127pub const VK_TRUE: VkBool32 = 1;
128pub const VK_FALSE: VkBool32 = 0;
129pub const VK_WHOLE_SIZE: VkDeviceSize = !0;
130pub const VK_QUEUE_FAMILY_IGNORED: u32 = !0;
131
132// Size limits  
133pub const VK_MAX_PHYSICAL_DEVICE_NAME_SIZE: usize = 256;
134pub const VK_UUID_SIZE: usize = 16;
135pub const VK_MAX_MEMORY_HEAPS: usize = 16;
136pub const VK_MAX_MEMORY_TYPES: usize = 32;
137
138// API version
139pub const VK_API_VERSION_1_0: u32 = (1 << 22) | (0 << 12) | 0;
140pub const VK_API_VERSION_1_1: u32 = (1 << 22) | (1 << 12) | 0;
141pub const VK_API_VERSION_1_2: u32 = (1 << 22) | (2 << 12) | 0;
142pub const VK_API_VERSION_1_3: u32 = (1 << 22) | (3 << 12) | 0;
143
144// Version macros
145#[inline]
146pub const fn VK_MAKE_VERSION(major: u32, minor: u32, patch: u32) -> u32 {
147    (major << 22) | (minor << 12) | patch
148}
149
150#[cfg(test)]
151mod tests {
152    use super::*;
153
154    #[test]
155    fn test_handle_null() {
156        let handle: VkDevice = Handle::NULL;
157        assert!(handle.is_null());
158        assert_eq!(handle.as_raw(), 0);
159    }
160
161    #[test]
162    fn test_handle_creation() {
163        let handle: VkBuffer = Handle::from_raw(42);
164        assert!(!handle.is_null());
165        assert_eq!(handle.as_raw(), 42);
166    }
167
168    #[test]
169    fn test_handle_equality() {
170        let h1: VkPipeline = Handle::from_raw(123);
171        let h2: VkPipeline = Handle::from_raw(123);
172        let h3: VkPipeline = Handle::from_raw(456);
173        
174        assert_eq!(h1, h2);
175        assert_ne!(h1, h3);
176    }
177
178    #[test]
179    fn test_handle_copy() {
180        let h1: VkQueue = Handle::from_raw(789);
181        let h2 = h1; // Copy
182        assert_eq!(h1, h2);
183        assert_eq!(h1.as_raw(), h2.as_raw());
184    }
185
186    #[test]
187    fn test_constants() {
188        assert_eq!(VK_TRUE, 1);
189        assert_eq!(VK_FALSE, 0);
190        assert_eq!(VK_WHOLE_SIZE, u64::MAX);
191        assert_eq!(VK_QUEUE_FAMILY_IGNORED, u32::MAX);
192    }
193
194    #[test]
195    fn test_handle_debug() {
196        let handle: VkDevice = Handle::from_raw(999);
197        let debug_str = format!("{:?}", handle);
198        assert!(debug_str.contains("raw: 999"));
199    }
200}