diff --git a/src/backends/wasm_js.rs b/src/backends/wasm_js.rs index 61198f53..5feb0f3b 100644 --- a/src/backends/wasm_js.rs +++ b/src/backends/wasm_js.rs @@ -16,7 +16,7 @@ pub use crate::util::{inner_u32, inner_u64}; #[cfg(not(all(target_arch = "wasm32", any(target_os = "unknown", target_os = "none"))))] compile_error!("`wasm_js` backend can be enabled only for OS-less WASM targets!"); -use js_sys::{SharedArrayBuffer, Uint8Array, WebAssembly::Memory}; +use js_sys::{JsString, Object, Uint8Array, WebAssembly::Memory}; use wasm_bindgen::{prelude::wasm_bindgen, JsCast, JsValue}; // Size of our temporary Uint8Array buffer used with WebCrypto methods @@ -39,9 +39,15 @@ pub fn fill_inner(dest: &mut [MaybeUninit]) -> Result<(), Error> { MEMORY_KIND_SHARED => true, MEMORY_KIND_UNINIT => { let memory: Memory = wasm_bindgen::memory().unchecked_into(); - let val = if memory.buffer().is_instance_of::() { + // We can't use `instanceof` because of a bug in Firefox. + // Instead we compare the constructor name, which always works. + let constructor_name = Object::from(memory.buffer()).constructor().name(); + let val = if SHARED_ARRAY_BUFFER_NAME.with(|name| &constructor_name == name) { MEMORY_KIND_SHARED } else { + web_sys::console::log_1( + &Object::from(memory.buffer()).constructor().name(), + ); MEMORY_KIND_NOT_SHARED }; MEMORY_KIND.store(val, Ordering::Relaxed); @@ -87,6 +93,7 @@ pub fn fill_inner(dest: &mut [MaybeUninit]) -> Result<(), Error> { } #[wasm_bindgen] +#[rustfmt::skip] extern "C" { // Web Crypto API: Crypto interface (https://www.w3.org/TR/WebCryptoAPI/) type Crypto; @@ -98,4 +105,6 @@ extern "C" { fn get_random_values(this: &Crypto, buf: &Uint8Array) -> Result<(), JsValue>; #[wasm_bindgen(method, js_name = getRandomValues, catch)] fn get_random_values_ref(this: &Crypto, buf: &mut [u8]) -> Result<(), JsValue>; + #[wasm_bindgen(thread_local_v2, static_string)] + static SHARED_ARRAY_BUFFER_NAME: JsString = "SharedArrayBuffer"; }