1857c21b4SMisha Brukman //===-- ExecutionEngine.cpp - Common Implementation shared by EEs ---------===// 2996fe010SChris Lattner // 3482202a6SJohn Criswell // The LLVM Compiler Infrastructure 4482202a6SJohn Criswell // 5482202a6SJohn Criswell // This file was developed by the LLVM research group and is distributed under 6482202a6SJohn Criswell // the University of Illinois Open Source License. See LICENSE.TXT for details. 7482202a6SJohn Criswell // 8482202a6SJohn Criswell //===----------------------------------------------------------------------===// 9482202a6SJohn Criswell // 10996fe010SChris Lattner // This file defines the common interface used by the various execution engine 11996fe010SChris Lattner // subclasses. 12996fe010SChris Lattner // 13996fe010SChris Lattner //===----------------------------------------------------------------------===// 14996fe010SChris Lattner 15ee937c80SChris Lattner #define DEBUG_TYPE "jit" 16ad481312SChris Lattner #include "Interpreter/Interpreter.h" 1732ccf7e1SChris Lattner #include "JIT/JIT.h" 18996fe010SChris Lattner #include "llvm/Constants.h" 19260b0c88SMisha Brukman #include "llvm/DerivedTypes.h" 20996fe010SChris Lattner #include "llvm/Module.h" 21260b0c88SMisha Brukman #include "llvm/ModuleProvider.h" 224c96b088SChris Lattner #include "llvm/CodeGen/IntrinsicLowering.h" 23260b0c88SMisha Brukman #include "llvm/ExecutionEngine/ExecutionEngine.h" 24ad481312SChris Lattner #include "llvm/ExecutionEngine/GenericValue.h" 25996fe010SChris Lattner #include "llvm/Target/TargetData.h" 26ad481312SChris Lattner #include "Support/Debug.h" 27ad481312SChris Lattner #include "Support/Statistic.h" 28e8bbcfc2SBrian Gaeke #include "Support/DynamicLinker.h" 2929681deeSChris Lattner using namespace llvm; 30996fe010SChris Lattner 3129681deeSChris Lattner namespace { 32996fe010SChris Lattner Statistic<> NumInitBytes("lli", "Number of bytes of global vars initialized"); 336bbe3eceSChris Lattner Statistic<> NumGlobals ("lli", "Number of global vars initialized"); 3429681deeSChris Lattner } 35996fe010SChris Lattner 36260b0c88SMisha Brukman ExecutionEngine::ExecutionEngine(ModuleProvider *P) : 37260b0c88SMisha Brukman CurMod(*P->getModule()), MP(P) { 38260b0c88SMisha Brukman assert(P && "ModuleProvider is null?"); 39260b0c88SMisha Brukman } 40260b0c88SMisha Brukman 41260b0c88SMisha Brukman ExecutionEngine::ExecutionEngine(Module *M) : CurMod(*M), MP(0) { 42260b0c88SMisha Brukman assert(M && "Module is null?"); 43260b0c88SMisha Brukman } 44260b0c88SMisha Brukman 4592f8b30dSBrian Gaeke ExecutionEngine::~ExecutionEngine() { 462f1e2002SMisha Brukman delete MP; 4792f8b30dSBrian Gaeke } 4892f8b30dSBrian Gaeke 49748e8579SChris Lattner /// getGlobalValueAtAddress - Return the LLVM global value object that starts 50748e8579SChris Lattner /// at the specified address. 51748e8579SChris Lattner /// 52748e8579SChris Lattner const GlobalValue *ExecutionEngine::getGlobalValueAtAddress(void *Addr) { 53748e8579SChris Lattner // If we haven't computed the reverse mapping yet, do so first. 54748e8579SChris Lattner if (GlobalAddressReverseMap.empty()) { 55748e8579SChris Lattner for (std::map<const GlobalValue*, void *>::iterator I = 56748e8579SChris Lattner GlobalAddressMap.begin(), E = GlobalAddressMap.end(); I != E; ++I) 57748e8579SChris Lattner GlobalAddressReverseMap.insert(std::make_pair(I->second, I->first)); 58748e8579SChris Lattner } 59748e8579SChris Lattner 60748e8579SChris Lattner std::map<void *, const GlobalValue*>::iterator I = 61748e8579SChris Lattner GlobalAddressReverseMap.find(Addr); 62748e8579SChris Lattner return I != GlobalAddressReverseMap.end() ? I->second : 0; 63748e8579SChris Lattner } 645a0d4829SChris Lattner 655a0d4829SChris Lattner // CreateArgv - Turn a vector of strings into a nice argv style array of 665a0d4829SChris Lattner // pointers to null terminated strings. 675a0d4829SChris Lattner // 685a0d4829SChris Lattner static void *CreateArgv(ExecutionEngine *EE, 695a0d4829SChris Lattner const std::vector<std::string> &InputArgv) { 705a0d4829SChris Lattner unsigned PtrSize = EE->getTargetData().getPointerSize(); 715a0d4829SChris Lattner char *Result = new char[(InputArgv.size()+1)*PtrSize]; 725a0d4829SChris Lattner 735a0d4829SChris Lattner DEBUG(std::cerr << "ARGV = " << (void*)Result << "\n"); 745a0d4829SChris Lattner const Type *SBytePtr = PointerType::get(Type::SByteTy); 755a0d4829SChris Lattner 765a0d4829SChris Lattner for (unsigned i = 0; i != InputArgv.size(); ++i) { 775a0d4829SChris Lattner unsigned Size = InputArgv[i].size()+1; 785a0d4829SChris Lattner char *Dest = new char[Size]; 795a0d4829SChris Lattner DEBUG(std::cerr << "ARGV[" << i << "] = " << (void*)Dest << "\n"); 805a0d4829SChris Lattner 815a0d4829SChris Lattner std::copy(InputArgv[i].begin(), InputArgv[i].end(), Dest); 825a0d4829SChris Lattner Dest[Size-1] = 0; 835a0d4829SChris Lattner 845a0d4829SChris Lattner // Endian safe: Result[i] = (PointerTy)Dest; 855a0d4829SChris Lattner EE->StoreValueToMemory(PTOGV(Dest), (GenericValue*)(Result+i*PtrSize), 865a0d4829SChris Lattner SBytePtr); 875a0d4829SChris Lattner } 885a0d4829SChris Lattner 895a0d4829SChris Lattner // Null terminate it 905a0d4829SChris Lattner EE->StoreValueToMemory(PTOGV(0), 915a0d4829SChris Lattner (GenericValue*)(Result+InputArgv.size()*PtrSize), 925a0d4829SChris Lattner SBytePtr); 935a0d4829SChris Lattner return Result; 945a0d4829SChris Lattner } 955a0d4829SChris Lattner 965a0d4829SChris Lattner /// runFunctionAsMain - This is a helper function which wraps runFunction to 975a0d4829SChris Lattner /// handle the common task of starting up main with the specified argc, argv, 985a0d4829SChris Lattner /// and envp parameters. 995a0d4829SChris Lattner int ExecutionEngine::runFunctionAsMain(Function *Fn, 1005a0d4829SChris Lattner const std::vector<std::string> &argv, 1015a0d4829SChris Lattner const char * const * envp) { 1025a0d4829SChris Lattner std::vector<GenericValue> GVArgs; 1035a0d4829SChris Lattner GenericValue GVArgc; 1045a0d4829SChris Lattner GVArgc.IntVal = argv.size(); 1055a0d4829SChris Lattner GVArgs.push_back(GVArgc); // Arg #0 = argc. 1065a0d4829SChris Lattner GVArgs.push_back(PTOGV(CreateArgv(this, argv))); // Arg #1 = argv. 1075a0d4829SChris Lattner assert(((char **)GVTOP(GVArgs[1]))[0] && "argv[0] was null after CreateArgv"); 1085a0d4829SChris Lattner 1095a0d4829SChris Lattner std::vector<std::string> EnvVars; 1105a0d4829SChris Lattner for (unsigned i = 0; envp[i]; ++i) 1115a0d4829SChris Lattner EnvVars.push_back(envp[i]); 1125a0d4829SChris Lattner GVArgs.push_back(PTOGV(CreateArgv(this, EnvVars))); // Arg #2 = envp. 1135a0d4829SChris Lattner return runFunction(Fn, GVArgs).IntVal; 1145a0d4829SChris Lattner } 1155a0d4829SChris Lattner 1165a0d4829SChris Lattner 1175a0d4829SChris Lattner 118260b0c88SMisha Brukman /// If possible, create a JIT, unless the caller specifically requests an 119260b0c88SMisha Brukman /// Interpreter or there's an error. If even an Interpreter cannot be created, 120260b0c88SMisha Brukman /// NULL is returned. 121857c21b4SMisha Brukman /// 1222f1e2002SMisha Brukman ExecutionEngine *ExecutionEngine::create(ModuleProvider *MP, 123c8c6c03dSChris Lattner bool ForceInterpreter, 124c8c6c03dSChris Lattner IntrinsicLowering *IL) { 1254bd3bd5bSBrian Gaeke ExecutionEngine *EE = 0; 1264bd3bd5bSBrian Gaeke 127c8c6c03dSChris Lattner // Unless the interpreter was explicitly selected, try making a JIT. 12865cd5048SBrian Gaeke if (!ForceInterpreter) 129c8c6c03dSChris Lattner EE = JIT::create(MP, IL); 1304bd3bd5bSBrian Gaeke 1314bd3bd5bSBrian Gaeke // If we can't make a JIT, make an interpreter instead. 13293f7c408SChris Lattner if (EE == 0) { 133260b0c88SMisha Brukman try { 13493f7c408SChris Lattner Module *M = MP->materializeModule(); 13593f7c408SChris Lattner try { 13693f7c408SChris Lattner EE = Interpreter::create(M, IL); 137260b0c88SMisha Brukman } catch (...) { 13893f7c408SChris Lattner std::cerr << "Error creating the interpreter!\n"; 13993f7c408SChris Lattner } 1406967cd54SReid Spencer } catch (std::string& errmsg) { 1416967cd54SReid Spencer std::cerr << "Error reading the bytecode file: " << errmsg << "\n"; 14293f7c408SChris Lattner } catch (...) { 14393f7c408SChris Lattner std::cerr << "Error reading the bytecode file!\n"; 14493f7c408SChris Lattner } 145260b0c88SMisha Brukman } 146c8c6c03dSChris Lattner 147c8c6c03dSChris Lattner if (EE == 0) delete IL; 1484bd3bd5bSBrian Gaeke return EE; 1494bd3bd5bSBrian Gaeke } 1504bd3bd5bSBrian Gaeke 151857c21b4SMisha Brukman /// getPointerToGlobal - This returns the address of the specified global 152857c21b4SMisha Brukman /// value. This may involve code generation if it's a function. 153857c21b4SMisha Brukman /// 154996fe010SChris Lattner void *ExecutionEngine::getPointerToGlobal(const GlobalValue *GV) { 1551678e859SBrian Gaeke if (Function *F = const_cast<Function*>(dyn_cast<Function>(GV))) 156996fe010SChris Lattner return getPointerToFunction(F); 157996fe010SChris Lattner 158748e8579SChris Lattner assert(GlobalAddressMap[GV] && "Global hasn't had an address allocated yet?"); 159748e8579SChris Lattner return GlobalAddressMap[GV]; 160996fe010SChris Lattner } 161996fe010SChris Lattner 162857c21b4SMisha Brukman /// FIXME: document 163857c21b4SMisha Brukman /// 164996fe010SChris Lattner GenericValue ExecutionEngine::getConstantValue(const Constant *C) { 165996fe010SChris Lattner GenericValue Result; 1669de0d14dSChris Lattner 16768cbcc3eSChris Lattner if (ConstantExpr *CE = const_cast<ConstantExpr*>(dyn_cast<ConstantExpr>(C))) { 1689de0d14dSChris Lattner switch (CE->getOpcode()) { 1699de0d14dSChris Lattner case Instruction::GetElementPtr: { 17068cbcc3eSChris Lattner Result = getConstantValue(CE->getOperand(0)); 1719de0d14dSChris Lattner std::vector<Value*> Indexes(CE->op_begin()+1, CE->op_end()); 1729de0d14dSChris Lattner uint64_t Offset = 1739de0d14dSChris Lattner TD->getIndexedOffset(CE->getOperand(0)->getType(), Indexes); 1749de0d14dSChris Lattner 1759de0d14dSChris Lattner Result.LongVal += Offset; 1769de0d14dSChris Lattner return Result; 1779de0d14dSChris Lattner } 17868cbcc3eSChris Lattner case Instruction::Cast: { 17968cbcc3eSChris Lattner // We only need to handle a few cases here. Almost all casts will 18068cbcc3eSChris Lattner // automatically fold, just the ones involving pointers won't. 18168cbcc3eSChris Lattner // 18268cbcc3eSChris Lattner Constant *Op = CE->getOperand(0); 1835def7a57SChris Lattner GenericValue GV = getConstantValue(Op); 18468cbcc3eSChris Lattner 18568cbcc3eSChris Lattner // Handle cast of pointer to pointer... 1866b727599SChris Lattner if (Op->getType()->getTypeID() == C->getType()->getTypeID()) 1875def7a57SChris Lattner return GV; 18868cbcc3eSChris Lattner 1890627a96eSChris Lattner // Handle a cast of pointer to any integral type... 1908e693398SChris Lattner if (isa<PointerType>(Op->getType()) && C->getType()->isIntegral()) 1915def7a57SChris Lattner return GV; 1920627a96eSChris Lattner 1935def7a57SChris Lattner // Handle cast of integer to a pointer... 1945def7a57SChris Lattner if (isa<PointerType>(C->getType()) && Op->getType()->isIntegral()) 1956b727599SChris Lattner switch (Op->getType()->getTypeID()) { 1965def7a57SChris Lattner case Type::BoolTyID: return PTOGV((void*)(uintptr_t)GV.BoolVal); 1975def7a57SChris Lattner case Type::SByteTyID: return PTOGV((void*)( intptr_t)GV.SByteVal); 1985def7a57SChris Lattner case Type::UByteTyID: return PTOGV((void*)(uintptr_t)GV.UByteVal); 1995def7a57SChris Lattner case Type::ShortTyID: return PTOGV((void*)( intptr_t)GV.ShortVal); 2005def7a57SChris Lattner case Type::UShortTyID: return PTOGV((void*)(uintptr_t)GV.UShortVal); 2015def7a57SChris Lattner case Type::IntTyID: return PTOGV((void*)( intptr_t)GV.IntVal); 2025def7a57SChris Lattner case Type::UIntTyID: return PTOGV((void*)(uintptr_t)GV.UIntVal); 2035def7a57SChris Lattner case Type::LongTyID: return PTOGV((void*)( intptr_t)GV.LongVal); 2045def7a57SChris Lattner case Type::ULongTyID: return PTOGV((void*)(uintptr_t)GV.ULongVal); 2055def7a57SChris Lattner default: assert(0 && "Unknown integral type!"); 2065def7a57SChris Lattner } 20768cbcc3eSChris Lattner break; 20868cbcc3eSChris Lattner } 20968cbcc3eSChris Lattner 21068cbcc3eSChris Lattner case Instruction::Add: 211*c4e6bb5fSChris Lattner switch (CE->getOperand(0)->getType()->getTypeID()) { 212*c4e6bb5fSChris Lattner default: assert(0 && "Bad add type!"); abort(); 213*c4e6bb5fSChris Lattner case Type::LongTyID: 214*c4e6bb5fSChris Lattner case Type::ULongTyID: 2153b3276beSChris Lattner Result.LongVal = getConstantValue(CE->getOperand(0)).LongVal + 2163b3276beSChris Lattner getConstantValue(CE->getOperand(1)).LongVal; 21768cbcc3eSChris Lattner break; 218*c4e6bb5fSChris Lattner case Type::IntTyID: 219*c4e6bb5fSChris Lattner case Type::UIntTyID: 220*c4e6bb5fSChris Lattner Result.IntVal = getConstantValue(CE->getOperand(0)).IntVal + 221*c4e6bb5fSChris Lattner getConstantValue(CE->getOperand(1)).IntVal; 222*c4e6bb5fSChris Lattner break; 223*c4e6bb5fSChris Lattner case Type::ShortTyID: 224*c4e6bb5fSChris Lattner case Type::UShortTyID: 225*c4e6bb5fSChris Lattner Result.ShortVal = getConstantValue(CE->getOperand(0)).ShortVal + 226*c4e6bb5fSChris Lattner getConstantValue(CE->getOperand(1)).ShortVal; 227*c4e6bb5fSChris Lattner break; 228*c4e6bb5fSChris Lattner case Type::SByteTyID: 229*c4e6bb5fSChris Lattner case Type::UByteTyID: 230*c4e6bb5fSChris Lattner Result.SByteVal = getConstantValue(CE->getOperand(0)).SByteVal + 231*c4e6bb5fSChris Lattner getConstantValue(CE->getOperand(1)).SByteVal; 232*c4e6bb5fSChris Lattner break; 233*c4e6bb5fSChris Lattner case Type::FloatTyID: 234*c4e6bb5fSChris Lattner Result.FloatVal = getConstantValue(CE->getOperand(0)).FloatVal + 235*c4e6bb5fSChris Lattner getConstantValue(CE->getOperand(1)).FloatVal; 236*c4e6bb5fSChris Lattner break; 237*c4e6bb5fSChris Lattner case Type::DoubleTyID: 238*c4e6bb5fSChris Lattner Result.DoubleVal = getConstantValue(CE->getOperand(0)).DoubleVal + 239*c4e6bb5fSChris Lattner getConstantValue(CE->getOperand(1)).DoubleVal; 240*c4e6bb5fSChris Lattner break; 241*c4e6bb5fSChris Lattner } 24268cbcc3eSChris Lattner return Result; 2439de0d14dSChris Lattner default: 24468cbcc3eSChris Lattner break; 24568cbcc3eSChris Lattner } 24668cbcc3eSChris Lattner std::cerr << "ConstantExpr not handled as global var init: " << *CE << "\n"; 2479de0d14dSChris Lattner abort(); 2489de0d14dSChris Lattner } 249996fe010SChris Lattner 2506b727599SChris Lattner switch (C->getType()->getTypeID()) { 2519de0d14dSChris Lattner #define GET_CONST_VAL(TY, CLASS) \ 2529de0d14dSChris Lattner case Type::TY##TyID: Result.TY##Val = cast<CLASS>(C)->getValue(); break 253996fe010SChris Lattner GET_CONST_VAL(Bool , ConstantBool); 254996fe010SChris Lattner GET_CONST_VAL(UByte , ConstantUInt); 255996fe010SChris Lattner GET_CONST_VAL(SByte , ConstantSInt); 256996fe010SChris Lattner GET_CONST_VAL(UShort , ConstantUInt); 257996fe010SChris Lattner GET_CONST_VAL(Short , ConstantSInt); 258996fe010SChris Lattner GET_CONST_VAL(UInt , ConstantUInt); 259996fe010SChris Lattner GET_CONST_VAL(Int , ConstantSInt); 260996fe010SChris Lattner GET_CONST_VAL(ULong , ConstantUInt); 261996fe010SChris Lattner GET_CONST_VAL(Long , ConstantSInt); 262996fe010SChris Lattner GET_CONST_VAL(Float , ConstantFP); 263996fe010SChris Lattner GET_CONST_VAL(Double , ConstantFP); 264996fe010SChris Lattner #undef GET_CONST_VAL 265996fe010SChris Lattner case Type::PointerTyID: 266996fe010SChris Lattner if (isa<ConstantPointerNull>(C)) { 267996fe010SChris Lattner Result.PointerVal = 0; 268996fe010SChris Lattner } else if (const ConstantPointerRef *CPR = dyn_cast<ConstantPointerRef>(C)){ 269e6492f10SChris Lattner if (Function *F = 270e6492f10SChris Lattner const_cast<Function*>(dyn_cast<Function>(CPR->getValue()))) 271e6492f10SChris Lattner Result = PTOGV(getPointerToFunctionOrStub(F)); 272e6492f10SChris Lattner else 273fbcc0aa1SChris Lattner Result = PTOGV(getOrEmitGlobalVariable( 274fbcc0aa1SChris Lattner cast<GlobalVariable>(CPR->getValue()))); 275996fe010SChris Lattner 276996fe010SChris Lattner } else { 277996fe010SChris Lattner assert(0 && "Unknown constant pointer type!"); 278996fe010SChris Lattner } 279996fe010SChris Lattner break; 280996fe010SChris Lattner default: 2815aa56633SChris Lattner std::cout << "ERROR: Constant unimp for type: " << C->getType() << "\n"; 2829de0d14dSChris Lattner abort(); 283996fe010SChris Lattner } 284996fe010SChris Lattner return Result; 285996fe010SChris Lattner } 286996fe010SChris Lattner 287857c21b4SMisha Brukman /// FIXME: document 288857c21b4SMisha Brukman /// 289996fe010SChris Lattner void ExecutionEngine::StoreValueToMemory(GenericValue Val, GenericValue *Ptr, 290996fe010SChris Lattner const Type *Ty) { 291996fe010SChris Lattner if (getTargetData().isLittleEndian()) { 2926b727599SChris Lattner switch (Ty->getTypeID()) { 293996fe010SChris Lattner case Type::BoolTyID: 294996fe010SChris Lattner case Type::UByteTyID: 295996fe010SChris Lattner case Type::SByteTyID: Ptr->Untyped[0] = Val.UByteVal; break; 296996fe010SChris Lattner case Type::UShortTyID: 297996fe010SChris Lattner case Type::ShortTyID: Ptr->Untyped[0] = Val.UShortVal & 255; 298996fe010SChris Lattner Ptr->Untyped[1] = (Val.UShortVal >> 8) & 255; 299996fe010SChris Lattner break; 300b348952dSChris Lattner Store4BytesLittleEndian: 301996fe010SChris Lattner case Type::FloatTyID: 302996fe010SChris Lattner case Type::UIntTyID: 303996fe010SChris Lattner case Type::IntTyID: Ptr->Untyped[0] = Val.UIntVal & 255; 304996fe010SChris Lattner Ptr->Untyped[1] = (Val.UIntVal >> 8) & 255; 305996fe010SChris Lattner Ptr->Untyped[2] = (Val.UIntVal >> 16) & 255; 306996fe010SChris Lattner Ptr->Untyped[3] = (Val.UIntVal >> 24) & 255; 307996fe010SChris Lattner break; 30869cab0ddSChris Lattner case Type::PointerTyID: if (getTargetData().getPointerSize() == 4) 309b348952dSChris Lattner goto Store4BytesLittleEndian; 310996fe010SChris Lattner case Type::DoubleTyID: 311996fe010SChris Lattner case Type::ULongTyID: 312b348952dSChris Lattner case Type::LongTyID: Ptr->Untyped[0] = Val.ULongVal & 255; 313996fe010SChris Lattner Ptr->Untyped[1] = (Val.ULongVal >> 8) & 255; 314996fe010SChris Lattner Ptr->Untyped[2] = (Val.ULongVal >> 16) & 255; 315996fe010SChris Lattner Ptr->Untyped[3] = (Val.ULongVal >> 24) & 255; 316996fe010SChris Lattner Ptr->Untyped[4] = (Val.ULongVal >> 32) & 255; 317996fe010SChris Lattner Ptr->Untyped[5] = (Val.ULongVal >> 40) & 255; 318996fe010SChris Lattner Ptr->Untyped[6] = (Val.ULongVal >> 48) & 255; 319996fe010SChris Lattner Ptr->Untyped[7] = (Val.ULongVal >> 56) & 255; 320996fe010SChris Lattner break; 321996fe010SChris Lattner default: 3225aa56633SChris Lattner std::cout << "Cannot store value of type " << Ty << "!\n"; 323996fe010SChris Lattner } 324996fe010SChris Lattner } else { 3256b727599SChris Lattner switch (Ty->getTypeID()) { 326996fe010SChris Lattner case Type::BoolTyID: 327996fe010SChris Lattner case Type::UByteTyID: 328996fe010SChris Lattner case Type::SByteTyID: Ptr->Untyped[0] = Val.UByteVal; break; 329996fe010SChris Lattner case Type::UShortTyID: 330996fe010SChris Lattner case Type::ShortTyID: Ptr->Untyped[1] = Val.UShortVal & 255; 331996fe010SChris Lattner Ptr->Untyped[0] = (Val.UShortVal >> 8) & 255; 332996fe010SChris Lattner break; 333b348952dSChris Lattner Store4BytesBigEndian: 334996fe010SChris Lattner case Type::FloatTyID: 335996fe010SChris Lattner case Type::UIntTyID: 336996fe010SChris Lattner case Type::IntTyID: Ptr->Untyped[3] = Val.UIntVal & 255; 337996fe010SChris Lattner Ptr->Untyped[2] = (Val.UIntVal >> 8) & 255; 338996fe010SChris Lattner Ptr->Untyped[1] = (Val.UIntVal >> 16) & 255; 339996fe010SChris Lattner Ptr->Untyped[0] = (Val.UIntVal >> 24) & 255; 340996fe010SChris Lattner break; 34169cab0ddSChris Lattner case Type::PointerTyID: if (getTargetData().getPointerSize() == 4) 342b348952dSChris Lattner goto Store4BytesBigEndian; 343996fe010SChris Lattner case Type::DoubleTyID: 344996fe010SChris Lattner case Type::ULongTyID: 345b348952dSChris Lattner case Type::LongTyID: Ptr->Untyped[7] = Val.ULongVal & 255; 346996fe010SChris Lattner Ptr->Untyped[6] = (Val.ULongVal >> 8) & 255; 347996fe010SChris Lattner Ptr->Untyped[5] = (Val.ULongVal >> 16) & 255; 348996fe010SChris Lattner Ptr->Untyped[4] = (Val.ULongVal >> 24) & 255; 349996fe010SChris Lattner Ptr->Untyped[3] = (Val.ULongVal >> 32) & 255; 350996fe010SChris Lattner Ptr->Untyped[2] = (Val.ULongVal >> 40) & 255; 351996fe010SChris Lattner Ptr->Untyped[1] = (Val.ULongVal >> 48) & 255; 352996fe010SChris Lattner Ptr->Untyped[0] = (Val.ULongVal >> 56) & 255; 353996fe010SChris Lattner break; 354996fe010SChris Lattner default: 3555aa56633SChris Lattner std::cout << "Cannot store value of type " << Ty << "!\n"; 356996fe010SChris Lattner } 357996fe010SChris Lattner } 358996fe010SChris Lattner } 359996fe010SChris Lattner 360857c21b4SMisha Brukman /// FIXME: document 361857c21b4SMisha Brukman /// 3627f389e8cSChris Lattner GenericValue ExecutionEngine::LoadValueFromMemory(GenericValue *Ptr, 3637f389e8cSChris Lattner const Type *Ty) { 3647f389e8cSChris Lattner GenericValue Result; 3657f389e8cSChris Lattner if (getTargetData().isLittleEndian()) { 3666b727599SChris Lattner switch (Ty->getTypeID()) { 3677f389e8cSChris Lattner case Type::BoolTyID: 3687f389e8cSChris Lattner case Type::UByteTyID: 3697f389e8cSChris Lattner case Type::SByteTyID: Result.UByteVal = Ptr->Untyped[0]; break; 3707f389e8cSChris Lattner case Type::UShortTyID: 3717f389e8cSChris Lattner case Type::ShortTyID: Result.UShortVal = (unsigned)Ptr->Untyped[0] | 3727f389e8cSChris Lattner ((unsigned)Ptr->Untyped[1] << 8); 3737f389e8cSChris Lattner break; 3747f389e8cSChris Lattner Load4BytesLittleEndian: 3757f389e8cSChris Lattner case Type::FloatTyID: 3767f389e8cSChris Lattner case Type::UIntTyID: 3777f389e8cSChris Lattner case Type::IntTyID: Result.UIntVal = (unsigned)Ptr->Untyped[0] | 3787f389e8cSChris Lattner ((unsigned)Ptr->Untyped[1] << 8) | 3797f389e8cSChris Lattner ((unsigned)Ptr->Untyped[2] << 16) | 3807f389e8cSChris Lattner ((unsigned)Ptr->Untyped[3] << 24); 3817f389e8cSChris Lattner break; 38269cab0ddSChris Lattner case Type::PointerTyID: if (getTargetData().getPointerSize() == 4) 3837f389e8cSChris Lattner goto Load4BytesLittleEndian; 3847f389e8cSChris Lattner case Type::DoubleTyID: 3857f389e8cSChris Lattner case Type::ULongTyID: 3867f389e8cSChris Lattner case Type::LongTyID: Result.ULongVal = (uint64_t)Ptr->Untyped[0] | 3877f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[1] << 8) | 3887f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[2] << 16) | 3897f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[3] << 24) | 3907f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[4] << 32) | 3917f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[5] << 40) | 3927f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[6] << 48) | 3937f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[7] << 56); 3947f389e8cSChris Lattner break; 3957f389e8cSChris Lattner default: 3967f389e8cSChris Lattner std::cout << "Cannot load value of type " << *Ty << "!\n"; 3977f389e8cSChris Lattner abort(); 3987f389e8cSChris Lattner } 3997f389e8cSChris Lattner } else { 4006b727599SChris Lattner switch (Ty->getTypeID()) { 4017f389e8cSChris Lattner case Type::BoolTyID: 4027f389e8cSChris Lattner case Type::UByteTyID: 4037f389e8cSChris Lattner case Type::SByteTyID: Result.UByteVal = Ptr->Untyped[0]; break; 4047f389e8cSChris Lattner case Type::UShortTyID: 4057f389e8cSChris Lattner case Type::ShortTyID: Result.UShortVal = (unsigned)Ptr->Untyped[1] | 4067f389e8cSChris Lattner ((unsigned)Ptr->Untyped[0] << 8); 4077f389e8cSChris Lattner break; 4087f389e8cSChris Lattner Load4BytesBigEndian: 4097f389e8cSChris Lattner case Type::FloatTyID: 4107f389e8cSChris Lattner case Type::UIntTyID: 4117f389e8cSChris Lattner case Type::IntTyID: Result.UIntVal = (unsigned)Ptr->Untyped[3] | 4127f389e8cSChris Lattner ((unsigned)Ptr->Untyped[2] << 8) | 4137f389e8cSChris Lattner ((unsigned)Ptr->Untyped[1] << 16) | 4147f389e8cSChris Lattner ((unsigned)Ptr->Untyped[0] << 24); 4157f389e8cSChris Lattner break; 41669cab0ddSChris Lattner case Type::PointerTyID: if (getTargetData().getPointerSize() == 4) 4177f389e8cSChris Lattner goto Load4BytesBigEndian; 4187f389e8cSChris Lattner case Type::DoubleTyID: 4197f389e8cSChris Lattner case Type::ULongTyID: 4207f389e8cSChris Lattner case Type::LongTyID: Result.ULongVal = (uint64_t)Ptr->Untyped[7] | 4217f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[6] << 8) | 4227f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[5] << 16) | 4237f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[4] << 24) | 4247f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[3] << 32) | 4257f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[2] << 40) | 4267f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[1] << 48) | 4277f389e8cSChris Lattner ((uint64_t)Ptr->Untyped[0] << 56); 4287f389e8cSChris Lattner break; 4297f389e8cSChris Lattner default: 4307f389e8cSChris Lattner std::cout << "Cannot load value of type " << *Ty << "!\n"; 4317f389e8cSChris Lattner abort(); 4327f389e8cSChris Lattner } 4337f389e8cSChris Lattner } 4347f389e8cSChris Lattner return Result; 4357f389e8cSChris Lattner } 4367f389e8cSChris Lattner 437996fe010SChris Lattner // InitializeMemory - Recursive function to apply a Constant value into the 438996fe010SChris Lattner // specified memory location... 439996fe010SChris Lattner // 440996fe010SChris Lattner void ExecutionEngine::InitializeMemory(const Constant *Init, void *Addr) { 441996fe010SChris Lattner if (Init->getType()->isFirstClassType()) { 442996fe010SChris Lattner GenericValue Val = getConstantValue(Init); 443996fe010SChris Lattner StoreValueToMemory(Val, (GenericValue*)Addr, Init->getType()); 444996fe010SChris Lattner return; 445834b1272SChris Lattner } else if (isa<ConstantAggregateZero>(Init)) { 446834b1272SChris Lattner unsigned Size = getTargetData().getTypeSize(Init->getType()); 447834b1272SChris Lattner memset(Addr, 0, Size); 448834b1272SChris Lattner return; 449996fe010SChris Lattner } 450996fe010SChris Lattner 4516b727599SChris Lattner switch (Init->getType()->getTypeID()) { 452996fe010SChris Lattner case Type::ArrayTyID: { 453996fe010SChris Lattner const ConstantArray *CPA = cast<ConstantArray>(Init); 4545aa56633SChris Lattner const std::vector<Use> &Val = CPA->getValues(); 455996fe010SChris Lattner unsigned ElementSize = 456996fe010SChris Lattner getTargetData().getTypeSize(cast<ArrayType>(CPA->getType())->getElementType()); 457996fe010SChris Lattner for (unsigned i = 0; i < Val.size(); ++i) 458996fe010SChris Lattner InitializeMemory(cast<Constant>(Val[i].get()), (char*)Addr+i*ElementSize); 459996fe010SChris Lattner return; 460996fe010SChris Lattner } 461996fe010SChris Lattner 462996fe010SChris Lattner case Type::StructTyID: { 463996fe010SChris Lattner const ConstantStruct *CPS = cast<ConstantStruct>(Init); 464996fe010SChris Lattner const StructLayout *SL = 465996fe010SChris Lattner getTargetData().getStructLayout(cast<StructType>(CPS->getType())); 4665aa56633SChris Lattner const std::vector<Use> &Val = CPS->getValues(); 467996fe010SChris Lattner for (unsigned i = 0; i < Val.size(); ++i) 468996fe010SChris Lattner InitializeMemory(cast<Constant>(Val[i].get()), 469996fe010SChris Lattner (char*)Addr+SL->MemberOffsets[i]); 470996fe010SChris Lattner return; 471996fe010SChris Lattner } 472996fe010SChris Lattner 473996fe010SChris Lattner default: 474996fe010SChris Lattner std::cerr << "Bad Type: " << Init->getType() << "\n"; 475996fe010SChris Lattner assert(0 && "Unknown constant type to initialize memory with!"); 476996fe010SChris Lattner } 477996fe010SChris Lattner } 478996fe010SChris Lattner 479996fe010SChris Lattner /// EmitGlobals - Emit all of the global variables to memory, storing their 480996fe010SChris Lattner /// addresses into GlobalAddress. This must make sure to copy the contents of 481996fe010SChris Lattner /// their initializers into the memory. 482996fe010SChris Lattner /// 483996fe010SChris Lattner void ExecutionEngine::emitGlobals() { 484996fe010SChris Lattner const TargetData &TD = getTargetData(); 485996fe010SChris Lattner 486996fe010SChris Lattner // Loop over all of the global variables in the program, allocating the memory 487996fe010SChris Lattner // to hold them. 488996fe010SChris Lattner for (Module::giterator I = getModule().gbegin(), E = getModule().gend(); 489996fe010SChris Lattner I != E; ++I) 490996fe010SChris Lattner if (!I->isExternal()) { 491996fe010SChris Lattner // Get the type of the global... 492996fe010SChris Lattner const Type *Ty = I->getType()->getElementType(); 493996fe010SChris Lattner 494996fe010SChris Lattner // Allocate some memory for it! 495996fe010SChris Lattner unsigned Size = TD.getTypeSize(Ty); 4966bbe3eceSChris Lattner addGlobalMapping(I, new char[Size]); 497996fe010SChris Lattner } else { 498e8bbcfc2SBrian Gaeke // External variable reference. Try to use the dynamic loader to 499e8bbcfc2SBrian Gaeke // get a pointer to it. 500e8bbcfc2SBrian Gaeke if (void *SymAddr = GetAddressOfSymbol(I->getName().c_str())) 501748e8579SChris Lattner addGlobalMapping(I, SymAddr); 5029de0d14dSChris Lattner else { 5039de0d14dSChris Lattner std::cerr << "Could not resolve external global address: " 5049de0d14dSChris Lattner << I->getName() << "\n"; 5059de0d14dSChris Lattner abort(); 5069de0d14dSChris Lattner } 507996fe010SChris Lattner } 508996fe010SChris Lattner 509996fe010SChris Lattner // Now that all of the globals are set up in memory, loop through them all and 510996fe010SChris Lattner // initialize their contents. 511996fe010SChris Lattner for (Module::giterator I = getModule().gbegin(), E = getModule().gend(); 512996fe010SChris Lattner I != E; ++I) 513996fe010SChris Lattner if (!I->isExternal()) 5146bbe3eceSChris Lattner EmitGlobalVariable(I); 5156bbe3eceSChris Lattner } 5166bbe3eceSChris Lattner 5176bbe3eceSChris Lattner // EmitGlobalVariable - This method emits the specified global variable to the 5186bbe3eceSChris Lattner // address specified in GlobalAddresses, or allocates new memory if it's not 5196bbe3eceSChris Lattner // already in the map. 520fbcc0aa1SChris Lattner void ExecutionEngine::EmitGlobalVariable(const GlobalVariable *GV) { 521748e8579SChris Lattner void *GA = getPointerToGlobalIfAvailable(GV); 522dc631735SChris Lattner DEBUG(std::cerr << "Global '" << GV->getName() << "' -> " << GA << "\n"); 523dc631735SChris Lattner 524fbcc0aa1SChris Lattner const Type *ElTy = GV->getType()->getElementType(); 5256bbe3eceSChris Lattner if (GA == 0) { 5266bbe3eceSChris Lattner // If it's not already specified, allocate memory for the global. 527fbcc0aa1SChris Lattner GA = new char[getTargetData().getTypeSize(ElTy)]; 528748e8579SChris Lattner addGlobalMapping(GV, GA); 5296bbe3eceSChris Lattner } 530fbcc0aa1SChris Lattner 5316bbe3eceSChris Lattner InitializeMemory(GV->getInitializer(), GA); 532fbcc0aa1SChris Lattner NumInitBytes += getTargetData().getTypeSize(ElTy); 5336bbe3eceSChris Lattner ++NumGlobals; 534996fe010SChris Lattner } 535