From bce892b6255ff76d4a6c021cb3a29ec6ee60f8cd Mon Sep 17 00:00:00 2001 From: Nick Fitzgerald Date: Thu, 11 Jul 2019 15:12:48 -0700 Subject: [PATCH] Add `#[wasm_bindgen(assert_no_shim)]` on imported functions for testing This should not be used outside of wasm-bindgen's test suite. --- crates/backend/src/ast.rs | 1 + crates/backend/src/encode.rs | 1 + crates/cli-support/src/js/mod.rs | 11 ++++++++++- crates/cli-support/src/webidl/mod.rs | 5 +++++ crates/macro-support/src/parser.rs | 5 +++++ crates/shared/src/lib.rs | 1 + crates/webidl/src/util.rs | 1 + tests/wasm/no_shims.rs | 10 ++++++++++ 8 files changed, 34 insertions(+), 1 deletion(-) mode change 100644 => 100755 crates/shared/src/lib.rs diff --git a/crates/backend/src/ast.rs b/crates/backend/src/ast.rs index 574042bdb..3cf8d28c4 100644 --- a/crates/backend/src/ast.rs +++ b/crates/backend/src/ast.rs @@ -122,6 +122,7 @@ pub struct ImportFunction { pub catch: bool, pub variadic: bool, pub structural: bool, + pub assert_no_shim: bool, pub kind: ImportFunctionKind, pub shim: Ident, pub doc_comment: Option, diff --git a/crates/backend/src/encode.rs b/crates/backend/src/encode.rs index 66711f1fb..b59975bfc 100644 --- a/crates/backend/src/encode.rs +++ b/crates/backend/src/encode.rs @@ -272,6 +272,7 @@ fn shared_import_function<'a>( shim: intern.intern(&i.shim), catch: i.catch, method, + assert_no_shim: i.assert_no_shim, structural: i.structural, function: shared_function(&i.function, intern), variadic: i.variadic, diff --git a/crates/cli-support/src/js/mod.rs b/crates/cli-support/src/js/mod.rs index 2ff84f979..b18900f66 100644 --- a/crates/cli-support/src/js/mod.rs +++ b/crates/cli-support/src/js/mod.rs @@ -1839,7 +1839,8 @@ impl<'a> Context<'a> { for (id, import) in sorted_iter(&aux.import_map) { let variadic = aux.imports_with_variadic.contains(&id); let catch = aux.imports_with_catch.contains(&id); - self.generate_import(*id, import, bindings, variadic, catch) + let assert_no_shim = aux.imports_with_assert_no_shim.contains(&id); + self.generate_import(*id, import, bindings, variadic, catch, assert_no_shim) .with_context(|_| { format!("failed to generate bindings for import `{:?}`", import,) })?; @@ -1978,6 +1979,7 @@ impl<'a> Context<'a> { bindings: &NonstandardWebidlSection, variadic: bool, catch: bool, + assert_no_shim: bool, ) -> Result<(), Error> { let binding = &bindings.imports[&id]; let webidl = bindings @@ -1996,6 +1998,13 @@ impl<'a> Context<'a> { ) } _ => { + if assert_no_shim { + panic!( + "imported function was annotated with `#[wasm_bindgen(assert_no_shim)]` \ + but we need to generate a JS shim for it" + ); + } + let mut builder = binding::Builder::new(self); builder.catch(catch)?; let js = builder.process( diff --git a/crates/cli-support/src/webidl/mod.rs b/crates/cli-support/src/webidl/mod.rs index 6adb08847..d0dcc00e2 100644 --- a/crates/cli-support/src/webidl/mod.rs +++ b/crates/cli-support/src/webidl/mod.rs @@ -163,6 +163,7 @@ pub struct WasmBindgenAux { /// Small bits of metadata about imports. pub imports_with_catch: HashSet, pub imports_with_variadic: HashSet, + pub imports_with_assert_no_shim: HashSet, /// Auxiliary information to go into JS/TypeScript bindings describing the /// exported enums from Rust. @@ -793,6 +794,7 @@ impl<'a> Context<'a> { method, structural, function, + assert_no_shim, } = function; let (import_id, _id) = match self.function_imports.get(*shim) { Some(pair) => *pair, @@ -811,6 +813,9 @@ impl<'a> Context<'a> { if *catch { self.aux.imports_with_catch.insert(import_id); } + if *assert_no_shim { + self.aux.imports_with_assert_no_shim.insert(import_id); + } // Perform two functions here. First we're saving off our WebIDL // bindings signature, indicating what we think our import is going to diff --git a/crates/macro-support/src/parser.rs b/crates/macro-support/src/parser.rs index 78d63c912..697d35008 100644 --- a/crates/macro-support/src/parser.rs +++ b/crates/macro-support/src/parser.rs @@ -52,6 +52,9 @@ macro_rules! attrgen { (typescript_custom_section, TypescriptCustomSection(Span)), (start, Start(Span)), (skip, Skip(Span)), + + // For testing purposes only. + (assert_no_shim, AssertNoShim(Span)), } }; } @@ -496,8 +499,10 @@ impl<'a> ConvertToAst<(BindgenAttrs, &'a ast::ImportModule)> for syn::ForeignIte return Err(Diagnostic::span_error(*span, msg)); } } + let assert_no_shim = opts.assert_no_shim().is_some(); let ret = ast::ImportKind::Function(ast::ImportFunction { function: wasm, + assert_no_shim, kind, js_ret, catch, diff --git a/crates/shared/src/lib.rs b/crates/shared/src/lib.rs old mode 100644 new mode 100755 index 845b384f9..b8fa9f241 --- a/crates/shared/src/lib.rs +++ b/crates/shared/src/lib.rs @@ -44,6 +44,7 @@ macro_rules! shared_api { shim: &'a str, catch: bool, variadic: bool, + assert_no_shim: bool, method: Option>, structural: bool, function: Function<'a>, diff --git a/crates/webidl/src/util.rs b/crates/webidl/src/util.rs index dbaad4df2..03492ed0e 100644 --- a/crates/webidl/src/util.rs +++ b/crates/webidl/src/util.rs @@ -314,6 +314,7 @@ impl<'src> FirstPassRecord<'src> { variadic, catch, structural, + assert_no_shim: false, shim: { let ns = match kind { ast::ImportFunctionKind::Normal => "", diff --git a/tests/wasm/no_shims.rs b/tests/wasm/no_shims.rs index bf47fa29c..9140de51b 100644 --- a/tests/wasm/no_shims.rs +++ b/tests/wasm/no_shims.rs @@ -35,20 +35,30 @@ use wasm_bindgen_test::*; }; ")] extern "C" { + #[wasm_bindgen(assert_no_shim)] fn trivial(); + #[wasm_bindgen(assert_no_shim)] fn incoming_i32() -> i32; + #[wasm_bindgen(assert_no_shim)] fn incoming_f32() -> f32; + #[wasm_bindgen(assert_no_shim)] fn incoming_f64() -> f64; + #[wasm_bindgen(assert_no_shim)] fn outgoing_i32(x: i32); + #[wasm_bindgen(assert_no_shim)] fn outgoing_f32(y: f32); + #[wasm_bindgen(assert_no_shim)] fn outgoing_f64(z: f64); + #[wasm_bindgen(assert_no_shim)] fn many(x: i32, y: f32, z: f64) -> i32; // Note that this should only skip the JS shim if we have anyref support // enabled. + // + // #[wasm_bindgen(assert_no_shim)] fn works_when_anyref_support_is_enabled(v: JsValue) -> JsValue; }