From a47697aa4459e8cc0cc4fd336ca31cfea9d734fc Mon Sep 17 00:00:00 2001 From: Matt Valentine-House Date: Tue, 16 Mar 2021 10:47:35 +0000 Subject: LLDB: Introduce dump_page helper This dumps out object type information for every object on a page in the form: bits [LM R ] T_CLASS [389]: Addr: 0x1007ebcf0 (flags: 0x100000062) --- misc/lldb_cruby.py | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 53 insertions(+) (limited to 'misc') diff --git a/misc/lldb_cruby.py b/misc/lldb_cruby.py index 7341e0447f..e0cf53760f 100755 --- a/misc/lldb_cruby.py +++ b/misc/lldb_cruby.py @@ -526,6 +526,57 @@ def dump_bits(target, result, page, object_address, end = "\n"): check_bits(page, "marking_bits", bitmap_index, bitmap_bit, "R"), check_bits(page, "wb_unprotected_bits", bitmap_index, bitmap_bit, "U"), ), end=end, file=result) + +def dump_page(debugger, command, result, internal_dict): + if not ('RUBY_Qfalse' in globals()): + lldb_init(debugger) + + target = debugger.GetSelectedTarget() + process = target.GetProcess() + thread = process.GetSelectedThread() + frame = thread.GetSelectedFrame() + + tHeapPageP = target.FindFirstType("struct heap_page").GetPointerType() + page = frame.EvaluateExpression(command) + page = page.Cast(tHeapPageP) + + tRBasic = target.FindFirstType("struct RBasic") + tRValue = target.FindFirstType("struct RVALUE") + + obj_address = page.GetChildMemberWithName('start').GetValueAsUnsigned(); + num_slots = page.GetChildMemberWithName('total_slots').unsigned + + ruby_type_map = ruby_types(debugger) + + for j in range(0, num_slots): + offset = obj_address + (j * tRValue.GetByteSize()) + obj_addr = lldb.SBAddress(offset, target) + p = target.CreateValueFromAddress("object", obj_addr, tRBasic) + dump_bits(target, result, page, offset, end = " ") + flags = p.GetChildMemberWithName('flags').GetValueAsUnsigned() + print("%s [%3d]: Addr: %0#x (flags: %0#x)" % (rb_type(flags, ruby_type_map), j, offset, flags), file=result) + +def rb_type(flags, ruby_types): + flType = flags & RUBY_T_MASK + return "%-10s" % (ruby_types.get(flType, ("%0#x" % flType))) + +def ruby_types(debugger): + target = debugger.GetSelectedTarget() + + types = {} + for enum in target.FindFirstGlobalVariable('ruby_dummy_gdb_enums'): + enum = enum.GetType() + members = enum.GetEnumMembers() + for i in range(0, members.GetSize()): + member = members.GetTypeEnumMemberAtIndex(i) + name = member.GetName() + value = member.GetValueAsUnsigned() + + if name.startswith('RUBY_T_'): + types[value] = name.replace('RUBY_', '') + + return types + def __lldb_init_module(debugger, internal_dict): debugger.HandleCommand("command script add -f lldb_cruby.lldb_rp rp") debugger.HandleCommand("command script add -f lldb_cruby.count_objects rb_count_objects") @@ -534,5 +585,7 @@ def __lldb_init_module(debugger, internal_dict): debugger.HandleCommand("command script add -f lldb_cruby.heap_page heap_page") debugger.HandleCommand("command script add -f lldb_cruby.heap_page_body heap_page_body") debugger.HandleCommand("command script add -f lldb_cruby.rb_backtrace rbbt") + debugger.HandleCommand("command script add -f lldb_cruby.dump_page dump_page") + lldb_init(debugger) print("lldb scripts for ruby has been installed.") -- cgit v1.2.3