Skip to content

Commit

Permalink
feat: Add env::set_dynamic function
Browse files Browse the repository at this point in the history
  • Loading branch information
GrayJack committed Apr 22, 2024
1 parent d780065 commit 2aa2e1d
Show file tree
Hide file tree
Showing 2 changed files with 45 additions and 2 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ All notable changes to the library should be put here
- Feat: Add `JanetBuffer::push_janet_string` method
- Feat: Add `assert_deep_eq!` macro
- Feat: Add `assert_deep_ne!` macro
- Feat: Add `env::set_dynamic` function
- Perf: Avoid allocation in `Janet::dynamic` if the passed argument is already null terminated
- Refactor: Simplify `jpanic!` macro
- Refactor: janetrs_macros 0.7.0 — Update `syn` crate to 2.0
Expand Down
46 changes: 44 additions & 2 deletions src/env.rs
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
//! Module for the Janet environment structure and methods.
//! Module for the Janet VM environment structure, methods and functions.
use core::ptr;

#[cfg(not(feature = "std"))]
use alloc::{format, string::String};

use crate::{
function::JanetRawCFunction, Janet, JanetKeyword, JanetString, JanetSymbol, JanetTable,
function::JanetRawCFunction, Janet, JanetBuffer, JanetKeyword, JanetString, JanetSymbol,
JanetTable,
};

/// Representation of the Janet runtime environment, like global definitions, available
Expand Down Expand Up @@ -323,6 +324,36 @@ impl<'a> CFunOptions<'a> {
}
}

/// Set a dynamic binding in the VM runtime, binding a `value` to a `keyword`.
///
/// Once set, you can later retrieve it by using [`Janet::dynamic`] fucntion.
///
/// # Examples
/// ```
/// use janetrs::Janet;
/// # let _client = janetrs::client::JanetClient::init().unwrap();
///
/// assert_eq!(Janet::dynamic("my_dyn_value"), None);
/// janetrs::env::set_dynamic("my_dyn_value", Janet::number(10.0));
/// assert_eq!(Janet::dynamic("my_dyn_value"), Some(Janet::number(10.0)));
/// ```
pub fn set_dynamic(keyword: impl AsRef<[u8]>, value: Janet) {
use core::ffi::c_char;
unsafe fn set_dyn(keyword: *const c_char, value: Janet) {
evil_janet::janet_setdyn(keyword, value.into())
}

let keyword = keyword.as_ref();
if keyword.contains(&b'\0') {
unsafe { set_dyn(keyword.as_ptr().cast(), value) }
} else {
let mut keyword: JanetBuffer = keyword.into();
keyword.push('\0');

unsafe { set_dyn(keyword.as_ptr().cast(), value) }
}
}


#[cfg(all(test, any(feature = "amalgation", feature = "link-system")))]
mod tests {
Expand Down Expand Up @@ -356,4 +387,15 @@ mod tests {

Ok(())
}

#[test]
fn set_dynamic() -> Result<(), crate::client::Error> {
let _client = crate::client::JanetClient::init()?;

assert_eq!(Janet::dynamic("my_dyn_value"), None);
super::set_dynamic("my_dyn_value", Janet::number(10.0));
assert_eq!(Janet::dynamic("my_dyn_value"), Some(Janet::number(10.0)));

Ok(())
}
}

0 comments on commit 2aa2e1d

Please sign in to comment.