Mouse
How LainDOS turns emulator PS/2 packets into DOS mouse-driver state: INT 33h calls, button edges, callbacks, mickey scaling, emulator capture, and the game-specific behavior this small driver is meant to cover.
From packet to callback
LainDOS does not load a TSR mouse driver. The kernel owns the INT 33h vector and the IRQ12 packet path directly, which keeps the implementation small and lets games see a mouse driver before any shell command or AUTOEXEC helper is involved.
0102030405INT 33h dispatch
Every mouse call polls hardware before serving state.The INT 33hINT 33hThe conventional DOS mouse-driver interrupt implemented by LainDOS for game input. handler keeps a narrow implemented surface. It logs optional traces, polls any queued PS/2 bytes, then dispatches known AX values. Unknown functions return with a plain iret instead of pretending to implement a broad mouse-driver API.
Reset returns the installed-driver signature in AX and the two-button count in BX. It also resets ranges, position, motion counters, press/release counters, callback state, and the mickey/pixel ratio.
Tests that pin this
Position, ranges, and ratio
Coordinates are scaled and clamped inside the active range.Position calls use the conventional BX/CX/DX register shape. AX=0004h stores CX/DX, clears scaling remainders, then clamps. Range calls accept either order for CX/DX and immediately clamp the current coordinate.
AX=000Fh changes the mickey/pixel ratio. LainDOS scales signed PS/2 deltas with delta * 8 / ratio and keeps signed remainders so slow movement still accumulates correctly.
Tests that pin this
PS/2 packet path
QEMU/86Box mouse input arrives as standard three-byte PS/2 packets.At boot the kernel enables the auxiliary device, sends mouse defaults and streaming commands, writes the controller command byte, unmasks IRQ12, and records whether PS/2 setup succeeded. The INT 33hINT 33hThe conventional DOS mouse-driver interrupt implemented by LainDOS for game input. path also polls the controller so tests can observe movement without waiting for an interrupt window.
The packet decoder rejects unsynchronized first bytes, sign-extends deltas, ignores overflowed axes, negates Y to match screen coordinates, adds raw motion counters, and applies scaled movement to the clamped cursor position.
Tests that pin this
Edges and callbacks
Movement and button edges can call back into a game.Once a full packet has updated movement and button state, LainDOS sets event-mask bits for motion, left press/release, and right press/release. It records edge positions and updates current button bits before considering a callback.
Callback invocation is guarded against recursive mouse callbacks. The IRQ12 handler acknowledges both PICs before processing, and the callback itself runs with interrupts enabled so timer ticks and keystrokes keep flowing during long game callbacks. The game receives AX=matched mask, BX=buttons, CX/DX=position, and SI/DI=movement deltas, then returns with RETF. INT 21hINT 21hThe main DOS API interrupt. Programs select services such as open, read, EXEC, and exit with AH. calls made from the callback are rejected so DOS file I/O state is not re-entered.
Tests that pin this
Implemented narrowly on purpose
The mouse surface grows only when a target program or regression proves it needs more. Current support is enough for the known game paths without claiming complete Microsoft Mouse driver compatibility.