Implement lazy resolution of function calls
authorChris Lattner <sabre@nondot.org>
Wed, 4 Dec 2002 04:47:34 +0000 (04:47 +0000)
committerChris Lattner <sabre@nondot.org>
Wed, 4 Dec 2002 04:47:34 +0000 (04:47 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@4899 91177308-0d34-0410-b5e6-96231b3b80d8

tools/jello/Emitter.cpp
tools/jello/VM.cpp
tools/jello/VM.h

index 89695ad2b4f5224f522ba604187ab6de0d8884d7..0e54322ef9b40c6fc90aaf37c1bd3aa1ac39bd00 100644 (file)
@@ -68,7 +68,9 @@ void Emitter::emitByte(unsigned char B) {
 // resolved on demand.  Keep track of these markers.
 //
 void Emitter::emitPCRelativeDisp(Value *V) {
-  unsigned ZeroAddr = -(unsigned)CurByte;  // Calculate displacement to null
+  TheVM.addFunctionRef(CurByte, cast<Function>(V));
+
+  unsigned ZeroAddr = -(unsigned)CurByte-4; // Calculate displacement to null
   *(unsigned*)CurByte = ZeroAddr;   // 4 byte offset
   CurByte += 4;
 }
index 497c42ef90efb9af6f2605aeb0beddb00c3bf13b..b5a8ca1c22d77cf061fca01bcf88132125eeea83 100644 (file)
@@ -43,6 +43,21 @@ int VM::run(Function *F) {
   return PF();
 }
 
+void *VM::resolveFunctionReference(void *RefAddr) {
+  Function *F = FunctionRefs[RefAddr];
+  assert(F && "Reference address not known!");
+
+  void *Addr = getPointerToFunction(F);
+  assert(Addr && "Pointer to function unknown!");
+
+  FunctionRefs.erase(RefAddr);
+  return Addr;
+}
+
+const std::string &VM::getFunctionReferencedName(void *RefAddr) {
+  return FunctionRefs[RefAddr]->getName();
+}
+
 
 /// getPointerToFunction - This method is used to get the address of the
 /// specified function, compiling it if neccesary.
index 5d0cd38941c4e71eb518d1a0dee89f383a20d1c8..b25cd4625e482c8ca247820cdcda99b78dab613f 100644 (file)
@@ -10,6 +10,7 @@
 #include "llvm/PassManager.h"
 #include <string>
 #include <map>
+#include <vector>
 
 class TargetMachine;
 class Function;
@@ -23,12 +24,21 @@ class VM {
   PassManager PM;          // Passes to compile a function
   MachineCodeEmitter *MCE; // MCE object
 
+  // GlobalAddress - A mapping between LLVM values and their native code
+  // generated versions...
   std::map<const GlobalValue*, void *> GlobalAddress;
+
+  // FunctionRefs - A mapping between addresses that refer to unresolved
+  // functions and the LLVM function object itself.  This is used by the fault
+  // handler to lazily patch up references...
+  //
+  std::map<void*, Function*> FunctionRefs;
 public:
   VM(const std::string &name, Module &m, TargetMachine &tm)
     : ExeName(name), M(m), TM(tm) {
     MCE = createEmitter(*this);  // Initialize MCE
     setupPassManager();
+    registerCallback();
   }
 
   ~VM();
@@ -41,10 +51,19 @@ public:
     CurVal = Addr;
   }
 
+  void addFunctionRef(void *Ref, Function *F) {
+    FunctionRefs[Ref] = F;
+  }
+
+  const std::string &getFunctionReferencedName(void *RefAddr);
+
+  void *resolveFunctionReference(void *RefAddr);
+
 private:
   static MachineCodeEmitter *createEmitter(VM &V);
   void setupPassManager();
   void *getPointerToFunction(Function *F);
+  void registerCallback();
 };
 
 #endif