mirror of
https://git.k-space.ee/arti/vt1200.git
synced 2026-10-30 12:03:54 +02:00
46 lines
1.8 KiB
Lua
46 lines
1.8 KiB
Lua
-- VT1200: demonstrate the pcfReadBitmaps n*4 integer overflow in-emulator.
|
|
--
|
|
-- We jump straight into the arithmetic block with a crafted PCF_CharInfo:
|
|
-- a9 = fake pCS, pCS->nChars at a9+0x270
|
|
-- a13 = fake arg blk, n (32-bit pcfReadInt32 result) at a13+0x20
|
|
-- PC = 3f984e70
|
|
-- A breakpoint after 'sll 0x2,a11' (3f985060) prints the resulting size and
|
|
-- quits, so we never enter fosAlloc with a bogus heap.
|
|
--
|
|
-- <mame> vt1200 -rompath harness/mame/roms -video none -sound none -nothrottle \
|
|
-- -debug -debugger none -debuglog \
|
|
-- -autoboot_script harness/mame/overflow.lua -autoboot_delay 0
|
|
|
|
local function hex(v) return string.format("%08X", v) end
|
|
|
|
local machine = manager.machine
|
|
local cpu = machine.devices[':maincpu']
|
|
local dbg = machine.debugger
|
|
local prog = cpu.spaces['program']
|
|
|
|
if not dbg then
|
|
print("ERROR: debugger not enabled; pass -debug")
|
|
machine:exit()
|
|
return
|
|
end
|
|
|
|
-- n defaults to 0x40000001: n*4 wraps mod 2^32 to 4, but the following loop
|
|
-- still writes n CARD32 entries -- a heap overflow. Override with OVF_N
|
|
-- (decimal) to run a control case.
|
|
local n = tonumber(os.getenv("OVF_N") or "1073741825")
|
|
|
|
cpu.state['SP'].value = 0x00080000
|
|
cpu.state['A9'].value = 0x00040000 -- fake pCS
|
|
cpu.state['A13'].value = 0x00060000 -- fake arg block
|
|
prog:write_u32(0x00040270, 0) -- pCS->nChars = 0
|
|
prog:write_u32(0x00060020, n) -- n
|
|
cpu.state['PC'].value = 0x3f984e70 -- pcfReadBitmaps arithmetic block
|
|
|
|
print(string.format("setup: n=%s (n*4 should wrap to 00000004)", hex(n)))
|
|
|
|
-- 3f985060 is the instruction right after '3f985050 sll 0x2,a11'.
|
|
dbg:command("bpset 3f985060,,{ printf \"RESULT n=%08X a11_fosAlloc_arg=%08X nChars=%08X\\n\", d@00060020, a11, d@00040270 ; quit }")
|
|
|
|
dbg.visible_cpu = cpu
|
|
dbg.execution_state = 'run'
|