Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix WASMER_METADATA alignment in the dylib engine #2742

Merged
merged 3 commits into from Jan 4, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
1 change: 1 addition & 0 deletions Makefile
Expand Up @@ -575,6 +575,7 @@ test-wasi:
cargo test --release --tests $(compiler_features) -- wasi::wasitests

test-examples:
cargo test $(compiler_features) --features wasi --examples
cargo test --release $(compiler_features) --features wasi --examples

test-integration:
Expand Down
7 changes: 6 additions & 1 deletion examples/early_exit.rs
Expand Up @@ -16,7 +16,7 @@

use anyhow::bail;
use std::fmt;
use wasmer::{imports, wat2wasm, Function, Instance, Module, NativeFunc, RuntimeError, Store};
use wasmer::{imports, wat2wasm, Function, Instance, Module, NativeFunc, Store};
use wasmer_compiler_cranelift::Cranelift;
use wasmer_engine_universal::Universal;

Expand Down Expand Up @@ -107,3 +107,8 @@ fn main() -> anyhow::Result<()> {
},
}
}

#[test]
fn test_early_exit() -> anyhow::Result<()> {
main()
}
5 changes: 5 additions & 0 deletions examples/features.rs
Expand Up @@ -54,3 +54,8 @@ fn main() -> anyhow::Result<()> {

Ok(())
}

#[test]
fn test_features() -> anyhow::Result<()> {
main()
}
5 changes: 5 additions & 0 deletions examples/hello_world.rs
Expand Up @@ -85,3 +85,8 @@ fn main() -> anyhow::Result<()> {

Ok(())
}

#[test]
fn test_hello_world() -> anyhow::Result<()> {
main()
}
5 changes: 5 additions & 0 deletions examples/memory.rs
Expand Up @@ -137,3 +137,8 @@ fn main() -> anyhow::Result<()> {

Ok(())
}

#[test]
fn test_memory() -> anyhow::Result<()> {
main()
}
8 changes: 8 additions & 0 deletions examples/table.rs
Expand Up @@ -152,3 +152,11 @@ fn main() -> anyhow::Result<()> {

Ok(())
}

// This test is currently failing with:
// not implemented: Native function definitions can't be directly called from the host yet
#[cfg(FALSE)]
#[test]
fn test_table() -> anyhow::Result<()> {
main()
}
1 change: 1 addition & 0 deletions lib/compiler-llvm/src/compiler.rs
Expand Up @@ -172,6 +172,7 @@ impl LLVMCompiler {
metadata_gv.set_initializer(&metadata_init);
metadata_gv.set_linkage(Linkage::DLLExport);
metadata_gv.set_dll_storage_class(DLLStorageClass::Export);
metadata_gv.set_alignment(16);

if self.config().enable_verifier {
merged_module.verify().unwrap();
Expand Down
28 changes: 10 additions & 18 deletions lib/engine-dylib/src/artifact.rs
Expand Up @@ -2,7 +2,7 @@
//! to be done as separate steps.

use crate::engine::{DylibEngine, DylibEngineInner};
use crate::serialize::{ArchivedModuleMetadata, ModuleMetadata};
use crate::serialize::ModuleMetadata;
use enumset::EnumSet;
use libloading::{Library, Symbol as LibrarySymbol};
use loupe::MemoryUsage;
Expand Down Expand Up @@ -217,7 +217,7 @@ impl DylibArtifact {

let serialized_data = metadata.serialize()?;

let mut metadata_binary = vec![0; 12];
let mut metadata_binary = vec![0; 16];
let mut writable = &mut metadata_binary[..];
leb128::write::unsigned(&mut writable, serialized_data.len() as u64)
.expect("Should write number");
Expand Down Expand Up @@ -256,13 +256,8 @@ impl DylibArtifact {
function_body_inputs,
)?;
let mut obj = get_object_for_target(&target_triple).map_err(to_compile_error)?;
emit_data(
&mut obj,
WASMER_METADATA_SYMBOL,
&metadata_binary,
std::mem::align_of::<ArchivedModuleMetadata>() as u64,
)
.map_err(to_compile_error)?;
emit_data(&mut obj, WASMER_METADATA_SYMBOL, &metadata_binary, 16)
.map_err(to_compile_error)?;
emit_compilation(&mut obj, compilation, &symbol_registry, &target_triple)
.map_err(to_compile_error)?;
let file = tempfile::Builder::new()
Expand Down Expand Up @@ -623,27 +618,24 @@ impl DylibArtifact {
DeserializeError::CorruptedBinary(format!("Library loading failed: {}", e))
})?;
let shared_path: PathBuf = PathBuf::from(path);
// We use 12 + 1, as the length of the module will take 12 bytes
// (we construct it like that in `metadata_length`) and we also want
// to take the first element of the data to construct the slice from
// it.
let symbol: LibrarySymbol<*mut [u8; 12 + 1]> =
// We reserve 16 bytes for the length because the rest of the metadata
// needs to be aligned to 16 bytes.
let symbol: LibrarySymbol<*mut [u8; 16]> =
lib.get(WASMER_METADATA_SYMBOL).map_err(|e| {
DeserializeError::CorruptedBinary(format!(
"The provided object file doesn't seem to be generated by Wasmer: {}",
e
))
})?;
use std::ops::Deref;
use std::slice;

let size = &mut **symbol.deref();
let mut readable = &size[..];
let metadata = &**symbol;
let mut readable = &metadata[..];
let metadata_len = leb128::read::unsigned(&mut readable).map_err(|_e| {
DeserializeError::CorruptedBinary("Can't read metadata size".to_string())
})?;
let metadata_slice: &'static [u8] =
slice::from_raw_parts(&size[12] as *const u8, metadata_len as usize);
slice::from_raw_parts(metadata.as_ptr().add(16), metadata_len as usize);

let metadata = ModuleMetadata::deserialize(metadata_slice)?;

Expand Down