Initial checkin of LLVM JIT, codenamed jello. This tool is not built by
authorChris Lattner <sabre@nondot.org>
Fri, 25 Oct 2002 22:58:53 +0000 (22:58 +0000)
committerChris Lattner <sabre@nondot.org>
Fri, 25 Oct 2002 22:58:53 +0000 (22:58 +0000)
default, until it becomes stable.  Even then it will only work for for X86
targets.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@4285 91177308-0d34-0410-b5e6-96231b3b80d8

tools/jello/Makefile [new file with mode: 0644]
tools/jello/jello.cpp [new file with mode: 0644]

diff --git a/tools/jello/Makefile b/tools/jello/Makefile
new file mode 100644 (file)
index 0000000..3543c82
--- /dev/null
@@ -0,0 +1,10 @@
+LEVEL = ../..
+TOOLNAME = jello
+USEDLIBS = bcreader vmcore codegen x86 support.a target.a
+
+# Have gcc tell the linker to export symbols from the program so that
+# dynamically loaded modules can be linked against them.
+#
+TOOLLINKOPTS = -ldl $(ExportSymbols)
+
+include $(LEVEL)/Makefile.common
diff --git a/tools/jello/jello.cpp b/tools/jello/jello.cpp
new file mode 100644 (file)
index 0000000..3cf83bc
--- /dev/null
@@ -0,0 +1,76 @@
+//===-- jello.cpp - LLVM Just in Time Compiler ----------------------------===//
+//
+// This tool implements a just-in-time compiler for LLVM, allowing direct
+// execution of LLVM bytecode in an efficient manner.
+//
+// FIXME: This code will get more object oriented as we get the call back
+// intercept stuff implemented.
+//
+//===----------------------------------------------------------------------===//
+
+#include "llvm/Module.h"
+#include "llvm/Bytecode/Reader.h"
+#include "llvm/CodeGen/MFunction.h"
+#include "../lib/Target/X86/X86.h"   // FIXME: become generic eventually
+#include "../lib/Target/X86/X86InstructionInfo.h"
+#include "Support/CommandLine.h"
+#include "Support/Statistic.h"
+
+namespace {
+  cl::opt<std::string>
+  InputFile(cl::desc("<input bytecode>"), cl::Positional, cl::init("-"));
+
+  cl::opt<std::string>
+  MainFunction("f", cl::desc("Function to execute"), cl::init("main"),
+               cl::value_desc("function name"));
+}
+
+
+/// ExecuteFunction - Compile the specified function to machine code, and
+/// execute it.
+///
+static void ExecuteFunction(Function &F) {
+  X86InstructionInfo II;
+
+  // Perform instruction selection to turn the function into an x86 SSA form
+  MFunction *MF = X86SimpleInstructionSelection(F);
+
+  // TODO: optional optimizations go here
+
+  // If -debug is specified, output selected code to stderr
+  /*DEBUG*/(MF->print(std::cerr, II));
+
+  // Perform register allocation to convert to a concrete x86 representation
+  X86SimpleRegisterAllocation(MF);
+  
+  // If -debug is specified, output compiled code to stderr
+  /*DEBUG*/(X86PrintCode(MF, std::cerr));
+
+  // Emit register allocated X86 code now...
+  void *PFun = X86EmitCodeToMemory(MF);
+
+  // We don't need the machine specific representation for this function anymore
+  delete MF;
+}
+
+
+//===----------------------------------------------------------------------===//
+// main Driver function
+//
+int main(int argc, char **argv) {
+  cl::ParseCommandLineOptions(argc, argv, " llvm just in time compiler\n");
+
+  std::string ErrorMsg;
+  if (Module *M = ParseBytecodeFile(InputFile, &ErrorMsg)) {
+    for (Module::iterator I = M->begin(), E = M->end(); I != E; ++I)
+      if (I->getName() == MainFunction)
+        ExecuteFunction(*I);
+
+    delete M;
+    return 0;
+  }
+  
+  std::cerr << "Error parsing '" << InputFile << "': " << ErrorMsg << "\n";
+  return 1;
+}
+