diff --git a/csharp_mod/SlangExtensions.cs b/csharp_mod/SlangExtensions.cs new file mode 100644 index 0000000..be39dcd --- /dev/null +++ b/csharp_mod/SlangExtensions.cs @@ -0,0 +1,52 @@ +using System; +using System.Collections.Generic; +using System.Text; +using StationeersIC10Editor; + +namespace Slang +{ + public static unsafe class SlangExtensions + { + // 1. Convert the Rust Byte Vector (Vec_uint8_t) to a C# String + public static string AsString(this Vec_uint8_t vec) + { + if (vec.ptr == null || vec.len == UIntPtr.Zero) + { + return string.Empty; + } + + // Rust strings are UTF-8. Read bytes from raw pointer. + var toReturn = Encoding.UTF8.GetString(vec.ptr, (int)vec.len); + + return toReturn; + } + + public static void Drop(this Vec_uint8_t vec) + { + Ffi.free_string(vec); + } + + // 2. Convert Rust Token Vector to C# List + public static List AsList(this Vec_FfiToken_t vec) + { + var list = new List((int)vec.len); + var currentPtr = vec.ptr; + + // Iterate through the raw memory array + for (int i = 0; i < (int)vec.len; i++) + { + // Dereference pointer to get the struct at index i + FfiToken_t token = currentPtr[i]; + + var newToken = new Token(token.text.AsString(), token.column); + newToken.Error = token.error.AsString(); + + list.Add(newToken); + } + + Ffi.free_ffi_token_vec(vec); + + return list; + } + } +} diff --git a/csharp_mod/SlangGlue.cs b/csharp_mod/SlangGlue.cs index 8e99ae1..bc5b128 100644 --- a/csharp_mod/SlangGlue.cs +++ b/csharp_mod/SlangGlue.cs @@ -70,6 +70,18 @@ public unsafe struct Vec_FfiToken_t { public UIntPtr cap; } +public unsafe partial class Ffi { + [DllImport(RustLib, ExactSpelling = true)] public static unsafe extern + void free_ffi_token_vec ( + Vec_FfiToken_t v); +} + +public unsafe partial class Ffi { + [DllImport(RustLib, ExactSpelling = true)] public static unsafe extern + void free_string ( + Vec_uint8_t s); +} + public unsafe partial class Ffi { [DllImport(RustLib, ExactSpelling = true)] public static unsafe extern Vec_FfiToken_t tokenize_line ( diff --git a/rust_compiler/libs/compiler/src/test/branching.rs b/rust_compiler/libs/compiler/src/test/branching.rs index fb06024..d23d880 100644 --- a/rust_compiler/libs/compiler/src/test/branching.rs +++ b/rust_compiler/libs/compiler/src/test/branching.rs @@ -155,4 +155,3 @@ fn test_spilled_variable_update_in_branch() -> anyhow::Result<()> { Ok(()) } - diff --git a/rust_compiler/src/lib.rs b/rust_compiler/src/lib.rs index f2b5ead..2657211 100644 --- a/rust_compiler/src/lib.rs +++ b/rust_compiler/src/lib.rs @@ -69,6 +69,16 @@ pub fn tokenize_line(input: safer_ffi::char_p::char_p_ref<'_>) -> safer_ffi::Vec tokens.into() } +#[ffi_export] +pub fn free_ffi_token_vec(v: safer_ffi::Vec) { + drop(v) +} + +#[ffi_export] +pub fn free_string(s: safer_ffi::String) { + drop(s) +} + #[cfg(feature = "headers")] pub fn generate_headers() -> std::io::Result<()> { ::safer_ffi::headers::builder()