Skip to main content
Glama

mgba_read_range

Read a contiguous range of memory addresses from Game Boy, GBC, or GBA ROMs to analyze game data, debug code, or extract information for automated testing.

Instructions

Read a contiguous range of memory addresses

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
rom_pathYesPath to the ROM file
start_addressYesStarting memory address
lengthYesNumber of bytes to read
savestate_pathNoOptional savestate to load
framesNoFrames to run before reading (default: 60)

Implementation Reference

  • Core implementation of mgba_read_range: generates Lua script to read contiguous memory range using emu:read8() loop after specified frames, writes JSON output, takes screenshot, and quits.
    def read_memory_range( self, rom_path: str, start_addr: int, length: int, savestate_path: Optional[str] = None, frames_before_read: int = 60, ) -> EmulatorResult: """Read a range of memory addresses.""" lua_script = f""" local frame = 0 callbacks:add("frame", function() frame = frame + 1 if frame >= {frames_before_read} then local f = io.open("output.json", "w") if f then f:write('{{"start": {start_addr}, "length": {length}, "data": [') for i = 0, {length - 1} do if i > 0 then f:write(',') end f:write(tostring(emu:read8({start_addr} + i))) end f:write(']}}') f:close() end emu:screenshot("screenshot.png") emu:quit() end end) """ return self._run_with_lua(rom_path, lua_script, savestate_path)
  • MCP tool dispatch handler for mgba_read_range: calls emulator.read_memory_range and formats the result as a formatted hex dump text output, includes screenshot if available.
    elif name == "mgba_read_range": result = emu.read_memory_range( rom_path=arguments["rom_path"], start_addr=arguments["start_address"], length=arguments["length"], savestate_path=arguments.get("savestate_path"), frames_before_read=arguments.get("frames", 60), ) if result.success and result.data: data = result.data["data"] start = result.data["start"] # Format as hex dump with 16 bytes per line lines = [f"Memory range 0x{start:04X} - 0x{start + len(data) - 1:04X}:"] for i in range(0, len(data), 16): addr = start + i hex_bytes = " ".join(f"{b:02X}" for b in data[i:i+16]) lines.append(f" {addr:04X}: {hex_bytes}") result_content.append(TextContent(type="text", text="\n".join(lines))) if result.screenshot: result_content.append(ImageContent( type="image", data=base64.b64encode(result.screenshot).decode(), mimeType="image/png", )) else: result_content.append(TextContent(type="text", text=f"Error: {result.error}"))
  • Input schema definition for the mgba_read_range tool, specifying parameters like rom_path, start_address, length, savestate_path, and frames.
    Tool( name="mgba_read_range", description="Read a contiguous range of memory addresses", inputSchema={ "type": "object", "properties": { "rom_path": { "type": "string", "description": "Path to the ROM file", }, "start_address": { "type": "integer", "description": "Starting memory address", }, "length": { "type": "integer", "description": "Number of bytes to read", }, "savestate_path": { "type": "string", "description": "Optional savestate to load", }, "frames": { "type": "integer", "description": "Frames to run before reading (default: 60)", "default": 60, }, }, "required": ["rom_path", "start_address", "length"], }, ),
  • Registration of mgba_read_range tool via the list_tools() handler that returns all available Tool objects to the MCP server.
    @server.list_tools() async def list_tools() -> list[Tool]: """List available MCP tools.""" return [ Tool( name="mgba_run", description="Run a GB/GBC/GBA ROM for a specified number of frames and capture a screenshot", inputSchema={ "type": "object", "properties": { "rom_path": { "type": "string", "description": "Path to the ROM file (.gb, .gbc, .gba)", }, "frames": { "type": "integer", "description": "Number of frames to run (default: 60)", "default": 60, }, "savestate_path": { "type": "string", "description": "Optional path to a savestate file to load", }, }, "required": ["rom_path"], }, ), Tool( name="mgba_read_memory", description="Read memory at specified addresses after running for some frames", inputSchema={ "type": "object", "properties": { "rom_path": { "type": "string", "description": "Path to the ROM file", }, "addresses": { "type": "array", "items": {"type": "integer"}, "description": "List of memory addresses to read (as integers, e.g., [0xC200, 0xFFBF])", }, "savestate_path": { "type": "string", "description": "Optional savestate to load", }, "frames": { "type": "integer", "description": "Frames to run before reading (default: 60)", "default": 60, }, }, "required": ["rom_path", "addresses"], }, ), Tool( name="mgba_read_range", description="Read a contiguous range of memory addresses", inputSchema={ "type": "object", "properties": { "rom_path": { "type": "string", "description": "Path to the ROM file", }, "start_address": { "type": "integer", "description": "Starting memory address", }, "length": { "type": "integer", "description": "Number of bytes to read", }, "savestate_path": { "type": "string", "description": "Optional savestate to load", }, "frames": { "type": "integer", "description": "Frames to run before reading (default: 60)", "default": 60, }, }, "required": ["rom_path", "start_address", "length"], }, ), Tool( name="mgba_dump_oam", description="Dump OAM (Object Attribute Memory) sprite data - shows all 40 sprites with position, tile, flags, and palette", inputSchema={ "type": "object", "properties": { "rom_path": { "type": "string", "description": "Path to the ROM file", }, "savestate_path": { "type": "string", "description": "Optional savestate to load", }, "frames": { "type": "integer", "description": "Frames to run before dumping (default: 60)", "default": 60, }, }, "required": ["rom_path"], }, ), Tool( name="mgba_dump_entities", description="Dump entity/actor data from WRAM - useful for analyzing game objects", inputSchema={ "type": "object", "properties": { "rom_path": { "type": "string", "description": "Path to the ROM file", }, "entity_base": { "type": "integer", "description": "Base address of entity array (default: 0xC200)", "default": 49664, }, "entity_size": { "type": "integer", "description": "Size of each entity in bytes (default: 24)", "default": 24, }, "entity_count": { "type": "integer", "description": "Number of entities to dump (default: 10)", "default": 10, }, "savestate_path": { "type": "string", "description": "Optional savestate to load", }, "frames": { "type": "integer", "description": "Frames to run before dumping (default: 60)", "default": 60, }, }, "required": ["rom_path"], }, ), Tool( name="mgba_run_lua", description="Run a custom Lua script in the emulator. The script can use emu:read8(), emu:write8(), emu:screenshot(), callbacks:add(), etc.", inputSchema={ "type": "object", "properties": { "rom_path": { "type": "string", "description": "Path to the ROM file", }, "script": { "type": "string", "description": "Lua script to execute. Use emu:quit() to exit. Write JSON to 'output.json' for structured data.", }, "savestate_path": { "type": "string", "description": "Optional savestate to load", }, "timeout": { "type": "integer", "description": "Timeout in seconds (default: 30)", "default": 30, }, }, "required": ["rom_path", "script"], }, ), ]

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/struktured-labs/mgba-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server