Skip to content

Commit

Permalink
Merge #1754
Browse files Browse the repository at this point in the history
1754: Implement aarch64 ABI for compiler-llvm. r=nlewycky a=nlewycky

With this PR, `make llvm-test-native` passes on our arm64 machine.

Co-authored-by: Nick Lewycky <nick@wasmer.io>
  • Loading branch information
bors[bot] and nlewycky authored Oct 23, 2020
2 parents a49c4e5 + e89b1c0 commit 7eddb46
Show file tree
Hide file tree
Showing 12 changed files with 1,457 additions and 799 deletions.
3 changes: 3 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,9 @@ endif

ifeq ($(ARCH), aarch64)
test_compilers_engines += cranelift-jit
ifneq (, $(findstring llvm,$(compilers)))
test_compilers_engines += llvm-native
endif
endif

compilers := $(filter-out ,$(compilers))
Expand Down
555 changes: 555 additions & 0 deletions lib/compiler-llvm/src/abi/aarch64_systemv.rs

Large diffs are not rendered by default.

85 changes: 85 additions & 0 deletions lib/compiler-llvm/src/abi/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
// LLVM implements part of the ABI lowering internally, but also requires that
// the user pack and unpack values themselves sometimes. This can help the LLVM
// optimizer by exposing operations to the optimizer, but it requires that the
// frontend know exactly what IR to produce in order to get the right ABI.

#![deny(dead_code, missing_docs)]

use crate::translator::intrinsics::Intrinsics;
use inkwell::{
attributes::{Attribute, AttributeLoc},
builder::Builder,
context::Context,
targets::TargetMachine,
types::FunctionType,
values::{BasicValueEnum, CallSiteValue, FunctionValue, PointerValue},
};
use wasmer_compiler::CompileError;
use wasmer_types::FunctionType as FuncSig;

mod aarch64_systemv;
mod x86_64_systemv;

use aarch64_systemv::Aarch64SystemV;
use x86_64_systemv::X86_64SystemV;

pub fn get_abi(target_machine: &TargetMachine) -> Box<dyn Abi> {
if target_machine
.get_triple()
.as_str()
.to_string_lossy()
.starts_with("aarch64")
{
Box::new(Aarch64SystemV {})
} else {
Box::new(X86_64SystemV {})
}
}

/// We need to produce different LLVM IR for different platforms. (Contrary to
/// popular knowledge LLVM IR is not intended to be portable in that way.) This
/// trait deals with differences between function signatures on different
/// targets.
pub trait Abi {
/// Given a function definition, retrieve the parameter that is the vmctx pointer.
fn get_vmctx_ptr_param<'ctx>(&self, func_value: &FunctionValue<'ctx>) -> PointerValue<'ctx>;

/// Given a wasm function type, produce an llvm function declaration.
fn func_type_to_llvm<'ctx>(
&self,
context: &'ctx Context,
intrinsics: &Intrinsics<'ctx>,
sig: &FuncSig,
) -> Result<(FunctionType<'ctx>, Vec<(Attribute, AttributeLoc)>), CompileError>;

/// Marshall wasm stack values into function parameters.
fn args_to_call<'ctx>(
&self,
alloca_builder: &Builder<'ctx>,
func_sig: &FuncSig,
ctx_ptr: PointerValue<'ctx>,
llvm_fn_ty: &FunctionType<'ctx>,
values: &[BasicValueEnum<'ctx>],
) -> Vec<BasicValueEnum<'ctx>>;

/// Given a CallSite, extract the returned values and return them in a Vec.
fn rets_from_call<'ctx>(
&self,
builder: &Builder<'ctx>,
intrinsics: &Intrinsics<'ctx>,
call_site: CallSiteValue<'ctx>,
func_sig: &FuncSig,
) -> Vec<BasicValueEnum<'ctx>>;

/// Whether the llvm equivalent of this wasm function has an `sret` attribute.
fn is_sret(&self, func_sig: &FuncSig) -> Result<bool, CompileError>;

/// Pack LLVM IR values representing individual wasm values into the return type for the function.
fn pack_values_for_register_return<'ctx>(
&self,
intrinsics: &Intrinsics<'ctx>,
builder: &Builder<'ctx>,
values: &[BasicValueEnum<'ctx>],
func_type: &FunctionType<'ctx>,
) -> Result<BasicValueEnum<'ctx>, CompileError>;
}
Loading

0 comments on commit 7eddb46

Please sign in to comment.