From 3af5dcf34d705cc52c1ffe5b85c2a90b5104e4c9 Mon Sep 17 00:00:00 2001 From: Zuhaitz Méndez Fernández de Aránguiz Date: Mon, 19 Jan 2026 22:18:33 +0000 Subject: Improve 'std/cuda.zc' and 'std/vec.zc' + iteration... --- std/cuda.zc | 85 +++++++++++++++++++++++++++++++++++++++++++++++ std/vec.zc | 109 ++++++++++++++++++++++++++++++++++++++++++++++++++++-------- 2 files changed, 181 insertions(+), 13 deletions(-) (limited to 'std') diff --git a/std/cuda.zc b/std/cuda.zc index 851acb3..dbb1fe6 100644 --- a/std/cuda.zc +++ b/std/cuda.zc @@ -1,5 +1,7 @@ include +import "./string.zc" +import "./mem.zc" // Memory Management. @@ -97,3 +99,86 @@ fn cuda_last_error() -> int { fn cuda_ok() -> bool { return cuda_last_error() == 0; } + + +raw { + void _z_cuda_get_props(int dev, char* name, size_t* total_mem, int* sm_count, int* major, int* minor, int* max_threads, int* warp_size) { + struct cudaDeviceProp prop; + if (cudaGetDeviceProperties(&prop, dev) == 0) { + strcpy(name, prop.name); + *total_mem = prop.totalGlobalMem; + *sm_count = prop.multiProcessorCount; + *major = prop.major; + *minor = prop.minor; + *max_threads = prop.maxThreadsPerBlock; + *warp_size = prop.warpSize; + } + } +} + +extern fn _z_cuda_get_props(dev: int, name: char*, mem: usize*, sm: int*, maj: int*, min: int*, max_t: int*, warp: int*); + +struct CudaDeviceProp { + name: String; + total_global_mem: usize; + multi_processor_count: int; + major: int; + minor: int; + max_threads_per_block: int; + warp_size: int; +} + +struct CudaMemInfo { + free: usize; + total: usize; +} + +fn cuda_device_properties(device_id: int) -> CudaDeviceProp { + var mem: usize = 0; + var sm: int = 0; + var maj: int = 0; + var min: int = 0; + var max_t: int = 0; + var warp: int = 0; + + var name_ptr = alloc_n(256); + name_ptr[0] = 0; + + _z_cuda_get_props(device_id, name_ptr, &mem, &sm, &maj, &min, &max_t, &warp); + + var s = String::new(name_ptr); + free(name_ptr); + + return CudaDeviceProp { + name: s, + total_global_mem: mem, + multi_processor_count: sm, + major: maj, + minor: min, + max_threads_per_block: max_t, + warp_size: warp + }; +} + +fn cuda_driver_version() -> int { + var d: int = 0; + cudaDriverGetVersion(&d); + return d; +} + +fn cuda_runtime_version() -> int { + var r: int = 0; + cudaRuntimeGetVersion(&r); + return r; +} + +fn cuda_mem_info() -> CudaMemInfo { + var f: usize = 0; + var t: usize = 0; + cudaMemGetInfo(&f, &t); + return CudaMemInfo { free: f, total: t }; +} + +fn cuda_device_reset() { + cudaDeviceReset(); +} diff --git a/std/vec.zc b/std/vec.zc index 1d9e6e1..be4dc05 100644 --- a/std/vec.zc +++ b/std/vec.zc @@ -14,6 +14,30 @@ struct VecIter { idx: usize; } +struct VecIterResult { + ptr: T*; +} + +impl VecIterResult { + fn is_none(self) -> bool { + return self.ptr == 0; + } + + fn unwrap(self) -> T* { + if (self.ptr == 0) { + !"Panic: unwrap called on null VecIterResult"; + exit(1); + } + return self.ptr; + } +} + +struct VecIterRef { + data: T*; + count: usize; + idx: usize; +} + impl VecIter { fn next(self) -> Option { if (self.idx < self.count) { @@ -23,6 +47,25 @@ impl VecIter { } return Option::None(); } + + fn iterator(self) -> VecIter { + return *self; + } +} + +impl VecIterRef { + fn next(self) -> VecIterResult { + if (self.idx < self.count) { + var item = &self.data[self.idx]; + self.idx = self.idx + 1; + return VecIterResult { ptr: item }; + } + return VecIterResult { ptr: 0 }; + } + + fn iterator(self) -> VecIterRef { + return *self; + } } impl Vec { @@ -30,6 +73,23 @@ impl Vec { return Vec { data: 0, len: 0, cap: 0 }; } + fn with_capacity(cap: usize) -> Vec { + if (cap == 0) { + return Vec { data: 0, len: 0, cap: 0 }; + } + return Vec { + data: (T*)malloc(cap * sizeof(T)), + len: 0, + cap: cap + }; + } + + fn grow(self) { + if (self.cap == 0) { self.cap = 8; } + else { self.cap = self.cap * 2; } + self.data = (T*)realloc(self.data, self.cap * sizeof(T)); + } + fn iterator(self) -> VecIter { return VecIter { data: self.data, @@ -37,16 +97,21 @@ impl Vec { idx: 0 }; } + + fn iter_ref(self) -> VecIterRef { + return VecIterRef { + data: self.data, + count: self.len, + idx: 0 + }; + } fn push(self, item: T) { if (self.len >= self.cap) { - if (self.cap == 0) { self.cap = 8; - } - else { self.cap = self.cap * 2; - } - self.data = realloc(self.data, self.cap * sizeof(T)); + self.grow(); } self.data[self.len] = item; + self.data[self.len] = item; self.len = self.len + 1; } @@ -56,11 +121,7 @@ impl Vec { exit(1); } if (self.len >= self.cap) { - if (self.cap == 0) { self.cap = 8; - } - else { self.cap = self.cap * 2; - } - self.data = realloc(self.data, self.cap * sizeof(T)); + self.grow(); } // Shift elements right if (idx < self.len) { @@ -79,6 +140,14 @@ impl Vec { return self.data[self.len]; } + fn pop_opt(self) -> Option { + if (self.len == 0) { + return Option::None(); + } + self.len = self.len - 1; + return Option::Some(self.data[self.len]); + } + fn remove(self, idx: usize) -> T { if (idx >= self.len) { !"Panic: Remove index out of bounds"; @@ -176,12 +245,26 @@ impl Vec { } fn clone(self) -> Vec { - var new_vec: Vec = Vec::new(); + if (self.len == 0) { + return Vec { data: 0, len: 0, cap: 0 }; + } + var new_data = (T*)malloc(self.len * sizeof(T)); var i: usize = 0; while i < self.len { - new_vec.push(self.data[i]); + new_data[i] = self.data[i]; i = i + 1; } - return new_vec; + return Vec { + data: new_data, + len: self.len, + cap: self.len // Set capacity to exact length + }; + // No local Vec variable means no Drop is called here. + } +} + +impl Drop for Vec { + fn drop(self) { + self.free(); } } -- cgit v1.2.3