Source code

Revision control

Copy as Markdown

Other Tools

# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this file,
# You can obtain one at http://mozilla.org/MPL/2.0/.
# Pretty-printers for InterpreterRegs.
import gdb
import mozilla.prettyprinters as prettyprinters
prettyprinters.clear_module_printers(__name__)
from mozilla.prettyprinters import pretty_printer
class InterpreterTypeCache(object):
# Cache information about the Interpreter types for this objfile.
def __init__(self):
self.tValue = gdb.lookup_type("JS::Value")
self.tJSOp = gdb.lookup_type("JSOp")
try:
self.tScriptFrameIterData = gdb.lookup_type("js::ScriptFrameIter::Data")
except gdb.error:
# Work around problem with gcc optimized debuginfo where it doesn't
# seem to be able to see that ScriptFrameIter inherits the
# FrameIter::Data type.
self.tScriptFrameIterData = gdb.lookup_type("js::FrameIter::Data")
self.tInterpreterFrame = gdb.lookup_type("js::InterpreterFrame")
self.tBaselineFrame = gdb.lookup_type("js::jit::BaselineFrame")
self.tRematerializedFrame = gdb.lookup_type("js::jit::RematerializedFrame")
self.tDebugFrame = gdb.lookup_type("js::wasm::DebugFrame")
@pretty_printer("js::InterpreterRegs")
class InterpreterRegs(object):
def __init__(self, value, cache):
self.value = value
self.cache = cache
if not cache.mod_Interpreter:
cache.mod_Interpreter = InterpreterTypeCache()
self.itc = cache.mod_Interpreter
# There's basically no way to co-operate with 'set print pretty' (how would
# you get the current level of indentation?), so we don't even bother
# trying. No 'children', just 'to_string'.
def to_string(self):
fp_ = "fp_ = {}".format(self.value["fp_"])
slots = (self.value["fp_"] + 1).cast(self.itc.tValue.pointer())
sp = "sp = fp_.slots() + {}".format(self.value["sp"] - slots)
pc = "pc = {}".format(self.value["pc"])
return "{{ {}, {}, {} }}".format(fp_, sp, pc)
@pretty_printer("js::AbstractFramePtr")
class AbstractFramePtr(object):
Tag_InterpreterFrame = 0x0
Tag_BaselineFrame = 0x1
Tag_RematerializedFrame = 0x2
Tag_WasmDebugFrame = 0x3
TagMask = 0x3
def __init__(self, value, cache):
self.value = value
self.cache = cache
if not cache.mod_Interpreter:
cache.mod_Interpreter = InterpreterTypeCache()
self.itc = cache.mod_Interpreter
def to_string(self):
ptr = self.value["ptr_"]
tag = ptr & AbstractFramePtr.TagMask
ptr = ptr & ~AbstractFramePtr.TagMask
if tag == AbstractFramePtr.Tag_InterpreterFrame:
label = "js::InterpreterFrame"
ptr = ptr.cast(self.itc.tInterpreterFrame.pointer())
if tag == AbstractFramePtr.Tag_BaselineFrame:
label = "js::jit::BaselineFrame"
ptr = ptr.cast(self.itc.tBaselineFrame.pointer())
if tag == AbstractFramePtr.Tag_RematerializedFrame:
label = "js::jit::RematerializedFrame"
ptr = ptr.cast(self.itc.tRematerializedFrame.pointer())
if tag == AbstractFramePtr.Tag_WasmDebugFrame:
label = "js::wasm::DebugFrame"
ptr = ptr.cast(self.itc.tDebugFrame.pointer())
return "AbstractFramePtr (({} *) {})".format(label, ptr)
# Provide the ptr_ field as a child, so it prints after the pretty string
# provided above.
def children(self):
yield ("ptr_", self.value["ptr_"])