diff options
author | Benjamin Kramer <benny.kra@googlemail.com> | 2013-09-29 11:18:56 +0000 |
---|---|---|
committer | Benjamin Kramer <benny.kra@googlemail.com> | 2013-09-29 11:18:56 +0000 |
commit | fd40d514ec7e95fe4a59a7a467c887b026364ff2 (patch) | |
tree | 0c758421154f5f33345a6bb7eae43ee4cb8d4313 | |
parent | 951fcc9ce8add9a3542eeb18b1c862ae31d418ec (diff) | |
download | external_llvm-fd40d514ec7e95fe4a59a7a467c887b026364ff2.zip external_llvm-fd40d514ec7e95fe4a59a7a467c887b026364ff2.tar.gz external_llvm-fd40d514ec7e95fe4a59a7a467c887b026364ff2.tar.bz2 |
Allocate AtomicSDNode operands in SelectionDAG's allocator to stop leakage.
SDNode destructors are never called. As an optimization use AtomicSDNode's
internal storage if we have a small number of operands.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@191636 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | include/llvm/CodeGen/SelectionDAGNodes.h | 17 | ||||
-rw-r--r-- | lib/CodeGen/SelectionDAG/SelectionDAG.cpp | 12 |
2 files changed, 17 insertions, 12 deletions
diff --git a/include/llvm/CodeGen/SelectionDAGNodes.h b/include/llvm/CodeGen/SelectionDAGNodes.h index 4166340..13f5d4e 100644 --- a/include/llvm/CodeGen/SelectionDAGNodes.h +++ b/include/llvm/CodeGen/SelectionDAGNodes.h @@ -1073,7 +1073,6 @@ public: /// class AtomicSDNode : public MemSDNode { SDUse Ops[4]; - SDUse* DynOps; void InitAtomic(AtomicOrdering Ordering, SynchronizationScope SynchScope) { // This must match encodeMemSDNodeFlags() in SelectionDAG.cpp. @@ -1101,7 +1100,7 @@ public: SDValue Chain, SDValue Ptr, SDValue Cmp, SDValue Swp, MachineMemOperand *MMO, AtomicOrdering Ordering, SynchronizationScope SynchScope) - : MemSDNode(Opc, Order, dl, VTL, MemVT, MMO), DynOps(NULL) { + : MemSDNode(Opc, Order, dl, VTL, MemVT, MMO) { InitAtomic(Ordering, SynchScope); InitOperands(Ops, Chain, Ptr, Cmp, Swp); } @@ -1110,7 +1109,7 @@ public: SDValue Chain, SDValue Ptr, SDValue Val, MachineMemOperand *MMO, AtomicOrdering Ordering, SynchronizationScope SynchScope) - : MemSDNode(Opc, Order, dl, VTL, MemVT, MMO), DynOps(NULL) { + : MemSDNode(Opc, Order, dl, VTL, MemVT, MMO) { InitAtomic(Ordering, SynchScope); InitOperands(Ops, Chain, Ptr, Val); } @@ -1119,21 +1118,19 @@ public: SDValue Chain, SDValue Ptr, MachineMemOperand *MMO, AtomicOrdering Ordering, SynchronizationScope SynchScope) - : MemSDNode(Opc, Order, dl, VTL, MemVT, MMO), DynOps(NULL) { + : MemSDNode(Opc, Order, dl, VTL, MemVT, MMO) { InitAtomic(Ordering, SynchScope); InitOperands(Ops, Chain, Ptr); } AtomicSDNode(unsigned Opc, unsigned Order, DebugLoc dl, SDVTList VTL, EVT MemVT, - SDValue* AllOps, unsigned NumOps, + SDValue* AllOps, SDUse *DynOps, unsigned NumOps, MachineMemOperand *MMO, AtomicOrdering Ordering, SynchronizationScope SynchScope) : MemSDNode(Opc, Order, dl, VTL, MemVT, MMO) { - DynOps = new SDUse[NumOps]; InitAtomic(Ordering, SynchScope); - InitOperands(DynOps, AllOps, NumOps); - } - ~AtomicSDNode() { - delete[] DynOps; + assert((DynOps || NumOps <= array_lengthof(Ops)) && + "Too many ops for internal storage!"); + InitOperands(DynOps ? DynOps : Ops, AllOps, NumOps); } const SDValue &getBasePtr() const { return getOperand(1); } diff --git a/lib/CodeGen/SelectionDAG/SelectionDAG.cpp b/lib/CodeGen/SelectionDAG/SelectionDAG.cpp index b96c4b1..62ceb8b 100644 --- a/lib/CodeGen/SelectionDAG/SelectionDAG.cpp +++ b/lib/CodeGen/SelectionDAG/SelectionDAG.cpp @@ -4125,10 +4125,18 @@ SDValue SelectionDAG::getAtomic(unsigned Opcode, SDLoc dl, EVT MemVT, cast<AtomicSDNode>(E)->refineAlignment(MMO); return SDValue(E, 0); } + + // Allocate the operands array for the node out of the BumpPtrAllocator, since + // SDNode doesn't have access to it. This memory will be "leaked" when + // the node is deallocated, but recovered when the allocator is released. + // If the number of operands is less than 5 we use AtomicSDNode's internal + // storage. + SDUse *DynOps = NumOps > 4 ? OperandAllocator.Allocate<SDUse>(NumOps) : 0; + SDNode *N = new (NodeAllocator) AtomicSDNode(Opcode, dl.getIROrder(), dl.getDebugLoc(), VTList, MemVT, - Ops, NumOps, MMO, Ordering, - SynchScope); + Ops, DynOps, NumOps, MMO, + Ordering, SynchScope); CSEMap.InsertNode(N, IP); AllNodes.push_back(N); return SDValue(N, 0); |