lldb-test ir-memory-map: Use IntervalMap::contains
authorPavel Labath <pavel@labath.sk>
Thu, 27 Dec 2018 09:32:04 +0000 (09:32 +0000)
committerPavel Labath <pavel@labath.sk>
Thu, 27 Dec 2018 09:32:04 +0000 (09:32 +0000)
Summary:
Simplify the code by using the contains implementation in IntervalMap.

There is a slight change of behavior here: We now treat an allocation of
size 0, as if it was size 1. This guarantees that the returned addresses
will be unique, whereas previously we would allow the allocation
function to return the same zero-sized region multiple times, as long as
it is not null, and not in the middle of an existing interval (but the
situation when we were placing an larger interval over a zero-sized one
was not detected).

I think this behavior makes more sense, as that is pretty much the same
guarantee as offered by malloc (except that is permitted to also return
nullptr).

Reviewers: vsk

Subscribers: lldb-commits

Differential Revision: https://reviews.llvm.org/D55761

llvm-svn: 350087

lldb/tools/lldb-test/lldb-test.cpp

index d8f4472..62abc42 100644 (file)
@@ -209,7 +209,6 @@ struct IRMemoryMapTestState {
       : Target(Target), Map(Target), Allocations(IntervalMapAllocator) {}
 };
 
-bool areAllocationsOverlapping(const AllocationT &L, const AllocationT &R);
 bool evalMalloc(StringRef Line, IRMemoryMapTestState &State);
 bool evalFree(StringRef Line, IRMemoryMapTestState &State);
 int evaluateMemoryMapCommands(Debugger &Dbg);
@@ -808,13 +807,6 @@ static int dumpObjectFiles(Debugger &Dbg) {
   return HadErrors;
 }
 
-/// Check if two half-open intervals intersect:
-///   http://world.std.com/~swmcd/steven/tech/interval.html
-bool opts::irmemorymap::areAllocationsOverlapping(const AllocationT &L,
-                                                  const AllocationT &R) {
-  return R.first < L.second && L.first < R.second;
-}
-
 bool opts::irmemorymap::evalMalloc(StringRef Line,
                                    IRMemoryMapTestState &State) {
   // ::= <label> = malloc <size> <alignment>
@@ -861,28 +853,21 @@ bool opts::irmemorymap::evalMalloc(StringRef Line,
     exit(1);
   }
 
-  // Check that the allocation does not overlap another allocation. Do so by
-  // testing each allocation which may cover the interval [Addr, EndOfRegion).
-  addr_t EndOfRegion = Addr + Size;
-  auto Probe = State.Allocations.begin();
-  Probe.advanceTo(Addr); //< First interval s.t stop >= Addr.
-  AllocationT NewAllocation = {Addr, EndOfRegion};
-  while (Probe != State.Allocations.end() && Probe.start() < EndOfRegion) {
-    AllocationT ProbeAllocation = {Probe.start(), Probe.stop()};
-    if (areAllocationsOverlapping(ProbeAllocation, NewAllocation)) {
-      outs() << "Malloc error: overlapping allocation detected"
-             << formatv(", previous allocation at [{0:x}, {1:x})\n",
-                        Probe.start(), Probe.stop());
-      exit(1);
-    }
-    ++Probe;
+  // In case of Size == 0, we still expect the returned address to be unique and
+  // non-overlapping.
+  addr_t EndOfRegion = Addr + std::max<size_t>(Size, 1);
+  if (State.Allocations.overlaps(Addr, EndOfRegion)) {
+    auto I = State.Allocations.find(Addr);
+    outs() << "Malloc error: overlapping allocation detected"
+           << formatv(", previous allocation at [{0:x}, {1:x})\n", I.start(),
+                      I.stop());
+    exit(1);
   }
 
   // Insert the new allocation into the interval map. Use unique allocation
   // IDs to inhibit interval coalescing.
   static unsigned AllocationID = 0;
-  if (Size)
-    State.Allocations.insert(Addr, EndOfRegion, AllocationID++);
+  State.Allocations.insert(Addr, EndOfRegion, AllocationID++);
 
   // Store the label -> address mapping.
   State.Label2AddrMap[Label] = Addr;