From 5ac39291fdf397808278835f53ec24f067f94c83 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ralph=20K=C3=BCpper?= Date: Sat, 26 Sep 2026 17:50:33 +0200 Subject: [PATCH 1/2] docs, tests: CodeRabbit follow-ups from #11402 and #11405 - authoring-guide async one-shot example: import StringHeader / JsString / read_string and define the my_digest stand-in so the snippet compiles. - tls_import_routes_net_wrapper: hold env_lock() across well_known_iteration_set, which reads PERRY_FORCE_WELL_KNOWN. --- .../src/commands/compile/optimized_libs/tests.rs | 3 +++ docs/src/native-libraries/authoring-guide.md | 16 +++++++++++++--- 2 files changed, 16 insertions(+), 3 deletions(-) diff --git a/crates/perry/src/commands/compile/optimized_libs/tests.rs b/crates/perry/src/commands/compile/optimized_libs/tests.rs index 2c69ff13c6..80c446fa12 100644 --- a/crates/perry/src/commands/compile/optimized_libs/tests.rs +++ b/crates/perry/src/commands/compile/optimized_libs/tests.rs @@ -942,6 +942,9 @@ fn tls_import_routes_net_wrapper() { let dir = tempfile::tempdir().expect("tempdir"); let mut ctx = CompilationContext::new(dir.path().to_path_buf()); ctx.native_module_imports.insert("node:tls".to_string()); + // `well_known_iteration_set` reads PERRY_FORCE_WELL_KNOWN, which other + // tests in this binary mutate; hold the env lock across the read. + let _guard = env_lock(); assert!(well_known_iteration_set(&ctx).contains("net")); } diff --git a/docs/src/native-libraries/authoring-guide.md b/docs/src/native-libraries/authoring-guide.md index 6f7d775534..fa6b52d105 100644 --- a/docs/src/native-libraries/authoring-guide.md +++ b/docs/src/native-libraries/authoring-guide.md @@ -347,13 +347,23 @@ under `NativeLibraries///` in app bundles. ### Async one-shot (hashing, compression, a blocking client call) ```rust -use perry_ffi::{pool, JsPromise, Promise}; +use perry_ffi::{pool, read_string, JsPromise, JsString, Promise, StringHeader}; +/// Stand-in for your real CPU-bound work. Owned Rust data in, owned out. +fn my_digest(input: &str) -> Result { + Ok(format!("{:08x}", input.len())) +} + +/// # Safety +/// `input_ptr` must be null or a Perry-runtime `StringHeader`. #[no_mangle] -pub extern "C" fn js_my_digest(input_ptr: *const StringHeader) -> *mut Promise { +pub unsafe extern "C" fn js_my_digest(input_ptr: *mut StringHeader) -> *mut Promise { let promise = JsPromise::new(); let raw = promise.as_raw(); - let input = unsafe { read_str(input_ptr) }.unwrap_or_default(); + // Copy the argument out of the JS heap before crossing threads. + let input = read_string(JsString::from_raw(input_ptr)) + .unwrap_or_default() + .to_owned(); // `work` runs on a pool thread with owned Rust data only; `deliver` runs // on the thread that owns the JS heap, where the promise is settled. From 3d3d307288d9a4bba5348361688cb98366efa34f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ralph=20K=C3=BCpper?= Date: Sat, 26 Sep 2026 19:34:57 +0200 Subject: [PATCH 2/2] changelog: CodeRabbit follow-ups (#11421) --- changelog.d/11421-coderabbit-tokio-followups.md | 2 ++ 1 file changed, 2 insertions(+) create mode 100644 changelog.d/11421-coderabbit-tokio-followups.md diff --git a/changelog.d/11421-coderabbit-tokio-followups.md b/changelog.d/11421-coderabbit-tokio-followups.md new file mode 100644 index 0000000000..57608ac904 --- /dev/null +++ b/changelog.d/11421-coderabbit-tokio-followups.md @@ -0,0 +1,2 @@ +- Docs: the native-bindings authoring guide's async one-shot example now compiles as written. It imports `StringHeader`, `JsString` and `read_string`, reads its argument with `read_string(JsString::from_raw(..))` and defines its `my_digest` stand-in. (A CodeRabbit follow-up from #11402.) +- Tests: `tls_import_routes_net_wrapper` holds `env_lock()` around `well_known_iteration_set`, which reads `PERRY_FORCE_WELL_KNOWN`. (A CodeRabbit follow-up from #11405.)