Interpreter.cpp revision 82d8277ad5862b54341808812bb4016e52347060
1bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner//===- Interpreter.cpp - Top-Level LLVM Interpreter Implementation --------===// 2bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// 3bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// This file implements the top-level functionality for the LLVM interpreter. 4bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// This interpreter is designed to be a very simple, portable, inefficient 5bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// interpreter. 6bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// 7bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner//===----------------------------------------------------------------------===// 8bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner 9bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner#include "Interpreter.h" 1039c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner#include "llvm/Module.h" 11bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner 1282d8277ad5862b54341808812bb4016e52347060Brian Gaeke/// create - Create a new interpreter object. This can never fail. 13bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner/// 1482d8277ad5862b54341808812bb4016e52347060Brian GaekeExecutionEngine *Interpreter::create(Module *M, bool DebugMode, bool TraceMode){ 1539c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner bool isLittleEndian; 1639c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner switch (M->getEndianness()) { 1739c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner case Module::LittleEndian: isLittleEndian = true; break; 1839c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner case Module::BigEndian: isLittleEndian = false; break; 1939c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner case Module::AnyPointerSize: 2039c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner int Test = 0; 2139c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner *(char*)&Test = 1; // Return true if the host is little endian 2239c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner isLittleEndian = (Test == 1); 2339c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner break; 2439c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner } 2539c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner 2639c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner bool isLongPointer; 2739c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner switch (M->getPointerSize()) { 2839c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner case Module::Pointer32: isLongPointer = false; break; 2939c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner case Module::Pointer64: isLongPointer = true; break; 3039c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner case Module::AnyPointerSize: 3139c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner isLongPointer = (sizeof(void*) == 8); // Follow host 3239c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner break; 3339c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner } 3439c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner 3539c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner return new Interpreter(M, isLittleEndian, isLongPointer, DebugMode,TraceMode); 36bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner} 37bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner 38bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner//===----------------------------------------------------------------------===// 39bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// Interpreter ctor - Initialize stuff 40bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// 4139c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris LattnerInterpreter::Interpreter(Module *M, bool isLittleEndian, bool isLongPointer, 4239c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner bool DebugMode, bool TraceMode) 43bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner : ExecutionEngine(M), ExitCode(0), Debug(DebugMode), Trace(TraceMode), 4439c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner CurFrame(-1), TD("lli", isLittleEndian, isLongPointer ? 8 : 4, 4539c07264da992fd5d37fa7eaac0b9f02f55f80d0Chris Lattner isLongPointer ? 8 : 4, isLongPointer ? 8 : 4) { 46bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner 47bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner setTargetData(TD); 48bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner // Initialize the "backend" 49bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner initializeExecutionEngine(); 50da82ed52ac02497d343b898cca0bb2cf303f062dChris Lattner initializeExternalFunctions(); 51bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner CW.setModule(M); // Update Writer 5256adf152f6354a9b5609e059050fd2315ad5960cChris Lattner emitGlobals(); 53bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner} 54bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner 55bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner/// run - Start execution with the specified function and arguments. 56bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner/// 57bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattnerint Interpreter::run(const std::string &MainFunction, 5869582b35b6aa4e48cbbad7f6f1193c967da96b25John Criswell const std::vector<std::string> &Args, 5969582b35b6aa4e48cbbad7f6f1193c967da96b25John Criswell const char ** envp) { 60bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner // Start interpreter into the main function... 61bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner // 62da82ed52ac02497d343b898cca0bb2cf303f062dChris Lattner if (!callMainFunction(MainFunction, Args) && !Debug) { 63bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner // If not in debug mode and if the call succeeded, run the code now... 64bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner run(); 65bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner } 66bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner 6744edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner do { 6844edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner // If debug mode, allow the user to interact... also, if the user pressed 6944edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner // ctrl-c or execution hit an error, enter the event loop... 7044edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner if (Debug || isStopped()) 7144edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner handleUserInput(); 7244edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner 7344edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner // If the program has exited, run atexit handlers... 7444edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner if (ECStack.empty() && !AtExitHandlers.empty()) { 7544edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner callFunction(AtExitHandlers.back(), std::vector<GenericValue>()); 7644edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner AtExitHandlers.pop_back(); 7744edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner run(); 7844edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner } 7944edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner } while (!ECStack.empty()); 8044edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner 8144edb6bdd2edc48eb31ed160a09006b610cead67Chris Lattner PerformExitStuff(); 82bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner return ExitCode; 83bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner} 84bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner 85