Merge branch 'feature/vm_refactor' of github.com:wasmerio/wasmer into feature/vm_refactor

This commit is contained in:
Lachlan Sneff 2019-01-08 16:04:25 -05:00
commit 55b7cae523
2 changed files with 38 additions and 35 deletions

View File

@ -73,14 +73,16 @@ pub mod converter {
} }
// Compile functions. // Compile functions.
// TODO: Rearrange, Abstract
use crate::runtime::vmcalls::{memory_grow_static, memory_size}; use crate::runtime::vmcalls::{memory_grow_static, memory_size};
use crate::webassembly::{ use crate::webassembly::{
get_isa, libcalls, get_isa, libcalls,
relocation::{Reloc, RelocSink, Relocation, RelocationType}, relocation::{Reloc, RelocSink, Relocation, RelocationType},
}; };
use cranelift_codegen::{binemit::NullTrapSink, ir::LibCall, isa::TargetIsa, Context}; use cranelift_codegen::{binemit::NullTrapSink, ir::LibCall, Context};
use std::ptr::write_unaligned; use std::ptr::write_unaligned;
// Get the machine ISA.
let isa = &*get_isa(); let isa = &*get_isa();
let functions_length = cranelift_module.function_bodies.len(); let functions_length = cranelift_module.function_bodies.len();
@ -95,37 +97,38 @@ pub mod converter {
let mut trap_sink = NullTrapSink {}; let mut trap_sink = NullTrapSink {};
// Compile IR to machine code. // Compile IR to machine code.
func_context let result = func_context.compile_and_emit(isa, &mut code_buf, &mut reloc_sink, &mut trap_sink);
.compile_and_emit(isa, &mut code_buf, &mut reloc_sink, &mut trap_sink) if result.is_err() {
.map_err(|e| { panic!("CompileError: {}", result.unwrap_err().to_string());
panic!("CompileError: {}", e.to_string()); }
});
unsafe { unsafe {
// Make code buffer executable. // Make code buffer executable.
region::protect( let result = region::protect(
code_buf.as_ptr(), code_buf.as_ptr(),
code_buf.len(), code_buf.len(),
region::Protection::ReadWriteExecute, region::Protection::ReadWriteExecute,
) );
.map_err(|e| {
if result.is_err() {
panic!( panic!(
"failed to give executable permission to code: {}", "failed to give executable permission to code: {}",
e.to_string() result.unwrap_err().to_string()
); );
}); }
} }
// Push // Push compiled functions and relocations
compiled_functions.push(code_buf); compiled_functions.push(code_buf);
relocations.push(reloc_sink.func_relocs); relocations.push(reloc_sink.func_relocs);
} }
// Apply relocations.
for (index, relocs) in relocations.iter().enumerate() { for (index, relocs) in relocations.iter().enumerate() {
for ref reloc in relocs { for ref reloc in relocs {
let target_func_address: isize = match reloc.target { let target_func_address: isize = match reloc.target {
RelocationType::Normal(func_index) => { RelocationType::Normal(func_index) => {
compiled_functions[index].as_ptr() as isize compiled_functions[func_index as usize].as_ptr() as isize
} }
RelocationType::CurrentMemory => memory_size as isize, RelocationType::CurrentMemory => memory_size as isize,
RelocationType::GrowMemory => memory_grow_static as isize, RelocationType::GrowMemory => memory_grow_static as isize,
@ -148,10 +151,9 @@ pub mod converter {
} }
}; };
// ???
let func_addr = compiled_functions[index].as_ptr(); let func_addr = compiled_functions[index].as_ptr();
// Determine relocation type and apply relocation // Determine relocation type and apply relocations.
match reloc.reloc { match reloc.reloc {
Reloc::Abs8 => unsafe { Reloc::Abs8 => unsafe {
let reloc_address = func_addr.offset(reloc.offset as isize) as i64; let reloc_address = func_addr.offset(reloc.offset as isize) as i64;
@ -172,9 +174,6 @@ pub mod converter {
} }
} }
// Create func_resolver.
let func_resolver = Box::new(CraneliftFunctionResolver::new());
// Get other fields from the cranelift_module. // Get other fields from the cranelift_module.
let CraneliftModule { let CraneliftModule {
imported_functions, imported_functions,
@ -190,7 +189,7 @@ pub mod converter {
// Create Wasmer module from data above // Create Wasmer module from data above
WasmerModule { WasmerModule {
func_resolver, func_resolver: Box::new(CraneliftFunctionResolver::new(compiled_functions)),
memories, memories,
globals, globals,
tables, tables,
@ -392,20 +391,35 @@ impl CraneliftModule {
} }
// Resolves a function index to a function address. // Resolves a function index to a function address.
pub struct CraneliftFunctionResolver {} pub struct CraneliftFunctionResolver {
compiled_functions: Vec<Vec<u8>>,
}
impl CraneliftFunctionResolver { impl CraneliftFunctionResolver {
fn new() -> Self { fn new(compiled_functions: Vec<Vec<u8>>) -> Self {
Self {} Self {
compiled_functions,
}
} }
} }
// Implements FuncResolver trait. // Implements FuncResolver trait.
impl FuncResolver for CraneliftFunctionResolver { impl FuncResolver for CraneliftFunctionResolver {
// NOTE: This gets internal defined functions only. Will need access to vmctx to return imported function address.
fn get(&self, module: &WasmerModule, index: WasmerFuncIndex) -> Option<NonNull<vm::Func>> { fn get(&self, module: &WasmerModule, index: WasmerFuncIndex) -> Option<NonNull<vm::Func>> {
let index = index.index();
let imported_functions_length = module.imported_functions.len();
let internal_functions_length = self.compiled_functions.len();
let limit = imported_functions_length + internal_functions_length;
// Making sure it is not an imported function.
if index >= imported_functions_length && index < limit {
Some(NonNull::new(self.compiled_functions[index].as_ptr() as *mut _).unwrap())
} else {
None None
} }
} }
}
/// The `FuncEnvironment` implementation for use by the `CraneliftModule`. /// The `FuncEnvironment` implementation for use by the `CraneliftModule`.
pub struct FuncEnvironment<'environment> { pub struct FuncEnvironment<'environment> {

View File

@ -307,16 +307,5 @@ macro_rules! define_map_index {
}; };
} }
define_map_index![FuncIndex, MemoryIndex, TableIndex, SigIndex,]; define_map_index![GlobalIndex, FuncIndex, MemoryIndex, TableIndex, SigIndex,];
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
pub struct GlobalIndex(u32);
impl MapIndex for GlobalIndex {
fn new(index: usize) -> Self {
GlobalIndex(index as _)
}
fn index(&self) -> usize {
self.0 as usize
}
}