Skip to content

Instantly share code, notes, and snippets.

@frankplow
Created May 5, 2024 17:33
Show Gist options
  • Save frankplow/027f25c935ddc06f417e7cd07e1e5670 to your computer and use it in GitHub Desktop.
Save frankplow/027f25c935ddc06f417e7cd07e1e5670 to your computer and use it in GitHub Desktop.
An LLDB plugin to render blocks of pixels from memory
import lldb
import matplotlib.pyplot as plt
import numpy as np
def __lldb_init_module(debugger, internal_dict):
debugger.HandleCommand("command script add -f lldb_showimg.showimg showimg")
def _pop_arg(args):
arg = args.pop(0)
if arg.startswith('"'):
while not arg.endswith('"'):
arg += " " + args.pop(0)
arg = arg[1:-1]
return arg
# @TODO: Replace with ParsedCommand when this is in an LLVM release
def _parse_args(args):
args = args.split()
base = _pop_arg(args)
stride = _pop_arg(args)
width = _pop_arg(args)
height = _pop_arg(args)
bitdepth = _pop_arg(args)
return base, stride, width, height, bitdepth
def showimg(debugger, command, exe_ctx, result, internal_dict):
frame = exe_ctx.GetFrame()
target = debugger.GetSelectedTarget()
process = target.GetProcess()
base, stride, width, height, bitdepth = _parse_args(command)
base = frame.EvaluateExpression(base).unsigned
# @TODO: Use GetValueAsAddress if available
base = base.GetValueAsUnsigned()
stride = frame.EvaluateExpression(stride).signed
width = frame.EvaluateExpression(width).unsigned
height = frame.EvaluateExpression(height).unsigned
bitdepth = frame.EvaluateExpression(bitdepth).unsigned
sample_size = (bitdepth + 7) // 8
array = np.empty((height, width))
for y in range(height):
for x in range(width):
addr = base + y * stride + x * sample_size
error_ref = lldb.SBError()
sample = process.ReadMemory(addr, sample_size, error_ref)
sample = int.from_bytes(sample, byteorder="little")
array[y][x] = sample
plt.imshow(array, cmap="gray", vmin=0, vmax=1 << bitdepth)
plt.show()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment