From 07b96113b88979a1f0f2a399ace74fcfcaff4085 Mon Sep 17 00:00:00 2001 From: Russel Arbore <russel.jma@gmail.com> Date: Sat, 11 Jan 2025 21:46:26 -0800 Subject: [PATCH] Box definition --- Cargo.lock | 4 ++ Cargo.toml | 1 + hercules_rt/Cargo.toml | 7 ++++ hercules_rt/src/lib.rs | 91 ++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 103 insertions(+) create mode 100644 hercules_rt/Cargo.toml create mode 100644 hercules_rt/src/lib.rs diff --git a/Cargo.lock b/Cargo.lock index 7b70c0b0..088dc069 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -651,6 +651,10 @@ dependencies = [ "take_mut", ] +[[package]] +name = "hercules_rt" +version = "0.1.0" + [[package]] name = "hermit-abi" version = "0.4.0" diff --git a/Cargo.toml b/Cargo.toml index dc0c6478..86307fd8 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -4,6 +4,7 @@ members = [ "hercules_cg", "hercules_ir", "hercules_opt", + "hercules_rt", "hercules_tools/hercules_driver", diff --git a/hercules_rt/Cargo.toml b/hercules_rt/Cargo.toml new file mode 100644 index 00000000..0bf19adf --- /dev/null +++ b/hercules_rt/Cargo.toml @@ -0,0 +1,7 @@ +[package] +name = "hercules_rt" +version = "0.1.0" +authors = ["Russel Arbore <rarbore2@illinois.edu>"] + +[dependencies] + diff --git a/hercules_rt/src/lib.rs b/hercules_rt/src/lib.rs new file mode 100644 index 00000000..bb460ab5 --- /dev/null +++ b/hercules_rt/src/lib.rs @@ -0,0 +1,91 @@ +use std::alloc::{alloc, alloc_zeroed, dealloc, Layout}; +use std::marker::PhantomData; +use std::ptr::{copy_nonoverlapping, NonNull}; + +/* + * An in-memory collection object that can be used by functions compiled by the + * Hercules compiler. + */ +pub struct HerculesBox<'a> { + cpu_shared: Option<NonNull<u8>>, + cpu_exclusive: Option<NonNull<u8>>, + cpu_owned: Option<NonNull<u8>>, + + size: usize, + _phantom: PhantomData<&'a u8>, +} + +impl<'a> HerculesBox<'a> { + pub fn from_slice<T>(slice: &'a [T]) -> Self { + HerculesBox { + cpu_shared: Some(unsafe { NonNull::new_unchecked(slice.as_ptr() as *mut u8) }), + cpu_exclusive: None, + cpu_owned: None, + size: slice.len() * align_of::<T>(), + _phantom: PhantomData, + } + } + + pub fn from_slice_mut<T>(slice: &'a mut [T]) -> Self { + HerculesBox { + cpu_shared: None, + cpu_exclusive: Some(unsafe { NonNull::new_unchecked(slice.as_mut_ptr() as *mut u8) }), + cpu_owned: None, + size: slice.len() * align_of::<T>(), + _phantom: PhantomData, + } + } + + unsafe fn into_cpu(&mut self) -> NonNull<u8> { + self.cpu_shared + .or(self.cpu_exclusive) + .or(self.cpu_owned) + .unwrap() + } + + unsafe fn into_cpu_mut(&mut self) -> NonNull<u8> { + if let Some(ptr) = self.cpu_exclusive.or(self.cpu_owned) { + ptr + } else { + let ptr = + NonNull::new(alloc(Layout::from_size_align_unchecked(self.size, 16))).unwrap(); + copy_nonoverlapping(self.cpu_shared.unwrap().as_ptr(), ptr.as_ptr(), self.size); + self.cpu_owned = Some(ptr); + self.cpu_shared = None; + ptr + } + } + + pub unsafe fn __zeros(size: usize) -> Self { + HerculesBox { + cpu_shared: None, + cpu_exclusive: None, + cpu_owned: Some( + NonNull::new(alloc_zeroed(Layout::from_size_align_unchecked(size, 16))).unwrap(), + ), + size: size, + _phantom: PhantomData, + } + } + + pub unsafe fn __cpu_ptr(&mut self) -> *mut u8 { + self.into_cpu().as_ptr() + } + + pub unsafe fn __cpu_ptr_mut(&mut self) -> *mut u8 { + self.into_cpu_mut().as_ptr() + } +} + +impl<'a> Drop for HerculesBox<'a> { + fn drop(&mut self) { + if let Some(ptr) = self.cpu_owned { + unsafe { + dealloc( + ptr.as_ptr(), + Layout::from_size_align_unchecked(self.size, 16), + ) + } + } + } +} -- GitLab