summaryrefslogtreecommitdiffstats
path: root/contrib/llvm/lib/ExecutionEngine/JIT
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/llvm/lib/ExecutionEngine/JIT')
-rw-r--r--contrib/llvm/lib/ExecutionEngine/JIT/JIT.cpp156
-rw-r--r--contrib/llvm/lib/ExecutionEngine/JIT/JITDwarfEmitter.cpp596
-rw-r--r--contrib/llvm/lib/ExecutionEngine/JIT/JITDwarfEmitter.h77
-rw-r--r--contrib/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp52
-rw-r--r--contrib/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp44
5 files changed, 13 insertions, 912 deletions
diff --git a/contrib/llvm/lib/ExecutionEngine/JIT/JIT.cpp b/contrib/llvm/lib/ExecutionEngine/JIT/JIT.cpp
index 53ea0a2..246a675 100644
--- a/contrib/llvm/lib/ExecutionEngine/JIT/JIT.cpp
+++ b/contrib/llvm/lib/ExecutionEngine/JIT/JIT.cpp
@@ -67,140 +67,6 @@ static struct RegisterJIT {
extern "C" void LLVMLinkInJIT() {
}
-// Determine whether we can register EH tables.
-#if (defined(__GNUC__) && !defined(__ARM_EABI__) && \
- !defined(__USING_SJLJ_EXCEPTIONS__))
-#define HAVE_EHTABLE_SUPPORT 1
-#else
-#define HAVE_EHTABLE_SUPPORT 0
-#endif
-
-#if HAVE_EHTABLE_SUPPORT
-
-// libgcc defines the __register_frame function to dynamically register new
-// dwarf frames for exception handling. This functionality is not portable
-// across compilers and is only provided by GCC. We use the __register_frame
-// function here so that code generated by the JIT cooperates with the unwinding
-// runtime of libgcc. When JITting with exception handling enable, LLVM
-// generates dwarf frames and registers it to libgcc with __register_frame.
-//
-// The __register_frame function works with Linux.
-//
-// Unfortunately, this functionality seems to be in libgcc after the unwinding
-// library of libgcc for darwin was written. The code for darwin overwrites the
-// value updated by __register_frame with a value fetched with "keymgr".
-// "keymgr" is an obsolete functionality, which should be rewritten some day.
-// In the meantime, since "keymgr" is on all libgccs shipped with apple-gcc, we
-// need a workaround in LLVM which uses the "keymgr" to dynamically modify the
-// values of an opaque key, used by libgcc to find dwarf tables.
-
-extern "C" void __register_frame(void*);
-extern "C" void __deregister_frame(void*);
-
-#if defined(__APPLE__) && MAC_OS_X_VERSION_MAX_ALLOWED <= 1050
-# define USE_KEYMGR 1
-#else
-# define USE_KEYMGR 0
-#endif
-
-#if USE_KEYMGR
-
-namespace {
-
-// LibgccObject - This is the structure defined in libgcc. There is no #include
-// provided for this structure, so we also define it here. libgcc calls it
-// "struct object". The structure is undocumented in libgcc.
-struct LibgccObject {
- void *unused1;
- void *unused2;
- void *unused3;
-
- /// frame - Pointer to the exception table.
- void *frame;
-
- /// encoding - The encoding of the object?
- union {
- struct {
- unsigned long sorted : 1;
- unsigned long from_array : 1;
- unsigned long mixed_encoding : 1;
- unsigned long encoding : 8;
- unsigned long count : 21;
- } b;
- size_t i;
- } encoding;
-
- /// fde_end - libgcc defines this field only if some macro is defined. We
- /// include this field even if it may not there, to make libgcc happy.
- char *fde_end;
-
- /// next - At least we know it's a chained list!
- struct LibgccObject *next;
-};
-
-// "kemgr" stuff. Apparently, all frame tables are stored there.
-extern "C" void _keymgr_set_and_unlock_processwide_ptr(int, void *);
-extern "C" void *_keymgr_get_and_lock_processwide_ptr(int);
-#define KEYMGR_GCC3_DW2_OBJ_LIST 302 /* Dwarf2 object list */
-
-/// LibgccObjectInfo - libgcc defines this struct as km_object_info. It
-/// probably contains all dwarf tables that are loaded.
-struct LibgccObjectInfo {
-
- /// seenObjects - LibgccObjects already parsed by the unwinding runtime.
- ///
- struct LibgccObject* seenObjects;
-
- /// unseenObjects - LibgccObjects not parsed yet by the unwinding runtime.
- ///
- struct LibgccObject* unseenObjects;
-
- unsigned unused[2];
-};
-
-/// darwin_register_frame - Since __register_frame does not work with darwin's
-/// libgcc,we provide our own function, which "tricks" libgcc by modifying the
-/// "Dwarf2 object list" key.
-void DarwinRegisterFrame(void* FrameBegin) {
- // Get the key.
- LibgccObjectInfo* LOI = (struct LibgccObjectInfo*)
- _keymgr_get_and_lock_processwide_ptr(KEYMGR_GCC3_DW2_OBJ_LIST);
- assert(LOI && "This should be preallocated by the runtime");
-
- // Allocate a new LibgccObject to represent this frame. Deallocation of this
- // object may be impossible: since darwin code in libgcc was written after
- // the ability to dynamically register frames, things may crash if we
- // deallocate it.
- struct LibgccObject* ob = (struct LibgccObject*)
- malloc(sizeof(struct LibgccObject));
-
- // Do like libgcc for the values of the field.
- ob->unused1 = (void *)-1;
- ob->unused2 = 0;
- ob->unused3 = 0;
- ob->frame = FrameBegin;
- ob->encoding.i = 0;
- ob->encoding.b.encoding = llvm::dwarf::DW_EH_PE_omit;
-
- // Put the info on both places, as libgcc uses the first or the second
- // field. Note that we rely on having two pointers here. If fde_end was a
- // char, things would get complicated.
- ob->fde_end = (char*)LOI->unseenObjects;
- ob->next = LOI->unseenObjects;
-
- // Update the key's unseenObjects list.
- LOI->unseenObjects = ob;
-
- // Finally update the "key". Apparently, libgcc requires it.
- _keymgr_set_and_unlock_processwide_ptr(KEYMGR_GCC3_DW2_OBJ_LIST,
- LOI);
-
-}
-
-}
-#endif // __APPLE__
-#endif // HAVE_EHTABLE_SUPPORT
-
/// createJIT - This is the factory method for creating a JIT for the current
/// machine, it does not fall back to the interpreter. This takes ownership
/// of the module.
@@ -293,33 +159,11 @@ JIT::JIT(Module *M, TargetMachine &tm, TargetJITInfo &tji,
report_fatal_error("Target does not support machine code emission!");
}
- // Register routine for informing unwinding runtime about new EH frames
-#if HAVE_EHTABLE_SUPPORT
-#if USE_KEYMGR
- struct LibgccObjectInfo* LOI = (struct LibgccObjectInfo*)
- _keymgr_get_and_lock_processwide_ptr(KEYMGR_GCC3_DW2_OBJ_LIST);
-
- // The key is created on demand, and libgcc creates it the first time an
- // exception occurs. Since we need the key to register frames, we create
- // it now.
- if (!LOI)
- LOI = (LibgccObjectInfo*)calloc(sizeof(struct LibgccObjectInfo), 1);
- _keymgr_set_and_unlock_processwide_ptr(KEYMGR_GCC3_DW2_OBJ_LIST, LOI);
- InstallExceptionTableRegister(DarwinRegisterFrame);
- // Not sure about how to deregister on Darwin.
-#else
- InstallExceptionTableRegister(__register_frame);
- InstallExceptionTableDeregister(__deregister_frame);
-#endif // __APPLE__
-#endif // HAVE_EHTABLE_SUPPORT
-
// Initialize passes.
PM.doInitialization();
}
JIT::~JIT() {
- // Unregister all exception tables registered by this JIT.
- DeregisterAllTables();
// Cleanup.
AllJits->Remove(this);
delete jitstate;
diff --git a/contrib/llvm/lib/ExecutionEngine/JIT/JITDwarfEmitter.cpp b/contrib/llvm/lib/ExecutionEngine/JIT/JITDwarfEmitter.cpp
deleted file mode 100644
index 35d2b8b..0000000
--- a/contrib/llvm/lib/ExecutionEngine/JIT/JITDwarfEmitter.cpp
+++ /dev/null
@@ -1,596 +0,0 @@
-//===----- JITDwarfEmitter.cpp - Write dwarf tables into memory -----------===//
-//
-// The LLVM Compiler Infrastructure
-//
-// This file is distributed under the University of Illinois Open Source
-// License. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-//
-// This file defines a JITDwarfEmitter object that is used by the JIT to
-// write dwarf tables to memory.
-//
-//===----------------------------------------------------------------------===//
-
-#include "JITDwarfEmitter.h"
-#include "JIT.h"
-#include "llvm/ADT/DenseMap.h"
-#include "llvm/CodeGen/JITCodeEmitter.h"
-#include "llvm/CodeGen/MachineFunction.h"
-#include "llvm/CodeGen/MachineModuleInfo.h"
-#include "llvm/ExecutionEngine/JITMemoryManager.h"
-#include "llvm/IR/DataLayout.h"
-#include "llvm/IR/Function.h"
-#include "llvm/MC/MCAsmInfo.h"
-#include "llvm/MC/MCSymbol.h"
-#include "llvm/MC/MachineLocation.h"
-#include "llvm/Support/ErrorHandling.h"
-#include "llvm/Target/TargetFrameLowering.h"
-#include "llvm/Target/TargetInstrInfo.h"
-#include "llvm/Target/TargetMachine.h"
-#include "llvm/Target/TargetRegisterInfo.h"
-using namespace llvm;
-
-JITDwarfEmitter::JITDwarfEmitter(JIT& theJit) : MMI(0), Jit(theJit) {}
-
-
-unsigned char* JITDwarfEmitter::EmitDwarfTable(MachineFunction& F,
- JITCodeEmitter& jce,
- unsigned char* StartFunction,
- unsigned char* EndFunction,
- unsigned char* &EHFramePtr) {
- assert(MMI && "MachineModuleInfo not registered!");
-
- const TargetMachine& TM = F.getTarget();
- TD = TM.getDataLayout();
- stackGrowthDirection = TM.getFrameLowering()->getStackGrowthDirection();
- RI = TM.getRegisterInfo();
- MAI = TM.getMCAsmInfo();
- JCE = &jce;
-
- unsigned char* ExceptionTable = EmitExceptionTable(&F, StartFunction,
- EndFunction);
-
- unsigned char* Result = 0;
-
- const std::vector<const Function *> Personalities = MMI->getPersonalities();
- EHFramePtr = EmitCommonEHFrame(Personalities[MMI->getPersonalityIndex()]);
-
- Result = EmitEHFrame(Personalities[MMI->getPersonalityIndex()], EHFramePtr,
- StartFunction, EndFunction, ExceptionTable);
-
- return Result;
-}
-
-
-void
-JITDwarfEmitter::EmitFrameMoves(intptr_t BaseLabelPtr,
- const std::vector<MachineMove> &Moves) const {
- unsigned PointerSize = TD->getPointerSize();
- int stackGrowth = stackGrowthDirection == TargetFrameLowering::StackGrowsUp ?
- PointerSize : -PointerSize;
- MCSymbol *BaseLabel = 0;
-
- for (unsigned i = 0, N = Moves.size(); i < N; ++i) {
- const MachineMove &Move = Moves[i];
- MCSymbol *Label = Move.getLabel();
-
- // Throw out move if the label is invalid.
- if (Label && (*JCE->getLabelLocations())[Label] == 0)
- continue;
-
- intptr_t LabelPtr = 0;
- if (Label) LabelPtr = JCE->getLabelAddress(Label);
-
- const MachineLocation &Dst = Move.getDestination();
- const MachineLocation &Src = Move.getSource();
-
- // Advance row if new location.
- if (BaseLabelPtr && Label && BaseLabel != Label) {
- JCE->emitByte(dwarf::DW_CFA_advance_loc4);
- JCE->emitInt32(LabelPtr - BaseLabelPtr);
-
- BaseLabel = Label;
- BaseLabelPtr = LabelPtr;
- }
-
- // If advancing cfa.
- if (Dst.isReg() && Dst.getReg() == MachineLocation::VirtualFP) {
- if (!Src.isReg()) {
- if (Src.getReg() == MachineLocation::VirtualFP) {
- JCE->emitByte(dwarf::DW_CFA_def_cfa_offset);
- } else {
- JCE->emitByte(dwarf::DW_CFA_def_cfa);
- JCE->emitULEB128Bytes(RI->getDwarfRegNum(Src.getReg(), true));
- }
-
- JCE->emitULEB128Bytes(-Src.getOffset());
- } else {
- llvm_unreachable("Machine move not supported yet.");
- }
- } else if (Src.isReg() &&
- Src.getReg() == MachineLocation::VirtualFP) {
- if (Dst.isReg()) {
- JCE->emitByte(dwarf::DW_CFA_def_cfa_register);
- JCE->emitULEB128Bytes(RI->getDwarfRegNum(Dst.getReg(), true));
- } else {
- llvm_unreachable("Machine move not supported yet.");
- }
- } else {
- unsigned Reg = RI->getDwarfRegNum(Src.getReg(), true);
- int Offset = Dst.getOffset() / stackGrowth;
-
- if (Offset < 0) {
- JCE->emitByte(dwarf::DW_CFA_offset_extended_sf);
- JCE->emitULEB128Bytes(Reg);
- JCE->emitSLEB128Bytes(Offset);
- } else if (Reg < 64) {
- JCE->emitByte(dwarf::DW_CFA_offset + Reg);
- JCE->emitULEB128Bytes(Offset);
- } else {
- JCE->emitByte(dwarf::DW_CFA_offset_extended);
- JCE->emitULEB128Bytes(Reg);
- JCE->emitULEB128Bytes(Offset);
- }
- }
- }
-}
-
-/// SharedTypeIds - How many leading type ids two landing pads have in common.
-static unsigned SharedTypeIds(const LandingPadInfo *L,
- const LandingPadInfo *R) {
- const std::vector<int> &LIds = L->TypeIds, &RIds = R->TypeIds;
- unsigned LSize = LIds.size(), RSize = RIds.size();
- unsigned MinSize = LSize < RSize ? LSize : RSize;
- unsigned Count = 0;
-
- for (; Count != MinSize; ++Count)
- if (LIds[Count] != RIds[Count])
- return Count;
-
- return Count;
-}
-
-
-/// PadLT - Order landing pads lexicographically by type id.
-static bool PadLT(const LandingPadInfo *L, const LandingPadInfo *R) {
- const std::vector<int> &LIds = L->TypeIds, &RIds = R->TypeIds;
- unsigned LSize = LIds.size(), RSize = RIds.size();
- unsigned MinSize = LSize < RSize ? LSize : RSize;
-
- for (unsigned i = 0; i != MinSize; ++i)
- if (LIds[i] != RIds[i])
- return LIds[i] < RIds[i];
-
- return LSize < RSize;
-}
-
-namespace {
-
-/// ActionEntry - Structure describing an entry in the actions table.
-struct ActionEntry {
- int ValueForTypeID; // The value to write - may not be equal to the type id.
- int NextAction;
- struct ActionEntry *Previous;
-};
-
-/// PadRange - Structure holding a try-range and the associated landing pad.
-struct PadRange {
- // The index of the landing pad.
- unsigned PadIndex;
- // The index of the begin and end labels in the landing pad's label lists.
- unsigned RangeIndex;
-};
-
-typedef DenseMap<MCSymbol*, PadRange> RangeMapType;
-
-/// CallSiteEntry - Structure describing an entry in the call-site table.
-struct CallSiteEntry {
- MCSymbol *BeginLabel; // zero indicates the start of the function.
- MCSymbol *EndLabel; // zero indicates the end of the function.
- MCSymbol *PadLabel; // zero indicates that there is no landing pad.
- unsigned Action;
-};
-
-}
-
-unsigned char* JITDwarfEmitter::EmitExceptionTable(MachineFunction* MF,
- unsigned char* StartFunction,
- unsigned char* EndFunction) const {
- assert(MMI && "MachineModuleInfo not registered!");
-
- // Map all labels and get rid of any dead landing pads.
- MMI->TidyLandingPads(JCE->getLabelLocations());
-
- const std::vector<const GlobalVariable *> &TypeInfos = MMI->getTypeInfos();
- const std::vector<unsigned> &FilterIds = MMI->getFilterIds();
- const std::vector<LandingPadInfo> &PadInfos = MMI->getLandingPads();
- if (PadInfos.empty()) return 0;
-
- // Sort the landing pads in order of their type ids. This is used to fold
- // duplicate actions.
- SmallVector<const LandingPadInfo *, 64> LandingPads;
- LandingPads.reserve(PadInfos.size());
- for (unsigned i = 0, N = PadInfos.size(); i != N; ++i)
- LandingPads.push_back(&PadInfos[i]);
- std::sort(LandingPads.begin(), LandingPads.end(), PadLT);
-
- // Negative type ids index into FilterIds, positive type ids index into
- // TypeInfos. The value written for a positive type id is just the type
- // id itself. For a negative type id, however, the value written is the
- // (negative) byte offset of the corresponding FilterIds entry. The byte
- // offset is usually equal to the type id, because the FilterIds entries
- // are written using a variable width encoding which outputs one byte per
- // entry as long as the value written is not too large, but can differ.
- // This kind of complication does not occur for positive type ids because
- // type infos are output using a fixed width encoding.
- // FilterOffsets[i] holds the byte offset corresponding to FilterIds[i].
- SmallVector<int, 16> FilterOffsets;
- FilterOffsets.reserve(FilterIds.size());
- int Offset = -1;
- for(std::vector<unsigned>::const_iterator I = FilterIds.begin(),
- E = FilterIds.end(); I != E; ++I) {
- FilterOffsets.push_back(Offset);
- Offset -= MCAsmInfo::getULEB128Size(*I);
- }
-
- // Compute the actions table and gather the first action index for each
- // landing pad site.
- SmallVector<ActionEntry, 32> Actions;
- SmallVector<unsigned, 64> FirstActions;
- FirstActions.reserve(LandingPads.size());
-
- int FirstAction = 0;
- unsigned SizeActions = 0;
- for (unsigned i = 0, N = LandingPads.size(); i != N; ++i) {
- const LandingPadInfo *LP = LandingPads[i];
- const std::vector<int> &TypeIds = LP->TypeIds;
- const unsigned NumShared = i ? SharedTypeIds(LP, LandingPads[i-1]) : 0;
- unsigned SizeSiteActions = 0;
-
- if (NumShared < TypeIds.size()) {
- unsigned SizeAction = 0;
- ActionEntry *PrevAction = 0;
-
- if (NumShared) {
- const unsigned SizePrevIds = LandingPads[i-1]->TypeIds.size();
- assert(Actions.size());
- PrevAction = &Actions.back();
- SizeAction = MCAsmInfo::getSLEB128Size(PrevAction->NextAction) +
- MCAsmInfo::getSLEB128Size(PrevAction->ValueForTypeID);
- for (unsigned j = NumShared; j != SizePrevIds; ++j) {
- SizeAction -= MCAsmInfo::getSLEB128Size(PrevAction->ValueForTypeID);
- SizeAction += -PrevAction->NextAction;
- PrevAction = PrevAction->Previous;
- }
- }
-
- // Compute the actions.
- for (unsigned I = NumShared, M = TypeIds.size(); I != M; ++I) {
- int TypeID = TypeIds[I];
- assert(-1-TypeID < (int)FilterOffsets.size() && "Unknown filter id!");
- int ValueForTypeID = TypeID < 0 ? FilterOffsets[-1 - TypeID] : TypeID;
- unsigned SizeTypeID = MCAsmInfo::getSLEB128Size(ValueForTypeID);
-
- int NextAction = SizeAction ? -(SizeAction + SizeTypeID) : 0;
- SizeAction = SizeTypeID + MCAsmInfo::getSLEB128Size(NextAction);
- SizeSiteActions += SizeAction;
-
- ActionEntry Action = {ValueForTypeID, NextAction, PrevAction};
- Actions.push_back(Action);
-
- PrevAction = &Actions.back();
- }
-
- // Record the first action of the landing pad site.
- FirstAction = SizeActions + SizeSiteActions - SizeAction + 1;
- } // else identical - re-use previous FirstAction
-
- FirstActions.push_back(FirstAction);
-
- // Compute this sites contribution to size.
- SizeActions += SizeSiteActions;
- }
-
- // Compute the call-site table. Entries must be ordered by address.
- SmallVector<CallSiteEntry, 64> CallSites;
-
- RangeMapType PadMap;
- for (unsigned i = 0, N = LandingPads.size(); i != N; ++i) {
- const LandingPadInfo *LandingPad = LandingPads[i];
- for (unsigned j=0, E = LandingPad->BeginLabels.size(); j != E; ++j) {
- MCSymbol *BeginLabel = LandingPad->BeginLabels[j];
- assert(!PadMap.count(BeginLabel) && "Duplicate landing pad labels!");
- PadRange P = { i, j };
- PadMap[BeginLabel] = P;
- }
- }
-
- bool MayThrow = false;
- MCSymbol *LastLabel = 0;
- for (MachineFunction::const_iterator I = MF->begin(), E = MF->end();
- I != E; ++I) {
- for (MachineBasicBlock::const_iterator MI = I->begin(), E = I->end();
- MI != E; ++MI) {
- if (!MI->isLabel()) {
- MayThrow |= MI->isCall();
- continue;
- }
-
- MCSymbol *BeginLabel = MI->getOperand(0).getMCSymbol();
- assert(BeginLabel && "Invalid label!");
-
- if (BeginLabel == LastLabel)
- MayThrow = false;
-
- RangeMapType::iterator L = PadMap.find(BeginLabel);
-
- if (L == PadMap.end())
- continue;
-
- PadRange P = L->second;
- const LandingPadInfo *LandingPad = LandingPads[P.PadIndex];
-
- assert(BeginLabel == LandingPad->BeginLabels[P.RangeIndex] &&
- "Inconsistent landing pad map!");
-
- // If some instruction between the previous try-range and this one may
- // throw, create a call-site entry with no landing pad for the region
- // between the try-ranges.
- if (MayThrow) {
- CallSiteEntry Site = {LastLabel, BeginLabel, 0, 0};
- CallSites.push_back(Site);
- }
-
- LastLabel = LandingPad->EndLabels[P.RangeIndex];
- CallSiteEntry Site = {BeginLabel, LastLabel,
- LandingPad->LandingPadLabel, FirstActions[P.PadIndex]};
-
- assert(Site.BeginLabel && Site.EndLabel && Site.PadLabel &&
- "Invalid landing pad!");
-
- // Try to merge with the previous call-site.
- if (CallSites.size()) {
- CallSiteEntry &Prev = CallSites.back();
- if (Site.PadLabel == Prev.PadLabel && Site.Action == Prev.Action) {
- // Extend the range of the previous entry.
- Prev.EndLabel = Site.EndLabel;
- continue;
- }
- }
-
- // Otherwise, create a new call-site.
- CallSites.push_back(Site);
- }
- }
- // If some instruction between the previous try-range and the end of the
- // function may throw, create a call-site entry with no landing pad for the
- // region following the try-range.
- if (MayThrow) {
- CallSiteEntry Site = {LastLabel, 0, 0, 0};
- CallSites.push_back(Site);
- }
-
- // Final tallies.
- unsigned SizeSites = CallSites.size() * (sizeof(int32_t) + // Site start.
- sizeof(int32_t) + // Site length.
- sizeof(int32_t)); // Landing pad.
- for (unsigned i = 0, e = CallSites.size(); i < e; ++i)
- SizeSites += MCAsmInfo::getULEB128Size(CallSites[i].Action);
-
- unsigned SizeTypes = TypeInfos.size() * TD->getPointerSize();
-
- unsigned TypeOffset = sizeof(int8_t) + // Call site format
- // Call-site table length
- MCAsmInfo::getULEB128Size(SizeSites) +
- SizeSites + SizeActions + SizeTypes;
-
- // Begin the exception table.
- JCE->emitAlignmentWithFill(4, 0);
- // Asm->EOL("Padding");
-
- unsigned char* DwarfExceptionTable = (unsigned char*)JCE->getCurrentPCValue();
-
- // Emit the header.
- JCE->emitByte(dwarf::DW_EH_PE_omit);
- // Asm->EOL("LPStart format (DW_EH_PE_omit)");
- JCE->emitByte(dwarf::DW_EH_PE_absptr);
- // Asm->EOL("TType format (DW_EH_PE_absptr)");
- JCE->emitULEB128Bytes(TypeOffset);
- // Asm->EOL("TType base offset");
- JCE->emitByte(dwarf::DW_EH_PE_udata4);
- // Asm->EOL("Call site format (DW_EH_PE_udata4)");
- JCE->emitULEB128Bytes(SizeSites);
- // Asm->EOL("Call-site table length");
-
- // Emit the landing pad site information.
- for (unsigned i = 0; i < CallSites.size(); ++i) {
- CallSiteEntry &S = CallSites[i];
- intptr_t BeginLabelPtr = 0;
- intptr_t EndLabelPtr = 0;
-
- if (!S.BeginLabel) {
- BeginLabelPtr = (intptr_t)StartFunction;
- JCE->emitInt32(0);
- } else {
- BeginLabelPtr = JCE->getLabelAddress(S.BeginLabel);
- JCE->emitInt32(BeginLabelPtr - (intptr_t)StartFunction);
- }
-
- // Asm->EOL("Region start");
-
- if (!S.EndLabel)
- EndLabelPtr = (intptr_t)EndFunction;
- else
- EndLabelPtr = JCE->getLabelAddress(S.EndLabel);
-
- JCE->emitInt32(EndLabelPtr - BeginLabelPtr);
- //Asm->EOL("Region length");
-
- if (!S.PadLabel) {
- JCE->emitInt32(0);
- } else {
- unsigned PadLabelPtr = JCE->getLabelAddress(S.PadLabel);
- JCE->emitInt32(PadLabelPtr - (intptr_t)StartFunction);
- }
- // Asm->EOL("Landing pad");
-
- JCE->emitULEB128Bytes(S.Action);
- // Asm->EOL("Action");
- }
-
- // Emit the actions.
- for (unsigned I = 0, N = Actions.size(); I != N; ++I) {
- ActionEntry &Action = Actions[I];
-
- JCE->emitSLEB128Bytes(Action.ValueForTypeID);
- //Asm->EOL("TypeInfo index");
- JCE->emitSLEB128Bytes(Action.NextAction);
- //Asm->EOL("Next action");
- }
-
- // Emit the type ids.
- for (unsigned M = TypeInfos.size(); M; --M) {
- const GlobalVariable *GV = TypeInfos[M - 1];
-
- if (GV) {
- if (TD->getPointerSize() == sizeof(int32_t))
- JCE->emitInt32((intptr_t)Jit.getOrEmitGlobalVariable(GV));
- else
- JCE->emitInt64((intptr_t)Jit.getOrEmitGlobalVariable(GV));
- } else {
- if (TD->getPointerSize() == sizeof(int32_t))
- JCE->emitInt32(0);
- else
- JCE->emitInt64(0);
- }
- // Asm->EOL("TypeInfo");
- }
-
- // Emit the filter typeids.
- for (unsigned j = 0, M = FilterIds.size(); j < M; ++j) {
- unsigned TypeID = FilterIds[j];
- JCE->emitULEB128Bytes(TypeID);
- //Asm->EOL("Filter TypeInfo index");
- }
-
- JCE->emitAlignmentWithFill(4, 0);
-
- return DwarfExceptionTable;
-}
-
-unsigned char*
-JITDwarfEmitter::EmitCommonEHFrame(const Function* Personality) const {
- unsigned PointerSize = TD->getPointerSize();
- int stackGrowth = stackGrowthDirection == TargetFrameLowering::StackGrowsUp ?
- PointerSize : -PointerSize;
-
- unsigned char* StartCommonPtr = (unsigned char*)JCE->getCurrentPCValue();
- // EH Common Frame header
- JCE->allocateSpace(4, 0);
- unsigned char* FrameCommonBeginPtr = (unsigned char*)JCE->getCurrentPCValue();
- JCE->emitInt32((int)0);
- JCE->emitByte(dwarf::DW_CIE_VERSION);
- JCE->emitString(Personality ? "zPLR" : "zR");
- JCE->emitULEB128Bytes(1);
- JCE->emitSLEB128Bytes(stackGrowth);
- JCE->emitByte(RI->getDwarfRegNum(RI->getRARegister(), true));
-
- if (Personality) {
- // Augmentation Size: 3 small ULEBs of one byte each, and the personality
- // function which size is PointerSize.
- JCE->emitULEB128Bytes(3 + PointerSize);
-
- // We set the encoding of the personality as direct encoding because we use
- // the function pointer. The encoding is not relative because the current
- // PC value may be bigger than the personality function pointer.
- if (PointerSize == 4) {
- JCE->emitByte(dwarf::DW_EH_PE_sdata4);
- JCE->emitInt32(((intptr_t)Jit.getPointerToGlobal(Personality)));
- } else {
- JCE->emitByte(dwarf::DW_EH_PE_sdata8);
- JCE->emitInt64(((intptr_t)Jit.getPointerToGlobal(Personality)));
- }
-
- // LSDA encoding: This must match the encoding used in EmitEHFrame ()
- if (PointerSize == 4)
- JCE->emitULEB128Bytes(dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4);
- else
- JCE->emitULEB128Bytes(dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata8);
- JCE->emitULEB128Bytes(dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4);
- } else {
- JCE->emitULEB128Bytes(1);
- JCE->emitULEB128Bytes(dwarf::DW_EH_PE_pcrel | dwarf::DW_EH_PE_sdata4);
- }
-
- EmitFrameMoves(0, MAI->getInitialFrameState());
-
- JCE->emitAlignmentWithFill(PointerSize, dwarf::DW_CFA_nop);
-
- JCE->emitInt32At((uintptr_t*)StartCommonPtr,
- (uintptr_t)((unsigned char*)JCE->getCurrentPCValue() -
- FrameCommonBeginPtr));
-
- return StartCommonPtr;
-}
-
-
-unsigned char*
-JITDwarfEmitter::EmitEHFrame(const Function* Personality,
- unsigned char* StartCommonPtr,
- unsigned char* StartFunction,
- unsigned char* EndFunction,
- unsigned char* ExceptionTable) const {
- unsigned PointerSize = TD->getPointerSize();
-
- // EH frame header.
- unsigned char* StartEHPtr = (unsigned char*)JCE->getCurrentPCValue();
- JCE->allocateSpace(4, 0);
- unsigned char* FrameBeginPtr = (unsigned char*)JCE->getCurrentPCValue();
- // FDE CIE Offset
- JCE->emitInt32(FrameBeginPtr - StartCommonPtr);
- JCE->emitInt32(StartFunction - (unsigned char*)JCE->getCurrentPCValue());
- JCE->emitInt32(EndFunction - StartFunction);
-
- // If there is a personality and landing pads then point to the language
- // specific data area in the exception table.
- if (Personality) {
- JCE->emitULEB128Bytes(PointerSize == 4 ? 4 : 8);
-
- if (PointerSize == 4) {
- if (!MMI->getLandingPads().empty())
- JCE->emitInt32(ExceptionTable-(unsigned char*)JCE->getCurrentPCValue());
- else
- JCE->emitInt32((int)0);
- } else {
- if (!MMI->getLandingPads().empty())
- JCE->emitInt64(ExceptionTable-(unsigned char*)JCE->getCurrentPCValue());
- else
- JCE->emitInt64((int)0);
- }
- } else {
- JCE->emitULEB128Bytes(0);
- }
-
- // Indicate locations of function specific callee saved registers in
- // frame.
- EmitFrameMoves((intptr_t)StartFunction, MMI->getFrameMoves());
-
- JCE->emitAlignmentWithFill(PointerSize, dwarf::DW_CFA_nop);
-
- // Indicate the size of the table
- JCE->emitInt32At((uintptr_t*)StartEHPtr,
- (uintptr_t)((unsigned char*)JCE->getCurrentPCValue() -
- StartEHPtr));
-
- // Double zeroes for the unwind runtime
- if (PointerSize == 8) {
- JCE->emitInt64(0);
- JCE->emitInt64(0);
- } else {
- JCE->emitInt32(0);
- JCE->emitInt32(0);
- }
-
- return StartEHPtr;
-}
diff --git a/contrib/llvm/lib/ExecutionEngine/JIT/JITDwarfEmitter.h b/contrib/llvm/lib/ExecutionEngine/JIT/JITDwarfEmitter.h
deleted file mode 100644
index 98ac340..0000000
--- a/contrib/llvm/lib/ExecutionEngine/JIT/JITDwarfEmitter.h
+++ /dev/null
@@ -1,77 +0,0 @@
-//===------ JITDwarfEmitter.h - Write dwarf tables into memory ------------===//
-//
-// The LLVM Compiler Infrastructure
-//
-// This file is distributed under the University of Illinois Open Source
-// License. See LICENSE.TXT for details.
-//
-//===----------------------------------------------------------------------===//
-//
-// This file defines a JITDwarfEmitter object that is used by the JIT to
-// write dwarf tables to memory.
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_EXECUTION_ENGINE_JIT_DWARFEMITTER_H
-#define LLVM_EXECUTION_ENGINE_JIT_DWARFEMITTER_H
-
-#include "llvm/Support/DataTypes.h"
-#include <vector>
-
-namespace llvm {
-
-class Function;
-class JIT;
-class JITCodeEmitter;
-class MachineFunction;
-class MachineModuleInfo;
-class MachineMove;
-class MCAsmInfo;
-class DataLayout;
-class TargetMachine;
-class TargetRegisterInfo;
-
-class JITDwarfEmitter {
- const DataLayout* TD;
- JITCodeEmitter* JCE;
- const TargetRegisterInfo* RI;
- const MCAsmInfo *MAI;
- MachineModuleInfo* MMI;
- JIT& Jit;
- bool stackGrowthDirection;
-
- unsigned char* EmitExceptionTable(MachineFunction* MF,
- unsigned char* StartFunction,
- unsigned char* EndFunction) const;
-
- void EmitFrameMoves(intptr_t BaseLabelPtr,
- const std::vector<MachineMove> &Moves) const;
-
- unsigned char* EmitCommonEHFrame(const Function* Personality) const;
-
- unsigned char* EmitEHFrame(const Function* Personality,
- unsigned char* StartBufferPtr,
- unsigned char* StartFunction,
- unsigned char* EndFunction,
- unsigned char* ExceptionTable) const;
-
-public:
-
- JITDwarfEmitter(JIT& jit);
-
- unsigned char* EmitDwarfTable(MachineFunction& F,
- JITCodeEmitter& JCE,
- unsigned char* StartFunction,
- unsigned char* EndFunction,
- unsigned char* &EHFramePtr);
-
-
- void setModuleInfo(MachineModuleInfo* Info) {
- MMI = Info;
- }
-};
-
-
-} // end namespace llvm
-
-#endif // LLVM_EXECUTION_ENGINE_JIT_DWARFEMITTER_H
diff --git a/contrib/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp b/contrib/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp
index c273876..acbbfa1 100644
--- a/contrib/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp
+++ b/contrib/llvm/lib/ExecutionEngine/JIT/JITEmitter.cpp
@@ -14,7 +14,6 @@
#define DEBUG_TYPE "jit"
#include "JIT.h"
-#include "JITDwarfEmitter.h"
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/OwningPtr.h"
#include "llvm/ADT/SmallPtrSet.h"
@@ -325,9 +324,6 @@ namespace {
/// Resolver - This contains info about the currently resolved functions.
JITResolver Resolver;
- /// DE - The dwarf emitter for the jit.
- OwningPtr<JITDwarfEmitter> DE;
-
/// LabelLocations - This vector is a mapping from Label ID's to their
/// address.
DenseMap<MCSymbol*, uintptr_t> LabelLocations;
@@ -363,22 +359,16 @@ namespace {
/// Instance of the JIT
JIT *TheJIT;
- bool JITExceptionHandling;
-
public:
JITEmitter(JIT &jit, JITMemoryManager *JMM, TargetMachine &TM)
: SizeEstimate(0), Resolver(jit, *this), MMI(0), CurFn(0),
- EmittedFunctions(this), TheJIT(&jit),
- JITExceptionHandling(TM.Options.JITExceptionHandling) {
+ EmittedFunctions(this), TheJIT(&jit) {
MemMgr = JMM ? JMM : JITMemoryManager::CreateDefaultMemManager();
if (jit.getJITInfo().needsGOT()) {
MemMgr->AllocateGOT();
DEBUG(dbgs() << "JIT is managing a GOT\n");
}
- if (JITExceptionHandling) {
- DE.reset(new JITDwarfEmitter(jit));
- }
}
~JITEmitter() {
delete MemMgr;
@@ -460,7 +450,6 @@ namespace {
virtual void setModuleInfo(MachineModuleInfo* Info) {
MMI = Info;
- if (DE.get()) DE->setModuleInfo(Info);
}
private:
@@ -964,40 +953,6 @@ bool JITEmitter::finishFunction(MachineFunction &F) {
}
});
- if (JITExceptionHandling) {
- uintptr_t ActualSize = 0;
- SavedBufferBegin = BufferBegin;
- SavedBufferEnd = BufferEnd;
- SavedCurBufferPtr = CurBufferPtr;
- uint8_t *FrameRegister;
-
- while (true) {
- BufferBegin = CurBufferPtr = MemMgr->startExceptionTable(F.getFunction(),
- ActualSize);
- BufferEnd = BufferBegin+ActualSize;
- EmittedFunctions[F.getFunction()].ExceptionTable = BufferBegin;
- uint8_t *EhStart;
- FrameRegister = DE->EmitDwarfTable(F, *this, FnStart, FnEnd, EhStart);
-
- // If the buffer was large enough to hold the table then we are done.
- if (CurBufferPtr != BufferEnd)
- break;
-
- // Try again with twice as much space.
- ActualSize = (CurBufferPtr - BufferBegin) * 2;
- MemMgr->deallocateExceptionTable(BufferBegin);
- }
- MemMgr->endExceptionTable(F.getFunction(), BufferBegin, CurBufferPtr,
- FrameRegister);
- BufferBegin = SavedBufferBegin;
- BufferEnd = SavedBufferEnd;
- CurBufferPtr = SavedCurBufferPtr;
-
- if (JITExceptionHandling) {
- TheJIT->RegisterTable(F.getFunction(), FrameRegister);
- }
- }
-
if (MMI)
MMI->EndFunction();
@@ -1027,15 +982,10 @@ void JITEmitter::deallocateMemForFunction(const Function *F) {
Emitted = EmittedFunctions.find(F);
if (Emitted != EmittedFunctions.end()) {
MemMgr->deallocateFunctionBody(Emitted->second.FunctionBody);
- MemMgr->deallocateExceptionTable(Emitted->second.ExceptionTable);
TheJIT->NotifyFreeingMachineCode(Emitted->second.Code);
EmittedFunctions.erase(Emitted);
}
-
- if (JITExceptionHandling) {
- TheJIT->DeregisterTable(F);
- }
}
diff --git a/contrib/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp b/contrib/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp
index 66aeb77..f58d31b 100644
--- a/contrib/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp
+++ b/contrib/llvm/lib/ExecutionEngine/JIT/JITMemoryManager.cpp
@@ -464,11 +464,15 @@ namespace {
/// allocateCodeSection - Allocate memory for a code section.
uint8_t *allocateCodeSection(uintptr_t Size, unsigned Alignment,
- unsigned SectionID) {
+ unsigned SectionID, StringRef SectionName) {
// Grow the required block size to account for the block header
Size += sizeof(*CurBlock);
- // FIXME: Alignement handling.
+ // Alignment handling.
+ if (!Alignment)
+ Alignment = 16;
+ Size += Alignment - 1;
+
FreeRangeHeader* candidateBlock = FreeMemoryList;
FreeRangeHeader* head = FreeMemoryList;
FreeRangeHeader* iter = head->Next;
@@ -500,39 +504,21 @@ namespace {
FreeMemoryList = candidateBlock->AllocateBlock();
// Release the memory at the end of this block that isn't needed.
FreeMemoryList = CurBlock->TrimAllocationToSize(FreeMemoryList, Size);
- return (uint8_t *)(CurBlock + 1);
+ uintptr_t unalignedAddr = (uintptr_t)CurBlock + sizeof(*CurBlock);
+ return (uint8_t*)RoundUpToAlignment((uint64_t)unalignedAddr, Alignment);
}
/// allocateDataSection - Allocate memory for a data section.
uint8_t *allocateDataSection(uintptr_t Size, unsigned Alignment,
- unsigned SectionID, bool IsReadOnly) {
+ unsigned SectionID, StringRef SectionName,
+ bool IsReadOnly) {
return (uint8_t*)DataAllocator.Allocate(Size, Alignment);
}
- bool applyPermissions(std::string *ErrMsg) {
+ bool finalizeMemory(std::string *ErrMsg) {
return false;
}
- /// startExceptionTable - Use startFunctionBody to allocate memory for the
- /// function's exception table.
- uint8_t* startExceptionTable(const Function* F, uintptr_t &ActualSize) {
- return startFunctionBody(F, ActualSize);
- }
-
- /// endExceptionTable - The exception table of F is now allocated,
- /// and takes the memory in the range [TableStart,TableEnd).
- void endExceptionTable(const Function *F, uint8_t *TableStart,
- uint8_t *TableEnd, uint8_t* FrameRegister) {
- assert(TableEnd > TableStart);
- assert(TableStart == (uint8_t *)(CurBlock+1) &&
- "Mismatched table start/end!");
-
- uintptr_t BlockSize = TableEnd - (uint8_t *)CurBlock;
-
- // Release the memory at the end of this block that isn't needed.
- FreeMemoryList =CurBlock->TrimAllocationToSize(FreeMemoryList, BlockSize);
- }
-
uint8_t *getGOTBase() const {
return GOTBase;
}
@@ -557,12 +543,6 @@ namespace {
if (Body) deallocateBlock(Body);
}
- /// deallocateExceptionTable - Deallocate memory for the specified
- /// exception table.
- void deallocateExceptionTable(void *ET) {
- if (ET) deallocateBlock(ET);
- }
-
/// setMemoryWritable - When code generation is in progress,
/// the code pages may need permissions changed.
void setMemoryWritable()
@@ -814,7 +794,7 @@ static void runAtExitHandlers() {
// not inlined, and hiding their real definitions in a separate archive file
// that the dynamic linker can't see. For more info, search for
// 'libc_nonshared.a' on Google, or read http://llvm.org/PR274.
-#if defined(__linux__)
+#if defined(__linux__) && defined(__GLIBC__)
/* stat functions are redirecting to __xstat with a version number. On x86-64
* linking with libc_nonshared.a and -Wl,--export-dynamic doesn't make 'stat'
* available as an exported symbol, so we have to add it explicitly.
OpenPOWER on IntegriCloud