Files
Custom-Operating-System/utils/qprof/ProfNode.py

62 lines
1.8 KiB
Python

from AddrResolver import AddrResolver
class Profiler:
def __init__(self, filename):
self.addr_resolver = AddrResolver(filename)
def resolver(self):
return self.addr_resolver
class ProfNode:
def __init__(self, profiler, pc=0):
self.profiler = profiler
self.pc = pc
self.name = "NOT SET"
self.call_count = 0
self.children = {}
self.children_by_name = {}
def merge(self, node):
self.call_count += node.call_count
self.children = {**self.children, **node.children}
def add_stacktrace(self, stacktrace):
if len(stacktrace) == 0:
return
child_pc = stacktrace[-1]
if child_pc in self.children.keys():
self.children[child_pc].call_count += 1
else:
self.children[child_pc] = ProfNode(self.profiler, child_pc)
self.children[child_pc].call_count += 1
self.children[child_pc].add_stacktrace(stacktrace[:-1])
def process_node(self):
named_nodes = {}
for k, v in self.children.items():
v.process_node()
func_name = self.profiler.resolver().get(k)
if func_name in named_nodes.keys():
named_nodes[func_name].merge(v)
else:
named_nodes[func_name] = ProfNode(self.profiler)
named_nodes[func_name].name = func_name
named_nodes[func_name].merge(v)
self.children = named_nodes
def print(self, tabs=0):
print('{} {:>4} {}'.format(" "*tabs, self.call_count, self.name))
def trace(self, tabs=0):
self.print(tabs)
rd = sorted(self.children.values(),
key=lambda node: node.call_count, reverse=True)
for v in rd:
v.trace(tabs + 1)