Skip to content

Commit

Permalink
feat: Use llvm.experimental.constrained intrinsics
Browse files Browse the repository at this point in the history
This patch also makes NaN canonicalization a configurable behavior in
LLVM Compiler.

LLVM compiler now defaults to no canonicalization. This can be enable using
the dedicated functions, either through the Rust API or C API.
  • Loading branch information
jubianchi committed May 5, 2021
1 parent 7f7017c commit 22bf49b
Show file tree
Hide file tree
Showing 14 changed files with 2,383 additions and 1,776 deletions.
8 changes: 3 additions & 5 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions lib/c-api/build.rs
Original file line number Diff line number Diff line change
Expand Up @@ -476,6 +476,7 @@ fn exclude_items_from_wasm_c_api(builder: Builder) -> Builder {
.exclude_item("wasi_version_t")
.exclude_item("wasm_config_push_middleware")
.exclude_item("wasm_config_set_compiler")
.exclude_item("wasm_config_canonicalize_nans")
.exclude_item("wasm_config_set_engine")
.exclude_item("wasm_config_set_features")
.exclude_item("wasm_config_set_target")
Expand Down
5 changes: 5 additions & 0 deletions lib/c-api/src/wasm_c_api/engine.rs
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,7 @@ pub struct wasm_config_t {
compiler: wasmer_compiler_t,
#[cfg(feature = "middlewares")]
pub(super) middlewares: Vec<wasmer_middleware_t>,
pub(super) nan_canonicalization: bool,
pub(super) features: Option<Box<wasmer_features_t>>,
pub(super) target: Option<Box<wasmer_target_t>>,
}
Expand Down Expand Up @@ -482,6 +483,10 @@ pub extern "C" fn wasm_engine_new_with_config(
compiler_config.push_middleware(middleware.inner);
}

if config.nan_canonicalization {
compiler_config.canonicalize_nans(true);
}

let inner: Arc<dyn Engine + Send + Sync> = match config.engine {
wasmer_engine_t::JIT => {
cfg_if! {
Expand Down
39 changes: 39 additions & 0 deletions lib/c-api/src/wasm_c_api/unstable/engine.rs
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,45 @@ pub extern "C" fn wasm_config_set_features(
config.features = Some(features);
}

/// Updates the configuration to enable NaN canonicalization.
///
/// This is a Wasmer-specific function.
///
/// # Example
///
/// ```rust
/// # use inline_c::assert_c;
/// # fn main() {
/// # (assert_c! {
/// # #include "tests/wasmer_wasm.h"
/// #
/// int main() {
/// // Create the configuration.
/// wasm_config_t* config = wasm_config_new();
///
/// // Enable NaN canonicalization.
/// wasm_config_canonicalize_nans(config, true);
///
/// // Create the engine.
/// wasm_engine_t* engine = wasm_engine_new_with_config(config);
///
/// // Check we have an engine!
/// assert(engine);
///
/// // Free everything.
/// wasm_engine_delete(engine);
///
/// return 0;
/// }
/// # })
/// # .success();
/// # }
/// ```
#[no_mangle]
pub extern "C" fn wasm_config_canonicalize_nans(config: &mut wasm_config_t, enable: bool) {
config.nan_canonicalization = enable;
}

/// Check whether the given compiler is available, i.e. part of this
/// compiled library.
#[no_mangle]
Expand Down
2 changes: 2 additions & 0 deletions lib/c-api/wasmer_wasm.h
Original file line number Diff line number Diff line change
Expand Up @@ -772,6 +772,8 @@ bool wasi_get_unordered_imports(const wasm_store_t *store,
enum wasi_version_t wasi_get_wasi_version(const wasm_module_t *module);
#endif

void wasm_config_canonicalize_nans(wasm_config_t *config, bool enable);

void wasm_config_push_middleware(wasm_config_t *config, struct wasmer_middleware_t *middleware);

#if defined(WASMER_COMPILER_ENABLED)
Expand Down
17 changes: 8 additions & 9 deletions lib/compiler-cranelift/src/config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -53,15 +53,6 @@ impl Cranelift {
}
}

/// Enable NaN canonicalization.
///
/// NaN canonicalization is useful when trying to run WebAssembly
/// deterministically across different architectures.
pub fn canonicalize_nans(&mut self, enable: bool) -> &mut Self {
self.enable_nan_canonicalization = enable;
self
}

/// Enable SIMD support.
pub fn enable_simd(&mut self, enable: bool) -> &mut Self {
self.enable_simd = enable;
Expand Down Expand Up @@ -197,6 +188,14 @@ impl CompilerConfig for Cranelift {
self.enable_verifier = true;
}

fn enable_nan_canonicalization(&mut self) {
self.enable_nan_canonicalization = true;
}

fn canonicalize_nans(&mut self, enable: bool) {
self.enable_nan_canonicalization = enable;
}

/// Transform it into the compiler
fn compiler(self: Box<Self>) -> Box<dyn Compiler> {
Box::new(CraneliftCompiler::new(*self))
Expand Down
3 changes: 2 additions & 1 deletion lib/compiler-llvm/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,8 @@ rayon = "1.5"
loupe = "0.1"

[dependencies.inkwell]
version = "=0.1.0-beta.2"
git = "https://github.com/wasmerio/inkwell"
branch = "add-metadata-support"
default-features = false
features = ["llvm11-0", "target-x86", "target-aarch64"]

Expand Down
18 changes: 9 additions & 9 deletions lib/compiler-llvm/src/config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -65,15 +65,6 @@ impl LLVM {
}
}

/// Enable NaN canonicalization.
///
/// NaN canonicalization is useful when trying to run WebAssembly
/// deterministically across different architectures.
pub fn canonicalize_nans(&mut self, enable: bool) -> &mut Self {
self.enable_nan_canonicalization = enable;
self
}

/// The optimization levels when optimizing the IR.
pub fn opt_level(&mut self, opt_level: LLVMOptLevel) -> &mut Self {
self.opt_level = opt_level;
Expand Down Expand Up @@ -209,6 +200,15 @@ impl CompilerConfig for LLVM {
self.enable_verifier = true;
}

/// Enable NaN canonicalization.
fn enable_nan_canonicalization(&mut self) {
self.enable_nan_canonicalization = true;
}

fn canonicalize_nans(&mut self, enable: bool) {
self.enable_nan_canonicalization = enable;
}

/// Transform it into the compiler.
fn compiler(self: Box<Self>) -> Box<dyn Compiler> {
Box::new(LLVMCompiler::new(*self))
Expand Down
Loading

0 comments on commit 22bf49b

Please sign in to comment.