mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-01-06 04:31:08 +00:00
1. Tidy up jump table info.
2. Allow the jit to handle PIC relocable jump tables. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@32581 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
8897a7b02e
commit
acd80ac7bb
@ -39,9 +39,11 @@ struct MachineJumpTableEntry {
|
||||
|
||||
class MachineJumpTableInfo {
|
||||
const TargetData *TD;
|
||||
unsigned EntrySize;
|
||||
std::vector<MachineJumpTableEntry> JumpTables;
|
||||
public:
|
||||
MachineJumpTableInfo(const TargetData *td) : TD(td) {}
|
||||
MachineJumpTableInfo(const TargetData *td, unsigned ES)
|
||||
: TD(td), EntrySize(ES) {}
|
||||
|
||||
/// getJumpTableIndex - Create a new jump table or return an existing one.
|
||||
///
|
||||
@ -77,8 +79,9 @@ public:
|
||||
return MadeChange;
|
||||
}
|
||||
|
||||
/// getEntrySize - returns the size of an individual field in a jump table
|
||||
unsigned getEntrySize() const;
|
||||
/// getEntrySize - Returns the size of an individual field in a jump table.
|
||||
///
|
||||
unsigned getEntrySize() const { return EntrySize; }
|
||||
|
||||
/// getAlignment - returns the target's preferred alignment for jump tables
|
||||
unsigned getAlignment() const;
|
||||
|
@ -188,36 +188,31 @@ void AsmPrinter::EmitJumpTableInfo(MachineJumpTableInfo *MJTI,
|
||||
MachineFunction &MF) {
|
||||
const std::vector<MachineJumpTableEntry> &JT = MJTI->getJumpTables();
|
||||
if (JT.empty()) return;
|
||||
const TargetData *TD = TM.getTargetData();
|
||||
bool IsPic = TM.getRelocationModel() == Reloc::PIC_;
|
||||
|
||||
// JTEntryDirective is a string to print sizeof(ptr) for non-PIC jump tables,
|
||||
// and 32 bits for PIC since PIC jump table entries are differences, not
|
||||
// pointers to blocks.
|
||||
// Use the architecture specific relocation directive, if it is set
|
||||
// Use JumpTableDirective otherwise honor the entry size from the jump table
|
||||
// info.
|
||||
const char *JTEntryDirective = TAI->getJumpTableDirective();
|
||||
if (!JTEntryDirective)
|
||||
JTEntryDirective = TAI->getData32bitsDirective();
|
||||
bool HadJTEntryDirective = JTEntryDirective != NULL;
|
||||
if (!HadJTEntryDirective) {
|
||||
JTEntryDirective = MJTI->getEntrySize() == 4 ?
|
||||
TAI->getData32bitsDirective() : TAI->getData64bitsDirective();
|
||||
}
|
||||
|
||||
// Pick the directive to use to print the jump table entries, and switch to
|
||||
// the appropriate section.
|
||||
if (TM.getRelocationModel() == Reloc::PIC_) {
|
||||
TargetLowering *LoweringInfo = TM.getTargetLowering();
|
||||
if (LoweringInfo && LoweringInfo->usesGlobalOffsetTable()) {
|
||||
SwitchToDataSection(TAI->getJumpTableDataSection());
|
||||
if (TD->getPointerSize() == 8 && !JTEntryDirective)
|
||||
JTEntryDirective = TAI->getData64bitsDirective();
|
||||
} else {
|
||||
// In PIC mode, we need to emit the jump table to the same section as the
|
||||
// function body itself, otherwise the label differences won't make sense.
|
||||
const Function *F = MF.getFunction();
|
||||
SwitchToTextSection(getSectionForFunction(*F).c_str(), F);
|
||||
}
|
||||
TargetLowering *LoweringInfo = TM.getTargetLowering();
|
||||
|
||||
if (IsPic && !(LoweringInfo && LoweringInfo->usesGlobalOffsetTable())) {
|
||||
// In PIC mode, we need to emit the jump table to the same section as the
|
||||
// function body itself, otherwise the label differences won't make sense.
|
||||
const Function *F = MF.getFunction();
|
||||
SwitchToTextSection(getSectionForFunction(*F).c_str(), F);
|
||||
} else {
|
||||
SwitchToDataSection(TAI->getJumpTableDataSection());
|
||||
if (TD->getPointerSize() == 8)
|
||||
JTEntryDirective = TAI->getData64bitsDirective();
|
||||
}
|
||||
EmitAlignment(Log2_32(TD->getPointerAlignment()));
|
||||
|
||||
EmitAlignment(Log2_32(MJTI->getAlignment()));
|
||||
|
||||
for (unsigned i = 0, e = JT.size(); i != e; ++i) {
|
||||
const std::vector<MachineBasicBlock*> &JTBBs = JT[i].MBBs;
|
||||
@ -229,7 +224,7 @@ void AsmPrinter::EmitJumpTableInfo(MachineJumpTableInfo *MJTI,
|
||||
// the number of relocations the assembler will generate for the jump table.
|
||||
// Set directives are all printed before the jump table itself.
|
||||
std::set<MachineBasicBlock*> EmittedSets;
|
||||
if (TAI->getSetDirective() && TM.getRelocationModel() == Reloc::PIC_)
|
||||
if (TAI->getSetDirective() && IsPic)
|
||||
for (unsigned ii = 0, ee = JTBBs.size(); ii != ee; ++ii)
|
||||
if (EmittedSets.insert(JTBBs[ii]).second)
|
||||
printSetLabel(i, JTBBs[ii]);
|
||||
@ -247,12 +242,12 @@ void AsmPrinter::EmitJumpTableInfo(MachineJumpTableInfo *MJTI,
|
||||
if (!EmittedSets.empty()) {
|
||||
O << TAI->getPrivateGlobalPrefix() << getFunctionNumber()
|
||||
<< '_' << i << "_set_" << JTBBs[ii]->getNumber();
|
||||
} else if (TM.getRelocationModel() == Reloc::PIC_) {
|
||||
} else if (IsPic) {
|
||||
printBasicBlockLabel(JTBBs[ii], false, false);
|
||||
//If the arch uses custom Jump Table directives, don't calc relative to JT
|
||||
if (!TAI->getJumpTableDirective())
|
||||
O << '-' << TAI->getPrivateGlobalPrefix() << "JTI"
|
||||
<< getFunctionNumber() << '_' << i;
|
||||
//If the arch uses custom Jump Table directives, don't calc relative to JT
|
||||
if (!HadJTEntryDirective)
|
||||
O << '-' << TAI->getPrivateGlobalPrefix() << "JTI"
|
||||
<< getFunctionNumber() << '_' << i;
|
||||
} else {
|
||||
printBasicBlockLabel(JTBBs[ii], false, false);
|
||||
}
|
||||
|
@ -21,6 +21,7 @@
|
||||
#include "llvm/CodeGen/MachineJumpTableInfo.h"
|
||||
#include "llvm/CodeGen/Passes.h"
|
||||
#include "llvm/Target/TargetData.h"
|
||||
#include "llvm/Target/TargetLowering.h"
|
||||
#include "llvm/Target/TargetMachine.h"
|
||||
#include "llvm/Target/TargetFrameInfo.h"
|
||||
#include "llvm/Function.h"
|
||||
@ -117,7 +118,14 @@ MachineFunction::MachineFunction(const Function *F,
|
||||
MFInfo = 0;
|
||||
FrameInfo = new MachineFrameInfo();
|
||||
ConstantPool = new MachineConstantPool(TM.getTargetData());
|
||||
JumpTableInfo = new MachineJumpTableInfo(TM.getTargetData());
|
||||
|
||||
// Set up jump table.
|
||||
const TargetData &TD = *TM.getTargetData();
|
||||
bool IsPic = TM.getRelocationModel() == Reloc::PIC_;
|
||||
unsigned EntrySize = IsPic ? 4 : TD.getPointerSize();
|
||||
unsigned Alignment = IsPic ? TD.getIntAlignment() : TD.getPointerAlignment();
|
||||
JumpTableInfo = new MachineJumpTableInfo(EntrySize, Alignment);
|
||||
|
||||
BasicBlocks.Parent = this;
|
||||
}
|
||||
|
||||
@ -380,14 +388,6 @@ void MachineJumpTableInfo::print(std::ostream &OS) const {
|
||||
}
|
||||
}
|
||||
|
||||
unsigned MachineJumpTableInfo::getEntrySize() const {
|
||||
return TD->getPointerSize();
|
||||
}
|
||||
|
||||
unsigned MachineJumpTableInfo::getAlignment() const {
|
||||
return TD->getPointerAlignment();
|
||||
}
|
||||
|
||||
void MachineJumpTableInfo::dump() const { print(*cerr.stream()); }
|
||||
|
||||
|
||||
|
@ -14,6 +14,7 @@
|
||||
#include "llvm/CodeGen/SelectionDAG.h"
|
||||
#include "llvm/CodeGen/MachineFunction.h"
|
||||
#include "llvm/CodeGen/MachineFrameInfo.h"
|
||||
#include "llvm/CodeGen/MachineJumpTableInfo.h"
|
||||
#include "llvm/Target/TargetLowering.h"
|
||||
#include "llvm/Target/TargetData.h"
|
||||
#include "llvm/Target/TargetMachine.h"
|
||||
@ -1275,13 +1276,19 @@ SDOperand SelectionDAGLegalize::LegalizeOp(SDOperand Op) {
|
||||
SDOperand Index = Result.getOperand(2);
|
||||
|
||||
MVT::ValueType PTy = TLI.getPointerTy();
|
||||
bool isPIC = TLI.getTargetMachine().getRelocationModel() == Reloc::PIC_;
|
||||
// PIC jump table entries are 32-bit values.
|
||||
unsigned EntrySize = isPIC ? 4 : MVT::getSizeInBits(PTy)/8;
|
||||
MachineFunction &MF = DAG.getMachineFunction();
|
||||
unsigned EntrySize = MF.getJumpTableInfo()->getEntrySize();
|
||||
Index= DAG.getNode(ISD::MUL, PTy, Index, DAG.getConstant(EntrySize, PTy));
|
||||
SDOperand Addr = DAG.getNode(ISD::ADD, PTy, Index, Table);
|
||||
SDOperand LD = DAG.getLoad(isPIC ? MVT::i32 : PTy, Chain, Addr, NULL, 0);
|
||||
if (isPIC) {
|
||||
|
||||
SDOperand LD;
|
||||
switch (EntrySize) {
|
||||
default: assert(0 && "Size of jump table not supported yet."); break;
|
||||
case 4: LD = DAG.getLoad(MVT::i32, Chain, Addr, NULL, 0); break;
|
||||
case 8: LD = DAG.getLoad(MVT::i64, Chain, Addr, NULL, 0); break;
|
||||
}
|
||||
|
||||
if (TLI.getTargetMachine().getRelocationModel() == Reloc::PIC_) {
|
||||
// For PIC, the sequence is:
|
||||
// BRIND(load(Jumptable + index) + RelocBase)
|
||||
// RelocBase is the JumpTable on PPC and X86, GOT on Alpha
|
||||
|
@ -25,6 +25,7 @@
|
||||
#include "llvm/ExecutionEngine/GenericValue.h"
|
||||
#include "llvm/Target/TargetData.h"
|
||||
#include "llvm/Target/TargetJITInfo.h"
|
||||
#include "llvm/Target/TargetMachine.h"
|
||||
#include "llvm/Support/Debug.h"
|
||||
#include "llvm/Support/MutexGuard.h"
|
||||
#include "llvm/ADT/Statistic.h"
|
||||
@ -700,7 +701,7 @@ public:
|
||||
|
||||
void emitConstantPool(MachineConstantPool *MCP);
|
||||
void initJumpTableInfo(MachineJumpTableInfo *MJTI);
|
||||
void emitJumpTableInfo(MachineJumpTableInfo *MJTI);
|
||||
void emitJumpTableInfo(MachineJumpTableInfo *MJTI, Reloc::Model RM);
|
||||
|
||||
virtual void startFunctionStub(unsigned StubSize, unsigned Alignment = 1);
|
||||
virtual void* finishFunctionStub(const Function *F);
|
||||
@ -791,7 +792,7 @@ bool JITEmitter::finishFunction(MachineFunction &F) {
|
||||
abort();
|
||||
}
|
||||
|
||||
emitJumpTableInfo(F.getJumpTableInfo());
|
||||
emitJumpTableInfo(F.getJumpTableInfo(), F.getTarget().getRelocationModel());
|
||||
|
||||
// FnStart is the start of the text, not the start of the constant pool and
|
||||
// other per-function data.
|
||||
@ -821,7 +822,7 @@ bool JITEmitter::finishFunction(MachineFunction &F) {
|
||||
MR.doesntNeedFunctionStub());
|
||||
} else if (MR.isBasicBlock()) {
|
||||
ResultPtr = (void*)getMachineBasicBlockAddress(MR.getBasicBlock());
|
||||
} else if (MR.isConstantPoolIndex()){
|
||||
} else if (MR.isConstantPoolIndex()) {
|
||||
ResultPtr=(void*)getConstantPoolEntryAddress(MR.getConstantPoolIndex());
|
||||
} else {
|
||||
assert(MR.isJumpTableIndex());
|
||||
@ -914,22 +915,38 @@ void JITEmitter::initJumpTableInfo(MachineJumpTableInfo *MJTI) {
|
||||
JumpTableBase = allocateSpace(NumEntries * EntrySize, MJTI->getAlignment());
|
||||
}
|
||||
|
||||
void JITEmitter::emitJumpTableInfo(MachineJumpTableInfo *MJTI) {
|
||||
void JITEmitter::emitJumpTableInfo(MachineJumpTableInfo *MJTI, Reloc::Model RM){
|
||||
const std::vector<MachineJumpTableEntry> &JT = MJTI->getJumpTables();
|
||||
if (JT.empty() || JumpTableBase == 0) return;
|
||||
|
||||
assert(MJTI->getEntrySize() == sizeof(void*) && "Cross JIT'ing?");
|
||||
|
||||
// For each jump table, map each target in the jump table to the address of
|
||||
// an emitted MachineBasicBlock.
|
||||
intptr_t *SlotPtr = (intptr_t*)JumpTableBase;
|
||||
if (RM == Reloc::PIC_) {
|
||||
assert(MJTI->getEntrySize() == 4 && "Cross JIT'ing?");
|
||||
// For each jump table, place the offset from the beginning of the table
|
||||
// to the target address.
|
||||
int *SlotPtr = (int*)JumpTableBase;
|
||||
|
||||
for (unsigned i = 0, e = JT.size(); i != e; ++i) {
|
||||
const std::vector<MachineBasicBlock*> &MBBs = JT[i].MBBs;
|
||||
// Store the address of the basic block for this jump table slot in the
|
||||
// memory we allocated for the jump table in 'initJumpTableInfo'
|
||||
for (unsigned mi = 0, me = MBBs.size(); mi != me; ++mi)
|
||||
*SlotPtr++ = getMachineBasicBlockAddress(MBBs[mi]);
|
||||
for (unsigned i = 0, e = JT.size(); i != e; ++i) {
|
||||
const std::vector<MachineBasicBlock*> &MBBs = JT[i].MBBs;
|
||||
// Store the offset of the basic block for this jump table slot in the
|
||||
// memory we allocated for the jump table in 'initJumpTableInfo'
|
||||
intptr_t Base = (intptr_t)SlotPtr;
|
||||
for (unsigned mi = 0, me = MBBs.size(); mi != me; ++mi)
|
||||
*SlotPtr++ = (intptr_t)getMachineBasicBlockAddress(MBBs[mi]) - Base;
|
||||
}
|
||||
} else {
|
||||
assert(MJTI->getEntrySize() == sizeof(void*) && "Cross JIT'ing?");
|
||||
|
||||
// For each jump table, map each target in the jump table to the address of
|
||||
// an emitted MachineBasicBlock.
|
||||
intptr_t *SlotPtr = (intptr_t*)JumpTableBase;
|
||||
|
||||
for (unsigned i = 0, e = JT.size(); i != e; ++i) {
|
||||
const std::vector<MachineBasicBlock*> &MBBs = JT[i].MBBs;
|
||||
// Store the address of the basic block for this jump table slot in the
|
||||
// memory we allocated for the jump table in 'initJumpTableInfo'
|
||||
for (unsigned mi = 0, me = MBBs.size(); mi != me; ++mi)
|
||||
*SlotPtr++ = getMachineBasicBlockAddress(MBBs[mi]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -972,7 +989,9 @@ intptr_t JITEmitter::getJumpTableEntryAddress(unsigned Index) const {
|
||||
unsigned EntrySize = JumpTable->getEntrySize();
|
||||
|
||||
for (unsigned i = 0; i < Index; ++i)
|
||||
Offset += JT[i].MBBs.size() * EntrySize;
|
||||
Offset += JT[i].MBBs.size();
|
||||
|
||||
Offset *= EntrySize;
|
||||
|
||||
return (intptr_t)((char *)JumpTableBase + Offset);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user