diff options
-rw-r--r-- | lib/Target/Target.td | 91 | ||||
-rw-r--r-- | lib/Target/TargetSelectionDAG.td | 214 |
2 files changed, 216 insertions, 89 deletions
diff --git a/lib/Target/Target.td b/lib/Target/Target.td index 6eae93a1b0..4e36223123 100644 --- a/lib/Target/Target.td +++ b/lib/Target/Target.td @@ -241,94 +241,7 @@ class Target { list<AsmWriter> AssemblyWriters = [DefaultAsmWriter]; } - //===----------------------------------------------------------------------===// -// DAG node definitions used by the instruction selector. -// -// NOTE: all of this is a work-in-progress and should be ignored for now. +// Pull in the common support for DAG isel generation // -/* -class Expander<dag pattern, list<dag> result> { - dag Pattern = pattern; - list<dag> Result = result; -} - -class DagNodeValType; -def DNVT_any : DagNodeValType; // No constraint on tree node -def DNVT_void : DagNodeValType; // Tree node always returns void -def DNVT_val : DagNodeValType; // A non-void type -def DNVT_arg0 : DagNodeValType; // Tree node returns same type as Arg0 -def DNVT_arg1 : DagNodeValType; // Tree node returns same type as Arg1 -def DNVT_ptr : DagNodeValType; // The target pointer type -def DNVT_i8 : DagNodeValType; // Always have an i8 value - -class DagNode<DagNodeValType ret, list<DagNodeValType> args> { - DagNodeValType RetType = ret; - list<DagNodeValType> ArgTypes = args; - string EnumName = ?; -} - -// BuiltinDagNodes are built into the instruction selector and correspond to -// enum values. -class BuiltinDagNode<DagNodeValType Ret, list<DagNodeValType> Args, - string Ename> : DagNode<Ret, Args> { - let EnumName = Ename; -} - -// Magic nodes... -def Void : RegisterClass<isVoid,0,[]> { let isDummyClass = 1; } -def set : DagNode<DNVT_void, [DNVT_val, DNVT_arg0]>; -def chain : BuiltinDagNode<DNVT_void, [DNVT_void, DNVT_void], "ChainNode">; -def blockchain : BuiltinDagNode<DNVT_void, [DNVT_void, DNVT_void], - "BlockChainNode">; -def ChainExpander : Expander<(chain Void, Void), []>; -def BlockChainExpander : Expander<(blockchain Void, Void), []>; - - -// Terminals... -def imm : BuiltinDagNode<DNVT_val, [], "Constant">; -def frameidx : BuiltinDagNode<DNVT_ptr, [], "FrameIndex">; -def basicblock : BuiltinDagNode<DNVT_ptr, [], "BasicBlock">; - -// Arithmetic... -def plus : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "Plus">; -def minus : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "Minus">; -def times : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "Times">; -def sdiv : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "SDiv">; -def udiv : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "UDiv">; -def srem : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "SRem">; -def urem : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "URem">; -def and : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "And">; -def or : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "Or">; -def xor : BuiltinDagNode<DNVT_arg0, [DNVT_arg1, DNVT_arg0], "Xor">; - -// Comparisons... -def seteq : BuiltinDagNode<DNVT_i8 , [DNVT_arg1, DNVT_arg0], "SetEQ">; -def setne : BuiltinDagNode<DNVT_i8 , [DNVT_arg1, DNVT_arg0], "SetNE">; -def setlt : BuiltinDagNode<DNVT_i8 , [DNVT_arg1, DNVT_arg0], "SetLT">; -def setle : BuiltinDagNode<DNVT_i8 , [DNVT_arg1, DNVT_arg0], "SetLE">; -def setgt : BuiltinDagNode<DNVT_i8 , [DNVT_arg1, DNVT_arg0], "SetGT">; -def setge : BuiltinDagNode<DNVT_i8 , [DNVT_arg1, DNVT_arg0], "SetGE">; - -def load : BuiltinDagNode<DNVT_val, [DNVT_ptr], "Load">; -//def store : BuiltinDagNode<DNVT_Void, [DNVT_ptr, DNVT_val]>; - -// Other... -def ret : BuiltinDagNode<DNVT_void, [DNVT_val], "Ret">; -def retvoid : BuiltinDagNode<DNVT_void, [], "RetVoid">; -def br : BuiltinDagNode<DNVT_void, [DNVT_ptr], "Br">; -def brcond : BuiltinDagNode<DNVT_void, [DNVT_i8, DNVT_ptr, DNVT_ptr], - "BrCond">; - -def unspec1 : BuiltinDagNode<DNVT_any , [DNVT_val], "Unspec1">; -def unspec2 : BuiltinDagNode<DNVT_any , [DNVT_val, DNVT_val], "Unspec2">; - -//===----------------------------------------------------------------------===// -// DAG nonterminals definitions used by the instruction selector... -// -class Nonterminal<dag pattern> { - dag Pattern = pattern; - bit BuiltIn = 0; -} - -*/ +include "../TargetSelectionDAG.td" diff --git a/lib/Target/TargetSelectionDAG.td b/lib/Target/TargetSelectionDAG.td new file mode 100644 index 0000000000..ed63fcbd50 --- /dev/null +++ b/lib/Target/TargetSelectionDAG.td @@ -0,0 +1,214 @@ +//===- TargetSelectionDAG.td - Common code for DAG isels ---*- tablegen -*-===// +// +// 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. +// +//===----------------------------------------------------------------------===// +// +// This file defines the target-independent interfaces used by SelectionDAG +// instruction selection generators. +// +//===----------------------------------------------------------------------===// + +//===----------------------------------------------------------------------===// +// Selection DAG Type Constraint definitions. +// +// Note that the semantics of these constraints are hard coded into tblgen. To +// modify or add constraints, you have to hack tblgen. +// + +class SDTypeConstraint<int opnum> { + int OperandNum = opnum; +} + +// SDTCisVT - The specified operand has exactly this VT. +class SDTCisVT <int OpNum, ValueType vt> : SDTypeConstraint<OpNum> { + ValueType VT = vt; +} + +// SDTCisInt - The specified operand is has integer type. +class SDTCisInt<int OpNum> : SDTypeConstraint<OpNum>; + +// SDTCisFP - The specified operand is has floating point type. +class SDTCisFP <int OpNum> : SDTypeConstraint<OpNum>; + +// SDTCisSameAs - The two specified operands have identical types. +class SDTCisSameAs<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> { + int OtherOperandNum = OtherOp; +} + +// SDTCisVTSmallerThanOp - The specified operand is a VT SDNode, and its type is +// smaller than the 'Other' operand. +class SDTCisVTSmallerThanOp<int OpNum, int OtherOp> : SDTypeConstraint<OpNum> { + int OtherOperandNum = OtherOp; +} + +//===----------------------------------------------------------------------===// +// Selection DAG Type Profile definitions. +// +// These use the constraints defined above to describe the type requirements of +// the various nodes. These are not hard coded into tblgen, allowing targets to +// add their own if needed. +// + +// SDTypeProfile - This profile describes the type requirements of a Selection +// DAG node. +class SDTypeProfile<int numresults, int numoperands, + list<SDTypeConstraint> constraints> { + int NumResults = numresults; + int NumOperands = numoperands; + list<SDTypeConstraint> Constraints = constraints; +} + +// Builtin profiles. +def SDTImm : SDTypeProfile<1, 0, [SDTCisInt<0>]>; // for 'imm'. +def SDTVT : SDTypeProfile<1, 0, [SDTCisVT<0, OtherVT>]>; // for 'vt' +def SDTIntBinOp : SDTypeProfile<1, 2, [ // add, and, or, xor, udiv, etc. + SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisInt<0> +]>; +def SDTFPBinOp : SDTypeProfile<1, 2, [ // fadd, fmul, etc. + SDTCisSameAs<0, 1>, SDTCisSameAs<0, 2>, SDTCisFP<0> +]>; +def SDTIntUnaryOp : SDTypeProfile<1, 1, [ // ctlz + SDTCisSameAs<0, 1>, SDTCisInt<0> +]>; +def SDTFPUnaryOp : SDTypeProfile<1, 1, [ // fneg, fsqrt, etc + SDTCisSameAs<0, 1>, SDTCisFP<0> +]>; +def SDTExtInreg : SDTypeProfile<1, 2, [ // sext_inreg + SDTCisSameAs<0, 1>, SDTCisInt<0>, SDTCisVT<2, OtherVT>, + SDTCisVTSmallerThanOp<2, 1> +]>; + +//===----------------------------------------------------------------------===// +// Selection DAG Node Properties. +// +// Note: These are hard coded into tblgen. +// +class SDNodeProperty; +def SDNPCommutative : SDNodeProperty; // X op Y == Y op X +def SDNPAssociative : SDNodeProperty; // (X op Y) op Z == X op (Y op Z) + +//===----------------------------------------------------------------------===// +// Selection DAG Node definitions. +// +class SDNode<string opcode, SDTypeProfile typeprof, + list<SDNodeProperty> props = [], string sdclass = "SDNode"> { + string Opcode = opcode; + string SDClass = sdclass; + list<SDNodeProperty> Properties = props; + SDTypeProfile TypeProfile = typeprof; +} + +def set; +def node; + +def imm : SDNode<"ISD::Constant" , SDTImm , [], "ConstantSDNode">; +def vt : SDNode<"ISD::VALUETYPE" , SDTVT , [], "VTSDNode">; +def add : SDNode<"ISD::ADD" , SDTIntBinOp , + [SDNPCommutative, SDNPAssociative]>; +def sub : SDNode<"ISD::SUB" , SDTIntBinOp>; +def mul : SDNode<"ISD::MUL" , SDTIntBinOp, + [SDNPCommutative, SDNPAssociative]>; +def mulhs : SDNode<"ISD::MULHS" , SDTIntBinOp, [SDNPCommutative]>; +def mulhu : SDNode<"ISD::MULHU" , SDTIntBinOp, [SDNPCommutative]>; +def sdiv : SDNode<"ISD::SDIV" , SDTIntBinOp>; +def udiv : SDNode<"ISD::UDIV" , SDTIntBinOp>; +def srem : SDNode<"ISD::SREM" , SDTIntBinOp>; +def urem : SDNode<"ISD::UREM" , SDTIntBinOp>; +def srl : SDNode<"ISD::SRL" , SDTIntBinOp>; +def sra : SDNode<"ISD::SRA" , SDTIntBinOp>; +def shl : SDNode<"ISD::SHL" , SDTIntBinOp>; +def and : SDNode<"ISD::AND" , SDTIntBinOp, + [SDNPCommutative, SDNPAssociative]>; +def or : SDNode<"ISD::OR" , SDTIntBinOp, + [SDNPCommutative, SDNPAssociative]>; +def xor : SDNode<"ISD::XOR" , SDTIntBinOp, + [SDNPCommutative, SDNPAssociative]>; +def fadd : SDNode<"ISD::FADD" , SDTFPBinOp, [SDNPCommutative]>; +def fsub : SDNode<"ISD::FSUB" , SDTFPBinOp>; +def fmul : SDNode<"ISD::FMUL" , SDTFPBinOp, [SDNPCommutative]>; +def fdiv : SDNode<"ISD::FDIV" , SDTFPBinOp>; +def frem : SDNode<"ISD::FREM" , SDTFPBinOp>; +def fabs : SDNode<"ISD::FABS" , SDTFPUnaryOp>; +def fneg : SDNode<"ISD::FNEG" , SDTFPUnaryOp>; +def fsqrt : SDNode<"ISD::FSQRT" , SDTFPUnaryOp>; + +def sext_inreg : SDNode<"ISD::SIGN_EXTEND_INREG", SDTExtInreg>; +def ctlz : SDNode<"ISD::CTLZ" , SDTIntUnaryOp>; + +//===----------------------------------------------------------------------===// +// Selection DAG Node Transformation Functions. +// +// This mechanism allows targets to manipulate nodes in the output DAG once a +// match has been formed. This is typically used to manipulate immediate +// values. +// +class SDNodeXForm<SDNode opc, code xformFunction> { + SDNode Opcode = opc; + code XFormFunction = xformFunction; +} + +def NOOP_SDNodeXForm : SDNodeXForm<imm, [{}]>; + + +//===----------------------------------------------------------------------===// +// Selection DAG Pattern Fragments. +// +// Pattern fragments are reusable chunks of dags that match specific things. +// They can take arguments and have C++ predicates that control whether they +// match. They are intended to make the patterns for common instructions more +// compact and readable. +// + +/// PatFrag - Represents a pattern fragment. This can match something on the +/// DAG, frame a single node to multiply nested other fragments. +/// +class PatFrag<dag ops, dag frag, code pred = [{}], + SDNodeXForm xform = NOOP_SDNodeXForm> { + dag Operands = ops; + dag Fragment = frag; + code Predicate = pred; + SDNodeXForm OperandTransform = xform; +} + +// PatLeaf's are pattern fragments that have no operands. This is just a helper +// to define immediates and other common things concisely. +class PatLeaf<dag frag, code pred = [{}], SDNodeXForm xform = NOOP_SDNodeXForm> + : PatFrag<(ops), frag, pred, xform>; + +// Leaf fragments. + +def immAllOnes : PatLeaf<(imm), [{ return N->isAllOnesValue(); }]>; +def immZero : PatLeaf<(imm), [{ return N->isNullValue(); }]>; + +def vtInt : PatLeaf<(vt), [{ return MVT::isInteger(N->getVT()); }]>; +def vtFP : PatLeaf<(vt), [{ return MVT::isFloatingPoint(N->getVT()); }]>; + +// Other helper fragments. + +def not : PatFrag<(ops node:$in), (xor node:$in, immAllOnes)>; +def ineg : PatFrag<(ops node:$in), (sub immZero, node:$in)>; + +//===----------------------------------------------------------------------===// +// Selection DAG Pattern Support. +// +// Patterns are what are actually matched against the target-flavored +// instruction selection DAG. Instructions defined by the target implicitly +// define patterns in most cases, but patterns can also be explicitly added when +// an operation is defined by a sequence of instructions (e.g. loading a large +// immediate value on RISC targets that do not support immediates as large as +// their GPRs). +// + +class Pattern<dag patternToMatch, list<dag> resultInstrs> { + dag PatternToMatch = patternToMatch; + list<dag> ResultInstrs = resultInstrs; +} + +// Pat - A simple (but common) form of a pattern, which produces a simple result +// not needing a full list. +class Pat<dag pattern, dag result> : Pattern<pattern, [result]>; + |