From 8c2b52552c90f39e4b2fed43e309e599e742b6ac Mon Sep 17 00:00:00 2001 From: Dan Gohman Date: Fri, 30 Oct 2009 01:27:03 +0000 Subject: Initial target-independent CodeGen support for BlockAddresses. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@85556 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/llvm/CodeGen/AsmPrinter.h | 7 +++++++ include/llvm/CodeGen/MachineBasicBlock.h | 12 ++++++++++++ include/llvm/CodeGen/SelectionDAG.h | 2 ++ include/llvm/CodeGen/SelectionDAGNodes.h | 21 +++++++++++++++++++-- include/llvm/Target/TargetSelectionDAG.td | 4 ++++ 5 files changed, 44 insertions(+), 2 deletions(-) (limited to 'include') diff --git a/include/llvm/CodeGen/AsmPrinter.h b/include/llvm/CodeGen/AsmPrinter.h index 62d0679..a0bd330 100644 --- a/include/llvm/CodeGen/AsmPrinter.h +++ b/include/llvm/CodeGen/AsmPrinter.h @@ -22,6 +22,7 @@ #include "llvm/ADT/DenseMap.h" namespace llvm { + class BlockAddress; class GCStrategy; class Constant; class ConstantArray; @@ -334,6 +335,12 @@ namespace llvm { /// block label. MCSymbol *GetMBBSymbol(unsigned MBBID) const; + /// GetBlockAddressSymbol - Return the MCSymbol used to satisfy BlockAddress + /// uses of the specified basic block. + MCSymbol *GetBlockAddressSymbol(const BlockAddress *BA) const; + MCSymbol *GetBlockAddressSymbol(const Function *F, + const BasicBlock *BB) const; + /// EmitBasicBlockStart - This method prints the label for the specified /// MachineBasicBlock, an alignment (if present) and a comment describing /// it if appropriate. diff --git a/include/llvm/CodeGen/MachineBasicBlock.h b/include/llvm/CodeGen/MachineBasicBlock.h index 2a9e86a..585ee14 100644 --- a/include/llvm/CodeGen/MachineBasicBlock.h +++ b/include/llvm/CodeGen/MachineBasicBlock.h @@ -76,6 +76,10 @@ class MachineBasicBlock : public ilist_node { /// exception handler. bool IsLandingPad; + /// AddressTaken - Indicate that this basic block is potentially the + /// target of an indirect branch. + bool AddressTaken; + // Intrusive list support MachineBasicBlock() {} @@ -92,6 +96,14 @@ public: /// const BasicBlock *getBasicBlock() const { return BB; } + /// hasAddressTaken - Test whether this block is potentially the target + /// of an indirect branch. + bool hasAddressTaken() const { return AddressTaken; } + + /// setHasAddressTaken - Set this block to reflect that it potentially + /// is the target of an indirect branch. + void setHasAddressTaken() { AddressTaken = true; } + /// getParent - Return the MachineFunction containing this basic block. /// const MachineFunction *getParent() const { return xParent; } diff --git a/include/llvm/CodeGen/SelectionDAG.h b/include/llvm/CodeGen/SelectionDAG.h index e0198ef..8400e86 100644 --- a/include/llvm/CodeGen/SelectionDAG.h +++ b/include/llvm/CodeGen/SelectionDAG.h @@ -326,6 +326,8 @@ public: unsigned Line, unsigned Col, MDNode *CU); SDValue getLabel(unsigned Opcode, DebugLoc dl, SDValue Root, unsigned LabelID); + SDValue getBlockAddress(BlockAddress *BA, DebugLoc dl, + bool isTarget = false); SDValue getCopyToReg(SDValue Chain, DebugLoc dl, unsigned Reg, SDValue N) { return getNode(ISD::CopyToReg, dl, MVT::Other, Chain, diff --git a/include/llvm/CodeGen/SelectionDAGNodes.h b/include/llvm/CodeGen/SelectionDAGNodes.h index d9e9cf7..f960851 100644 --- a/include/llvm/CodeGen/SelectionDAGNodes.h +++ b/include/llvm/CodeGen/SelectionDAGNodes.h @@ -97,7 +97,7 @@ namespace ISD { BasicBlock, VALUETYPE, CONDCODE, Register, Constant, ConstantFP, GlobalAddress, GlobalTLSAddress, FrameIndex, - JumpTable, ConstantPool, ExternalSymbol, + JumpTable, ConstantPool, ExternalSymbol, BlockAddress, // The address of the GOT GLOBAL_OFFSET_TABLE, @@ -146,6 +146,7 @@ namespace ISD { TargetJumpTable, TargetConstantPool, TargetExternalSymbol, + TargetBlockAddress, /// RESULT = INTRINSIC_WO_CHAIN(INTRINSICID, arg1, arg2, ...) /// This node represents a target intrinsic function with no side effects. @@ -2026,11 +2027,27 @@ public: } }; +class BlockAddressSDNode : public SDNode { + BlockAddress *BA; + friend class SelectionDAG; + BlockAddressSDNode(unsigned NodeTy, DebugLoc dl, EVT VT, BlockAddress *ba) + : SDNode(NodeTy, dl, getSDVTList(VT)), BA(ba) { + } +public: + BlockAddress *getBlockAddress() const { return BA; } + + static bool classof(const BlockAddressSDNode *) { return true; } + static bool classof(const SDNode *N) { + return N->getOpcode() == ISD::BlockAddress || + N->getOpcode() == ISD::TargetBlockAddress; + } +}; + class LabelSDNode : public SDNode { SDUse Chain; unsigned LabelID; friend class SelectionDAG; -LabelSDNode(unsigned NodeTy, DebugLoc dl, SDValue ch, unsigned id) + LabelSDNode(unsigned NodeTy, DebugLoc dl, SDValue ch, unsigned id) : SDNode(NodeTy, dl, getSDVTList(MVT::Other)), LabelID(id) { InitOperands(&Chain, ch); } diff --git a/include/llvm/Target/TargetSelectionDAG.td b/include/llvm/Target/TargetSelectionDAG.td index 700c64c..8d910dd 100644 --- a/include/llvm/Target/TargetSelectionDAG.td +++ b/include/llvm/Target/TargetSelectionDAG.td @@ -269,6 +269,10 @@ def externalsym : SDNode<"ISD::ExternalSymbol", SDTPtrLeaf, [], "ExternalSymbolSDNode">; def texternalsym: SDNode<"ISD::TargetExternalSymbol", SDTPtrLeaf, [], "ExternalSymbolSDNode">; +def blockaddress : SDNode<"ISD::BlockAddress", SDTPtrLeaf, [], + "BlockAddressSDNode">; +def tblockaddress: SDNode<"ISD::TargetBlockAddress", SDTPtrLeaf, [], + "BlockAddressSDNode">; def add : SDNode<"ISD::ADD" , SDTIntBinOp , [SDNPCommutative, SDNPAssociative]>; -- cgit v1.1