Files
jsix/scripts/parse_heap_allocs.py
Justin C. Miller 350396d70f [tools] Commit memory debug (et al) tooling
These are some changes I made to debug tooling while tracking down the
bugfix in the previous commit.

Each `scripts/debug_*_alloc.gdb` script has gdb output a `*_allocs.txt`
file, which in turn can be parsed by the `scripts/parse_*_allocs.py`
script to find errors.
2023-07-10 01:31:07 -07:00

63 lines
1.5 KiB
Python
Executable File

#!/usr/bin/env python3
from bisect import bisect_left, insort
from operator import attrgetter
by_start = attrgetter('start')
class alloc:
def __init__(self, start, size):
self.start = start
self.size = size
@property
def end(self):
return self.start + self.size
def overlaps(self, other):
return other.start < self.end and other.end > self.start
def __str__(self):
return f"[{self.start:012x} - {self.end:012x}]"
def __gt__(self, other):
return self.start > other.start
def add_alloc(allocs, addr, length):
a = alloc(addr, length)
for existing in allocs:
if a.overlaps(existing):
print(f"ERROR: allocation {a} overlaps existing {existing}")
insort(allocs, a)
def remove_alloc(allocs, addr):
a = alloc(addr, 0)
i = bisect_left(allocs, a)
if len(allocs) > i and allocs[i].start == addr:
del allocs[i]
else:
print(f"ERROR: freeing unallocated {a}")
def parse_line(allocs, line):
args = line.strip().split()
match args:
case ['+', addr, length]:
add_alloc(allocs, int(addr, base=16), int(length))
case ['-', addr]:
remove_alloc(allocs, int(addr, base=16))
case _:
pass
def parse_file(f):
allocs = []
for line in f.readlines():
parse_line(allocs, line)
if __name__ == "__main__":
import sys
if len(sys.argv) > 1:
with open(sys.argv[1]) as f:
parse_file(f)
else:
parse_file(sys.stdin)