ExecutionEngine.cpp revision 36343735cb23680c8f8675deafbbf825d46fd868
14afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman//===-- ExecutionEngine.cpp - Common Implementation shared by EEs ---------===//
2edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman//
3b576c94c15af9a440f69d9d03c2afead7971118cJohn Criswell//                     The LLVM Compiler Infrastructure
4b576c94c15af9a440f69d9d03c2afead7971118cJohn Criswell//
5b576c94c15af9a440f69d9d03c2afead7971118cJohn Criswell// This file was developed by the LLVM research group and is distributed under
6b576c94c15af9a440f69d9d03c2afead7971118cJohn Criswell// the University of Illinois Open Source License. See LICENSE.TXT for details.
7edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman//
8b576c94c15af9a440f69d9d03c2afead7971118cJohn Criswell//===----------------------------------------------------------------------===//
9edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman//
10bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// This file defines the common interface used by the various execution engine
11bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// subclasses.
12bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner//
13bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner//===----------------------------------------------------------------------===//
14bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
153785fad56eb90284d4e930d40e9306391630deb1Chris Lattner#define DEBUG_TYPE "jit"
16bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner#include "llvm/Constants.h"
1719684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman#include "llvm/DerivedTypes.h"
18bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner#include "llvm/Module.h"
1919684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman#include "llvm/ModuleProvider.h"
20df5a37efc997288da520ff4889443e3560d95387Reid Spencer#include "llvm/ADT/Statistic.h"
2119684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman#include "llvm/ExecutionEngine/ExecutionEngine.h"
22fd13129bdf7324b2e8181a653897269aaaecc4e8Chris Lattner#include "llvm/ExecutionEngine/GenericValue.h"
23551ccae044b0ff658fe629dd67edd5ffe75d10e8Reid Spencer#include "llvm/Support/Debug.h"
24e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner#include "llvm/Support/MutexGuard.h"
25df5a37efc997288da520ff4889443e3560d95387Reid Spencer#include "llvm/System/DynamicLibrary.h"
26df5a37efc997288da520ff4889443e3560d95387Reid Spencer#include "llvm/Target/TargetData.h"
27c2ee9b9c7a6517f959aea31fa2c61631fe2f2903Chris Lattnerusing namespace llvm;
28bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
2936343735cb23680c8f8675deafbbf825d46fd868Chris LattnerSTATISTIC(NumInitBytes, "Number of bytes of global vars initialized");
3036343735cb23680c8f8675deafbbf825d46fd868Chris LattnerSTATISTIC(NumGlobals  , "Number of global vars initialized");
31bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
322fe4bb06c6c40d16b7a5ae9cdf6bb6fe94d51be0Chris LattnerExecutionEngine::EECtorFn ExecutionEngine::JITCtor = 0;
332fe4bb06c6c40d16b7a5ae9cdf6bb6fe94d51be0Chris LattnerExecutionEngine::EECtorFn ExecutionEngine::InterpCtor = 0;
342fe4bb06c6c40d16b7a5ae9cdf6bb6fe94d51be0Chris Lattner
35fe854034677f59baca1e38075e71f6efca247a03Chris LattnerExecutionEngine::ExecutionEngine(ModuleProvider *P) {
363d6e33d2a3dcade0db9edc419857d0e266176460Chris Lattner  LazyCompilationDisabled = false;
37fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  Modules.push_back(P);
3819684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman  assert(P && "ModuleProvider is null?");
3919684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman}
4019684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman
41fe854034677f59baca1e38075e71f6efca247a03Chris LattnerExecutionEngine::ExecutionEngine(Module *M) {
423d6e33d2a3dcade0db9edc419857d0e266176460Chris Lattner  LazyCompilationDisabled = false;
4305701573aac26e87a33e8aa58817e4dc5a40050aMisha Brukman  assert(M && "Module is null?");
44fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  Modules.push_back(new ExistingModuleProvider(M));
4519684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman}
4619684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman
478e539488816c9e52bde0af475f72cd3e6407d558Brian GaekeExecutionEngine::~ExecutionEngine() {
48fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  for (unsigned i = 0, e = Modules.size(); i != e; ++i)
49fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    delete Modules[i];
508e539488816c9e52bde0af475f72cd3e6407d558Brian Gaeke}
518e539488816c9e52bde0af475f72cd3e6407d558Brian Gaeke
52fe854034677f59baca1e38075e71f6efca247a03Chris Lattner/// FindFunctionNamed - Search all of the active modules to find the one that
53fe854034677f59baca1e38075e71f6efca247a03Chris Lattner/// defines FnName.  This is very slow operation and shouldn't be used for
54fe854034677f59baca1e38075e71f6efca247a03Chris Lattner/// general code.
55fe854034677f59baca1e38075e71f6efca247a03Chris LattnerFunction *ExecutionEngine::FindFunctionNamed(const char *FnName) {
56fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  for (unsigned i = 0, e = Modules.size(); i != e; ++i) {
57fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    if (Function *F = Modules[i]->getModule()->getNamedFunction(FnName))
58fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      return F;
59fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  }
60fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  return 0;
61fe854034677f59baca1e38075e71f6efca247a03Chris Lattner}
62fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
63fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
64e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// addGlobalMapping - Tell the execution engine that the specified global is
65e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// at the specified location.  This is used internally as functions are JIT'd
66e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// and as global variables are laid out in memory.  It can and should also be
67e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// used by clients of the EE that want to have an LLVM global overlay
68e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// existing data in memory.
69e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattnervoid ExecutionEngine::addGlobalMapping(const GlobalValue *GV, void *Addr) {
70e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  MutexGuard locked(lock);
71e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
72e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  void *&CurVal = state.getGlobalAddressMap(locked)[GV];
73e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  assert((CurVal == 0 || Addr == 0) && "GlobalMapping already established!");
74e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  CurVal = Addr;
75e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
76e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  // If we are using the reverse mapping, add it too
77e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  if (!state.getGlobalAddressReverseMap(locked).empty()) {
78e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    const GlobalValue *&V = state.getGlobalAddressReverseMap(locked)[Addr];
79e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    assert((V == 0 || GV == 0) && "GlobalMapping already established!");
80e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    V = GV;
81e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  }
82e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner}
83e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
84e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// clearAllGlobalMappings - Clear all global mappings and start over again
85e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// use in dynamic compilation scenarios when you want to move globals
86e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattnervoid ExecutionEngine::clearAllGlobalMappings() {
87e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  MutexGuard locked(lock);
88e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
89e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  state.getGlobalAddressMap(locked).clear();
90e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  state.getGlobalAddressReverseMap(locked).clear();
91e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner}
92e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
93e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// updateGlobalMapping - Replace an existing mapping for GV with a new
94e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// address.  This updates both maps as required.  If "Addr" is null, the
95e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// entry for the global is removed from the mappings.
96e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattnervoid ExecutionEngine::updateGlobalMapping(const GlobalValue *GV, void *Addr) {
97e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  MutexGuard locked(lock);
98e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
99e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  // Deleting from the mapping?
100e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  if (Addr == 0) {
101e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    state.getGlobalAddressMap(locked).erase(GV);
102e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    if (!state.getGlobalAddressReverseMap(locked).empty())
103e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner      state.getGlobalAddressReverseMap(locked).erase(Addr);
104e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    return;
105e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  }
106e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
107e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  void *&CurVal = state.getGlobalAddressMap(locked)[GV];
108e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  if (CurVal && !state.getGlobalAddressReverseMap(locked).empty())
109e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    state.getGlobalAddressReverseMap(locked).erase(CurVal);
110e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  CurVal = Addr;
111e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
112e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  // If we are using the reverse mapping, add it too
113e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  if (!state.getGlobalAddressReverseMap(locked).empty()) {
114e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    const GlobalValue *&V = state.getGlobalAddressReverseMap(locked)[Addr];
115e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    assert((V == 0 || GV == 0) && "GlobalMapping already established!");
116e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    V = GV;
117e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  }
118e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner}
119e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
120e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// getPointerToGlobalIfAvailable - This returns the address of the specified
121e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner/// global value if it is has already been codegen'd, otherwise it returns null.
122e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner///
123e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattnervoid *ExecutionEngine::getPointerToGlobalIfAvailable(const GlobalValue *GV) {
124e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  MutexGuard locked(lock);
125e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
126e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  std::map<const GlobalValue*, void*>::iterator I =
127e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  state.getGlobalAddressMap(locked).find(GV);
128e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner  return I != state.getGlobalAddressMap(locked).end() ? I->second : 0;
129e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner}
130e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner
13155d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner/// getGlobalValueAtAddress - Return the LLVM global value object that starts
13255d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner/// at the specified address.
13355d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner///
13455d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattnerconst GlobalValue *ExecutionEngine::getGlobalValueAtAddress(void *Addr) {
135ee448630bdf7eb6037fe2c50518d32010c433ca3Reid Spencer  MutexGuard locked(lock);
136ee448630bdf7eb6037fe2c50518d32010c433ca3Reid Spencer
13755d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner  // If we haven't computed the reverse mapping yet, do so first.
138ee448630bdf7eb6037fe2c50518d32010c433ca3Reid Spencer  if (state.getGlobalAddressReverseMap(locked).empty()) {
139e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner    for (std::map<const GlobalValue*, void *>::iterator
140e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner         I = state.getGlobalAddressMap(locked).begin(),
141e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner         E = state.getGlobalAddressMap(locked).end(); I != E; ++I)
142e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner      state.getGlobalAddressReverseMap(locked).insert(std::make_pair(I->second,
143e7fd553b3be8b95dc0946cd3267bc2db859cd3d8Chris Lattner                                                                     I->first));
14455d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner  }
14555d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner
14655d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner  std::map<void *, const GlobalValue*>::iterator I =
147ee448630bdf7eb6037fe2c50518d32010c433ca3Reid Spencer    state.getGlobalAddressReverseMap(locked).find(Addr);
148ee448630bdf7eb6037fe2c50518d32010c433ca3Reid Spencer  return I != state.getGlobalAddressReverseMap(locked).end() ? I->second : 0;
14955d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner}
15087f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner
15187f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner// CreateArgv - Turn a vector of strings into a nice argv style array of
15287f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner// pointers to null terminated strings.
15387f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner//
15487f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattnerstatic void *CreateArgv(ExecutionEngine *EE,
15587f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner                        const std::vector<std::string> &InputArgv) {
156a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson  unsigned PtrSize = EE->getTargetData()->getPointerSize();
15787f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  char *Result = new char[(InputArgv.size()+1)*PtrSize];
15887f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner
159480f093dc2b6aff9b501cc56cf5728513e55be81Bill Wendling  DOUT << "ARGV = " << (void*)Result << "\n";
16087f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  const Type *SBytePtr = PointerType::get(Type::SByteTy);
16187f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner
16287f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  for (unsigned i = 0; i != InputArgv.size(); ++i) {
16387f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner    unsigned Size = InputArgv[i].size()+1;
16487f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner    char *Dest = new char[Size];
165480f093dc2b6aff9b501cc56cf5728513e55be81Bill Wendling    DOUT << "ARGV[" << i << "] = " << (void*)Dest << "\n";
166edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman
16787f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner    std::copy(InputArgv[i].begin(), InputArgv[i].end(), Dest);
16887f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner    Dest[Size-1] = 0;
169edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman
17087f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner    // Endian safe: Result[i] = (PointerTy)Dest;
17187f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner    EE->StoreValueToMemory(PTOGV(Dest), (GenericValue*)(Result+i*PtrSize),
17287f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner                           SBytePtr);
17387f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  }
17487f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner
17587f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  // Null terminate it
17687f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  EE->StoreValueToMemory(PTOGV(0),
17787f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner                         (GenericValue*)(Result+InputArgv.size()*PtrSize),
17887f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner                         SBytePtr);
17987f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  return Result;
18087f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner}
18187f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner
1829ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner
1839ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner/// runStaticConstructorsDestructors - This method is used to execute all of
184fe854034677f59baca1e38075e71f6efca247a03Chris Lattner/// the static constructors or destructors for a program, depending on the
1859ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner/// value of isDtors.
1869ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattnervoid ExecutionEngine::runStaticConstructorsDestructors(bool isDtors) {
1879ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner  const char *Name = isDtors ? "llvm.global_dtors" : "llvm.global_ctors";
1889ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner
189fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  // Execute global ctors/dtors for each module in the program.
190fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  for (unsigned m = 0, e = Modules.size(); m != e; ++m) {
191fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    GlobalVariable *GV = Modules[m]->getModule()->getNamedGlobal(Name);
192fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
193fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // If this global has internal linkage, or if it has a use, then it must be
194fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // an old-style (llvmgcc3) static ctor with __main linked in and in use.  If
195fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // this is the case, don't execute any of the global ctors, __main will do
196fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // it.
197fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    if (!GV || GV->isExternal() || GV->hasInternalLinkage()) continue;
198fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
199fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // Should be an array of '{ int, void ()* }' structs.  The first value is
200fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // the init priority, which we ignore.
201fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    ConstantArray *InitList = dyn_cast<ConstantArray>(GV->getInitializer());
202fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    if (!InitList) continue;
203fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    for (unsigned i = 0, e = InitList->getNumOperands(); i != e; ++i)
204fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      if (ConstantStruct *CS =
205fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          dyn_cast<ConstantStruct>(InitList->getOperand(i))) {
206fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (CS->getNumOperands() != 2) break; // Not array of 2-element structs.
2079ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner
208fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        Constant *FP = CS->getOperand(1);
209fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (FP->isNullValue())
210fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          break;  // Found a null terminator, exit.
2119ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner
212fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (ConstantExpr *CE = dyn_cast<ConstantExpr>(FP))
2133da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer          if (CE->isCast())
214fe854034677f59baca1e38075e71f6efca247a03Chris Lattner            FP = CE->getOperand(0);
215fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (Function *F = dyn_cast<Function>(FP)) {
216fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          // Execute the ctor/dtor function!
217fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          runFunction(F, std::vector<GenericValue>());
218fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        }
2199ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner      }
220fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  }
2219ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner}
2229ca6cdaee91fddcd3ea57dedcd624c14c7a40f65Chris Lattner
22387f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner/// runFunctionAsMain - This is a helper function which wraps runFunction to
22487f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner/// handle the common task of starting up main with the specified argc, argv,
22587f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner/// and envp parameters.
22687f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattnerint ExecutionEngine::runFunctionAsMain(Function *Fn,
22787f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner                                       const std::vector<std::string> &argv,
22887f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner                                       const char * const * envp) {
22987f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  std::vector<GenericValue> GVArgs;
23087f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  GenericValue GVArgc;
23187f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  GVArgc.IntVal = argv.size();
232f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner  unsigned NumArgs = Fn->getFunctionType()->getNumParams();
233f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner  if (NumArgs) {
234f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner    GVArgs.push_back(GVArgc); // Arg #0 = argc.
235f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner    if (NumArgs > 1) {
236f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner      GVArgs.push_back(PTOGV(CreateArgv(this, argv))); // Arg #1 = argv.
237f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner      assert(((char **)GVTOP(GVArgs[1]))[0] &&
238f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner             "argv[0] was null after CreateArgv");
239f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner      if (NumArgs > 2) {
240f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner        std::vector<std::string> EnvVars;
241f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner        for (unsigned i = 0; envp[i]; ++i)
242f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner          EnvVars.push_back(envp[i]);
243f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner        GVArgs.push_back(PTOGV(CreateArgv(this, EnvVars))); // Arg #2 = envp.
244f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner      }
245f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner    }
246f24d09933c0fa2dae141426f2c38c8925693c73fChris Lattner  }
24787f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner  return runFunction(Fn, GVArgs).IntVal;
24887f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner}
24987f03108f282a9b5f172f91679bd89ddbb5a65beChris Lattner
25019684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman/// If possible, create a JIT, unless the caller specifically requests an
25119684164a7b695b9dc22d879675e8d2b286ef7e5Misha Brukman/// Interpreter or there's an error. If even an Interpreter cannot be created,
252edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman/// NULL is returned.
2534afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman///
254edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha BrukmanExecutionEngine *ExecutionEngine::create(ModuleProvider *MP,
255726c1ef2bdd72975f41e3188371bb7d6f40401beChris Lattner                                         bool ForceInterpreter) {
25682d8277ad5862b54341808812bb4016e52347060Brian Gaeke  ExecutionEngine *EE = 0;
25782d8277ad5862b54341808812bb4016e52347060Brian Gaeke
2587301178aac1baf1cc334e7c7a66bfe50a65fbf49Chris Lattner  // Unless the interpreter was explicitly selected, try making a JIT.
2592fe4bb06c6c40d16b7a5ae9cdf6bb6fe94d51be0Chris Lattner  if (!ForceInterpreter && JITCtor)
260726c1ef2bdd72975f41e3188371bb7d6f40401beChris Lattner    EE = JITCtor(MP);
26182d8277ad5862b54341808812bb4016e52347060Brian Gaeke
26282d8277ad5862b54341808812bb4016e52347060Brian Gaeke  // If we can't make a JIT, make an interpreter instead.
2632fe4bb06c6c40d16b7a5ae9cdf6bb6fe94d51be0Chris Lattner  if (EE == 0 && InterpCtor)
264726c1ef2bdd72975f41e3188371bb7d6f40401beChris Lattner    EE = InterpCtor(MP);
2657301178aac1baf1cc334e7c7a66bfe50a65fbf49Chris Lattner
266726c1ef2bdd72975f41e3188371bb7d6f40401beChris Lattner  if (EE) {
267edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman    // Make sure we can resolve symbols in the program as well. The zero arg
268df5a37efc997288da520ff4889443e3560d95387Reid Spencer    // to the function tells DynamicLibrary to load the program, not a library.
2696f3ada51aa7a3816609967231befd58de4053e4cChris Lattner    try {
2706f3ada51aa7a3816609967231befd58de4053e4cChris Lattner      sys::DynamicLibrary::LoadLibraryPermanently(0);
2716f3ada51aa7a3816609967231befd58de4053e4cChris Lattner    } catch (...) {
2726f3ada51aa7a3816609967231befd58de4053e4cChris Lattner    }
273726c1ef2bdd72975f41e3188371bb7d6f40401beChris Lattner  }
274df5a37efc997288da520ff4889443e3560d95387Reid Spencer
27582d8277ad5862b54341808812bb4016e52347060Brian Gaeke  return EE;
27682d8277ad5862b54341808812bb4016e52347060Brian Gaeke}
27782d8277ad5862b54341808812bb4016e52347060Brian Gaeke
2784afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman/// getPointerToGlobal - This returns the address of the specified global
2794afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman/// value.  This may involve code generation if it's a function.
2804afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman///
281bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattnervoid *ExecutionEngine::getPointerToGlobal(const GlobalValue *GV) {
28237df460874e8d9d28e6833e5fb66a9aa8e1ef50aBrian Gaeke  if (Function *F = const_cast<Function*>(dyn_cast<Function>(GV)))
283bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    return getPointerToFunction(F);
284bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
285ee448630bdf7eb6037fe2c50518d32010c433ca3Reid Spencer  MutexGuard locked(lock);
28668835dd5119150383938c701fc223077d2bc1e25Jeff Cohen  void *p = state.getGlobalAddressMap(locked)[GV];
28768835dd5119150383938c701fc223077d2bc1e25Jeff Cohen  if (p)
28868835dd5119150383938c701fc223077d2bc1e25Jeff Cohen    return p;
28968835dd5119150383938c701fc223077d2bc1e25Jeff Cohen
29068835dd5119150383938c701fc223077d2bc1e25Jeff Cohen  // Global variable might have been added since interpreter started.
29168835dd5119150383938c701fc223077d2bc1e25Jeff Cohen  if (GlobalVariable *GVar =
29268835dd5119150383938c701fc223077d2bc1e25Jeff Cohen          const_cast<GlobalVariable *>(dyn_cast<GlobalVariable>(GV)))
29368835dd5119150383938c701fc223077d2bc1e25Jeff Cohen    EmitGlobalVariable(GVar);
29468835dd5119150383938c701fc223077d2bc1e25Jeff Cohen  else
29568835dd5119150383938c701fc223077d2bc1e25Jeff Cohen    assert("Global hasn't had an address allocated yet!");
296ee448630bdf7eb6037fe2c50518d32010c433ca3Reid Spencer  return state.getGlobalAddressMap(locked)[GV];
297bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner}
298bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
2993da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer/// This function converts a Constant* into a GenericValue. The interesting
3003da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer/// part is if C is a ConstantExpr.
3013da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer/// @brief Get a GenericValue for a Constnat*
302bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris LattnerGenericValue ExecutionEngine::getConstantValue(const Constant *C) {
3033da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer  // Declare the result as garbage.
304bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  GenericValue Result;
3053da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer
3063da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer  // If its undefined, return the garbage.
3076f335f905c76187a7baf70a227fa843061473afeChris Lattner  if (isa<UndefValue>(C)) return Result;
308d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner
3093da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer  // If the value is a ConstantExpr
3103da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer  if (const ConstantExpr *CE = dyn_cast<ConstantExpr>(C)) {
311d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner    switch (CE->getOpcode()) {
312d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner    case Instruction::GetElementPtr: {
3133da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      // Compute the index
3149a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner      Result = getConstantValue(CE->getOperand(0));
315d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner      std::vector<Value*> Indexes(CE->op_begin()+1, CE->op_end());
316d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner      uint64_t Offset =
317d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner        TD->getIndexedOffset(CE->getOperand(0)->getType(), Indexes);
318edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman
319a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson      if (getTargetData()->getPointerSize() == 4)
3203db4b62c2fa43b23fa02d32a7d3253885acafb9fChris Lattner        Result.IntVal += Offset;
3213db4b62c2fa43b23fa02d32a7d3253885acafb9fChris Lattner      else
3223db4b62c2fa43b23fa02d32a7d3253885acafb9fChris Lattner        Result.LongVal += Offset;
323d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner      return Result;
324d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner    }
3253da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::Trunc:
3263da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::ZExt:
3273da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::SExt:
3283da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::FPTrunc:
3293da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::FPExt:
3303da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::UIToFP:
3313da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::SIToFP:
3323da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::FPToUI:
3333da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::FPToSI:
3343da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      break;
3353da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::PtrToInt: {
3363da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      Constant *Op = CE->getOperand(0);
3373da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      GenericValue GV = getConstantValue(Op);
3383da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      return GV;
3393da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    }
3403da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::BitCast: {
3413da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      // Bit casts are no-ops but we can only return the GV of the operand if
3423da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      // they are the same basic type (pointer->pointer, packed->packed, etc.)
3439a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner      Constant *Op = CE->getOperand(0);
3447d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner      GenericValue GV = getConstantValue(Op);
345f70c22b019494723d0e706f93d6542dfaa6e73a5Chris Lattner      if (Op->getType()->getTypeID() == C->getType()->getTypeID())
3467d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        return GV;
3473da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      break;
3483da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    }
3493da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer    case Instruction::IntToPtr: {
3503da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      // IntToPtr casts are just so special. Cast to intptr_t first.
3513da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      Constant *Op = CE->getOperand(0);
3523da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      GenericValue GV = getConstantValue(Op);
3533da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      switch (Op->getType()->getTypeID()) {
3547d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::BoolTyID:    return PTOGV((void*)(uintptr_t)GV.BoolVal);
3557d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::SByteTyID:   return PTOGV((void*)( intptr_t)GV.SByteVal);
3567d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::UByteTyID:   return PTOGV((void*)(uintptr_t)GV.UByteVal);
3577d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::ShortTyID:   return PTOGV((void*)( intptr_t)GV.ShortVal);
3587d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::UShortTyID:  return PTOGV((void*)(uintptr_t)GV.UShortVal);
3597d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::IntTyID:     return PTOGV((void*)( intptr_t)GV.IntVal);
3607d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::UIntTyID:    return PTOGV((void*)(uintptr_t)GV.UIntVal);
3617d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::LongTyID:    return PTOGV((void*)( intptr_t)GV.LongVal);
3627d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        case Type::ULongTyID:   return PTOGV((void*)(uintptr_t)GV.ULongVal);
3637d1bd336abf32752d9dcb6993eca899fdfccff93Chris Lattner        default: assert(0 && "Unknown integral type!");
3643da59db637a887474c1b1346c1f3ccf53b6c4663Reid Spencer      }
3659a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner      break;
366d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner    }
3679a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner    case Instruction::Add:
3685f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      switch (CE->getOperand(0)->getType()->getTypeID()) {
3695f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      default: assert(0 && "Bad add type!"); abort();
3705f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::LongTyID:
3715f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::ULongTyID:
3726b2125c62426190c4be63668e3116ecf3b25fc23Chris Lattner        Result.LongVal = getConstantValue(CE->getOperand(0)).LongVal +
3736b2125c62426190c4be63668e3116ecf3b25fc23Chris Lattner                         getConstantValue(CE->getOperand(1)).LongVal;
3749a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner        break;
3755f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::IntTyID:
3765f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::UIntTyID:
3775f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        Result.IntVal = getConstantValue(CE->getOperand(0)).IntVal +
3785f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner                        getConstantValue(CE->getOperand(1)).IntVal;
3795f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        break;
3805f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::ShortTyID:
3815f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::UShortTyID:
3825f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        Result.ShortVal = getConstantValue(CE->getOperand(0)).ShortVal +
3835f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner                          getConstantValue(CE->getOperand(1)).ShortVal;
3845f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        break;
3855f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::SByteTyID:
3865f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::UByteTyID:
3875f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        Result.SByteVal = getConstantValue(CE->getOperand(0)).SByteVal +
3885f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner                          getConstantValue(CE->getOperand(1)).SByteVal;
3895f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        break;
3905f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::FloatTyID:
3915f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        Result.FloatVal = getConstantValue(CE->getOperand(0)).FloatVal +
3925f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner                          getConstantValue(CE->getOperand(1)).FloatVal;
3935f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        break;
3945f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      case Type::DoubleTyID:
3955f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        Result.DoubleVal = getConstantValue(CE->getOperand(0)).DoubleVal +
3965f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner                           getConstantValue(CE->getOperand(1)).DoubleVal;
3975f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner        break;
3985f90cb8c9838ab03feef93c9dacd5ff652e5d8d2Chris Lattner      }
3999a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner      return Result;
4009a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner    default:
4019a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner      break;
4029a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner    }
403e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling    cerr << "ConstantExpr not handled as global var init: " << *CE << "\n";
4049a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner    abort();
4059a23122b6a4decff3d3f10cb8d9b5ccebe5c7474Chris Lattner  }
406edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman
407f70c22b019494723d0e706f93d6542dfaa6e73a5Chris Lattner  switch (C->getType()->getTypeID()) {
408b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer#define GET_CONST_VAL(TY, CTY, CLASS, GETMETH) \
409b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer  case Type::TY##TyID: Result.TY##Val = (CTY)cast<CLASS>(C)->GETMETH(); break
410b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(Bool   , bool          , ConstantBool, getValue);
411b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(UByte  , unsigned char , ConstantInt, getZExtValue);
412b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(SByte  , signed char   , ConstantInt, getSExtValue);
413b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(UShort , unsigned short, ConstantInt, getZExtValue);
414b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(Short  , signed short  , ConstantInt, getSExtValue);
415b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(UInt   , unsigned int  , ConstantInt, getZExtValue);
416b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(Int    , signed int    , ConstantInt, getSExtValue);
417b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(ULong  , uint64_t      , ConstantInt, getZExtValue);
418b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(Long   , int64_t       , ConstantInt, getSExtValue);
419b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(Float  , float         , ConstantFP, getValue);
420b83eb6447ba155342598f0fabe1f08f5baa9164aReid Spencer    GET_CONST_VAL(Double , double        , ConstantFP, getValue);
421bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner#undef GET_CONST_VAL
422bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  case Type::PointerTyID:
42340cf2f954e7d554872f6eca42c844bc065b02c11Reid Spencer    if (isa<ConstantPointerNull>(C))
424bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner      Result.PointerVal = 0;
42540cf2f954e7d554872f6eca42c844bc065b02c11Reid Spencer    else if (const Function *F = dyn_cast<Function>(C))
42640cf2f954e7d554872f6eca42c844bc065b02c11Reid Spencer      Result = PTOGV(getPointerToFunctionOrStub(const_cast<Function*>(F)));
42740cf2f954e7d554872f6eca42c844bc065b02c11Reid Spencer    else if (const GlobalVariable* GV = dyn_cast<GlobalVariable>(C))
42840cf2f954e7d554872f6eca42c844bc065b02c11Reid Spencer      Result = PTOGV(getOrEmitGlobalVariable(const_cast<GlobalVariable*>(GV)));
42940cf2f954e7d554872f6eca42c844bc065b02c11Reid Spencer    else
430bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner      assert(0 && "Unknown constant pointer type!");
431bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    break;
432bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  default:
433e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling    cerr << "ERROR: Constant unimp for type: " << *C->getType() << "\n";
434d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner    abort();
435bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  }
436bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  return Result;
437bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner}
438bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
43937efe6764568a3829fee26aba532283131d1a104Nate Begeman/// StoreValueToMemory - Stores the data in Val of type Ty at address Ptr.  Ptr
44037efe6764568a3829fee26aba532283131d1a104Nate Begeman/// is the address of the memory at which to store Val, cast to GenericValue *.
44137efe6764568a3829fee26aba532283131d1a104Nate Begeman/// It is not a pointer to a GenericValue containing the address at which to
44237efe6764568a3829fee26aba532283131d1a104Nate Begeman/// store Val.
4434afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman///
444bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattnervoid ExecutionEngine::StoreValueToMemory(GenericValue Val, GenericValue *Ptr,
4454afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman                                         const Type *Ty) {
446a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson  if (getTargetData()->isLittleEndian()) {
447f70c22b019494723d0e706f93d6542dfaa6e73a5Chris Lattner    switch (Ty->getTypeID()) {
448bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::BoolTyID:
449bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::UByteTyID:
450bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::SByteTyID:   Ptr->Untyped[0] = Val.UByteVal; break;
451bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::UShortTyID:
452bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::ShortTyID:   Ptr->Untyped[0] = Val.UShortVal & 255;
453bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            Ptr->Untyped[1] = (Val.UShortVal >> 8) & 255;
454bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            break;
4552be50797a1391278489fa698aa8e17d3f8b04a59Chris Lattner    Store4BytesLittleEndian:
456bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::FloatTyID:
457bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::UIntTyID:
458bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::IntTyID:     Ptr->Untyped[0] =  Val.UIntVal        & 255;
459bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            Ptr->Untyped[1] = (Val.UIntVal >>  8) & 255;
460bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            Ptr->Untyped[2] = (Val.UIntVal >> 16) & 255;
461bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            Ptr->Untyped[3] = (Val.UIntVal >> 24) & 255;
462bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            break;
463a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson    case Type::PointerTyID: if (getTargetData()->getPointerSize() == 4)
4642be50797a1391278489fa698aa8e17d3f8b04a59Chris Lattner                              goto Store4BytesLittleEndian;
465bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::DoubleTyID:
466bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::ULongTyID:
467813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner    case Type::LongTyID:
468813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[0] = (unsigned char)(Val.ULongVal      );
469813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[1] = (unsigned char)(Val.ULongVal >>  8);
470813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[2] = (unsigned char)(Val.ULongVal >> 16);
471813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[3] = (unsigned char)(Val.ULongVal >> 24);
472813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[4] = (unsigned char)(Val.ULongVal >> 32);
473813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[5] = (unsigned char)(Val.ULongVal >> 40);
474813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[6] = (unsigned char)(Val.ULongVal >> 48);
475813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[7] = (unsigned char)(Val.ULongVal >> 56);
476813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      break;
477bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    default:
478e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling      cerr << "Cannot store value of type " << *Ty << "!\n";
479bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    }
480bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  } else {
481f70c22b019494723d0e706f93d6542dfaa6e73a5Chris Lattner    switch (Ty->getTypeID()) {
482bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::BoolTyID:
483bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::UByteTyID:
484bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::SByteTyID:   Ptr->Untyped[0] = Val.UByteVal; break;
485bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::UShortTyID:
486bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::ShortTyID:   Ptr->Untyped[1] = Val.UShortVal & 255;
487bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            Ptr->Untyped[0] = (Val.UShortVal >> 8) & 255;
488bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            break;
4892be50797a1391278489fa698aa8e17d3f8b04a59Chris Lattner    Store4BytesBigEndian:
490bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::FloatTyID:
491bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::UIntTyID:
492bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::IntTyID:     Ptr->Untyped[3] =  Val.UIntVal        & 255;
493bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            Ptr->Untyped[2] = (Val.UIntVal >>  8) & 255;
494bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            Ptr->Untyped[1] = (Val.UIntVal >> 16) & 255;
495bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            Ptr->Untyped[0] = (Val.UIntVal >> 24) & 255;
496bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner                            break;
497a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson    case Type::PointerTyID: if (getTargetData()->getPointerSize() == 4)
4982be50797a1391278489fa698aa8e17d3f8b04a59Chris Lattner                              goto Store4BytesBigEndian;
499bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::DoubleTyID:
500bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    case Type::ULongTyID:
501813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner    case Type::LongTyID:
502edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman      Ptr->Untyped[7] = (unsigned char)(Val.ULongVal      );
503813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[6] = (unsigned char)(Val.ULongVal >>  8);
504813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[5] = (unsigned char)(Val.ULongVal >> 16);
505813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[4] = (unsigned char)(Val.ULongVal >> 24);
506813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[3] = (unsigned char)(Val.ULongVal >> 32);
507813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[2] = (unsigned char)(Val.ULongVal >> 40);
508813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[1] = (unsigned char)(Val.ULongVal >> 48);
509813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      Ptr->Untyped[0] = (unsigned char)(Val.ULongVal >> 56);
510813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner      break;
511bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    default:
512e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling      cerr << "Cannot store value of type " << *Ty << "!\n";
513bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    }
514bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  }
515bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner}
516bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
5174afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman/// FIXME: document
5184afac18fd4cae1b93907d7db03c5fdb7f2f66d64Misha Brukman///
519f88b9a639770327196b2a00f365155b954dd1d30Chris LattnerGenericValue ExecutionEngine::LoadValueFromMemory(GenericValue *Ptr,
520f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                                  const Type *Ty) {
521f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner  GenericValue Result;
522a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson  if (getTargetData()->isLittleEndian()) {
523f70c22b019494723d0e706f93d6542dfaa6e73a5Chris Lattner    switch (Ty->getTypeID()) {
524f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::BoolTyID:
525f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::UByteTyID:
526f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::SByteTyID:   Result.UByteVal = Ptr->Untyped[0]; break;
527f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::UShortTyID:
528f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::ShortTyID:   Result.UShortVal = (unsigned)Ptr->Untyped[0] |
529f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                              ((unsigned)Ptr->Untyped[1] << 8);
530f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                            break;
531edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman    Load4BytesLittleEndian:
532f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::FloatTyID:
533f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::UIntTyID:
534f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::IntTyID:     Result.UIntVal = (unsigned)Ptr->Untyped[0] |
535f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                            ((unsigned)Ptr->Untyped[1] <<  8) |
536f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                            ((unsigned)Ptr->Untyped[2] << 16) |
537f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                            ((unsigned)Ptr->Untyped[3] << 24);
538f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                            break;
539a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson    case Type::PointerTyID: if (getTargetData()->getPointerSize() == 4)
540f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                              goto Load4BytesLittleEndian;
541f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::DoubleTyID:
542f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::ULongTyID:
543f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::LongTyID:    Result.ULongVal = (uint64_t)Ptr->Untyped[0] |
544f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[1] <<  8) |
545f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[2] << 16) |
546f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[3] << 24) |
547f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[4] << 32) |
548f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[5] << 40) |
549f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[6] << 48) |
550f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[7] << 56);
551f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                            break;
552f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    default:
553e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling      cerr << "Cannot load value of type " << *Ty << "!\n";
554f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner      abort();
555f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    }
556f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner  } else {
557f70c22b019494723d0e706f93d6542dfaa6e73a5Chris Lattner    switch (Ty->getTypeID()) {
558f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::BoolTyID:
559f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::UByteTyID:
560f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::SByteTyID:   Result.UByteVal = Ptr->Untyped[0]; break;
561f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::UShortTyID:
562f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::ShortTyID:   Result.UShortVal = (unsigned)Ptr->Untyped[1] |
563f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                              ((unsigned)Ptr->Untyped[0] << 8);
564f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                            break;
565f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    Load4BytesBigEndian:
566f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::FloatTyID:
567f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::UIntTyID:
568f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::IntTyID:     Result.UIntVal = (unsigned)Ptr->Untyped[3] |
569f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                            ((unsigned)Ptr->Untyped[2] <<  8) |
570f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                            ((unsigned)Ptr->Untyped[1] << 16) |
571f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                            ((unsigned)Ptr->Untyped[0] << 24);
572f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                            break;
573a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson    case Type::PointerTyID: if (getTargetData()->getPointerSize() == 4)
574f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                              goto Load4BytesBigEndian;
575f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::DoubleTyID:
576f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::ULongTyID:
577f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    case Type::LongTyID:    Result.ULongVal = (uint64_t)Ptr->Untyped[7] |
578f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[6] <<  8) |
579f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[5] << 16) |
580f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[4] << 24) |
581f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[3] << 32) |
582f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[2] << 40) |
583f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[1] << 48) |
584f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                                             ((uint64_t)Ptr->Untyped[0] << 56);
585f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner                            break;
586f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    default:
587e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling      cerr << "Cannot load value of type " << *Ty << "!\n";
588f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner      abort();
589f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner    }
590f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner  }
591f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner  return Result;
592f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner}
593f88b9a639770327196b2a00f365155b954dd1d30Chris Lattner
594bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// InitializeMemory - Recursive function to apply a Constant value into the
595bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner// specified memory location...
596bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner//
597bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattnervoid ExecutionEngine::InitializeMemory(const Constant *Init, void *Addr) {
598bd1d382cc47dfc43ee758714bc22ab5a750bad15Chris Lattner  if (isa<UndefValue>(Init)) {
599bd1d382cc47dfc43ee758714bc22ab5a750bad15Chris Lattner    return;
6007c2b7c7c75a3549b2d6933edf3110294a33ff2d4Robert Bocchino  } else if (const ConstantPacked *CP = dyn_cast<ConstantPacked>(Init)) {
6017c2b7c7c75a3549b2d6933edf3110294a33ff2d4Robert Bocchino    unsigned ElementSize =
602a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson      getTargetData()->getTypeSize(CP->getType()->getElementType());
6037c2b7c7c75a3549b2d6933edf3110294a33ff2d4Robert Bocchino    for (unsigned i = 0, e = CP->getNumOperands(); i != e; ++i)
6047c2b7c7c75a3549b2d6933edf3110294a33ff2d4Robert Bocchino      InitializeMemory(CP->getOperand(i), (char*)Addr+i*ElementSize);
6057c2b7c7c75a3549b2d6933edf3110294a33ff2d4Robert Bocchino    return;
606bd1d382cc47dfc43ee758714bc22ab5a750bad15Chris Lattner  } else if (Init->getType()->isFirstClassType()) {
607bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    GenericValue Val = getConstantValue(Init);
608bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    StoreValueToMemory(Val, (GenericValue*)Addr, Init->getType());
609bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    return;
610dd2c82a427a089e7c704af44eeeb2a10a38e2519Chris Lattner  } else if (isa<ConstantAggregateZero>(Init)) {
611a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson    memset(Addr, 0, (size_t)getTargetData()->getTypeSize(Init->getType()));
612dd2c82a427a089e7c704af44eeeb2a10a38e2519Chris Lattner    return;
613bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  }
614bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
615f70c22b019494723d0e706f93d6542dfaa6e73a5Chris Lattner  switch (Init->getType()->getTypeID()) {
616bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  case Type::ArrayTyID: {
617bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    const ConstantArray *CPA = cast<ConstantArray>(Init);
618edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman    unsigned ElementSize =
619a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson      getTargetData()->getTypeSize(CPA->getType()->getElementType());
62015876bb28c9c0983279c30a123c13224648574c1Alkis Evlogimenos    for (unsigned i = 0, e = CPA->getNumOperands(); i != e; ++i)
62115876bb28c9c0983279c30a123c13224648574c1Alkis Evlogimenos      InitializeMemory(CPA->getOperand(i), (char*)Addr+i*ElementSize);
622bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    return;
623bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  }
624bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
625bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  case Type::StructTyID: {
626bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    const ConstantStruct *CPS = cast<ConstantStruct>(Init);
627bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    const StructLayout *SL =
628a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson      getTargetData()->getStructLayout(cast<StructType>(CPS->getType()));
62915876bb28c9c0983279c30a123c13224648574c1Alkis Evlogimenos    for (unsigned i = 0, e = CPS->getNumOperands(); i != e; ++i)
63015876bb28c9c0983279c30a123c13224648574c1Alkis Evlogimenos      InitializeMemory(CPS->getOperand(i), (char*)Addr+SL->MemberOffsets[i]);
631bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    return;
632bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  }
633bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
634bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  default:
635e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling    cerr << "Bad Type: " << *Init->getType() << "\n";
636bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    assert(0 && "Unknown constant type to initialize memory with!");
637bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  }
638bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner}
639bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner
640bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner/// EmitGlobals - Emit all of the global variables to memory, storing their
641bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner/// addresses into GlobalAddress.  This must make sure to copy the contents of
642bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner/// their initializers into the memory.
643bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner///
644bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattnervoid ExecutionEngine::emitGlobals() {
645a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson  const TargetData *TD = getTargetData();
646edf128a7fa90f2b0b7ee24741a04a7ae1ecd6f7eMisha Brukman
647bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner  // Loop over all of the global variables in the program, allocating the memory
648fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  // to hold them.  If there is more than one module, do a prepass over globals
649fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  // to figure out how the different modules should link together.
650fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  //
651fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  std::map<std::pair<std::string, const Type*>,
652fe854034677f59baca1e38075e71f6efca247a03Chris Lattner           const GlobalValue*> LinkedGlobalsMap;
653fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
654fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  if (Modules.size() != 1) {
655fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    for (unsigned m = 0, e = Modules.size(); m != e; ++m) {
656fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      Module &M = *Modules[m]->getModule();
657fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      for (Module::const_global_iterator I = M.global_begin(),
658fe854034677f59baca1e38075e71f6efca247a03Chris Lattner           E = M.global_end(); I != E; ++I) {
659fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        const GlobalValue *GV = I;
660fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (GV->hasInternalLinkage() || GV->isExternal() ||
661fe854034677f59baca1e38075e71f6efca247a03Chris Lattner            GV->hasAppendingLinkage() || !GV->hasName())
662fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          continue;// Ignore external globals and globals with internal linkage.
663fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
664fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        const GlobalValue *&GVEntry =
665fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          LinkedGlobalsMap[std::make_pair(GV->getName(), GV->getType())];
666fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
667fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // If this is the first time we've seen this global, it is the canonical
668fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // version.
669fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (!GVEntry) {
670fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          GVEntry = GV;
671fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          continue;
672fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        }
673fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
674fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // If the existing global is strong, never replace it.
675b74ed07bfd3af42331b1964c24c39912610a08f4Anton Korobeynikov        if (GVEntry->hasExternalLinkage() ||
676b74ed07bfd3af42331b1964c24c39912610a08f4Anton Korobeynikov            GVEntry->hasDLLImportLinkage() ||
677b74ed07bfd3af42331b1964c24c39912610a08f4Anton Korobeynikov            GVEntry->hasDLLExportLinkage())
678fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          continue;
679fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
680fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // Otherwise, we know it's linkonce/weak, replace it if this is a strong
681fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // symbol.
68278ee7b78c3c47b71c4b7a1475438d6574216a64bAnton Korobeynikov        if (GV->hasExternalLinkage() || GVEntry->hasExternalWeakLinkage())
683fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          GVEntry = GV;
684d8c03bfa0a8cbcbf3ee31b0e9b52126c9dbafe2aChris Lattner      }
685bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner    }
686fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  }
687fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
688fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  std::vector<const GlobalValue*> NonCanonicalGlobals;
689fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  for (unsigned m = 0, e = Modules.size(); m != e; ++m) {
690fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    Module &M = *Modules[m]->getModule();
691fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    for (Module::const_global_iterator I = M.global_begin(), E = M.global_end();
692fe854034677f59baca1e38075e71f6efca247a03Chris Lattner         I != E; ++I) {
693fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      // In the multi-module case, see what this global maps to.
694fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      if (!LinkedGlobalsMap.empty()) {
695fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (const GlobalValue *GVEntry =
696fe854034677f59baca1e38075e71f6efca247a03Chris Lattner              LinkedGlobalsMap[std::make_pair(I->getName(), I->getType())]) {
697fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          // If something else is the canonical global, ignore this one.
698fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          if (GVEntry != &*I) {
699fe854034677f59baca1e38075e71f6efca247a03Chris Lattner            NonCanonicalGlobals.push_back(I);
700fe854034677f59baca1e38075e71f6efca247a03Chris Lattner            continue;
701fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          }
702fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        }
703fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      }
704fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
705fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      if (!I->isExternal()) {
706fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // Get the type of the global.
707fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        const Type *Ty = I->getType()->getElementType();
708fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
709fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // Allocate some memory for it!
710fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        unsigned Size = TD->getTypeSize(Ty);
711fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        addGlobalMapping(I, new char[Size]);
712fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      } else {
713fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // External variable reference. Try to use the dynamic loader to
714fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        // get a pointer to it.
715fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (void *SymAddr =
716fe854034677f59baca1e38075e71f6efca247a03Chris Lattner            sys::DynamicLibrary::SearchForAddressOfSymbol(I->getName().c_str()))
717fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          addGlobalMapping(I, SymAddr);
718fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        else {
719e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling          cerr << "Could not resolve external global address: "
720e81561909d128c6e2d8033cb5465a49b2596b26aBill Wendling               << I->getName() << "\n";
721fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          abort();
722fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        }
723fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      }
724fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    }
725fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
726fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // If there are multiple modules, map the non-canonical globals to their
727fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // canonical location.
728fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    if (!NonCanonicalGlobals.empty()) {
729fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      for (unsigned i = 0, e = NonCanonicalGlobals.size(); i != e; ++i) {
730fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        const GlobalValue *GV = NonCanonicalGlobals[i];
731fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        const GlobalValue *CGV =
732fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          LinkedGlobalsMap[std::make_pair(GV->getName(), GV->getType())];
733fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        void *Ptr = getPointerToGlobalIfAvailable(CGV);
734fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        assert(Ptr && "Canonical global wasn't codegen'd!");
735fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        addGlobalMapping(GV, getPointerToGlobalIfAvailable(CGV));
736fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      }
737fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    }
738fe854034677f59baca1e38075e71f6efca247a03Chris Lattner
739fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // Now that all of the globals are set up in memory, loop through them all and
740fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    // initialize their contents.
741fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    for (Module::const_global_iterator I = M.global_begin(), E = M.global_end();
742fe854034677f59baca1e38075e71f6efca247a03Chris Lattner         I != E; ++I) {
743fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      if (!I->isExternal()) {
744fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        if (!LinkedGlobalsMap.empty()) {
745fe854034677f59baca1e38075e71f6efca247a03Chris Lattner          if (const GlobalValue *GVEntry =
746fe854034677f59baca1e38075e71f6efca247a03Chris Lattner                LinkedGlobalsMap[std::make_pair(I->getName(), I->getType())])
747fe854034677f59baca1e38075e71f6efca247a03Chris Lattner            if (GVEntry != &*I)  // Not the canonical variable.
748fe854034677f59baca1e38075e71f6efca247a03Chris Lattner              continue;
749fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        }
750fe854034677f59baca1e38075e71f6efca247a03Chris Lattner        EmitGlobalVariable(I);
751fe854034677f59baca1e38075e71f6efca247a03Chris Lattner      }
752fe854034677f59baca1e38075e71f6efca247a03Chris Lattner    }
753fe854034677f59baca1e38075e71f6efca247a03Chris Lattner  }
75424b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner}
75524b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner
75624b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner// EmitGlobalVariable - This method emits the specified global variable to the
75724b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner// address specified in GlobalAddresses, or allocates new memory if it's not
75824b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner// already in the map.
759c07ed1387503d25c0b93fcf617f69329d73fc589Chris Lattnervoid ExecutionEngine::EmitGlobalVariable(const GlobalVariable *GV) {
76055d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner  void *GA = getPointerToGlobalIfAvailable(GV);
761480f093dc2b6aff9b501cc56cf5728513e55be81Bill Wendling  DOUT << "Global '" << GV->getName() << "' -> " << GA << "\n";
76223c472436940aa7fc82ff99e8cca6788d08a8105Chris Lattner
763c07ed1387503d25c0b93fcf617f69329d73fc589Chris Lattner  const Type *ElTy = GV->getType()->getElementType();
764a69571c7991813c93cba64e88eced6899ce93d81Owen Anderson  size_t GVSize = (size_t)getTargetData()->getTypeSize(ElTy);
76524b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner  if (GA == 0) {
76624b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner    // If it's not already specified, allocate memory for the global.
767a98c5453b28b37c3fad118712ff4e634bfc36163Chris Lattner    GA = new char[GVSize];
76855d86482bd9fac6f90a7f6fb35c2f4dec9569fdbChris Lattner    addGlobalMapping(GV, GA);
76924b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner  }
770c07ed1387503d25c0b93fcf617f69329d73fc589Chris Lattner
77124b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner  InitializeMemory(GV->getInitializer(), GA);
772813c8152825db530a6ef4ee86e8038bbee16deb3Chris Lattner  NumInitBytes += (unsigned)GVSize;
77324b0a18c4357de0515c542e97edb2c2eacc543f2Chris Lattner  ++NumGlobals;
774bd199fb1148b9e16c4e6f3d0ee386c2505a55b71Chris Lattner}
775