From 75d214a3b5fb213e708bd7f51ea47136c0af9ff2 Mon Sep 17 00:00:00 2001 From: Matt Witherspoon <32485495+spoonincode@users.noreply.github.com> Date: Thu, 7 Jan 2021 11:17:42 -0500 Subject: [PATCH] llvm 11 support for EOS VM OC --- CMakeLists.txt | 4 +-- .../webassembly/eos-vm-oc/LLVMEmitIR.cpp | 31 ++++++++++++------- .../chain/webassembly/eos-vm-oc/LLVMJIT.cpp | 1 + 3 files changed, 23 insertions(+), 13 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index de23e74c7d3..a268bcc4e10 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -73,8 +73,8 @@ if(CMAKE_SIZEOF_VOID_P EQUAL 8 AND NOT WIN32) # EOS VM OC requires LLVM, but move the check up here to a central location so that the EosioTester.cmakes # can be created with the exact version found find_package(LLVM REQUIRED CONFIG) - if(LLVM_VERSION_MAJOR VERSION_LESS 7 OR LLVM_VERSION_MAJOR VERSION_GREATER 10) - message(FATAL_ERROR "EOSIO requires an LLVM version 7.0 to 10.0") + if(LLVM_VERSION_MAJOR VERSION_LESS 7 OR LLVM_VERSION_MAJOR VERSION_GREATER_EQUAL 12) + message(FATAL_ERROR "EOSIO requires an LLVM version 7 through 11") endif() endif() endif() diff --git a/libraries/chain/webassembly/eos-vm-oc/LLVMEmitIR.cpp b/libraries/chain/webassembly/eos-vm-oc/LLVMEmitIR.cpp index 5423207b00f..0f4d953f30f 100644 --- a/libraries/chain/webassembly/eos-vm-oc/LLVMEmitIR.cpp +++ b/libraries/chain/webassembly/eos-vm-oc/LLVMEmitIR.cpp @@ -345,6 +345,13 @@ namespace LLVMJIT "eosvmoc_internal.div0_or_overflow",FunctionType::get(),{}); } + //llvm11 removed inferring the function type automatically, plumb CreateCalls through here as done for 10 & earlier + llvm::CallInst* createCall(llvm::Value* Callee, llvm::ArrayRef Args) { + auto* PTy = llvm::cast(Callee->getType()); + auto* FTy = llvm::cast(PTy->getElementType()); + return irBuilder.CreateCall(FTy, Callee, Args); + } + llvm::Value* getLLVMIntrinsic(const std::initializer_list& argTypes,llvm::Intrinsic::ID id) { return llvm::Intrinsic::getDeclaration(moduleContext.llvmModule,id,llvm::ArrayRef(argTypes.begin(),argTypes.end())); @@ -356,7 +363,7 @@ namespace LLVMJIT const eosio::chain::eosvmoc::intrinsic_entry& ie = eosio::chain::eosvmoc::get_intrinsic_map().at(intrinsicName); llvm::Value* ic = irBuilder.CreateLoad( emitLiteralPointer((void*)(OFFSET_OF_FIRST_INTRINSIC-ie.ordinal*8), llvmI64Type->getPointerTo(256)) ); llvm::Value* itp = irBuilder.CreateIntToPtr(ic, asLLVMType(ie.type)->getPointerTo()); - return irBuilder.CreateCall(itp,llvm::ArrayRef(args.begin(),args.end())); + return createCall(itp,llvm::ArrayRef(args.begin(),args.end())); } // A helper function to emit a conditional call to a non-returning intrinsic function. @@ -707,7 +714,7 @@ namespace LLVMJIT popMultiple(llvmArgs,calleeType->parameters.size()); // Call the function. - auto result = irBuilder.CreateCall(callee,llvm::ArrayRef(llvmArgs,calleeType->parameters.size())); + auto result = createCall(callee,llvm::ArrayRef(llvmArgs,calleeType->parameters.size())); if(isExit) { irBuilder.CreateUnreachable(); enterUnreachable(); @@ -758,7 +765,7 @@ namespace LLVMJIT llvm::Value* running_code_start = irBuilder.CreateLoad(emitLiteralPointer((void*)OFFSET_OF_CONTROL_BLOCK_MEMBER(running_code_base), llvmI64Type->getPointerTo(256))); llvm::Value* offset_from_start = irBuilder.CreateAdd(running_code_start, functionInfo); llvm::Value* ptr_cast = irBuilder.CreateIntToPtr(offset_from_start, functionPointerType); - auto result = irBuilder.CreateCall(ptr_cast,llvm::ArrayRef(llvmArgs,calleeType->parameters.size())); + auto result = createCall(ptr_cast,llvm::ArrayRef(llvmArgs,calleeType->parameters.size())); // Push the result on the operand stack. if(calleeType->ret != ResultType::none) { push(result); } @@ -795,7 +802,7 @@ namespace LLVMJIT PN->addIncoming(offset_from_start, is_code_offset_block); llvm::Value* ptr_cast = irBuilder.CreateIntToPtr(PN, functionPointerType); - auto result = irBuilder.CreateCall(ptr_cast,llvm::ArrayRef(llvmArgs,calleeType->parameters.size())); + auto result = createCall(ptr_cast,llvm::ArrayRef(llvmArgs,calleeType->parameters.size())); // Push the result on the operand stack. if(calleeType->ret != ResultType::none) { push(result); } @@ -900,8 +907,10 @@ namespace LLVMJIT #if LLVM_VERSION_MAJOR < 10 #define LOAD_STORE_ALIGNMENT_PARAM 1 -#else +#elif LLVM_VERSION_MAJOR == 10 #define LOAD_STORE_ALIGNMENT_PARAM llvm::MaybeAlign(1) +#else + #define LOAD_STORE_ALIGNMENT_PARAM llvm::Align(1) #endif EMIT_LOAD_OP(i32,load8_s,llvmI8Type,0,irBuilder.CreateSExt,LOAD_STORE_ALIGNMENT_PARAM) EMIT_LOAD_OP(i32,load8_u,llvmI8Type,0,irBuilder.CreateZExt,LOAD_STORE_ALIGNMENT_PARAM) @@ -1072,9 +1081,9 @@ namespace LLVMJIT EMIT_INT_BINARY_OP(ge_u, coerceBoolToI32(irBuilder.CreateICmpUGE(left, right))) #endif - EMIT_INT_UNARY_OP(clz,irBuilder.CreateCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::ctlz),llvm::ArrayRef({operand,emitLiteral(false)}))) - EMIT_INT_UNARY_OP(ctz,irBuilder.CreateCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::cttz),llvm::ArrayRef({operand,emitLiteral(false)}))) - EMIT_INT_UNARY_OP(popcnt,irBuilder.CreateCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::ctpop),llvm::ArrayRef({operand}))) + EMIT_INT_UNARY_OP(clz,createCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::ctlz),llvm::ArrayRef({operand,emitLiteral(false)}))) + EMIT_INT_UNARY_OP(ctz,createCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::cttz),llvm::ArrayRef({operand,emitLiteral(false)}))) + EMIT_INT_UNARY_OP(popcnt,createCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::ctpop),llvm::ArrayRef({operand}))) EMIT_INT_UNARY_OP(eqz,coerceBoolToI32(irBuilder.CreateICmpEQ(operand,typedZeroConstants[(Uptr)type]))) // @@ -1085,11 +1094,11 @@ namespace LLVMJIT EMIT_FP_BINARY_OP(sub,irBuilder.CreateFSub(left,right)) EMIT_FP_BINARY_OP(mul,irBuilder.CreateFMul(left,right)) EMIT_FP_BINARY_OP(div,irBuilder.CreateFDiv(left,right)) - EMIT_FP_BINARY_OP(copysign,irBuilder.CreateCall(getLLVMIntrinsic({left->getType()},llvm::Intrinsic::copysign),llvm::ArrayRef({left,right}))) + EMIT_FP_BINARY_OP(copysign,createCall(getLLVMIntrinsic({left->getType()},llvm::Intrinsic::copysign),llvm::ArrayRef({left,right}))) EMIT_FP_UNARY_OP(neg,irBuilder.CreateFNeg(operand)) - EMIT_FP_UNARY_OP(abs,irBuilder.CreateCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::fabs),llvm::ArrayRef({operand}))) - EMIT_FP_UNARY_OP(sqrt,irBuilder.CreateCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::sqrt),llvm::ArrayRef({operand}))) + EMIT_FP_UNARY_OP(abs,createCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::fabs),llvm::ArrayRef({operand}))) + EMIT_FP_UNARY_OP(sqrt,createCall(getLLVMIntrinsic({operand->getType()},llvm::Intrinsic::sqrt),llvm::ArrayRef({operand}))) EMIT_FP_BINARY_OP(eq,coerceBoolToI32(irBuilder.CreateFCmpOEQ(left,right))) EMIT_FP_BINARY_OP(ne,coerceBoolToI32(irBuilder.CreateFCmpUNE(left,right))) diff --git a/libraries/chain/webassembly/eos-vm-oc/LLVMJIT.cpp b/libraries/chain/webassembly/eos-vm-oc/LLVMJIT.cpp index 340e5bf5dca..8345beeb799 100644 --- a/libraries/chain/webassembly/eos-vm-oc/LLVMJIT.cpp +++ b/libraries/chain/webassembly/eos-vm-oc/LLVMJIT.cpp @@ -40,6 +40,7 @@ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND #include "llvm/Object/SymbolSize.h" #include "llvm/Support/Debug.h" #include "llvm/Support/DataTypes.h" +#include "llvm/Support/FileSystem.h" #include "llvm/Support/TargetSelect.h" #include "llvm/Support/Host.h" #include "llvm/Support/DynamicLibrary.h"