mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2024-08-17 21:29:20 +00:00
These headers have been moved/merged into other files.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@15477 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
57195d1321
commit
826b19b4ec
@ -1,339 +0,0 @@
|
||||
//===-- llvm/CodeGen/InstForest.h -------------------------------*- C++ -*-===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file was developed by the LLVM research group and is distributed under
|
||||
// the University of Illinois Open Source License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// Purpose:
|
||||
// Convert SSA graph to instruction trees for instruction selection.
|
||||
//
|
||||
// Strategy:
|
||||
// The basic idea is that we would like to group instructions into a single
|
||||
// tree if one or more of them might be potentially combined into a single
|
||||
// complex instruction in the target machine.
|
||||
// Since this grouping is completely machine-independent, it is as
|
||||
// aggressive as possible. In particular, we group two instructions
|
||||
// O and I if:
|
||||
// (1) Instruction O computes an operand of instruction I, and
|
||||
// (2) O and I are part of the same basic block, and
|
||||
// (3) O has only a single use, viz., I.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_CODEGEN_INSTRFOREST_H
|
||||
#define LLVM_CODEGEN_INSTRFOREST_H
|
||||
|
||||
#include "llvm/Instruction.h"
|
||||
#include "Support/hash_map"
|
||||
|
||||
namespace llvm {
|
||||
|
||||
class Constant;
|
||||
class Function;
|
||||
class InstrTreeNode;
|
||||
class InstrForest;
|
||||
|
||||
} // End llvm namespace
|
||||
|
||||
using namespace llvm;
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
// OpLabel values for special-case nodes created for instruction selection.
|
||||
// All op-labels not defined here are identical to the instruction
|
||||
// opcode returned by Instruction::getOpcode()
|
||||
//--------------------------------------------------------------------------
|
||||
//
|
||||
|
||||
|
||||
const int InvalidOp = -1;
|
||||
const int VRegListOp = 97;
|
||||
const int VRegNodeOp = 98;
|
||||
const int ConstantNodeOp= 99;
|
||||
const int LabelNodeOp = 100;
|
||||
|
||||
const int RetValueOp = 100 + Instruction::Ret; // 101
|
||||
const int BrCondOp = 100 + Instruction::Br; // 102
|
||||
|
||||
const int BAndOp = 100 + Instruction::And; // 111
|
||||
const int BOrOp = 100 + Instruction::Or; // 112
|
||||
const int BXorOp = 100 + Instruction::Xor; // 113
|
||||
const int BNotOp = 200 + Instruction::Xor; // 213
|
||||
const int NotOp = 300 + Instruction::Xor; // 313
|
||||
|
||||
const int SetCCOp = 100 + Instruction::SetEQ; // 114
|
||||
|
||||
const int AllocaN = 100 + Instruction::Alloca; // 122
|
||||
const int LoadIdx = 100 + Instruction::Load; // 123
|
||||
const int GetElemPtrIdx= 100 + Instruction::GetElementPtr; // 125
|
||||
|
||||
const int ToBoolTy = 100 + Instruction::Cast; // 127
|
||||
const int ToUByteTy = ToBoolTy + 1;
|
||||
const int ToSByteTy = ToBoolTy + 2;
|
||||
const int ToUShortTy = ToBoolTy + 3;
|
||||
const int ToShortTy = ToBoolTy + 4;
|
||||
const int ToUIntTy = ToBoolTy + 5;
|
||||
const int ToIntTy = ToBoolTy + 6;
|
||||
const int ToULongTy = ToBoolTy + 7;
|
||||
const int ToLongTy = ToBoolTy + 8;
|
||||
const int ToFloatTy = ToBoolTy + 9;
|
||||
const int ToDoubleTy = ToBoolTy + 10;
|
||||
const int ToArrayTy = ToBoolTy + 11;
|
||||
const int ToPointerTy = ToBoolTy + 12;
|
||||
|
||||
//-------------------------------------------------------------------------
|
||||
// Data types needed by BURG and implemented by us
|
||||
//-------------------------------------------------------------------------
|
||||
|
||||
typedef int OpLabel;
|
||||
typedef int StateLabel;
|
||||
|
||||
//-------------------------------------------------------------------------
|
||||
// Declarations of data and functions created by BURG
|
||||
//-------------------------------------------------------------------------
|
||||
|
||||
extern short* burm_nts[];
|
||||
|
||||
extern StateLabel burm_label (InstrTreeNode* p);
|
||||
|
||||
extern StateLabel burm_state (OpLabel op, StateLabel leftState,
|
||||
StateLabel rightState);
|
||||
|
||||
extern StateLabel burm_rule (StateLabel state, int goalNT);
|
||||
|
||||
extern InstrTreeNode** burm_kids (InstrTreeNode* p, int eruleno,
|
||||
InstrTreeNode* kids[]);
|
||||
|
||||
extern void printcover (InstrTreeNode*, int, int);
|
||||
extern void printtree (InstrTreeNode*);
|
||||
extern int treecost (InstrTreeNode*, int, int);
|
||||
extern void printMatches (InstrTreeNode*);
|
||||
|
||||
namespace llvm {
|
||||
|
||||
//------------------------------------------------------------------------
|
||||
// class InstrTreeNode
|
||||
//
|
||||
// A single tree node in the instruction tree used for
|
||||
// instruction selection via BURG.
|
||||
//------------------------------------------------------------------------
|
||||
|
||||
class InstrTreeNode {
|
||||
InstrTreeNode(const InstrTreeNode &); // DO NOT IMPLEMENT
|
||||
void operator=(const InstrTreeNode &); // DO NOT IMPLEMENT
|
||||
public:
|
||||
enum InstrTreeNodeType { NTInstructionNode,
|
||||
NTVRegListNode,
|
||||
NTVRegNode,
|
||||
NTConstNode,
|
||||
NTLabelNode };
|
||||
|
||||
// BASIC TREE NODE START
|
||||
InstrTreeNode* LeftChild;
|
||||
InstrTreeNode* RightChild;
|
||||
InstrTreeNode* Parent;
|
||||
OpLabel opLabel;
|
||||
StateLabel state;
|
||||
// BASIC TREE NODE END
|
||||
|
||||
protected:
|
||||
InstrTreeNodeType treeNodeType;
|
||||
Value* val;
|
||||
|
||||
public:
|
||||
InstrTreeNode(InstrTreeNodeType nodeType, Value* _val)
|
||||
: treeNodeType(nodeType), val(_val) {
|
||||
LeftChild = RightChild = Parent = 0;
|
||||
opLabel = InvalidOp;
|
||||
}
|
||||
virtual ~InstrTreeNode() {
|
||||
delete LeftChild;
|
||||
delete RightChild;
|
||||
}
|
||||
|
||||
InstrTreeNodeType getNodeType () const { return treeNodeType; }
|
||||
|
||||
Value* getValue () const { return val; }
|
||||
|
||||
inline OpLabel getOpLabel () const { return opLabel; }
|
||||
|
||||
inline InstrTreeNode* leftChild() const {
|
||||
return LeftChild;
|
||||
}
|
||||
|
||||
// If right child is a list node, recursively get its *left* child
|
||||
inline InstrTreeNode* rightChild() const {
|
||||
return (!RightChild ? 0 :
|
||||
(RightChild->getOpLabel() == VRegListOp
|
||||
? RightChild->LeftChild : RightChild));
|
||||
}
|
||||
|
||||
inline InstrTreeNode *parent() const {
|
||||
return Parent;
|
||||
}
|
||||
|
||||
void dump(int dumpChildren, int indent) const;
|
||||
|
||||
protected:
|
||||
virtual void dumpNode(int indent) const = 0;
|
||||
|
||||
friend class InstrForest;
|
||||
};
|
||||
|
||||
|
||||
class InstructionNode : public InstrTreeNode {
|
||||
private:
|
||||
bool codeIsFoldedIntoParent;
|
||||
|
||||
public:
|
||||
InstructionNode(Instruction *_instr);
|
||||
|
||||
Instruction *getInstruction() const {
|
||||
assert(treeNodeType == NTInstructionNode);
|
||||
return cast<Instruction>(val);
|
||||
}
|
||||
|
||||
void markFoldedIntoParent() { codeIsFoldedIntoParent = true; }
|
||||
bool isFoldedIntoParent() { return codeIsFoldedIntoParent; }
|
||||
|
||||
// Methods to support type inquiry through isa, cast, and dyn_cast:
|
||||
static inline bool classof(const InstructionNode *N) { return true; }
|
||||
static inline bool classof(const InstrTreeNode *N) {
|
||||
return N->getNodeType() == InstrTreeNode::NTInstructionNode;
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual void dumpNode(int indent) const;
|
||||
};
|
||||
|
||||
|
||||
class VRegListNode : public InstrTreeNode {
|
||||
public:
|
||||
VRegListNode() : InstrTreeNode(NTVRegListNode, 0) {
|
||||
opLabel = VRegListOp;
|
||||
}
|
||||
|
||||
// Methods to support type inquiry through isa, cast, and dyn_cast:
|
||||
static inline bool classof(const VRegListNode *N) { return true; }
|
||||
static inline bool classof(const InstrTreeNode *N) {
|
||||
return N->getNodeType() == InstrTreeNode::NTVRegListNode;
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual void dumpNode(int indent) const;
|
||||
};
|
||||
|
||||
|
||||
class VRegNode : public InstrTreeNode {
|
||||
public:
|
||||
VRegNode(Value* _val) : InstrTreeNode(NTVRegNode, _val) {
|
||||
opLabel = VRegNodeOp;
|
||||
}
|
||||
|
||||
// Methods to support type inquiry through isa, cast, and dyn_cast:
|
||||
static inline bool classof(const VRegNode *N) { return true; }
|
||||
static inline bool classof(const InstrTreeNode *N) {
|
||||
return N->getNodeType() == InstrTreeNode::NTVRegNode;
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual void dumpNode(int indent) const;
|
||||
};
|
||||
|
||||
|
||||
class ConstantNode : public InstrTreeNode {
|
||||
public:
|
||||
ConstantNode(Constant *constVal)
|
||||
: InstrTreeNode(NTConstNode, (Value*)constVal) {
|
||||
opLabel = ConstantNodeOp;
|
||||
}
|
||||
Constant *getConstVal() const { return (Constant*) val;}
|
||||
|
||||
// Methods to support type inquiry through isa, cast, and dyn_cast:
|
||||
static inline bool classof(const ConstantNode *N) { return true; }
|
||||
static inline bool classof(const InstrTreeNode *N) {
|
||||
return N->getNodeType() == InstrTreeNode::NTConstNode;
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual void dumpNode(int indent) const;
|
||||
};
|
||||
|
||||
|
||||
class LabelNode : public InstrTreeNode {
|
||||
public:
|
||||
LabelNode(BasicBlock* BB) : InstrTreeNode(NTLabelNode, (Value*)BB) {
|
||||
opLabel = LabelNodeOp;
|
||||
}
|
||||
|
||||
BasicBlock *getBasicBlock() const { return (BasicBlock*)val;}
|
||||
|
||||
// Methods to support type inquiry through isa, cast, and dyn_cast:
|
||||
static inline bool classof(const LabelNode *N) { return true; }
|
||||
static inline bool classof(const InstrTreeNode *N) {
|
||||
return N->getNodeType() == InstrTreeNode::NTLabelNode;
|
||||
}
|
||||
|
||||
protected:
|
||||
virtual void dumpNode(int indent) const;
|
||||
};
|
||||
|
||||
|
||||
//------------------------------------------------------------------------
|
||||
// class InstrForest
|
||||
//
|
||||
// A forest of instruction trees, usually for a single method.
|
||||
//
|
||||
// Methods:
|
||||
// buildTreesForMethod() Builds the forest of trees for a method
|
||||
// getTreeNodeForInstr() Returns the tree node for an Instruction
|
||||
// getRootSet() Returns a set of root nodes for all the trees
|
||||
//
|
||||
//------------------------------------------------------------------------
|
||||
|
||||
class InstrForest : private hash_map<const Instruction *, InstructionNode*> {
|
||||
public:
|
||||
// Use a vector for the root set to get a deterministic iterator
|
||||
// for stable code generation. Even though we need to erase nodes
|
||||
// during forest construction, a vector should still be efficient
|
||||
// because the elements to erase are nearly always near the end.
|
||||
typedef std::vector<InstructionNode*> RootSet;
|
||||
typedef RootSet:: iterator root_iterator;
|
||||
typedef RootSet::const_iterator const_root_iterator;
|
||||
|
||||
private:
|
||||
RootSet treeRoots;
|
||||
|
||||
public:
|
||||
/*ctor*/ InstrForest (Function *F);
|
||||
/*dtor*/ ~InstrForest ();
|
||||
|
||||
inline InstructionNode *getTreeNodeForInstr(Instruction* instr) {
|
||||
return (*this)[instr];
|
||||
}
|
||||
|
||||
const_root_iterator roots_begin() const { return treeRoots.begin(); }
|
||||
root_iterator roots_begin() { return treeRoots.begin(); }
|
||||
const_root_iterator roots_end () const { return treeRoots.end(); }
|
||||
root_iterator roots_end () { return treeRoots.end(); }
|
||||
|
||||
void dump() const;
|
||||
|
||||
private:
|
||||
//
|
||||
// Private methods for buidling the instruction forest
|
||||
//
|
||||
void eraseRoot (InstructionNode* node);
|
||||
void setLeftChild (InstrTreeNode* parent, InstrTreeNode* child);
|
||||
void setRightChild(InstrTreeNode* parent, InstrTreeNode* child);
|
||||
void setParent (InstrTreeNode* child, InstrTreeNode* parent);
|
||||
void noteTreeNodeForInstr(Instruction* instr, InstructionNode* treeNode);
|
||||
|
||||
InstructionNode* buildTreeForInstruction(Instruction* instr);
|
||||
};
|
||||
|
||||
} // End llvm namespace
|
||||
|
||||
#endif
|
@ -1,110 +0,0 @@
|
||||
//===-- llvm/CodeGen/InstrSelection.h ---------------------------*- C++ -*-===//
|
||||
//
|
||||
// The LLVM Compiler Infrastructure
|
||||
//
|
||||
// This file was developed by the LLVM research group and is distributed under
|
||||
// the University of Illinois Open Source License. See LICENSE.TXT for details.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
//
|
||||
// External interface to instruction selection.
|
||||
//
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#ifndef LLVM_CODEGEN_INSTR_SELECTION_H
|
||||
#define LLVM_CODEGEN_INSTR_SELECTION_H
|
||||
|
||||
#include "llvm/Instruction.h"
|
||||
|
||||
namespace llvm {
|
||||
|
||||
class Function;
|
||||
class FunctionPass;
|
||||
class InstrForest;
|
||||
class InstructionNode;
|
||||
class MachineCodeForInstruction;
|
||||
class MachineInstr;
|
||||
class TargetMachine;
|
||||
|
||||
//===--------------------- Required Functions ---------------------------------
|
||||
// Target-dependent functions that MUST be implemented for each target.
|
||||
//
|
||||
|
||||
extern void GetInstructionsByRule (InstructionNode* subtreeRoot,
|
||||
int ruleForNode,
|
||||
short* nts,
|
||||
TargetMachine &Target,
|
||||
std::vector<MachineInstr*>& mvec);
|
||||
|
||||
extern bool ThisIsAChainRule (int eruleno);
|
||||
|
||||
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
// Function: createInstructionSelectionPass
|
||||
//
|
||||
// Purpose:
|
||||
// Entry point for instruction selection using BURG.
|
||||
// Return a pass that performs machine dependent instruction selection.
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
FunctionPass *createInstructionSelectionPass(TargetMachine &Target);
|
||||
|
||||
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
// class TmpInstruction
|
||||
//
|
||||
// This class represents temporary intermediate values
|
||||
// used within the machine code for a VM instruction
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
class TmpInstruction : public Instruction {
|
||||
TmpInstruction(const TmpInstruction &TI)
|
||||
: Instruction(TI.getType(), TI.getOpcode()) {
|
||||
if (!TI.Operands.empty()) {
|
||||
Operands.push_back(Use(TI.Operands[0], this));
|
||||
if (TI.Operands.size() == 2)
|
||||
Operands.push_back(Use(TI.Operands[1], this));
|
||||
else
|
||||
assert(0 && "Bad # operands to TmpInstruction!");
|
||||
}
|
||||
}
|
||||
public:
|
||||
// Constructor that uses the type of S1 as the type of the temporary.
|
||||
// s1 must be a valid value. s2 may be NULL.
|
||||
TmpInstruction(MachineCodeForInstruction& mcfi,
|
||||
Value *s1, Value *s2 = 0, const std::string &name = "");
|
||||
|
||||
// Constructor that uses the type of S1 as the type of the temporary,
|
||||
// but does not require a MachineCodeForInstruction.
|
||||
// s1 must be a valid value. s2 may be NULL.
|
||||
TmpInstruction(Value *s1, Value *s2 = 0, const std::string &name = "");
|
||||
|
||||
// Constructor that requires the type of the temporary to be specified.
|
||||
// Both S1 and S2 may be NULL.
|
||||
TmpInstruction(MachineCodeForInstruction& mcfi,
|
||||
const Type *Ty, Value *s1 = 0, Value* s2 = 0,
|
||||
const std::string &name = "");
|
||||
|
||||
virtual Instruction *clone() const {
|
||||
assert(0 && "Cannot clone TmpInstructions!");
|
||||
return 0;
|
||||
}
|
||||
virtual const char *getOpcodeName() const {
|
||||
return "TempValueForMachineInstr";
|
||||
}
|
||||
|
||||
// Methods for support type inquiry through isa, cast, and dyn_cast:
|
||||
static inline bool classof(const TmpInstruction *) { return true; }
|
||||
static inline bool classof(const Instruction *I) {
|
||||
return (I->getOpcode() == Instruction::UserOp1);
|
||||
}
|
||||
static inline bool classof(const Value *V) {
|
||||
return isa<Instruction>(V) && classof(cast<Instruction>(V));
|
||||
}
|
||||
};
|
||||
|
||||
} // End llvm namespace
|
||||
|
||||
#endif
|
Loading…
Reference in New Issue
Block a user