Skip to content

Commit

Permalink
update
Browse files Browse the repository at this point in the history
  • Loading branch information
jupyterkat committed Jul 9, 2024
1 parent 78b3bb2 commit 60fce40
Show file tree
Hide file tree
Showing 4 changed files with 84 additions and 37 deletions.
60 changes: 40 additions & 20 deletions crates/byondapi-macros/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -46,19 +46,29 @@ pub fn bind(attr: TokenStream, item: TokenStream) -> TokenStream {
let args = &input.sig.inputs;

//Check for returns
match &input.sig.output {
syn::ReturnType::Default => {} //

syn::ReturnType::Type(_, ty) => {
return syn::Error::new(ty.span(), "Do not specify the return value of binds")
.to_compile_error()
.into()
let func_return = match &input.sig.output {
syn::ReturnType::Default => {
return syn::Error::new(
input.span(),
"Empty returns are not allowed, please return a Result",
)
.to_compile_error()
.into()
}
}

syn::ReturnType::Type(_, ty) => match ty.as_ref() {
&syn::Type::Path(_) => &input.sig.output,
_ => {
return syn::Error::new(input.span(), "Invalid return type, please return a Result")
.to_compile_error()
.into()
}
},
};

let signature = quote! {
#[no_mangle]
pub unsafe extern "C" fn #func_name_ffi (
pub unsafe extern "C-unwind" fn #func_name_ffi (
__argc: ::byondapi::sys::u4c,
__argv: *mut ::byondapi::value::ByondValue
) -> ::byondapi::value::ByondValue
Expand Down Expand Up @@ -142,7 +152,7 @@ pub fn bind(attr: TokenStream, item: TokenStream) -> TokenStream {
}

}
fn #func_name(#args) -> ::eyre::Result<::byondapi::value::ByondValue>
fn #func_name(#args) #func_return
#body
};
result.into()
Expand All @@ -163,15 +173,25 @@ pub fn bind_raw_args(attr: TokenStream, item: TokenStream) -> TokenStream {
let func_name_ffi_disp = quote!(#func_name_ffi).to_string();

//Check for returns
match &input.sig.output {
syn::ReturnType::Default => {} //

syn::ReturnType::Type(_, ty) => {
return syn::Error::new(ty.span(), "Do not specify the return value of binds")
.to_compile_error()
.into()
let func_return = match &input.sig.output {
syn::ReturnType::Default => {
return syn::Error::new(
input.span(),
"Empty returns are not allowed, please return a Result",
)
.to_compile_error()
.into()
}
}

syn::ReturnType::Type(_, ty) => match ty.as_ref() {
&syn::Type::Path(_) => &input.sig.output,
_ => {
return syn::Error::new(input.span(), "Invalid return type, please return a Result")
.to_compile_error()
.into()
}
},
};

if !input.sig.inputs.is_empty() {
return syn::Error::new(
Expand All @@ -184,7 +204,7 @@ pub fn bind_raw_args(attr: TokenStream, item: TokenStream) -> TokenStream {

let signature = quote! {
#[no_mangle]
pub unsafe extern "C" fn #func_name_ffi (
pub unsafe extern "C-unwind" fn #func_name_ffi (
__argc: ::byondapi::sys::u4c,
__argv: *mut ::byondapi::value::ByondValue
) -> ::byondapi::value::ByondValue
Expand Down Expand Up @@ -249,7 +269,7 @@ pub fn bind_raw_args(attr: TokenStream, item: TokenStream) -> TokenStream {
}
}
}
fn #func_name(args: &mut [::byondapi::value::ByondValue]) -> ::eyre::Result<::byondapi::value::ByondValue>
fn #func_name(args: &mut [::byondapi::value::ByondValue]) #func_return
#body
};
result.into()
Expand Down
35 changes: 18 additions & 17 deletions crates/byondapi-rs-test/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
#![allow(clippy::missing_safety_doc)]

use byondapi::{byond_string, map::*, prelude::*};
use eyre::Result;

#[test]
fn generate_binds() {
Expand All @@ -18,20 +19,20 @@ fn setup_panic_handler() {
}

#[byondapi::bind]
fn test_connection() {
fn test_connection() -> Result<ByondValue> {
setup_panic_handler();
Ok(ByondValue::new_num(69.0))
}

#[byondapi::bind_raw_args]
fn test_args() {
fn test_args() -> Result<ByondValue> {
setup_panic_handler();
assert_eq!(args.len(), 2);
Ok(args[1])
}

#[byondapi::bind]
fn test_ptr(ptr: ByondValue) {
fn test_ptr(ptr: ByondValue) -> Result<ByondValue> {
setup_panic_handler();
let pointer = ByondValuePointer::new(ptr)?;

Expand All @@ -44,20 +45,20 @@ fn test_ptr(ptr: ByondValue) {
}

#[byondapi::bind]
fn test_proc_call(object: ByondValue) {
fn test_proc_call(object: ByondValue) -> Result<ByondValue> {
Ok(object.call("get_name", &[])?)
}

#[byondapi::bind]
fn test_readwrite_var(object: ByondValue) {
fn test_readwrite_var(object: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

object.read_var_id(byond_string!("name"))?.get_string()?;

Ok(object.read_string("name")?.try_into()?)
}
#[byondapi::bind]
fn test_list_push(mut list: ByondValue) {
fn test_list_push(mut list: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

list.push_list(ByondValue::new_num(8.0))?;
Expand All @@ -66,7 +67,7 @@ fn test_list_push(mut list: ByondValue) {
}

#[byondapi::bind]
fn test_list_double(list: ByondValue) {
fn test_list_double(list: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

let collection = list
Expand All @@ -78,14 +79,14 @@ fn test_list_double(list: ByondValue) {
}

#[byondapi::bind]
fn test_list_index(list: ByondValue) {
fn test_list_index(list: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

Ok(list.read_list_index(3.0)?)
}

#[byondapi::bind]
fn test_list_pop(mut list: ByondValue) {
fn test_list_pop(mut list: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

let element = list.pop_list()?;
Expand All @@ -98,13 +99,13 @@ fn test_list_pop(mut list: ByondValue) {
}

#[byondapi::bind]
fn test_length_with_list(list: ByondValue) {
fn test_length_with_list(list: ByondValue) -> Result<ByondValue> {
setup_panic_handler();
Ok(list.builtin_length()?)
}

#[byondapi::bind]
fn test_block() {
fn test_block() -> Result<ByondValue> {
setup_panic_handler();

let block = byond_block(
Expand All @@ -123,13 +124,13 @@ fn test_block() {
}

#[byondapi::bind]
fn test_length_with_str(object: ByondValue) {
fn test_length_with_str(object: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

Ok(object.builtin_length()?)
}
#[byondapi::bind]
fn test_list_key_lookup(mut list: ByondValue) {
fn test_list_key_lookup(mut list: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

let num: f32 = list.read_list_index("cat")?.try_into()?;
Expand Down Expand Up @@ -165,7 +166,7 @@ fn test_list_key_lookup(mut list: ByondValue) {
}

#[byondapi::bind]
fn test_ref(turf: ByondValue) {
fn test_ref(turf: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

let turf_type = turf.get_type();
Expand All @@ -177,7 +178,7 @@ fn test_ref(turf: ByondValue) {
}

#[byondapi::bind]
fn test_non_assoc_list(list: ByondValue) {
fn test_non_assoc_list(list: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

let map = list
Expand All @@ -199,7 +200,7 @@ fn test_non_assoc_list(list: ByondValue) {
}

#[byondapi::bind]
fn test_list_read(list: ByondValue) {
fn test_list_read(list: ByondValue) -> Result<ByondValue> {
setup_panic_handler();

let map = list.get_list_values()?;
Expand All @@ -217,7 +218,7 @@ fn test_list_read(list: ByondValue) {
}

#[byondapi::bind]
fn test_new_obj() {
fn test_new_obj() -> Result<ByondValue> {
Ok(ByondValue::builtin_new(
ByondValue::try_from("/datum/testobject")?,
&[],
Expand Down
1 change: 1 addition & 0 deletions crates/byondapi-rs/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ pub mod binds;
pub mod byond_string;
pub mod global_call;
pub mod prelude;
pub mod threadsync;
pub mod value;

use crate::value::ByondValue;
Expand Down
25 changes: 25 additions & 0 deletions crates/byondapi-rs/src/threadsync.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
use crate::static_global::byond;
use crate::value::ByondValue;
use byondapi_sys::CByondValue;
use std::os::raw::c_void;

struct CallbackData<F: FnOnce() -> ByondValue + Send> {
callback: Option<F>,
}

extern "C" fn trampoline<F: FnOnce() -> ByondValue + Send>(data: *mut c_void) -> CByondValue {
let data = unsafe { Box::from_raw(data as *mut CallbackData<F>) };
(data.callback.unwrap())().into_inner()
}

pub fn thread_sync<F>(callback: F, block: bool) -> ByondValue
where
F: FnOnce() -> ByondValue + Send + 'static,
{
let data = Box::new(CallbackData {
callback: Some(callback),
});
let data_ptr = Box::into_raw(data) as *mut c_void;

ByondValue(unsafe { byond().Byond_ThreadSync(Some(trampoline::<F>), data_ptr, block) })
}

0 comments on commit 60fce40

Please sign in to comment.