1//===-- ExecutionEngineBindings.cpp - C bindings for EEs ------------------===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is distributed under the University of Illinois Open Source 6// License. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9// 10// This file defines the C bindings for the ExecutionEngine library. 11// 12//===----------------------------------------------------------------------===// 13 14#include "llvm-c/ExecutionEngine.h" 15#include "llvm/ExecutionEngine/ExecutionEngine.h" 16#include "llvm/ExecutionEngine/GenericValue.h" 17#include "llvm/ExecutionEngine/RTDyldMemoryManager.h" 18#include "llvm/IR/DerivedTypes.h" 19#include "llvm/IR/Module.h" 20#include "llvm/Support/CodeGenCWrappers.h" 21#include "llvm/Support/ErrorHandling.h" 22#include "llvm/Target/TargetOptions.h" 23#include <cstring> 24 25using namespace llvm; 26 27#define DEBUG_TYPE "jit" 28 29// Wrapping the C bindings types. 30DEFINE_SIMPLE_CONVERSION_FUNCTIONS(GenericValue, LLVMGenericValueRef) 31 32 33static LLVMTargetMachineRef wrap(const TargetMachine *P) { 34 return 35 reinterpret_cast<LLVMTargetMachineRef>(const_cast<TargetMachine*>(P)); 36} 37 38/*===-- Operations on generic values --------------------------------------===*/ 39 40LLVMGenericValueRef LLVMCreateGenericValueOfInt(LLVMTypeRef Ty, 41 unsigned long long N, 42 LLVMBool IsSigned) { 43 GenericValue *GenVal = new GenericValue(); 44 GenVal->IntVal = APInt(unwrap<IntegerType>(Ty)->getBitWidth(), N, IsSigned); 45 return wrap(GenVal); 46} 47 48LLVMGenericValueRef LLVMCreateGenericValueOfPointer(void *P) { 49 GenericValue *GenVal = new GenericValue(); 50 GenVal->PointerVal = P; 51 return wrap(GenVal); 52} 53 54LLVMGenericValueRef LLVMCreateGenericValueOfFloat(LLVMTypeRef TyRef, double N) { 55 GenericValue *GenVal = new GenericValue(); 56 switch (unwrap(TyRef)->getTypeID()) { 57 case Type::FloatTyID: 58 GenVal->FloatVal = N; 59 break; 60 case Type::DoubleTyID: 61 GenVal->DoubleVal = N; 62 break; 63 default: 64 llvm_unreachable("LLVMGenericValueToFloat supports only float and double."); 65 } 66 return wrap(GenVal); 67} 68 69unsigned LLVMGenericValueIntWidth(LLVMGenericValueRef GenValRef) { 70 return unwrap(GenValRef)->IntVal.getBitWidth(); 71} 72 73unsigned long long LLVMGenericValueToInt(LLVMGenericValueRef GenValRef, 74 LLVMBool IsSigned) { 75 GenericValue *GenVal = unwrap(GenValRef); 76 if (IsSigned) 77 return GenVal->IntVal.getSExtValue(); 78 else 79 return GenVal->IntVal.getZExtValue(); 80} 81 82void *LLVMGenericValueToPointer(LLVMGenericValueRef GenVal) { 83 return unwrap(GenVal)->PointerVal; 84} 85 86double LLVMGenericValueToFloat(LLVMTypeRef TyRef, LLVMGenericValueRef GenVal) { 87 switch (unwrap(TyRef)->getTypeID()) { 88 case Type::FloatTyID: 89 return unwrap(GenVal)->FloatVal; 90 case Type::DoubleTyID: 91 return unwrap(GenVal)->DoubleVal; 92 default: 93 llvm_unreachable("LLVMGenericValueToFloat supports only float and double."); 94 } 95} 96 97void LLVMDisposeGenericValue(LLVMGenericValueRef GenVal) { 98 delete unwrap(GenVal); 99} 100 101/*===-- Operations on execution engines -----------------------------------===*/ 102 103LLVMBool LLVMCreateExecutionEngineForModule(LLVMExecutionEngineRef *OutEE, 104 LLVMModuleRef M, 105 char **OutError) { 106 std::string Error; 107 EngineBuilder builder(std::unique_ptr<Module>(unwrap(M))); 108 builder.setEngineKind(EngineKind::Either) 109 .setErrorStr(&Error); 110 if (ExecutionEngine *EE = builder.create()){ 111 *OutEE = wrap(EE); 112 return 0; 113 } 114 *OutError = strdup(Error.c_str()); 115 return 1; 116} 117 118LLVMBool LLVMCreateInterpreterForModule(LLVMExecutionEngineRef *OutInterp, 119 LLVMModuleRef M, 120 char **OutError) { 121 std::string Error; 122 EngineBuilder builder(std::unique_ptr<Module>(unwrap(M))); 123 builder.setEngineKind(EngineKind::Interpreter) 124 .setErrorStr(&Error); 125 if (ExecutionEngine *Interp = builder.create()) { 126 *OutInterp = wrap(Interp); 127 return 0; 128 } 129 *OutError = strdup(Error.c_str()); 130 return 1; 131} 132 133LLVMBool LLVMCreateJITCompilerForModule(LLVMExecutionEngineRef *OutJIT, 134 LLVMModuleRef M, 135 unsigned OptLevel, 136 char **OutError) { 137 std::string Error; 138 EngineBuilder builder(std::unique_ptr<Module>(unwrap(M))); 139 builder.setEngineKind(EngineKind::JIT) 140 .setErrorStr(&Error) 141 .setOptLevel((CodeGenOpt::Level)OptLevel); 142 if (ExecutionEngine *JIT = builder.create()) { 143 *OutJIT = wrap(JIT); 144 return 0; 145 } 146 *OutError = strdup(Error.c_str()); 147 return 1; 148} 149 150void LLVMInitializeMCJITCompilerOptions(LLVMMCJITCompilerOptions *PassedOptions, 151 size_t SizeOfPassedOptions) { 152 LLVMMCJITCompilerOptions options; 153 memset(&options, 0, sizeof(options)); // Most fields are zero by default. 154 options.CodeModel = LLVMCodeModelJITDefault; 155 156 memcpy(PassedOptions, &options, 157 std::min(sizeof(options), SizeOfPassedOptions)); 158} 159 160LLVMBool LLVMCreateMCJITCompilerForModule( 161 LLVMExecutionEngineRef *OutJIT, LLVMModuleRef M, 162 LLVMMCJITCompilerOptions *PassedOptions, size_t SizeOfPassedOptions, 163 char **OutError) { 164 LLVMMCJITCompilerOptions options; 165 // If the user passed a larger sized options struct, then they were compiled 166 // against a newer LLVM. Tell them that something is wrong. 167 if (SizeOfPassedOptions > sizeof(options)) { 168 *OutError = strdup( 169 "Refusing to use options struct that is larger than my own; assuming " 170 "LLVM library mismatch."); 171 return 1; 172 } 173 174 // Defend against the user having an old version of the API by ensuring that 175 // any fields they didn't see are cleared. We must defend against fields being 176 // set to the bitwise equivalent of zero, and assume that this means "do the 177 // default" as if that option hadn't been available. 178 LLVMInitializeMCJITCompilerOptions(&options, sizeof(options)); 179 memcpy(&options, PassedOptions, SizeOfPassedOptions); 180 181 TargetOptions targetOptions; 182 targetOptions.EnableFastISel = options.EnableFastISel; 183 std::unique_ptr<Module> Mod(unwrap(M)); 184 185 if (Mod) 186 // Set function attribute "no-frame-pointer-elim" based on 187 // NoFramePointerElim. 188 for (auto &F : *Mod) { 189 auto Attrs = F.getAttributes(); 190 auto Value = options.NoFramePointerElim ? "true" : "false"; 191 Attrs = Attrs.addAttribute(F.getContext(), AttributeSet::FunctionIndex, 192 "no-frame-pointer-elim", Value); 193 F.setAttributes(Attrs); 194 } 195 196 std::string Error; 197 EngineBuilder builder(std::move(Mod)); 198 builder.setEngineKind(EngineKind::JIT) 199 .setErrorStr(&Error) 200 .setOptLevel((CodeGenOpt::Level)options.OptLevel) 201 .setCodeModel(unwrap(options.CodeModel)) 202 .setTargetOptions(targetOptions); 203 if (options.MCJMM) 204 builder.setMCJITMemoryManager( 205 std::unique_ptr<RTDyldMemoryManager>(unwrap(options.MCJMM))); 206 if (ExecutionEngine *JIT = builder.create()) { 207 *OutJIT = wrap(JIT); 208 return 0; 209 } 210 *OutError = strdup(Error.c_str()); 211 return 1; 212} 213 214void LLVMDisposeExecutionEngine(LLVMExecutionEngineRef EE) { 215 delete unwrap(EE); 216} 217 218void LLVMRunStaticConstructors(LLVMExecutionEngineRef EE) { 219 unwrap(EE)->finalizeObject(); 220 unwrap(EE)->runStaticConstructorsDestructors(false); 221} 222 223void LLVMRunStaticDestructors(LLVMExecutionEngineRef EE) { 224 unwrap(EE)->finalizeObject(); 225 unwrap(EE)->runStaticConstructorsDestructors(true); 226} 227 228int LLVMRunFunctionAsMain(LLVMExecutionEngineRef EE, LLVMValueRef F, 229 unsigned ArgC, const char * const *ArgV, 230 const char * const *EnvP) { 231 unwrap(EE)->finalizeObject(); 232 233 std::vector<std::string> ArgVec(ArgV, ArgV + ArgC); 234 return unwrap(EE)->runFunctionAsMain(unwrap<Function>(F), ArgVec, EnvP); 235} 236 237LLVMGenericValueRef LLVMRunFunction(LLVMExecutionEngineRef EE, LLVMValueRef F, 238 unsigned NumArgs, 239 LLVMGenericValueRef *Args) { 240 unwrap(EE)->finalizeObject(); 241 242 std::vector<GenericValue> ArgVec; 243 ArgVec.reserve(NumArgs); 244 for (unsigned I = 0; I != NumArgs; ++I) 245 ArgVec.push_back(*unwrap(Args[I])); 246 247 GenericValue *Result = new GenericValue(); 248 *Result = unwrap(EE)->runFunction(unwrap<Function>(F), ArgVec); 249 return wrap(Result); 250} 251 252void LLVMFreeMachineCodeForFunction(LLVMExecutionEngineRef EE, LLVMValueRef F) { 253} 254 255void LLVMAddModule(LLVMExecutionEngineRef EE, LLVMModuleRef M){ 256 unwrap(EE)->addModule(std::unique_ptr<Module>(unwrap(M))); 257} 258 259LLVMBool LLVMRemoveModule(LLVMExecutionEngineRef EE, LLVMModuleRef M, 260 LLVMModuleRef *OutMod, char **OutError) { 261 Module *Mod = unwrap(M); 262 unwrap(EE)->removeModule(Mod); 263 *OutMod = wrap(Mod); 264 return 0; 265} 266 267LLVMBool LLVMFindFunction(LLVMExecutionEngineRef EE, const char *Name, 268 LLVMValueRef *OutFn) { 269 if (Function *F = unwrap(EE)->FindFunctionNamed(Name)) { 270 *OutFn = wrap(F); 271 return 0; 272 } 273 return 1; 274} 275 276void *LLVMRecompileAndRelinkFunction(LLVMExecutionEngineRef EE, 277 LLVMValueRef Fn) { 278 return nullptr; 279} 280 281LLVMTargetDataRef LLVMGetExecutionEngineTargetData(LLVMExecutionEngineRef EE) { 282 return wrap(&unwrap(EE)->getDataLayout()); 283} 284 285LLVMTargetMachineRef 286LLVMGetExecutionEngineTargetMachine(LLVMExecutionEngineRef EE) { 287 return wrap(unwrap(EE)->getTargetMachine()); 288} 289 290void LLVMAddGlobalMapping(LLVMExecutionEngineRef EE, LLVMValueRef Global, 291 void* Addr) { 292 unwrap(EE)->addGlobalMapping(unwrap<GlobalValue>(Global), Addr); 293} 294 295void *LLVMGetPointerToGlobal(LLVMExecutionEngineRef EE, LLVMValueRef Global) { 296 unwrap(EE)->finalizeObject(); 297 298 return unwrap(EE)->getPointerToGlobal(unwrap<GlobalValue>(Global)); 299} 300 301uint64_t LLVMGetGlobalValueAddress(LLVMExecutionEngineRef EE, const char *Name) { 302 return unwrap(EE)->getGlobalValueAddress(Name); 303} 304 305uint64_t LLVMGetFunctionAddress(LLVMExecutionEngineRef EE, const char *Name) { 306 return unwrap(EE)->getFunctionAddress(Name); 307} 308 309/*===-- Operations on memory managers -------------------------------------===*/ 310 311namespace { 312 313struct SimpleBindingMMFunctions { 314 LLVMMemoryManagerAllocateCodeSectionCallback AllocateCodeSection; 315 LLVMMemoryManagerAllocateDataSectionCallback AllocateDataSection; 316 LLVMMemoryManagerFinalizeMemoryCallback FinalizeMemory; 317 LLVMMemoryManagerDestroyCallback Destroy; 318}; 319 320class SimpleBindingMemoryManager : public RTDyldMemoryManager { 321public: 322 SimpleBindingMemoryManager(const SimpleBindingMMFunctions& Functions, 323 void *Opaque); 324 ~SimpleBindingMemoryManager() override; 325 326 uint8_t *allocateCodeSection(uintptr_t Size, unsigned Alignment, 327 unsigned SectionID, 328 StringRef SectionName) override; 329 330 uint8_t *allocateDataSection(uintptr_t Size, unsigned Alignment, 331 unsigned SectionID, StringRef SectionName, 332 bool isReadOnly) override; 333 334 bool finalizeMemory(std::string *ErrMsg) override; 335 336private: 337 SimpleBindingMMFunctions Functions; 338 void *Opaque; 339}; 340 341SimpleBindingMemoryManager::SimpleBindingMemoryManager( 342 const SimpleBindingMMFunctions& Functions, 343 void *Opaque) 344 : Functions(Functions), Opaque(Opaque) { 345 assert(Functions.AllocateCodeSection && 346 "No AllocateCodeSection function provided!"); 347 assert(Functions.AllocateDataSection && 348 "No AllocateDataSection function provided!"); 349 assert(Functions.FinalizeMemory && 350 "No FinalizeMemory function provided!"); 351 assert(Functions.Destroy && 352 "No Destroy function provided!"); 353} 354 355SimpleBindingMemoryManager::~SimpleBindingMemoryManager() { 356 Functions.Destroy(Opaque); 357} 358 359uint8_t *SimpleBindingMemoryManager::allocateCodeSection( 360 uintptr_t Size, unsigned Alignment, unsigned SectionID, 361 StringRef SectionName) { 362 return Functions.AllocateCodeSection(Opaque, Size, Alignment, SectionID, 363 SectionName.str().c_str()); 364} 365 366uint8_t *SimpleBindingMemoryManager::allocateDataSection( 367 uintptr_t Size, unsigned Alignment, unsigned SectionID, 368 StringRef SectionName, bool isReadOnly) { 369 return Functions.AllocateDataSection(Opaque, Size, Alignment, SectionID, 370 SectionName.str().c_str(), 371 isReadOnly); 372} 373 374bool SimpleBindingMemoryManager::finalizeMemory(std::string *ErrMsg) { 375 char *errMsgCString = nullptr; 376 bool result = Functions.FinalizeMemory(Opaque, &errMsgCString); 377 assert((result || !errMsgCString) && 378 "Did not expect an error message if FinalizeMemory succeeded"); 379 if (errMsgCString) { 380 if (ErrMsg) 381 *ErrMsg = errMsgCString; 382 free(errMsgCString); 383 } 384 return result; 385} 386 387} // anonymous namespace 388 389LLVMMCJITMemoryManagerRef LLVMCreateSimpleMCJITMemoryManager( 390 void *Opaque, 391 LLVMMemoryManagerAllocateCodeSectionCallback AllocateCodeSection, 392 LLVMMemoryManagerAllocateDataSectionCallback AllocateDataSection, 393 LLVMMemoryManagerFinalizeMemoryCallback FinalizeMemory, 394 LLVMMemoryManagerDestroyCallback Destroy) { 395 396 if (!AllocateCodeSection || !AllocateDataSection || !FinalizeMemory || 397 !Destroy) 398 return nullptr; 399 400 SimpleBindingMMFunctions functions; 401 functions.AllocateCodeSection = AllocateCodeSection; 402 functions.AllocateDataSection = AllocateDataSection; 403 functions.FinalizeMemory = FinalizeMemory; 404 functions.Destroy = Destroy; 405 return wrap(new SimpleBindingMemoryManager(functions, Opaque)); 406} 407 408void LLVMDisposeMCJITMemoryManager(LLVMMCJITMemoryManagerRef MM) { 409 delete unwrap(MM); 410} 411 412