diff --git a/llvm/include/llvm/CodeGen/LiveInterval.h b/llvm/include/llvm/CodeGen/LiveInterval.h index ce9845ee1673..788a649f717e 100644 --- a/llvm/include/llvm/CodeGen/LiveInterval.h +++ b/llvm/include/llvm/CodeGen/LiveInterval.h @@ -606,6 +606,10 @@ namespace llvm { LiveInterval(unsigned Reg, float Weight) : SubRanges(nullptr), reg(Reg), weight(Weight) {} + ~LiveInterval() { + clearSubRanges(); + } + template class SingleLinkedListIterator { T *P; @@ -681,9 +685,7 @@ namespace llvm { } /// Removes all subregister liveness information. - void clearSubRanges() { - SubRanges = nullptr; - } + void clearSubRanges(); /// Removes all subranges without any segments (subranges without segments /// are not considered valid and should only exist temporarily). @@ -733,6 +735,9 @@ namespace llvm { Range->Next = SubRanges; SubRanges = Range; } + + /// Free memory held by SubRange. + void freeSubRange(SubRange *S); }; inline raw_ostream &operator<<(raw_ostream &OS, const LiveInterval &LI) { diff --git a/llvm/lib/CodeGen/LiveInterval.cpp b/llvm/lib/CodeGen/LiveInterval.cpp index 9423edc30910..5790905ba5c3 100644 --- a/llvm/lib/CodeGen/LiveInterval.cpp +++ b/llvm/lib/CodeGen/LiveInterval.cpp @@ -598,6 +598,11 @@ VNInfo *LiveRange::MergeValueNumberInto(VNInfo *V1, VNInfo *V2) { return V2; } +void LiveInterval::freeSubRange(SubRange *S) { + S->~SubRange(); + // Memory was allocated with BumpPtr allocator and is not freed here. +} + void LiveInterval::removeEmptySubRanges() { SubRange **NextPtr = &SubRanges; SubRange *I = *NextPtr; @@ -609,12 +614,22 @@ void LiveInterval::removeEmptySubRanges() { } // Skip empty subranges until we find the first nonempty one. do { - I = I->Next; + SubRange *Next = I->Next; + freeSubRange(I); + I = Next; } while (I != nullptr && I->empty()); *NextPtr = I; } } +void LiveInterval::clearSubRanges() { + for (SubRange *I = SubRanges, *Next; I != nullptr; I = Next) { + Next = I->Next; + freeSubRange(I); + } + SubRanges = nullptr; +} + /// Helper function for constructMainRangeFromSubranges(): Search the CFG /// backwards until we find a place covered by a LiveRange segment that actually /// has a valno set.