modemwars/annotations/11_survey_notes_game_tileRules0200.json
2026-08-23 02:09:40 -05:00

49 lines
No EOL
4.9 KiB
JSON
Generated

{
"_comment": "generated by tools/mergeSurvey.py from survey/*.json - do not edit by hand",
"notes": {
"0200": {
"unit": "game/tileRules0200",
"block": [
"contourRuleTable: byteTable, 256 bytes. Terrain-contour rule table of the random map generator (overlay A, read at $7484 as contourRuleTable,Y). Y is an 8-bit mask of which of the eight neighbours of the current cell are higher terrain; the bit order is verified from the edge-clamp masks at $7463-$7481 ($D6 at column 0, $6B at column 39, $F8 at row 0, $1F at row 39): bit0=NW, bit1=N, bit2=NE, bit3=W, bit4=E, bit5=SW, bit6=S, bit7=SE. Entry semantics, confirmed against the actual bytes: $00 (index 0 only) = do nothing; $41-$51 = contour tile code to place (the generator subtracts contourTileOffset $0324, 0 for the summit ring, $20 for the lower-hill ring) - $51 north edge, $4D south edge, $4B west edge, $49 east edge, $45 N+W corner, $46 N+E, $47 W+S, $48 E+S, $44/$43/$42/$41 the isolated NW/NE/SW/SE diagonals; $80+n (105 entries, n = neighbour bit index) = randomly erase neighbour n instead; $91/$95/$97 (indexes $05 NW+NE, $A0 SW+SE, $84 NE+SE) = erase that neighbour or else fill; $FF (93 entries, including index $FF) = fill the cell with the interior tile. Loaded from track 18 sector 15 by loadSetupBlock/loadMapAndSetup; never written back to disk."
]
},
"0389": {
"unit": "game/tileRules0200",
"block": [
"setupBlockPadding: unknown, 119 bytes. $0389-$03FF, all zero on disk. Tail of track 18 sector 16 after the start-up code; not referenced as code or data by anything. At run time the page is later reused for other things (film directory, sprite shape buffer, map-generator variables)."
]
},
"0300": {
"routine": [
"initGameSystems - One-shot start-up routine that lives inside the block loaded from track 18 sectors 15-16. Called exactly once, from mainStart at $0A87 immediately after loadSetupBlock ($10BB). It calls resetGameVariables ($0C1C), resetSpritesAndVicBank ($035E), invertTextFonts ($031B), seeds the 24-bit game RNG with $49/$19/$02, calls buildMapRowAddressTable ($0339) and finally JMPs to initBitmapScreen ($2D41), which sets up the hires bitmap display and returns to mainStart.",
"In: none (runs with $01=$35, ROMs out, I/O in)",
"Out: zero page and $9008-$92FF cleared by resetGameVariables; zp_57/58/59 = $49/$19/$02 (RNG seed); all sprite registers and $9022 cleared; VIC bank 2 selected; fonts at $98BE-$9C6D inverted; map row tables at $BFB0/$BFD8 built; bitmap screen initialised; zp_48-zp_4B and zp_4E/4F clobbered"
],
"unit": "game/tileRules0200"
},
"031B": {
"routine": [
"invertTextFonts - Inverts (EOR #$FF) the 944 bytes at $98BE-$9C6D in place, walking the source pointer with advanceFillPointer ($C3F9) using zp_48/49 = $98BE and the limit zp_4A/4B = $9C6D. That range is exactly the two 59-glyph 8x8 character sets used by the $C000 overlay's text plotter: $98BE (multicolour / double-width glyphs) and $9A96 = $98BE+$1D8 (hires glyphs), selected at $C20B by bit 4 of the $D016 shadow $9001. The glyphs are stored positive on disk (1 bits = strokes) and are negatives after this call, so the plotter's ORA/EOR/CMP draw modes (set via setBitmapDrawMode, which patches $C22B) operate on inverted art.",
"In: none; hardcoded range $98BE..$9C6D",
"Out: $98BE-$9C6D EORed with $FF; zp_48/49 left at $9C6E, zp_4A/4B = $9C6D, zp_4E/4F incremented 944 times (never read)"
],
"unit": "game/tileRules0200"
},
"0339": {
"routine": [
"buildMapRowAddressTable - Builds the 40-entry row address table of the 40x40 battlefield map: for row 0..39 it stores the high byte of $F000+40*row at $BFD8+row and the low byte at $BFB0+row. These tables are what readMapCell ($25FA) and every other map accessor use to turn (column,row) into a pointer, so this must run before any map access. Uses zp_48/zp_49 as the running address.",
"In: none; base address $F000 and stride $28 are hardcoded",
"Out: $BFB0-$BFD7 = row address low bytes, $BFD8-$BFFF = high bytes; zp_48/zp_49 left at $F640 (one row past the map)"
],
"unit": "game/tileRules0200"
},
"035E": {
"routine": [
"resetSpritesAndVicBank - Clears all sprite state and picks the VIC bank. Zeroes $D000-$D010 (all eight sprite X/Y pairs plus the X-MSB register), $D015 (sprite enable) and its shadow $9022, $D017 (Y expand) and $D01A-$D01F (raster IRQ mask, sprite priority, sprite multicolour, X expand and the two collision latches, which the write clears). Then makes CIA2 port A bits 0-1 outputs and writes $05: VIC bank 2 ($8000-$BFFF, matching bitmap $A000 / screen $8C00) with the user-port RS-232 TXD latch left high. Ends with JMP clearAllSpriteData ($2FA5), which zeroes the sprite shape area $8A00-$8BFF.",
"In: none",
"Out: $D000-$D010, $D015, $D017, $D01A-$D01F = 0; $9022 = 0; CIA2_DDRA |= $03; CIA2_PRA = $05 (VIC bank 2); $8A00-$8BFF cleared; A = 0"
],
"unit": "game/tileRules0200"
}
}
}