(back to project page)

Epoch Disassembly

                   ********************************************************************************
                   * Epoch, by Larry Miller                                                       *
                   * Copyright 1981 Sirius Software                                               *
                   *                                                                              *
                   * Code is from the common 35840-byte single-file cracked version.              *
                   *                                                                              *
                   *   ** THIS IS A WORK IN PROGRESS **                                           *
                   *   (some of the math is not yet explained)                                    *
                   *                                                                              *
                   ********************************************************************************
                   * Disassembly by Andy McFadden, using 6502bench SourceGen v1.7.2.              *
                   * Last updated 2020/09/24                                                      *
                   ********************************************************************************
                   * Some notes on terminology and conventions:                                   *
                   *                                                                              *
                   * The game creates a collection of objects, representing enemy ships,          *
                   * projectiles, stars, and so on.  Each object is a collection of elements,     *
                   * which may be points, horizontal lines, vertical lines, or filled rectangles. *
                   * Elements are always parallel to the screen.                                  *
                   *                                                                              *
                   * When an enemy ship or base is destroyed, a "flare" object and several        *
                   * "chunk" objects are created.  The flare expires after a few frames, the      *
                   * chunks expand outward from the explosion.                                    *
                   *                                                                              *
                   * Most games define objects in "world" space, and then use a model-view        *
                   * transform to get "eye" (or "camera") coordinates.  Epoch maintains           *
                   * everything in eye space.  The camera has a 45-degree FOV, and treats the     *
                   * view area as square (which makes things stretch when projected).  Objects    *
                   * that move entirely outside the view frustum are deleted.                     *
                   ********************************************************************************
                   INSTR_JSR_ABS   .eq     $20    {const}    ;opcode for JSR abs
                   INSTR_RTS       .eq     $60    {const}    ;opcode for RTS
                   INSTR_TXA       .eq     $8a    {const}    ;opcode for TXA
                   INSTR_STA_DPIIY .eq     $91    {const}    ;opcode for STA (dp),Y
                   INSTR_STA_ABS   .eq     $99    {const}    ;opcode for STA abs
                   INSTR_LDA_ABS   .eq     $ad    {const}    ;opcode for LDA abs
                   ptr_10          .eq     $10    {addr/2}   ;low byte always 0; multiple uses
                   math_tab_ptr12  .eq     $12    {addr/2}   ;low byte always 0
                   math_tab_ptr14  .eq     $14    {addr/2}   ;low byte always 0
                   boot_slot       .eq     $2b               ;boot slot * 16, usually $60
                   cur_obj_index   .eq     $62               ;index of object we're working on
                   cur_elem_index  .eq     $64               ;index of element we're working on
                   avail_obj_index .eq     $66               ;index of next-available object slot
                   avail_elem_index .eq    $68               ;index of next-available element slot
                   head_obj_index  .eq     $6a               ;index of first object in list
                   head_enemy_obj_index .eq $6c              ;index of first enemy object in list
                   free_obj_count  .eq     $6d               ;count of free entries in object list
                   free_elem_count .eq     $6e               ;count of free entries in element list
                   mod_elem_type   .eq     $70               ;$00=pt, $01=hl, $80=vl, $81=rct
                   no_draw_obj_flag .eq    $72               ;bool 00/nz: don't draw cur object
                   prev_obj_index  .eq     $74               ;index from previous loop iteration
                   clamped_lr_count .eq    $76               ;inc if left/right edge clamped
                   clamped_tb_count .eq    $78               ;inc if top/bottom edge clamped
                   elem_bad_z_flag? .eq    $7a
                   no_draw_elem_flag? .eq  $7c
                   tmp_8a          .eq     $8a               ;various uses
                   move_tmp        .eq     $8e    {addr/2}
                   orig_elem_type  .eq     $91               ;$00=pt, $01=hlin, $80=rct, $ff=vlin
                   portal_delta_xc .eq     $94    {addr/2}   ;94/95 paired with 96/97
                   adj_fwd_speed   .eq     $98    {addr/2}   ;adjusted speed: $6da4 with fractional adj
                   joy_yaw_angle   .eq     $9a    {addr/2}   ;magnitude of movement in X axis (0-$7ff)
                   joy_yaw_sign    .eq     $9c               ;sign of movement in X axis (L=0 R=ff)
                   joy_pitch_angle .eq     $9d    {addr/2}   ;magnitude of movement in Y axis (0-$7ff)
                   joy_pitch_sign  .eq     $9f               ;sign of movement in Y axis (U=0 D=ff)
                   impact_flash_ctr .eq    $a0               ;counts number of times to flash after impact
                   drawn_elem_count .eq    $a1               ;counts the number of elements drawn in current obj
                   linked_obj_index .eq    $a2               ;used when creating linked objects (ship explosions)
                   shape_cl_index  .eq     $a3               ;shape class index (0-10)
                   wronly_a4?      .eq     $a4               ;written, never read
                   wronly_a5?      .eq     $a5               ;written/incremented, never read
                   test_obj_index  .eq     $a8               ;index of object being tested for collision
                   wronly_a9?      .eq     $a9               ;written, never read
                   orig_opcode     .eq     $af               ;opcode to restore after render op
                   mid_col_count   .eq     $b0               ;for rect, (right - left - 3) (write-only)
                   engine_sound_ctr? .eq   $b1    {addr/3}   ;appears involved in engine sounds
                   wronly_b4?      .eq     $b4               ;written, never read
                   end_game_cause  .eq     $b5               ;0=time, 4=fuel, 8=amun (string index)
                   score_rating_index .eq  $b6               ;rating (0-4) x16
                   update_mvmt_flag .eq    $bb               ;affects ship movement updates
                   zcoord_factor   .eq     $bc
                   zcoord_clz      .eq     $bd               ;count of leading zeroes in Z coord
                   prev_scale_tab_ptr11 .eq $be              ;previous value of high byte of ptr
                   initial_xpos    .eq     $bf    {addr/2}   ;initial object XC (signed, neg=left)
                   initial_ypos    .eq     $c1    {addr/2}   ;initial object YC (signed, neg=up)
                   prev_zpos       .eq     $c5    {addr/2}   ;holds previous Z value; minor optimization
                   sound_counters  .eq     $c8    {addr/5}   ;counters used for managing sfx
                   engine_sound_enable .eq $cc               ;appears to enable unused engine sound
                   portal_next_xc  .eq     $ce    {addr/2}   ;X coord of next portal boundary obj
                   portal_next_yc  .eq     $d0    {addr/2}   ;Y coord of next portal boundary obj
                   bit_mask_left9  .eq     $d5    {addr/9}   ;00/80/c0..ff, used with clz
                   bit_mask_right9 .eq     $de    {addr/9}   ;ff/7f/3f..00
                   bit_mask_right8 .eq     $e7    {addr/8}   ;01/03/07..ff
                   bit_mask_left8  .eq     $ef    {addr/8}   ;fe/fc/f8..00
                   elem_collision_flag .eq $f8               ;bool 00/nz: did we cross enemy element Z plane?
                   impact_sound_flag .eq   $fa               ;bool 00/01: play impact sound
                   HIRES_P1        .eq     $2000  {addr/8192} ;hi-res graphics page 1
                   DATA_AREA       .eq     $4000             ;start of shape and music data
                   obj_spdlim_z_lo .eq     $9d20  {addr/40}  ;Z speed limit, low (hdr +$11)
                   obj_spdlim_z_hi .eq     $9d48  {addr/40}  ;Z speed limit, high (hdr +$12)
                   obj_spdlim_x_lo .eq     $9d70  {addr/40}  ;X speed limit, low (hdr +$13)
                   obj_spdlim_x_hi .eq     $9d98  {addr/40}  ;X speed limit, high (hdr +$14)
                   obj_spdlim_y_lo .eq     $9dc0  {addr/40}  ;Y speed limit, low (hdr +$15)
                   obj_spdlim_y_hi .eq     $9de8  {addr/40}  ;Y speed limit, high (hdr +$16)
                   obj_move_zc_lo  .eq     $9e10  {addr/40}  ;object movement vector, Z low
                   obj_move_zc_hi  .eq     $9e38  {addr/40}  ;object movement vector, Z high
                   obj_move_xc_lo  .eq     $9e60  {addr/40}  ;object movement vector, X low
                   obj_move_xc_hi  .eq     $9e88  {addr/40}  ;object movement vector, X high
                   obj_move_yc_lo  .eq     $9eb0  {addr/40}  ;object movement vector, Y low
                   obj_move_yc_hi  .eq     $9ed8  {addr/40}  ;object movement vector, Y high
                   KBD             .eq     $c000             ;R last key pressed + 128
                   KBDSTRB         .eq     $c010             ;RW keyboard strobe
                   SPKR            .eq     $c030             ;RW toggle speaker
                   TXTCLR          .eq     $c050             ;RW display graphics
                   MIXCLR          .eq     $c052             ;RW display full screen
                   TXTPAGE1        .eq     $c054             ;RW display page 1
                   TXTPAGE2        .eq     $c055             ;RW display page 2 (or read/write aux mem)
                   LORES           .eq     $c056             ;RW display lo-res graphics
                   HIRES           .eq     $c057             ;RW display hi-res graphics
                   BUTN0           .eq     $c061             ;R switch input 0 / open-apple
                   BUTN1           .eq     $c062             ;R switch input 1 / closed-apple
                   PADDL0          .eq     $c064             ;R analog input 0
                   PADDL1          .eq     $c065             ;R analog input 1
                   PTRIG           .eq     $c070             ;RW analog input reset
                   LCBANK2_RW      .eq     $c080             ;RW read RAM bank 2, write off
                   ROMIN           .eq     $c081             ;RWx2 read ROM, write RAM bank 2
                   MON_HOME        .eq     $fc58             ;clear screen and reset text output to top-left
                   MON_WAIT        .eq     $fca8             ;delay for (26 + 27*Acc + 5*(Acc*Acc))/2 cycles
                   MON_6502_RESET  .eq     $fffc  {addr/2}   ;6502 reset vector

                                   .org    $0800
                   ********************************************************************************
                   * Program entry point.                                                         *
                   ********************************************************************************
0800: 20 58 fc     Entry           jsr     MON_HOME          ;clear the screen
0803: a0 00                        ldy     #$00
0805: b9 13 08     :Loop           lda     :spaces,y
0808: 99 84 06                     sta     $0684,y           ;clear this part even harder
080b: c8                           iny
080c: c0 20                        cpy     #$20              ;copies opcode byte ($a0) from $832
080e: d0 f5                        bne     :Loop
0810: 4c c0 08                     jmp     Init1

0813: a0 a0 a0 a0+ :spaces         .str    “                               ”

                   ; 
                   ; Program initialization continued: memory relocation.
                   ; 
0832: a0 00        Init2           ldy     #$00              ;relocate $0900-0cff to $0000-03ff
0834: b9 00 09     :_Load1         lda     $0900,y
0837: 99 00 00     :_Store1        sta     $0000,y
083a: c8                           iny
083b: d0 f7                        bne     :_Load1
083d: ee 36 08                     inc     :_Load1+2
0840: ee 39 08                     inc     :_Store1+2
0843: ae 39 08                     ldx     :_Store1+2
0846: e0 04                        cpx     #$04
0848: d0 ea                        bne     :_Load1
084a: b9 00 93     :_Load2         lda     $9300,y           ;relocate $7300-93ff to $9f00-bfff
084d: 99 00 bf     :_Store2        sta     $bf00,y
0850: 88                           dey
0851: d0 f7                        bne     :_Load2
0853: ce 4c 08                     dec     :_Load2+2
0856: ce 4f 08                     dec     :_Store2+2
0859: ae 4f 08                     ldx     :_Store2+2
085c: e0 9e                        cpx     #$9e
085e: d0 ea                        bne     :_Load2
0860: b9 00 70     :_Load3         lda     $7000,y           ;relocate $7000-72ff to $9a00-9cff
0863: 99 00 9a     :_Store3        sta     $9a00,y
0866: c8                           iny
0867: d0 f7                        bne     :_Load3
0869: ee 62 08                     inc     :_Load3+2
086c: ee 65 08                     inc     :_Store3+2
086f: ae 65 08                     ldx     :_Store3+2
0872: e0 9d                        cpx     #$9d
0874: d0 ea                        bne     :_Load3
0876: b9 00 6f     :_Load4         lda     $6f00,y           ;relocate $3700-6fff to $5e00-96ff
0879: 99 00 96     :_Store4        sta     $9600,y
087c: 88                           dey
087d: d0 f7                        bne     :_Load4
087f: ce 78 08                     dec     :_Load4+2
0882: ce 7b 08                     dec     :_Store4+2
0885: ae 7b 08                     ldx     :_Store4+2
0888: e0 5d                        cpx     #$5d
088a: d0 ea                        bne     :_Load4
088c: b9 00 1c     :_Load5         lda     $1c00,y           ;relocate $1c00-36ff to $4000-5aff
088f: 99 00 40     :_Store5        sta     $4000,y
0892: c8                           iny
0893: d0 f7                        bne     :_Load5
0895: ee 8e 08                     inc     :_Load5+2
0898: ee 91 08                     inc     :_Store5+2
089b: ae 91 08                     ldx     :_Store5+2
089e: e0 5b                        cpx     #$5b
08a0: d0 ea                        bne     :_Load5
08a2: b9 00 1b     :_Load6         lda     $1b00,y           ;relocate $0d00-1bff to $0f00-1dff
08a5: 99 00 1d     :_Store6        sta     $1d00,y
08a8: 88                           dey
08a9: d0 f7                        bne     :_Load6
08ab: ce a4 08                     dec     :_Load6+2
08ae: ce a7 08                     dec     :_Store6+2
08b1: ae a7 08                     ldx     :_Store6+2
08b4: e0 0e                        cpx     #$0e
08b6: d0 ea                        bne     :_Load6
08b8: 4c 33 81                     jmp     Start             ;start game

08bb: 00 00 00 00+                 .junk   5

                   ; 
                   ; Program initialization continued: pause briefly then jump to next bit of code.
                   ; 
08c0: a9 ff        Init1           lda     #$ff              ;pause briefly (why?)
08c2: 20 a8 fc                     jsr     MON_WAIT
08c5: 20 a8 fc                     jsr     MON_WAIT
08c8: 20 a8 fc                     jsr     MON_WAIT
08cb: 20 a8 fc                     jsr     MON_WAIT
08ce: 20 a8 fc                     jsr     MON_WAIT
08d1: 4c 32 08                     jmp     Init2

08d4: 00 00 00 00+                 .align  $0100 (44 bytes)

                                   .org    $d000
                   ; 
                   ; Zero-page memory.  For disassembly purposes it was getting in the way when set
                   ; to address zero -- global EQUs and local variables are easier to work with
                   ; than data explicitly assembled to $0000.  I gave it an address of $d000 just
                   ; to get it out of the way.
                   ; 
                   ; Some values here are not set anywhere else, and MUST have the correct values
                   ; (e.g. the bit masks and the check at $7655).
                   ; 
                   ; $60-d1 are zeroed at the start of every game.
                   ; 
d000: 05 3b c0 84+ zero_page       .bulk   $05,$3b,$c0,$84,$00,$95,$14,$ff ;$00
d008: ff ff ff 20+                 .bulk   $ff,$ff,$ff,$20,$21,$00,$0f,$55
d010: 00 3b 00 ae+                 .bulk   $00,$3b,$00,$ae,$00,$14,$95,$47 ;$10
d018: 28 22 ff ff+                 .bulk   $28,$22,$ff,$ff,$ff,$ff,$ff,$ff
d020: 00 28 00 18+                 .bulk   $00,$28,$00,$18,$00,$01,$00,$09 ;$20
d028: 80 04 d0 60+                 .bulk   $80,$04,$d0,$60,$ff,$ff,$ff,$ff
d030: f7 00 ff aa+                 .bulk   $f7,$00,$ff,$aa,$02,$28,$a2,$25 ;$30
d038: a2 05 ff ff+                 .bulk   $a2,$05,$ff,$ff,$ff,$01,$00,$00
d040: 00 00 00 c0+                 .bulk   $00,$00,$00,$c0,$01,$08,$ff,$ff ;$40
d048: 00 ff ff ff+                 .bulk   $00,$ff,$ff,$ff,$ff,$ff,$75,$53
d050: f7 ff f7 ff+                 .bulk   $f7,$ff,$f7,$ff,$ff,$ff,$ff,$ff ;$50
d058: ff ff ff ff+                 .bulk   $ff,$ff,$ff,$ff,$ff,$ff,$ff,$ff
d060: 00 00 06 00+                 .bulk   $00,$00,$06,$00,$18,$00,$05,$00 ;$60
d068: 17 00 01 00+                 .bulk   $17,$00,$01,$00,$ef,$20,$26,$00
d070: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$07,$00,$00,$00 ;$70
d078: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$76,$00
d080: 65 00 63 00+                 .bulk   $65,$00,$63,$00,$27,$00,$05,$3b ;$80
d088: 1a 19 df 01+                 .bulk   $1a,$19,$df,$01,$06,$0e,$7a,$0c
d090: 00 00 d4 00+                 .bulk   $00,$00,$d4,$00,$00,$00,$00,$00 ;$90
d098: 86 00 00 d0+                 .bulk   $86,$00,$00,$d0,$00,$00,$d0,$00
d0a0: 00 00 f7 00+                 .bulk   $00,$00,$f7,$00,$00,$00,$00,$00 ;$a0
d0a8: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$8a
d0b0: fd 00 b7 06+                 .bulk   $fd,$00,$b7,$06,$00,$00,$00,$00 ;$b0
d0b8: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$ed,$02,$ae,$00
d0c0: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$90,$90,$00 ;$c0
d0c8: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00
d0d0: 00 00 0b 9c+                 .bulk   $00,$00,$0b,$9c,$00,$00,$80,$c0 ;$d0
d0d8: e0 f0 f8 fc+                 .bulk   $e0,$f0,$f8,$fc,$fe,$ff,$ff,$7f
d0e0: 3f 1f 0f 07+                 .bulk   $3f,$1f,$0f,$07,$03,$01,$00,$01 ;$e0
d0e8: 03 07 0f 1f+                 .bulk   $03,$07,$0f,$1f,$3f,$7f,$ff,$fe
d0f0: fc f8 f0 e0+                 .bulk   $fc,$f8,$f0,$e0,$c0,$80,$00,$00 ;$f0
d0f8: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$01

                                   .org    $0100
                   ; 
                   ; 6502 stack.
                   ; 
0100: dd ff df ff+ STACK           .junk   256
                   ; 
                   ; System input buffer.
                   ; 
0200: 93           INPUT_BUFFER    .dd1    $93               ;used by copy protection check?
0201: 90 8d bc b8+                 .align  $0100 (255 bytes)

                   ; 
                   ; Called when the reset key is hit.  Erases memory.
                   ; 
                   ]memptr         .var    $00    {addr/2}

0300: a0 00        Reset           ldy     #$00              ;start at $0c00
0302: 84 00                        sty     ]memptr
0304: a9 0c                        lda     #$0c
0306: 85 01                        sta     ]memptr+1
0308: a2 b4                        ldx     #$b4              ;continue until $bfff
030a: 98                           tya                       ;A-reg=0
030b: 91 00        :Loop           sta     (]memptr),y
030d: c8                           iny
030e: d0 fb                        bne     :Loop
0310: e6 01                        inc     ]memptr+1         ;advance pointer to next page
0312: ca                           dex                       ;count down the pages
0313: d0 f6                        bne     :Loop
                   ; Make a sound.
                   ]counter        .var    $00    {addr/1}

0315: a9 c0                        lda     #$c0
0317: 85 00                        sta     ]counter
0319: a0 c0        L0319           ldy     #$c0
031b: ad 30 c0     L031B           lda     SPKR              ;click
031e: a6 00                        ldx     ]counter
0320: ca           L0320           dex
0321: d0 fd                        bne     L0320
0323: 88                           dey
0324: d0 f5                        bne     L031B
0326: 46 00                        lsr     ]counter
0328: d0 ef                        bne     L0319
                   ; Reboot.
032a: a6 2b                        ldx     boot_slot         ;get boot slot (e.g. $60)
032c: ca                           dex                       ;decrement to get previous (e.g. $5F)
032d: 8a                           txa
032e: 4a                           lsr     A                 ;divide by 16 to get slot num - 1
032f: 4a                           lsr     A
0330: 4a                           lsr     A
0331: 4a                           lsr     A
0332: 09 c0                        ora     #$c0              ;push slot address - 1 (e.g. $c5ff)
0334: 48                           pha
0335: a9 ff                        lda     #$ff
0337: 48                           pha
0338: 60                           rts                       ;jump to it

0339: 00 00 00 00+                 .junk   185
03f2: 00 03        L03F2           .dd2    Reset             ;reset vector
03f4: a6           L03F4           .dd1    $a6               ;power-up byte
03f5: ff ff ff ff+                 .junk   11

                                   .org    $0f00
0f00: 00 00 00 00+                 .junk   83

0f53: a2 40        unref_0f53      ldx     #$40
0f55: bd 40 05     :Loop           lda     $0540,x
0f58: 9d 00 03                     sta     Reset,x
0f5b: ca                           dex
0f5c: 10 f7                        bpl     :Loop
0f5e: ad 81 c0                     lda     ROMIN             ;read ROM, write RAM
0f61: ad 81 c0                     lda     ROMIN
0f64: a9 00                        lda     #$00              ;point RAM reset vector at $0300
0f66: 8d f2 03                     sta     L03F2
0f69: 8d fc ff                     sta     MON_6502_RESET
0f6c: a9 03                        lda     #$03
0f6e: 8d f3 03                     sta     L03F2+1
0f71: 8d fd ff                     sta     MON_6502_RESET+1
0f74: 49 a5                        eor     #$a5
0f76: 8d f4 03                     sta     L03F4
0f79: ad 80 c0                     lda     LCBANK2_RW        ;read RAM (write disabled)
0f7c: 4c 33 81                     jmp     Start

0f7f: 00                           .junk   1
0f80: 00 00 00 00+ copyright_msg   .junk   40                ;holds "decrypted" copyright message
0fa8: 00                           .junk   1

                   ; 
                   ; Init a series of pages to a value.
                   ; 
                   ; On entry:
                   ;   A-reg: value to store
                   ;   X-reg: start page
                   ;   Y-reg: end page
                   ;   $10: page offset (expected to be zero)
                   ; 
                   • Clear variables
                   ]memptr         .var    $10    {addr/2}
                   ]end_page       .var    $86    {addr/1}

0fa9: 84 86        Memset          sty     ]end_page
0fab: 86 11                        stx     ]memptr+1
0fad: a0 00        :PageLoop       ldy     #$00
0faf: 91 10        :_Loop          sta     (]memptr),y
0fb1: c8                           iny
0fb2: d0 fb                        bne     :_Loop
0fb4: e6 11                        inc     ]memptr+1
0fb6: a4 11                        ldy     ]memptr+1
0fb8: c4 86                        cpy     ]end_page
0fba: d0 f1                        bne     :PageLoop
0fbc: a9 91                        lda     #INSTR_STA_DPIIY  ;set store instruction
0fbe: 8d af 0f                     sta     :_Loop            ;(this doesn't seem useful)
0fc1: 60                           rts

0fc2: 00 00 00 00+                 .junk   46

0ff0: 60           Return0ff0      rts

0ff1: 00 00 00                     .junk   3

0ff4: 60           Return0ff4      rts

0ff5: 00 00 00 00+                 .align  $0100 (11 bytes)
                   ; 
                   ; Math table #1, maps ? to ?.
                   ; 
                   ; 8 256-byte pages.
                   ; 
                   ; The index into this is generally extracted from math table #2 ($ac00).
1000: 01 01 01 01+ math_tab1_base? .bulk   $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$04
                                    +      $04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04
                                    +      $04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04
                                    +      $04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04
                                    +      $04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04
                                    +      $04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04
                                    +      $04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$05,$05,$05,$05
                                    +      $05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05
                                    +      $05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05
                                    +      $05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05
                                    +      $05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05
                                    +      $05,$05,$05,$05,$05,$05,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06
                                    +      $06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06
                                    +      $06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06
                                    +      $06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06
                                    +      $06,$06,$06,$06,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$08,$08,$08,$08,$08,$08,$08
                                    +      $08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08
                                    +      $08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08,$08
                                    +      $08,$08,$08,$08,$08,$08,$08,$09,$09,$09,$09,$09,$09,$09,$09,$09
                                    +      $09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09
                                    +      $09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09,$09
                                    +      $0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a
                                    +      $0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a,$0a
                                    +      $0a,$0a,$0a,$0a,$0a,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b
                                    +      $0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b,$0b
                                    +      $0b,$0b,$0b,$0b,$0b,$0b,$0b,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c
                                    +      $0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0c
                                    +      $0c,$0c,$0c,$0c,$0c,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d
                                    +      $0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d,$0d
                                    +      $0d,$0d,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e
                                    +      $0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0f,$0f,$0f,$0f
                                    +      $0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f,$0f
                                    +      $0f,$0f,$0f,$0f,$0f,$10,$10,$10,$10,$10,$10,$10,$10,$10,$10,$10
                                    +      $10,$10,$10,$10,$10,$10,$10,$10,$10,$10,$10,$10,$11,$11,$11,$11
                                    +      $11,$11,$11,$11,$11,$11,$11,$11,$11,$11,$11,$11,$11,$11,$11,$11
                                    +      $11,$11,$12,$12,$12,$12,$12,$12,$12,$12,$12,$12,$12,$12,$12,$12
                                    +      $12,$12,$12,$12,$12,$12,$13,$13,$13,$13,$13,$13,$13,$13,$13,$13
                                    +      $13,$13,$13,$13,$13,$13,$13,$13,$13,$13,$14,$14,$14,$14,$14,$14
                                    +      $14,$14,$14,$14,$14,$14,$14,$14,$14,$14,$14,$14,$15,$15,$15,$15
                                    +      $15,$15,$15,$15,$15,$15,$15,$15,$15,$15,$15,$15,$15,$15,$16,$16
                                    +      $16,$16,$16,$16,$16,$16,$16,$16,$16,$16,$16,$16,$16,$16,$17,$17
                                    +      $17,$17,$17,$17,$17,$17,$17,$17,$17,$17,$17,$17,$17,$17,$18,$18
                                    +      $18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$19,$19
                                    +      $19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$1a,$1a,$1a
                                    +      $1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1b,$1b,$1b,$1b,$1b
                                    +      $1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1c,$1c,$1c,$1c,$1c,$1c,$1c
                                    +      $1c,$1c,$1c,$1c,$1c,$1c,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d
                                    +      $1d,$1d,$1e,$1e,$1e,$1e,$1e,$1e,$1e,$1e,$1e,$1e,$1e,$1e,$1e,$1f
                                    +      $1f,$1f,$1f,$1f,$1f,$1f,$1f,$1f,$1f,$1f,$1f,$20,$20,$20,$20,$20
                                    +      $20,$20,$20,$20,$20,$20,$21,$21,$21,$21,$21,$21,$21,$21,$21,$21
                                    +      $21,$21,$22,$22,$22,$22,$22,$22,$22,$22,$22,$22,$23,$23,$23,$23
                                    +      $23,$23,$23,$23,$23,$23,$23,$24,$24,$24,$24,$24,$24,$24,$24,$24
                                    +      $24,$25,$25,$25,$25,$25,$25,$25,$25,$25,$25,$26,$26,$26,$26,$26
                                    +      $26,$26,$26,$26,$26,$27,$27,$27,$27,$27,$27,$27,$27,$27,$28,$28
                                    +      $28,$28,$28,$28,$28,$28,$28,$29,$29,$29,$29,$29,$29,$29,$29,$29
                                    +      $2a,$2a,$2a,$2a,$2a,$2a,$2a,$2a,$2a,$2b,$2b,$2b,$2b,$2b,$2b,$2b
                                    +      $2b,$2b,$2c,$2c,$2c,$2c,$2c,$2c,$2c,$2c,$2d,$2d,$2d,$2d,$2d,$2d
                                    +      $2d,$2d,$2d,$2e,$2e,$2e,$2e,$2e,$2e,$2e,$2f,$2f,$2f,$2f,$2f,$2f
                                    +      $2f,$2f,$30,$30,$30,$30,$30,$30,$30,$30,$31,$31,$31,$31,$31,$31
                                    +      $31,$31,$32,$32,$32,$32,$32,$32,$32,$33,$33,$33,$33,$33,$33,$33
                                    +      $34,$34,$34,$34,$34,$34,$34,$35,$35,$35,$35,$35,$35,$35,$36,$36
                                    +      $36,$36,$36,$36,$36,$37,$37,$37,$37,$37,$37,$37,$38,$38,$38,$38
                                    +      $38,$38,$39,$39,$39,$39,$39,$39,$39,$3a,$3a,$3a,$3a,$3a,$3a,$3b
                                    +      $3b,$3b,$3b,$3b,$3b,$3b,$3c,$3c,$3c,$3c,$3c,$3c,$3d,$3d,$3d,$3d
                                    +      $3d,$3d,$3e,$3e,$3e,$3e,$3e,$3e,$3f,$3f,$3f,$3f,$3f,$3f,$40,$40
                                    +      $40,$40,$40,$41,$41,$41,$41,$41,$41,$42,$42,$42,$42,$42,$42,$43
                                    +      $43,$43,$43,$43,$44,$44,$44,$44,$44,$44,$45,$45,$45,$45,$45,$46
                                    +      $46,$46,$46,$46,$47,$47,$47,$47,$47,$48,$48,$48,$48,$48,$48,$49
                                    +      $49,$49,$49,$49,$4a,$4a,$4a,$4a,$4a,$4b,$4b,$4b,$4b,$4c,$4c,$4c
                                    +      $4c,$4c,$4d,$4d,$4d,$4d,$4d,$4e,$4e,$4e,$4e,$4e,$4f,$4f,$4f,$4f
                                    +      $4f,$50,$50,$50,$50,$51,$51,$51,$51,$51,$52,$52,$52,$52,$53,$53
                                    +      $53,$53,$53,$54,$54,$54,$54,$55,$55,$55,$55,$56,$56,$56,$56,$56
                                    +      $57,$57,$57,$57,$58,$58,$58,$58,$59,$59,$59,$59,$5a,$5a,$5a,$5a
                                    +      $5a,$5b,$5b,$5b,$5b,$5c,$5c,$5c,$5c,$5d,$5d,$5d,$5e,$5e,$5e,$5e
                                    +      $5f,$5f,$5f,$5f,$60,$60,$60,$60,$61,$61,$61,$61,$62,$62,$62,$62
                                    +      $63,$63,$63,$63,$64,$64,$64,$65,$65,$65,$65,$66,$66,$66,$66,$67
                                    +      $67,$67,$68,$68,$68,$68,$69,$69,$69,$6a,$6a,$6a,$6a,$6b,$6b,$6b
                                    +      $6c,$6c,$6c,$6d,$6d,$6d,$6d,$6e,$6e,$6e,$6f,$6f,$6f,$6f,$70,$70
                                    +      $70,$71,$71,$71,$72,$72,$72,$73,$73,$73,$73,$74,$74,$74,$75,$75
                                    +      $75,$76,$76,$76,$77,$77,$77,$78,$78,$78,$79,$79,$79,$7a,$7a,$7a
                                    +      $7b,$7b,$7b,$7c,$7c,$7c,$7d,$7d,$7d,$7e,$7e,$7e,$7f,$7f,$7f,$80
                   math_tab1_lastpg?
1700: 80 80 81 81+                 .bulk   $80,$80,$81,$81,$81,$82,$82,$82,$83,$83,$84,$84,$84,$85,$85,$85
                                    +      $86,$86,$86,$87,$87,$87,$88,$88,$89,$89,$89,$8a,$8a,$8a,$8b,$8b
                                    +      $8c,$8c,$8c,$8d,$8d,$8d,$8e,$8e,$8f,$8f,$8f,$90,$90,$91,$91,$91
                                    +      $92,$92,$93,$93,$93,$94,$94,$95,$95,$95,$96,$96,$97,$97,$97,$98
                                    +      $98,$99,$99,$99,$9a,$9a,$9b,$9b,$9c,$9c,$9c,$9d,$9d,$9e,$9e,$9e
                                    +      $9f,$9f,$a0,$a0,$a1,$a1,$a2,$a2,$a2,$a3,$a3,$a4,$a4,$a5,$a5,$a6
                                    +      $a6,$a6,$a7,$a7,$a8,$a8,$a9,$a9,$aa,$aa,$ab,$ab,$ab,$ac,$ac,$ad
                                    +      $ad,$ae,$ae,$af,$af,$b0,$b0,$b1,$b1,$b2,$b2,$b3,$b3,$b3,$b4,$b5
                                    +      $b5,$b6,$b6,$b6,$b7,$b7,$b8,$b8,$b9,$b9,$ba,$ba,$bb,$bb,$bc,$bc
                                    +      $bd,$bd,$be,$bf,$bf,$c0,$c0,$c1,$c1,$c2,$c2,$c3,$c3,$c4,$c4,$c5
                                    +      $c5,$c6,$c6,$c7,$c8,$c8,$c9,$c9,$ca,$ca,$cb,$cb,$cc,$cc,$cd,$ce
                                    +      $ce,$cf,$cf,$d0,$d0,$d1,$d2,$d2,$d3,$d3,$d4,$d4,$d5,$d5,$d6,$d7
                                    +      $d7,$d8,$d8,$d9,$da,$da,$db,$db,$dc,$dd,$dd,$de,$de,$df,$e0,$e0
                                    +      $e1,$e1,$e2,$e3,$e3,$e4,$e4,$e5,$e6,$e6,$e7,$e8,$e8,$e9,$e9,$ea
                                    +      $eb,$eb,$ec,$ed,$ed,$ee,$ef,$ef,$f0,$f0,$f1,$f2,$f2,$f3,$f4,$f4
                                    +      $f5,$f6,$f6,$f7,$f8,$f8,$f9,$fa,$fb,$fb,$fc,$fc,$fd,$fe,$ff,$ff

                   ; 
                   ; Draws a vertical stripe.
                   ; 
                   ; This is generally not called directly, the primary exception being when
                   ; drawing the crosshairs.  A lookup table ($b700/b800) converts line numbers to
                   ; addresses, which are then used as an indirect jump (for the top) or as a
                   ; location to store an RTS (for the bottom).
                   ; 
                   ; On entry:
                   ;   X-reg: pixel byte value (adjusted for odd/even)
                   ;   Y-reg: horizontal offset (0-39)
                   ; 
1800: 8a           UnrolledORA     txa
1801: 19 00 20                     ora     HIRES_P1,y
1804: 99 00 20                     sta     HIRES_P1,y
1807: 8a                           txa
1808: 19 00 24                     ora     HIRES_P1+$400,y
180b: 99 00 24                     sta     HIRES_P1+$400,y
180e: 8a                           txa
180f: 19 00 28                     ora     HIRES_P1+$800,y
1812: 99 00 28                     sta     HIRES_P1+$800,y
1815: 8a                           txa
1816: 19 00 2c                     ora     HIRES_P1+$c00,y
1819: 99 00 2c                     sta     HIRES_P1+$c00,y
181c: 8a                           txa
181d: 19 00 30                     ora     HIRES_P1+$1000,y
1820: 99 00 30                     sta     HIRES_P1+$1000,y
1823: 8a                           txa
1824: 19 00 34                     ora     HIRES_P1+$1400,y
1827: 99 00 34                     sta     HIRES_P1+$1400,y
182a: 8a                           txa
182b: 19 00 38                     ora     HIRES_P1+$1800,y
182e: 99 00 38                     sta     HIRES_P1+$1800,y
1831: 8a                           txa
1832: 19 00 3c                     ora     HIRES_P1+$1c00,y
1835: 99 00 3c                     sta     HIRES_P1+$1c00,y
1838: 8a                           txa
1839: 19 80 20                     ora     HIRES_P1+128,y
183c: 99 80 20                     sta     HIRES_P1+128,y
183f: 8a                           txa
1840: 19 80 24                     ora     HIRES_P1+$480,y
1843: 99 80 24                     sta     HIRES_P1+$480,y
1846: 8a                           txa
1847: 19 80 28                     ora     HIRES_P1+$880,y
184a: 99 80 28                     sta     HIRES_P1+$880,y
184d: 8a                           txa
184e: 19 80 2c                     ora     HIRES_P1+$c80,y
1851: 99 80 2c                     sta     HIRES_P1+$c80,y
1854: 8a                           txa
1855: 19 80 30                     ora     HIRES_P1+$1080,y
1858: 99 80 30                     sta     HIRES_P1+$1080,y
185b: 8a                           txa
185c: 19 80 34                     ora     HIRES_P1+$1480,y
185f: 99 80 34                     sta     HIRES_P1+$1480,y
1862: 8a                           txa
1863: 19 80 38                     ora     HIRES_P1+$1880,y
1866: 99 80 38                     sta     HIRES_P1+$1880,y
1869: 8a                           txa
186a: 19 80 3c                     ora     HIRES_P1+$1c80,y
186d: 99 80 3c                     sta     HIRES_P1+$1c80,y
1870: 8a                           txa
1871: 19 00 21                     ora     HIRES_P1+$100,y
1874: 99 00 21                     sta     HIRES_P1+$100,y
1877: 8a                           txa
1878: 19 00 25                     ora     HIRES_P1+$500,y
187b: 99 00 25                     sta     HIRES_P1+$500,y
187e: 8a                           txa
187f: 19 00 29                     ora     HIRES_P1+$900,y
1882: 99 00 29                     sta     HIRES_P1+$900,y
1885: 8a                           txa
1886: 19 00 2d                     ora     HIRES_P1+$d00,y
1889: 99 00 2d                     sta     HIRES_P1+$d00,y
188c: 8a                           txa
188d: 19 00 31                     ora     HIRES_P1+$1100,y
1890: 99 00 31                     sta     HIRES_P1+$1100,y
1893: 8a                           txa
1894: 19 00 35                     ora     HIRES_P1+$1500,y
1897: 99 00 35                     sta     HIRES_P1+$1500,y
189a: 8a                           txa
189b: 19 00 39                     ora     HIRES_P1+$1900,y
189e: 99 00 39                     sta     HIRES_P1+$1900,y
18a1: 8a                           txa
18a2: 19 00 3d                     ora     HIRES_P1+$1d00,y
18a5: 99 00 3d                     sta     HIRES_P1+$1d00,y
18a8: 8a                           txa
18a9: 19 80 21                     ora     HIRES_P1+$180,y
18ac: 99 80 21                     sta     HIRES_P1+$180,y
18af: 8a                           txa
18b0: 19 80 25                     ora     HIRES_P1+$580,y
18b3: 99 80 25                     sta     HIRES_P1+$580,y
18b6: 8a                           txa
18b7: 19 80 29                     ora     HIRES_P1+$980,y
18ba: 99 80 29                     sta     HIRES_P1+$980,y
18bd: 8a                           txa
18be: 19 80 2d                     ora     HIRES_P1+$d80,y
18c1: 99 80 2d                     sta     HIRES_P1+$d80,y
18c4: 8a                           txa
18c5: 19 80 31                     ora     HIRES_P1+$1180,y
18c8: 99 80 31                     sta     HIRES_P1+$1180,y
18cb: 8a                           txa
18cc: 19 80 35                     ora     HIRES_P1+$1580,y
18cf: 99 80 35                     sta     HIRES_P1+$1580,y
18d2: 8a                           txa
18d3: 19 80 39                     ora     HIRES_P1+$1980,y
18d6: 99 80 39                     sta     HIRES_P1+$1980,y
18d9: 8a                           txa
18da: 19 80 3d                     ora     HIRES_P1+$1d80,y
18dd: 99 80 3d                     sta     HIRES_P1+$1d80,y
18e0: 8a                           txa
18e1: 19 00 22                     ora     HIRES_P1+$200,y
18e4: 99 00 22                     sta     HIRES_P1+$200,y
18e7: 8a                           txa
18e8: 19 00 26                     ora     HIRES_P1+$600,y
18eb: 99 00 26                     sta     HIRES_P1+$600,y
18ee: 8a                           txa
18ef: 19 00 2a                     ora     HIRES_P1+$a00,y
18f2: 99 00 2a                     sta     HIRES_P1+$a00,y
18f5: 8a                           txa
18f6: 19 00 2e                     ora     HIRES_P1+$e00,y
18f9: 99 00 2e                     sta     HIRES_P1+$e00,y
18fc: 8a                           txa
18fd: 19 00 32                     ora     HIRES_P1+$1200,y
1900: 99 00 32                     sta     HIRES_P1+$1200,y
1903: 8a                           txa
1904: 19 00 36                     ora     HIRES_P1+$1600,y
1907: 99 00 36                     sta     HIRES_P1+$1600,y
190a: 8a                           txa
190b: 19 00 3a                     ora     HIRES_P1+$1a00,y
190e: 99 00 3a                     sta     HIRES_P1+$1a00,y
1911: 8a                           txa
1912: 19 00 3e                     ora     HIRES_P1+$1e00,y
1915: 99 00 3e                     sta     HIRES_P1+$1e00,y
1918: 8a                           txa
1919: 19 80 22                     ora     HIRES_P1+$280,y
191c: 99 80 22                     sta     HIRES_P1+$280,y
191f: 8a                           txa
1920: 19 80 26                     ora     HIRES_P1+$680,y
1923: 99 80 26                     sta     HIRES_P1+$680,y
1926: 8a                           txa
1927: 19 80 2a                     ora     HIRES_P1+$a80,y
192a: 99 80 2a                     sta     HIRES_P1+$a80,y
192d: 8a                           txa
192e: 19 80 2e                     ora     HIRES_P1+$e80,y
1931: 99 80 2e                     sta     HIRES_P1+$e80,y
1934: 8a                           txa
1935: 19 80 32                     ora     HIRES_P1+$1280,y
1938: 99 80 32                     sta     HIRES_P1+$1280,y
193b: 8a                           txa
193c: 19 80 36                     ora     HIRES_P1+$1680,y
193f: 99 80 36                     sta     HIRES_P1+$1680,y
1942: 8a                           txa
1943: 19 80 3a                     ora     HIRES_P1+$1a80,y
1946: 99 80 3a                     sta     HIRES_P1+$1a80,y
1949: 8a                           txa
194a: 19 80 3e                     ora     HIRES_P1+$1e80,y
194d: 99 80 3e                     sta     HIRES_P1+$1e80,y
1950: 8a                           txa
1951: 19 00 23                     ora     HIRES_P1+$300,y
1954: 99 00 23                     sta     HIRES_P1+$300,y
1957: 8a                           txa
1958: 19 00 27                     ora     HIRES_P1+$700,y
195b: 99 00 27                     sta     HIRES_P1+$700,y
195e: 8a                           txa
195f: 19 00 2b                     ora     HIRES_P1+$b00,y
1962: 99 00 2b                     sta     HIRES_P1+$b00,y
1965: 8a                           txa
1966: 19 00 2f                     ora     HIRES_P1+$f00,y
1969: 99 00 2f                     sta     HIRES_P1+$f00,y
196c: 8a                           txa
196d: 19 00 33                     ora     HIRES_P1+$1300,y
1970: 99 00 33                     sta     HIRES_P1+$1300,y
1973: 8a                           txa
1974: 19 00 37                     ora     HIRES_P1+$1700,y
1977: 99 00 37                     sta     HIRES_P1+$1700,y
197a: 8a                           txa
197b: 19 00 3b                     ora     HIRES_P1+$1b00,y
197e: 99 00 3b                     sta     HIRES_P1+$1b00,y
1981: 8a                           txa
1982: 19 00 3f                     ora     HIRES_P1+$1f00,y
1985: 99 00 3f                     sta     HIRES_P1+$1f00,y
1988: 8a                           txa
1989: 19 80 23                     ora     HIRES_P1+$380,y
198c: 99 80 23                     sta     HIRES_P1+$380,y
198f: 8a                           txa
1990: 19 80 27                     ora     HIRES_P1+$780,y
1993: 99 80 27                     sta     HIRES_P1+$780,y
1996: 8a                           txa
1997: 19 80 2b                     ora     HIRES_P1+$b80,y
199a: 99 80 2b                     sta     HIRES_P1+$b80,y
199d: 8a                           txa
199e: 19 80 2f                     ora     HIRES_P1+$f80,y
19a1: 99 80 2f                     sta     HIRES_P1+$f80,y
19a4: 8a                           txa
19a5: 19 80 33                     ora     HIRES_P1+$1380,y
19a8: 99 80 33                     sta     HIRES_P1+$1380,y
19ab: 8a                           txa
19ac: 19 80 37                     ora     HIRES_P1+$1780,y
19af: 99 80 37                     sta     HIRES_P1+$1780,y
19b2: 8a                           txa
19b3: 19 80 3b                     ora     HIRES_P1+$1b80,y
19b6: 99 80 3b                     sta     HIRES_P1+$1b80,y
19b9: 8a                           txa
19ba: 19 80 3f                     ora     HIRES_P1+$1f80,y
19bd: 99 80 3f                     sta     HIRES_P1+$1f80,y
19c0: 8a                           txa
19c1: 19 28 20                     ora     HIRES_P1+40,y
19c4: 99 28 20                     sta     HIRES_P1+40,y
19c7: 8a                           txa
19c8: 19 28 24                     ora     HIRES_P1+$428,y
19cb: 99 28 24                     sta     HIRES_P1+$428,y
19ce: 8a                           txa
19cf: 19 28 28                     ora     HIRES_P1+$828,y
19d2: 99 28 28                     sta     HIRES_P1+$828,y
19d5: 8a                           txa
19d6: 19 28 2c                     ora     HIRES_P1+$c28,y
19d9: 99 28 2c                     sta     HIRES_P1+$c28,y
19dc: 8a                           txa
19dd: 19 28 30                     ora     HIRES_P1+$1028,y
19e0: 99 28 30                     sta     HIRES_P1+$1028,y
19e3: 8a                           txa
19e4: 19 28 34                     ora     HIRES_P1+$1428,y
19e7: 99 28 34                     sta     HIRES_P1+$1428,y
19ea: 8a                           txa
19eb: 19 28 38                     ora     HIRES_P1+$1828,y
19ee: 99 28 38                     sta     HIRES_P1+$1828,y
19f1: 8a                           txa
19f2: 19 28 3c                     ora     HIRES_P1+$1c28,y
19f5: 99 28 3c                     sta     HIRES_P1+$1c28,y
19f8: 8a                           txa
19f9: 19 a8 20                     ora     HIRES_P1+168,y
19fc: 99 a8 20                     sta     HIRES_P1+168,y
19ff: 8a                           txa
1a00: 19 a8 24                     ora     HIRES_P1+$4a8,y
1a03: 99 a8 24                     sta     HIRES_P1+$4a8,y
1a06: 8a                           txa
1a07: 19 a8 28                     ora     HIRES_P1+$8a8,y
1a0a: 99 a8 28                     sta     HIRES_P1+$8a8,y
1a0d: 8a                           txa
1a0e: 19 a8 2c                     ora     HIRES_P1+$ca8,y
1a11: 99 a8 2c                     sta     HIRES_P1+$ca8,y
1a14: 8a                           txa
1a15: 19 a8 30                     ora     HIRES_P1+$10a8,y
1a18: 99 a8 30                     sta     HIRES_P1+$10a8,y
1a1b: 8a                           txa
1a1c: 19 a8 34                     ora     HIRES_P1+$14a8,y
1a1f: 99 a8 34                     sta     HIRES_P1+$14a8,y
1a22: 8a                           txa
1a23: 19 a8 38                     ora     HIRES_P1+$18a8,y
1a26: 99 a8 38                     sta     HIRES_P1+$18a8,y
1a29: 8a                           txa
1a2a: 19 a8 3c                     ora     HIRES_P1+$1ca8,y
1a2d: 99 a8 3c                     sta     HIRES_P1+$1ca8,y
1a30: 8a                           txa
1a31: 19 28 21                     ora     HIRES_P1+$128,y
1a34: 99 28 21                     sta     HIRES_P1+$128,y
1a37: 8a                           txa
1a38: 19 28 25                     ora     HIRES_P1+$528,y
1a3b: 99 28 25                     sta     HIRES_P1+$528,y
1a3e: 8a                           txa
1a3f: 19 28 29                     ora     HIRES_P1+$928,y
1a42: 99 28 29                     sta     HIRES_P1+$928,y
1a45: 8a                           txa
1a46: 19 28 2d                     ora     HIRES_P1+$d28,y
1a49: 99 28 2d                     sta     HIRES_P1+$d28,y
1a4c: 8a                           txa
1a4d: 19 28 31                     ora     HIRES_P1+$1128,y
1a50: 99 28 31                     sta     HIRES_P1+$1128,y
1a53: 8a           OraSeq_85       txa
1a54: 19 28 35                     ora     HIRES_P1+$1528,y  ;line 85
1a57: 99 28 35                     sta     HIRES_P1+$1528,y
1a5a: 8a           OraSeq_86       txa
1a5b: 19 28 39                     ora     HIRES_P1+$1928,y  ;line 86
1a5e: 99 28 39                     sta     HIRES_P1+$1928,y
1a61: 8a                           txa
1a62: 19 28 3d                     ora     HIRES_P1+$1d28,y
1a65: 99 28 3d                     sta     HIRES_P1+$1d28,y
1a68: 8a                           txa
1a69: 19 a8 21                     ora     HIRES_P1+$1a8,y
1a6c: 99 a8 21                     sta     HIRES_P1+$1a8,y
1a6f: 8a           OraSeq_89       txa
1a70: 19 a8 25                     ora     HIRES_P1+$5a8,y   ;line 89
1a73: 99 a8 25                     sta     HIRES_P1+$5a8,y
1a76: 8a                           txa
1a77: 19 a8 29                     ora     HIRES_P1+$9a8,y
1a7a: 99 a8 29                     sta     HIRES_P1+$9a8,y
1a7d: 8a                           txa
1a7e: 19 a8 2d                     ora     HIRES_P1+$da8,y
1a81: 99 a8 2d                     sta     HIRES_P1+$da8,y
1a84: 8a                           txa
1a85: 19 a8 31                     ora     HIRES_P1+$11a8,y
1a88: 99 a8 31                     sta     HIRES_P1+$11a8,y
1a8b: 8a           OraSeq_93       txa
1a8c: 19 a8 35                     ora     HIRES_P1+$15a8,y
1a8f: 99 a8 35                     sta     HIRES_P1+$15a8,y
1a92: 8a                           txa
1a93: 19 a8 39                     ora     HIRES_P1+$19a8,y
1a96: 99 a8 39                     sta     HIRES_P1+$19a8,y
1a99: 8a                           txa
1a9a: 19 a8 3d                     ora     HIRES_P1+$1da8,y
1a9d: 99 a8 3d                     sta     HIRES_P1+$1da8,y
1aa0: 8a                           txa
1aa1: 19 28 22                     ora     HIRES_P1+$228,y
1aa4: 99 28 22                     sta     HIRES_P1+$228,y
1aa7: 8a                           txa
1aa8: 19 28 26                     ora     HIRES_P1+$628,y
1aab: 99 28 26                     sta     HIRES_P1+$628,y
1aae: 8a                           txa
1aaf: 19 28 2a                     ora     HIRES_P1+$a28,y
1ab2: 99 28 2a                     sta     HIRES_P1+$a28,y
1ab5: 8a                           txa
1ab6: 19 28 2e                     ora     HIRES_P1+$e28,y
1ab9: 99 28 2e                     sta     HIRES_P1+$e28,y
1abc: 8a           OraSeq_100      txa
1abd: 19 28 32                     ora     HIRES_P1+$1228,y  ;line 100
1ac0: 99 28 32                     sta     HIRES_P1+$1228,y
1ac3: 8a                           txa
1ac4: 19 28 36                     ora     HIRES_P1+$1628,y
1ac7: 99 28 36                     sta     HIRES_P1+$1628,y
1aca: 8a                           txa
1acb: 19 28 3a                     ora     HIRES_P1+$1a28,y
1ace: 99 28 3a                     sta     HIRES_P1+$1a28,y
1ad1: 8a                           txa
1ad2: 19 28 3e                     ora     HIRES_P1+$1e28,y
1ad5: 99 28 3e                     sta     HIRES_P1+$1e28,y
1ad8: 8a                           txa
1ad9: 19 a8 22                     ora     HIRES_P1+$2a8,y
1adc: 99 a8 22                     sta     HIRES_P1+$2a8,y
1adf: 8a                           txa
1ae0: 19 a8 26                     ora     HIRES_P1+$6a8,y
1ae3: 99 a8 26                     sta     HIRES_P1+$6a8,y
1ae6: 8a                           txa
1ae7: 19 a8 2a                     ora     HIRES_P1+$aa8,y
1aea: 99 a8 2a                     sta     HIRES_P1+$aa8,y
1aed: 8a                           txa
1aee: 19 a8 2e                     ora     HIRES_P1+$ea8,y
1af1: 99 a8 2e                     sta     HIRES_P1+$ea8,y
1af4: 8a           OraSeq_108      txa
1af5: 19 a8 32                     ora     HIRES_P1+$12a8,y
1af8: 99 a8 32                     sta     HIRES_P1+$12a8,y
1afb: 8a                           txa
1afc: 19 a8 36                     ora     HIRES_P1+$16a8,y
1aff: 99 a8 36                     sta     HIRES_P1+$16a8,y
1b02: 8a                           txa
1b03: 19 a8 3a                     ora     HIRES_P1+$1aa8,y
1b06: 99 a8 3a                     sta     HIRES_P1+$1aa8,y
1b09: 8a                           txa
1b0a: 19 a8 3e                     ora     HIRES_P1+$1ea8,y
1b0d: 99 a8 3e                     sta     HIRES_P1+$1ea8,y
1b10: 8a                           txa
1b11: 19 28 23                     ora     HIRES_P1+$328,y
1b14: 99 28 23                     sta     HIRES_P1+$328,y
1b17: 8a                           txa
1b18: 19 28 27                     ora     HIRES_P1+$728,y
1b1b: 99 28 27                     sta     HIRES_P1+$728,y
1b1e: 8a                           txa
1b1f: 19 28 2b                     ora     HIRES_P1+$b28,y
1b22: 99 28 2b                     sta     HIRES_P1+$b28,y
1b25: 8a                           txa
1b26: 19 28 2f                     ora     HIRES_P1+$f28,y
1b29: 99 28 2f                     sta     HIRES_P1+$f28,y
1b2c: 8a                           txa
1b2d: 19 28 33                     ora     HIRES_P1+$1328,y
1b30: 99 28 33                     sta     HIRES_P1+$1328,y
1b33: 8a                           txa
1b34: 19 28 37                     ora     HIRES_P1+$1728,y
1b37: 99 28 37                     sta     HIRES_P1+$1728,y
1b3a: 8a                           txa
1b3b: 19 28 3b                     ora     HIRES_P1+$1b28,y
1b3e: 99 28 3b                     sta     HIRES_P1+$1b28,y
1b41: 8a                           txa
1b42: 19 28 3f                     ora     HIRES_P1+$1f28,y
1b45: 99 28 3f                     sta     HIRES_P1+$1f28,y
1b48: 8a                           txa
1b49: 19 a8 23                     ora     HIRES_P1+$3a8,y
1b4c: 99 a8 23                     sta     HIRES_P1+$3a8,y
1b4f: 8a                           txa
1b50: 19 a8 27                     ora     HIRES_P1+$7a8,y
1b53: 99 a8 27                     sta     HIRES_P1+$7a8,y
1b56: 8a                           txa
1b57: 19 a8 2b                     ora     HIRES_P1+$ba8,y
1b5a: 99 a8 2b                     sta     HIRES_P1+$ba8,y
1b5d: 8a                           txa
1b5e: 19 a8 2f                     ora     HIRES_P1+$fa8,y
1b61: 99 a8 2f                     sta     HIRES_P1+$fa8,y
1b64: 8a                           txa
1b65: 19 a8 33                     ora     HIRES_P1+$13a8,y
1b68: 99 a8 33                     sta     HIRES_P1+$13a8,y
1b6b: 8a                           txa
1b6c: 19 a8 37                     ora     HIRES_P1+$17a8,y
1b6f: 99 a8 37                     sta     HIRES_P1+$17a8,y
1b72: 8a                           txa
1b73: 19 a8 3b                     ora     HIRES_P1+$1ba8,y
1b76: 99 a8 3b                     sta     HIRES_P1+$1ba8,y
1b79: 8a                           txa
1b7a: 19 a8 3f                     ora     HIRES_P1+$1fa8,y
1b7d: 99 a8 3f                     sta     HIRES_P1+$1fa8,y
1b80: 8a                           txa
1b81: 19 50 20                     ora     HIRES_P1+80,y
1b84: 99 50 20                     sta     HIRES_P1+80,y
1b87: 8a                           txa
1b88: 19 50 24                     ora     HIRES_P1+$450,y
1b8b: 99 50 24                     sta     HIRES_P1+$450,y
1b8e: 8a                           txa
1b8f: 19 50 28                     ora     HIRES_P1+$850,y
1b92: 99 50 28                     sta     HIRES_P1+$850,y
1b95: 8a                           txa
1b96: 19 50 2c                     ora     HIRES_P1+$c50,y
1b99: 99 50 2c                     sta     HIRES_P1+$c50,y
1b9c: 8a                           txa
1b9d: 19 50 30                     ora     HIRES_P1+$1050,y
1ba0: 99 50 30                     sta     HIRES_P1+$1050,y
1ba3: 8a                           txa
1ba4: 19 50 34                     ora     HIRES_P1+$1450,y
1ba7: 99 50 34                     sta     HIRES_P1+$1450,y
1baa: 8a                           txa
1bab: 19 50 38                     ora     HIRES_P1+$1850,y
1bae: 99 50 38                     sta     HIRES_P1+$1850,y
1bb1: 8a                           txa
1bb2: 19 50 3c                     ora     HIRES_P1+$1c50,y
1bb5: 99 50 3c                     sta     HIRES_P1+$1c50,y
1bb8: 8a                           txa
1bb9: 19 d0 20                     ora     HIRES_P1+208,y
1bbc: 99 d0 20                     sta     HIRES_P1+208,y
1bbf: 8a                           txa
1bc0: 19 d0 24                     ora     HIRES_P1+$4d0,y
1bc3: 99 d0 24                     sta     HIRES_P1+$4d0,y
1bc6: 8a                           txa
1bc7: 19 d0 28                     ora     HIRES_P1+$8d0,y
1bca: 99 d0 28                     sta     HIRES_P1+$8d0,y
1bcd: 8a                           txa
1bce: 19 d0 2c                     ora     HIRES_P1+$cd0,y
1bd1: 99 d0 2c                     sta     HIRES_P1+$cd0,y
1bd4: 8a                           txa
1bd5: 19 d0 30                     ora     HIRES_P1+$10d0,y
1bd8: 99 d0 30                     sta     HIRES_P1+$10d0,y
1bdb: 8a                           txa
1bdc: 19 d0 34                     ora     HIRES_P1+$14d0,y
1bdf: 99 d0 34                     sta     HIRES_P1+$14d0,y
1be2: 8a                           txa
1be3: 19 d0 38                     ora     HIRES_P1+$18d0,y
1be6: 99 d0 38                     sta     HIRES_P1+$18d0,y
1be9: 8a                           txa
1bea: 19 d0 3c                     ora     HIRES_P1+$1cd0,y
1bed: 99 d0 3c                     sta     HIRES_P1+$1cd0,y
1bf0: 8a                           txa
1bf1: 19 50 21                     ora     HIRES_P1+$150,y
1bf4: 99 50 21                     sta     HIRES_P1+$150,y
1bf7: 8a                           txa
1bf8: 19 50 25                     ora     HIRES_P1+$550,y
1bfb: 99 50 25                     sta     HIRES_P1+$550,y
1bfe: 8a                           txa
1bff: 19 50 29                     ora     HIRES_P1+$950,y
1c02: 99 50 29                     sta     HIRES_P1+$950,y
1c05: 8a                           txa
1c06: 19 50 2d                     ora     HIRES_P1+$d50,y
1c09: 99 50 2d                     sta     HIRES_P1+$d50,y
1c0c: 8a                           txa
1c0d: 19 50 31                     ora     HIRES_P1+$1150,y
1c10: 99 50 31                     sta     HIRES_P1+$1150,y
1c13: 8a                           txa
1c14: 19 50 35                     ora     HIRES_P1+$1550,y
1c17: 99 50 35                     sta     HIRES_P1+$1550,y
1c1a: 8a                           txa
1c1b: 19 50 39                     ora     HIRES_P1+$1950,y
1c1e: 99 50 39                     sta     HIRES_P1+$1950,y
1c21: 8a                           txa
1c22: 19 50 3d                     ora     HIRES_P1+$1d50,y
1c25: 99 50 3d                     sta     HIRES_P1+$1d50,y
1c28: 8a                           txa
1c29: 19 d0 21                     ora     HIRES_P1+$1d0,y
1c2c: 99 d0 21                     sta     HIRES_P1+$1d0,y
1c2f: 8a                           txa
1c30: 19 d0 25                     ora     HIRES_P1+$5d0,y
1c33: 99 d0 25                     sta     HIRES_P1+$5d0,y
1c36: 8a                           txa
1c37: 19 d0 29                     ora     HIRES_P1+$9d0,y
1c3a: 99 d0 29                     sta     HIRES_P1+$9d0,y
1c3d: 8a                           txa
1c3e: 19 d0 2d                     ora     HIRES_P1+$dd0,y
1c41: 99 d0 2d                     sta     HIRES_P1+$dd0,y
1c44: 8a                           txa
1c45: 19 d0 31                     ora     HIRES_P1+$11d0,y
1c48: 99 d0 31                     sta     HIRES_P1+$11d0,y
1c4b: 8a                           txa
1c4c: 19 d0 35                     ora     HIRES_P1+$15d0,y
1c4f: 99 d0 35                     sta     HIRES_P1+$15d0,y
1c52: 8a                           txa
1c53: 19 d0 39                     ora     HIRES_P1+$19d0,y
1c56: 99 d0 39                     sta     HIRES_P1+$19d0,y
1c59: 8a                           txa
1c5a: 19 d0 3d                     ora     HIRES_P1+$1dd0,y
1c5d: 99 d0 3d                     sta     HIRES_P1+$1dd0,y
1c60: 8a                           txa
1c61: 19 50 22                     ora     HIRES_P1+$250,y
1c64: 99 50 22                     sta     HIRES_P1+$250,y
1c67: 8a                           txa
1c68: 19 50 26                     ora     HIRES_P1+$650,y
1c6b: 99 50 26                     sta     HIRES_P1+$650,y
1c6e: 8a                           txa
1c6f: 19 50 2a                     ora     HIRES_P1+$a50,y
1c72: 99 50 2a                     sta     HIRES_P1+$a50,y
1c75: 8a                           txa
1c76: 19 50 2e                     ora     HIRES_P1+$e50,y
1c79: 99 50 2e                     sta     HIRES_P1+$e50,y
1c7c: 8a                           txa
1c7d: 19 50 32                     ora     HIRES_P1+$1250,y
1c80: 99 50 32                     sta     HIRES_P1+$1250,y
1c83: 8a                           txa
1c84: 19 50 36                     ora     HIRES_P1+$1650,y
1c87: 99 50 36                     sta     HIRES_P1+$1650,y
1c8a: 8a                           txa
1c8b: 19 50 3a                     ora     HIRES_P1+$1a50,y
1c8e: 99 50 3a                     sta     HIRES_P1+$1a50,y
1c91: 8a                           txa
1c92: 19 50 3e                     ora     HIRES_P1+$1e50,y
1c95: 99 50 3e                     sta     HIRES_P1+$1e50,y
1c98: 8a                           txa
1c99: 19 d0 22                     ora     HIRES_P1+$2d0,y
1c9c: 99 d0 22                     sta     HIRES_P1+$2d0,y
1c9f: 8a                           txa
1ca0: 19 d0 26                     ora     HIRES_P1+$6d0,y
1ca3: 99 d0 26                     sta     HIRES_P1+$6d0,y
1ca6: 8a                           txa
1ca7: 19 d0 2a                     ora     HIRES_P1+$ad0,y
1caa: 99 d0 2a                     sta     HIRES_P1+$ad0,y
1cad: 8a                           txa
1cae: 19 d0 2e                     ora     HIRES_P1+$ed0,y
1cb1: 99 d0 2e                     sta     HIRES_P1+$ed0,y
1cb4: 8a                           txa
1cb5: 19 d0 32                     ora     HIRES_P1+$12d0,y
1cb8: 99 d0 32                     sta     HIRES_P1+$12d0,y
1cbb: 8a                           txa
1cbc: 19 d0 36                     ora     HIRES_P1+$16d0,y
1cbf: 99 d0 36                     sta     HIRES_P1+$16d0,y
1cc2: 8a                           txa
1cc3: 19 d0 3a                     ora     HIRES_P1+$1ad0,y
1cc6: 99 d0 3a                     sta     HIRES_P1+$1ad0,y
1cc9: 8a                           txa
1cca: 19 d0 3e                     ora     HIRES_P1+$1ed0,y
1ccd: 99 d0 3e                     sta     HIRES_P1+$1ed0,y
1cd0: 8a                           txa
1cd1: 19 50 23                     ora     HIRES_P1+$350,y
1cd4: 99 50 23                     sta     HIRES_P1+$350,y
1cd7: 8a                           txa
1cd8: 19 50 27                     ora     HIRES_P1+$750,y
1cdb: 99 50 27                     sta     HIRES_P1+$750,y
1cde: 8a                           txa
1cdf: 19 50 2b                     ora     HIRES_P1+$b50,y
1ce2: 99 50 2b                     sta     HIRES_P1+$b50,y
1ce5: 8a                           txa
1ce6: 19 50 2f                     ora     HIRES_P1+$f50,y
1ce9: 99 50 2f                     sta     HIRES_P1+$f50,y
1cec: 8a                           txa
1ced: 19 50 33                     ora     HIRES_P1+$1350,y
1cf0: 99 50 33                     sta     HIRES_P1+$1350,y
1cf3: 8a                           txa
1cf4: 19 50 37                     ora     HIRES_P1+$1750,y
1cf7: 99 50 37                     sta     HIRES_P1+$1750,y
1cfa: 8a                           txa
1cfb: 19 50 3b                     ora     HIRES_P1+$1b50,y
1cfe: 99 50 3b                     sta     HIRES_P1+$1b50,y
1d01: 8a                           txa
1d02: 19 50 3f                     ora     HIRES_P1+$1f50,y
1d05: 99 50 3f                     sta     HIRES_P1+$1f50,y
1d08: 8a                           txa
1d09: 19 d0 23                     ora     HIRES_P1+$3d0,y
1d0c: 99 d0 23                     sta     HIRES_P1+$3d0,y
1d0f: 8a                           txa
1d10: 19 d0 27                     ora     HIRES_P1+$7d0,y
1d13: 99 d0 27                     sta     HIRES_P1+$7d0,y
1d16: 8a                           txa
1d17: 19 d0 2b                     ora     HIRES_P1+$bd0,y
1d1a: 99 d0 2b                     sta     HIRES_P1+$bd0,y
1d1d: 8a                           txa
1d1e: 19 d0 2f                     ora     HIRES_P1+$fd0,y
1d21: 99 d0 2f                     sta     HIRES_P1+$fd0,y
1d24: 8a                           txa
1d25: 19 d0 33                     ora     HIRES_P1+$13d0,y
1d28: 99 d0 33                     sta     HIRES_P1+$13d0,y
1d2b: 8a                           txa
1d2c: 19 d0 37                     ora     HIRES_P1+$17d0,y
1d2f: 99 d0 37                     sta     HIRES_P1+$17d0,y
1d32: 8a                           txa
1d33: 19 d0 3b                     ora     HIRES_P1+$1bd0,y
1d36: 99 d0 3b                     sta     HIRES_P1+$1bd0,y
1d39: 8a                           txa
1d3a: 19 d0 3f                     ora     HIRES_P1+$1fd0,y
1d3d: 99 d0 3f                     sta     HIRES_P1+$1fd0,y
1d40: 60                           rts

1d41: 60 a0 20 99+                 .align  $0100 (191 bytes)

                                   .org    $4000
                   ; 
                   ; Offset to shape data.  Add $4000.
                   shape_data_offset
4000: f1 13                        .dd2    shape_cls_offs-$4000
                   ********************************************************************************
                   * Musical sequences.                                                           *
                   *                                                                              *
                   * Each sequence starts with a four byte header:                                *
                   *  +$00-01: global duration; affects speed of entire sequence                  *
                   *  +$02-03: unused                                                             *
                   *                                                                              *
                   * After that is a series of 4-byte entries:                                    *
                   *  +$00: pitch of voice #0                                                     *
                   *  +$01: pitch of voice #1                                                     *
                   *  +$02: pitch of voice #2                                                     *
                   *  +$03: note duration                                                         *
                   *                                                                              *
                   * Setting all three voices to the same value provides a steady tone.  The      *
                   * pitch values are indices into the table at $4012, which are used to          *
                   * increment three counters.  Higher values equate to higher pitches.           *
                   *                                                                              *
                   * The duration is an iteration count; the total iterations performed is equal  *
                   * to (note_duration * global_duration).                                        *
                   *                                                                              *
                   * The table below holds offsets to the seven defined music sequences.  Add     *
                   * $4000.                                                                       *
                   ********************************************************************************
4002: 77 07        music_offset    .dd2    music_00-$4000    ;$00
4004: 13 04                        .dd2    music_01-$4000    ;$01
4006: 0f 07                        .dd2    music_02-$4000    ;$02
4008: 33 07                        .dd2    music_03-$4000    ;$03
400a: 67 07                        .dd2    music_04-$4000    ;$04
400c: cb 00                        .dd2    music_05-$4000    ;$05
400e: b3 03                        .dd2    music_06-$4000    ;$06
4010: 33 07                        .dd2    music_03-$4000    ;$07 (same as $03)
                   ; 
                   ; Musical note value table.  The first three entries in the 4-bytes-per-entry
                   ; music tables are indexes into this.
                   ; 
                   ; There are 73 valid-looking entries ($00-48).  The highest actually used is
                   ; $3d.
4012: 00 00        note_values     .dd2    $0000
4014: 00 02                        .dd2    $0200
4016: 1e 02                        .dd2    $021e
4018: 40 02                        .dd2    $0240
401a: 61 02                        .dd2    $0261
401c: 88 02                        .dd2    $0288
401e: ab 02                        .dd2    $02ab
4020: d4 02                        .dd2    $02d4
4022: 00 03                        .dd2    $0300
4024: 2c 03                        .dd2    $032c
4026: 5d 03                        .dd2    $035d
4028: 90 03                        .dd2    $0390
402a: 9f 03                        .dd2    $039f
402c: 00 04                        .dd2    $0400
402e: 3c 04                        .dd2    $043c
4030: 80 04                        .dd2    $0480
4032: c2 04                        .dd2    $04c2
4034: 10 05                        .dd2    $0510
4036: 56 05                        .dd2    $0556
4038: a8 05                        .dd2    $05a8
403a: 00 06                        .dd2    $0600
403c: 58 06                        .dd2    $0658
403e: ba 06                        .dd2    $06ba
4040: 20 07                        .dd2    $0720
4042: 8e 07                        .dd2    $078e
4044: 00 08                        .dd2    $0800
4046: 78 08                        .dd2    $0878
4048: 00 09                        .dd2    $0900
404a: 84 09                        .dd2    $0984
404c: 20 0a                        .dd2    $0a20
404e: ac 0a                        .dd2    $0aac
4050: 50 0b                        .dd2    $0b50
4052: 00 0c                        .dd2    $0c00
4054: b0 0c                        .dd2    $0cb0
4056: 74 0d                        .dd2    $0d74
4058: 40 0e                        .dd2    $0e40
405a: 1c 0f                        .dd2    $0f1c
405c: 00 10                        .dd2    $1000
405e: f0 10                        .dd2    $10f0
4060: 00 12                        .dd2    $1200
4062: 08 13                        .dd2    $1308
4064: 40 14                        .dd2    $1440
4066: 58 15                        .dd2    $1558
4068: a0 16                        .dd2    $16a0
406a: 00 18                        .dd2    $1800
406c: 60 19                        .dd2    $1960
406e: e8 1a                        .dd2    $1ae8
4070: 80 1c                        .dd2    $1c80
4072: 38 1e                        .dd2    $1e38
4074: 00 20                        .dd2    $2000
4076: e0 21                        .dd2    $21e0
4078: 00 24                        .dd2    $2400
407a: 10 26                        .dd2    $2610
407c: 80 28                        .dd2    $2880
407e: b0 2a                        .dd2    $2ab0
4080: 40 2d                        .dd2    $2d40
4082: 00 30                        .dd2    $3000
4084: c0 32                        .dd2    $32c0
4086: d0 35                        .dd2    $35d0
4088: 00 39                        .dd2    $3900
408a: 70 3c                        .dd2    $3c70
408c: 00 40                        .dd2    $4000
408e: c0 43                        .dd2    $43c0
4090: 00 48                        .dd2    $4800
4092: 20 4c                        .dd2    $4c20
4094: 00 51                        .dd2    $5100
4096: 60 55                        .dd2    $5560
4098: 80 5a                        .dd2    $5a80
409a: 00 60                        .dd2    $6000
409c: 80 65                        .dd2    $6580
409e: a0 6b                        .dd2    $6ba0
40a0: 00 72                        .dd2    $7200
40a2: e0 78                        .dd2    $78e0
40a4: 00 80                        .dd2    $8000
40a6: 00 00                        .dd2    $0000
40a8: 00 3d 3d 3d+                 .junk   35
                   ; 
                   ; Music sequence $05: game over (high score).
40cb: 2c 01        music_05        .dd2    $012c
40cd: 00 00                        .dd2    $0000
40cf: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
40d3: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
40d7: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
40db: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
40df: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
40e3: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
40e7: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
40eb: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
40ef: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
40f3: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
40f7: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
40fb: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
40ff: 01 14 20 02                  .bulk   $01,$14,$20,$02
4103: 02 15 21 02                  .bulk   $02,$15,$21,$02
4107: 01 14 20 02                  .bulk   $01,$14,$20,$02
410b: 02 15 21 02                  .bulk   $02,$15,$21,$02
410f: 01 14 20 02                  .bulk   $01,$14,$20,$02
4113: 02 15 21 02                  .bulk   $02,$15,$21,$02
4117: 01 14 20 02                  .bulk   $01,$14,$20,$02
411b: 02 15 21 02                  .bulk   $02,$15,$21,$02
411f: 01 14 20 02                  .bulk   $01,$14,$20,$02
4123: 02 15 21 02                  .bulk   $02,$15,$21,$02
4127: 01 14 20 02                  .bulk   $01,$14,$20,$02
412b: 02 15 21 02                  .bulk   $02,$15,$21,$02
412f: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4133: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4137: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
413b: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
413f: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4143: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4147: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
414b: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
414f: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4153: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4157: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
415b: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
415f: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4163: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4167: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
416b: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
416f: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4173: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4177: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
417b: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
417f: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4183: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4187: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
418b: 20 25 29 03                  .bulk   $20,$25,$29,$03
418f: 20 25 28 18                  .bulk   $20,$25,$28,$18
4193: 20 25 28 1c                  .bulk   $20,$25,$28,$1c
4197: 08 08 08 04                  .bulk   $08,$08,$08,$04
419b: 01 01 01 04                  .bulk   $01,$01,$01,$04
419f: 08 08 08 04                  .bulk   $08,$08,$08,$04
41a3: 01 01 01 04                  .bulk   $01,$01,$01,$04
41a7: 08 08 08 04                  .bulk   $08,$08,$08,$04
41ab: 01 01 01 04                  .bulk   $01,$01,$01,$04
41af: 08 08 08 04                  .bulk   $08,$08,$08,$04
41b3: 01 01 01 04                  .bulk   $01,$01,$01,$04
41b7: 08 08 08 04                  .bulk   $08,$08,$08,$04
41bb: 01 01 01 04                  .bulk   $01,$01,$01,$04
41bf: 08 08 08 04                  .bulk   $08,$08,$08,$04
41c3: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
41c7: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
41cb: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
41cf: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
41d3: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
41d7: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
41db: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
41df: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
41e3: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
41e7: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
41eb: 01 0d 19 02                  .bulk   $01,$0d,$19,$02
41ef: 02 0e 1a 02                  .bulk   $02,$0e,$1a,$02
41f3: 01 14 20 02                  .bulk   $01,$14,$20,$02
41f7: 02 15 21 02                  .bulk   $02,$15,$21,$02
41fb: 01 14 20 02                  .bulk   $01,$14,$20,$02
41ff: 02 15 21 02                  .bulk   $02,$15,$21,$02
4203: 01 14 20 02                  .bulk   $01,$14,$20,$02
4207: 02 15 21 02                  .bulk   $02,$15,$21,$02
420b: 01 14 20 02                  .bulk   $01,$14,$20,$02
420f: 02 15 21 02                  .bulk   $02,$15,$21,$02
4213: 01 14 20 02                  .bulk   $01,$14,$20,$02
4217: 02 15 21 02                  .bulk   $02,$15,$21,$02
421b: 01 14 20 02                  .bulk   $01,$14,$20,$02
421f: 02 15 21 02                  .bulk   $02,$15,$21,$02
4223: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4227: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
422b: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
422f: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4233: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4237: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
423b: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
423f: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4243: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4247: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
424b: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
424f: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4253: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4257: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
425b: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
425f: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4263: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4267: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
426b: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
426f: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
4273: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
4277: 02 0e 26 02                  .bulk   $02,$0e,$26,$02
427b: 01 0d 25 02                  .bulk   $01,$0d,$25,$02
427f: 00 28 2c 03                  .bulk   $00,$28,$2c,$03
4283: 29 2c 31 18                  .bulk   $29,$2c,$31,$18
4287: 29 2c 31 1c                  .bulk   $29,$2c,$31,$1c
428b: 08 08 08 04                  .bulk   $08,$08,$08,$04
428f: 01 01 01 04                  .bulk   $01,$01,$01,$04
4293: 08 08 08 04                  .bulk   $08,$08,$08,$04
4297: 01 01 01 04                  .bulk   $01,$01,$01,$04
429b: 08 08 08 04                  .bulk   $08,$08,$08,$04
429f: 01 01 01 04                  .bulk   $01,$01,$01,$04
42a3: 08 08 08 04                  .bulk   $08,$08,$08,$04
42a7: 01 01 01 04                  .bulk   $01,$01,$01,$04
42ab: 08 08 08 04                  .bulk   $08,$08,$08,$04
42af: 01 01 01 04                  .bulk   $01,$01,$01,$04
42b3: 08 08 08 04                  .bulk   $08,$08,$08,$04
42b7: 01 0d 19 18                  .bulk   $01,$0d,$19,$18
42bb: 01 14 20 18                  .bulk   $01,$14,$20,$18
42bf: 01 0d 25 2d                  .bulk   $01,$0d,$25,$2d
42c3: 20 25 29 03                  .bulk   $20,$25,$29,$03
42c7: 25 2a 2e 30                  .bulk   $25,$2a,$2e,$30
42cb: 22 2a 2e 03                  .bulk   $22,$2a,$2e,$03
42cf: 24 2c 30 03                  .bulk   $24,$2c,$30,$03
42d3: 05 2e 31 1e                  .bulk   $05,$2e,$31,$1e
42d7: 2a 2d 33 0c                  .bulk   $2a,$2d,$33,$0c
42db: 2c 31 35 06                  .bulk   $2c,$31,$35,$06
42df: 2a 33 36 06                  .bulk   $2a,$33,$36,$06
42e3: 2c 31 38 06                  .bulk   $2c,$31,$38,$06
42e7: 29 31 38 06                  .bulk   $29,$31,$38,$06
42eb: 25 31 38 06                  .bulk   $25,$31,$38,$06
42ef: 20 31 38 06                  .bulk   $20,$31,$38,$06
42f3: 1d 31 38 06                  .bulk   $1d,$31,$38,$06
42f7: 07 31 35 03                  .bulk   $07,$31,$35,$03
42fb: 07 33 36 03                  .bulk   $07,$33,$36,$03
42ff: 0d 35 38 18                  .bulk   $0d,$35,$38,$18
4303: 11 31 3a 0c                  .bulk   $11,$31,$3a,$0c
4307: 08 33 3c 0c                  .bulk   $08,$33,$3c,$0c
430b: 0d 35 3d 30                  .bulk   $0d,$35,$3d,$30
430f: 00 00 00 00                  .bulk   $00,$00,$00,$00
                   ; 
                   ; Junk; copy of first part of music sequence $01.
4313: fa 00 00 00+                 .junk   160
                   ; 
                   ; Music sequence $06: exit time portal (max time).
43b3: fa 00        music_06        .dd2    $00fa
43b5: 00 00                        .dd2    $0000
43b7: 00 1b 20 01                  .bulk   $00,$1b,$20,$01
43bb: 00 1b 22 01                  .bulk   $00,$1b,$22,$01
43bf: 00 1d 24 01                  .bulk   $00,$1d,$24,$01
43c3: 00 1d 25 01                  .bulk   $00,$1d,$25,$01
43c7: 27 27 27 02                  .bulk   $27,$27,$27,$02
43cb: 29 29 29 02                  .bulk   $29,$29,$29,$02
43cf: 27 27 27 02                  .bulk   $27,$27,$27,$02
43d3: 29 29 29 02                  .bulk   $29,$29,$29,$02
43d7: 27 27 27 02                  .bulk   $27,$27,$27,$02
43db: 29 29 29 02                  .bulk   $29,$29,$29,$02
43df: 27 27 27 02                  .bulk   $27,$27,$27,$02
43e3: 29 29 29 02                  .bulk   $29,$29,$29,$02
43e7: 27 27 27 02                  .bulk   $27,$27,$27,$02
43eb: 29 29 29 02                  .bulk   $29,$29,$29,$02
43ef: 27 27 27 02                  .bulk   $27,$27,$27,$02
43f3: 29 29 29 02                  .bulk   $29,$29,$29,$02
43f7: 27 27 27 02                  .bulk   $27,$27,$27,$02
43fb: 29 29 29 02                  .bulk   $29,$29,$29,$02
43ff: 27 27 27 02                  .bulk   $27,$27,$27,$02
4403: 29 29 29 02                  .bulk   $29,$29,$29,$02
4407: 27 27 27 02                  .bulk   $27,$27,$27,$02
440b: 29 29 29 02                  .bulk   $29,$29,$29,$02
440f: 00 00 00 00                  .bulk   $00,$00,$00,$00
                   ; 
                   ; Music sequence $01: start of game.
4413: fa 00        music_01        .dd2    $00fa
4415: 00 00                        .dd2    $0000
4417: 08 08 08 01                  .bulk   $08,$08,$08,$01
441b: 0a 0a 0a 01                  .bulk   $0a,$0a,$0a,$01
441f: 0c 0c 0c 01                  .bulk   $0c,$0c,$0c,$01
4423: 0d 0d 0d 01                  .bulk   $0d,$0d,$0d,$01
4427: 0f 0f 0f 02                  .bulk   $0f,$0f,$0f,$02
442b: 11 11 11 02                  .bulk   $11,$11,$11,$02
442f: 0f 0f 0f 02                  .bulk   $0f,$0f,$0f,$02
4433: 11 11 11 02                  .bulk   $11,$11,$11,$02
4437: 0f 0f 0f 02                  .bulk   $0f,$0f,$0f,$02
443b: 11 11 11 02                  .bulk   $11,$11,$11,$02
443f: 0f 0f 0f 02                  .bulk   $0f,$0f,$0f,$02
4443: 11 11 11 02                  .bulk   $11,$11,$11,$02
4447: 0f 0f 0f 02                  .bulk   $0f,$0f,$0f,$02
444b: 11 11 11 02                  .bulk   $11,$11,$11,$02
444f: 0f 0f 0f 02                  .bulk   $0f,$0f,$0f,$02
4453: 11 11 11 02                  .bulk   $11,$11,$11,$02
4457: 0f 0f 0f 02                  .bulk   $0f,$0f,$0f,$02
445b: 11 11 11 02                  .bulk   $11,$11,$11,$02
445f: 0f 0f 0f 02                  .bulk   $0f,$0f,$0f,$02
4463: 11 11 11 02                  .bulk   $11,$11,$11,$02
4467: 0f 14 00 01                  .bulk   $0f,$14,$00,$01
446b: 0f 16 00 01                  .bulk   $0f,$16,$00,$01
446f: 11 18 00 01                  .bulk   $11,$18,$00,$01
4473: 11 19 00 01                  .bulk   $11,$19,$00,$01
4477: 1b 1b 00 02                  .bulk   $1b,$1b,$00,$02
447b: 1d 1d 00 02                  .bulk   $1d,$1d,$00,$02
447f: 1b 1b 00 02                  .bulk   $1b,$1b,$00,$02
4483: 1d 1d 00 02                  .bulk   $1d,$1d,$00,$02
4487: 1b 1b 00 02                  .bulk   $1b,$1b,$00,$02
448b: 1d 1d 00 02                  .bulk   $1d,$1d,$00,$02
448f: 1b 1b 00 02                  .bulk   $1b,$1b,$00,$02
4493: 1d 1d 00 02                  .bulk   $1d,$1d,$00,$02
4497: 1b 1b 00 02                  .bulk   $1b,$1b,$00,$02
449b: 1d 1d 00 02                  .bulk   $1d,$1d,$00,$02
449f: 1b 1b 00 02                  .bulk   $1b,$1b,$00,$02
44a3: 1d 1d 00 02                  .bulk   $1d,$1d,$00,$02
44a7: 1b 1b 00 02                  .bulk   $1b,$1b,$00,$02
44ab: 1d 1d 00 02                  .bulk   $1d,$1d,$00,$02
44af: 1b 1b 00 02                  .bulk   $1b,$1b,$00,$02
44b3: 1d 1d 00 02                  .bulk   $1d,$1d,$00,$02
44b7: 00 1b 20 01                  .bulk   $00,$1b,$20,$01
44bb: 00 1b 22 01                  .bulk   $00,$1b,$22,$01
44bf: 00 1d 24 01                  .bulk   $00,$1d,$24,$01
44c3: 00 1d 25 01                  .bulk   $00,$1d,$25,$01
44c7: 27 27 27 02                  .bulk   $27,$27,$27,$02
44cb: 29 29 29 02                  .bulk   $29,$29,$29,$02
44cf: 27 27 27 02                  .bulk   $27,$27,$27,$02
44d3: 29 29 29 02                  .bulk   $29,$29,$29,$02
44d7: 27 27 27 02                  .bulk   $27,$27,$27,$02
44db: 29 29 29 02                  .bulk   $29,$29,$29,$02
44df: 27 27 27 02                  .bulk   $27,$27,$27,$02
44e3: 29 29 29 02                  .bulk   $29,$29,$29,$02
44e7: 27 27 27 02                  .bulk   $27,$27,$27,$02
44eb: 29 29 29 02                  .bulk   $29,$29,$29,$02
44ef: 27 27 27 02                  .bulk   $27,$27,$27,$02
44f3: 29 29 29 02                  .bulk   $29,$29,$29,$02
44f7: 27 27 27 02                  .bulk   $27,$27,$27,$02
44fb: 29 29 29 02                  .bulk   $29,$29,$29,$02
44ff: 27 27 27 02                  .bulk   $27,$27,$27,$02
4503: 29 29 29 02                  .bulk   $29,$29,$29,$02
4507: 27 27 27 02                  .bulk   $27,$27,$27,$02
450b: 29 29 29 02                  .bulk   $29,$29,$29,$02
450f: 27 27 27 02                  .bulk   $27,$27,$27,$02
4513: 29 29 29 02                  .bulk   $29,$29,$29,$02
4517: 27 27 27 02                  .bulk   $27,$27,$27,$02
451b: 29 29 29 02                  .bulk   $29,$29,$29,$02
451f: 27 27 27 02                  .bulk   $27,$27,$27,$02
4523: 29 29 29 02                  .bulk   $29,$29,$29,$02
4527: 27 27 27 02                  .bulk   $27,$27,$27,$02
452b: 29 29 29 02                  .bulk   $29,$29,$29,$02
452f: 00 00 00 00                  .bulk   $00,$00,$00,$00
                   ; 
                   ; Junk, vaguely musical.
4533: 12 12 00 06+                 .bulk   $12,$12,$00,$06,$0d,$0d,$00,$02,$12,$14,$00,$01,$12,$16,$00,$01
                                    +      $12,$18,$00,$01,$12,$19,$00,$01,$16,$16,$00,$02,$16,$16,$00,$02
                                    +      $16,$16,$00,$02,$16,$16,$00,$02,$16,$00,$14,$01,$16,$00,$16,$01
                                    +      $16,$00,$18,$01,$16,$00,$19,$01,$12,$00,$1e,$02,$12,$00,$1e,$02
                                    +      $12,$00,$1e,$02,$12,$00,$1e,$02,$12,$00,$1e,$02,$12,$00,$1e,$02
                                    +      $16,$16,$00,$06,$12,$12,$00,$02,$16,$14,$00,$01,$16,$16,$00,$01
                                    +      $16,$18,$00,$01,$16,$19,$00,$01,$19,$19,$00,$02,$19,$19,$00,$02
                                    +      $19,$19,$00,$02,$19,$19,$00,$02,$19,$19,$20,$01,$19,$19,$22,$01
                                    +      $19,$19,$24,$01,$19,$19,$25,$01,$16,$00,$22,$02,$16,$00,$22,$02
                                    +      $16,$00,$22,$02,$16,$00,$22,$02,$16,$00,$22,$02,$16,$00,$22,$02
                                    +      $19,$19,$00,$06,$16,$16,$00,$02,$19,$00,$18,$01,$19,$00,$1a,$01
                                    +      $19,$00,$1b,$01,$19,$00,$1d,$01,$1d,$1d,$00,$08,$1d,$00,$18,$01
                                    +      $1d,$00,$1a,$01,$1d,$00,$1b,$01,$1d,$00,$1d,$01,$11,$11,$00,$08
                                    +      $11,$00,$1f,$01,$11,$00,$1d,$01,$11,$00,$1c,$01,$11,$00,$1a,$01
                                    +      $16,$16,$00,$02,$16,$16,$00,$02,$16,$16,$00,$02,$11,$11,$00,$02
                                    +      $16,$00,$16,$01,$16,$00,$13,$01,$16,$00,$15,$01,$16,$00,$17,$01
                                    +      $1a,$11,$0a,$0c,$1a,$11,$0a,$0c,$00,$00,$00,$00
                   ; 
                   ; Junk; copy of first part of "game over, new high score" music.
463f: 40 01 00 00+                 .bulk   $40,$01,$00,$00,$01,$0d,$19,$02,$02,$0e,$1a,$02,$01,$0d,$19,$02
                                    +      $02,$0e,$1a,$02,$01,$0d,$19,$02,$02,$0e,$1a,$02,$01,$0d,$19,$02
                                    +      $02,$0e,$1a,$02,$01,$0d,$19,$02,$02,$0e,$1a,$02,$01,$0d,$19,$02
                                    +      $02,$0e,$1a,$02,$01,$14,$20,$02,$02,$15,$21,$02,$01,$14,$20,$02
                                    +      $02,$15,$21,$02,$01,$14,$20,$02,$02,$15,$21,$02,$01,$14,$20,$02
                                    +      $02,$15,$21,$02,$01,$14,$20,$02,$02,$15,$21,$02,$01,$14,$20,$02
                                    +      $02,$15,$21,$02,$01,$0d,$25,$02,$02,$0e,$26,$02,$01,$0d,$25,$02
                                    +      $02,$0e,$26,$02,$01,$0d,$25,$02,$02,$0e,$26,$02,$01,$0d,$25,$02
                                    +      $02,$0e,$26,$02,$01,$0d,$25,$02,$02,$0e,$26,$02,$01,$0d,$25,$02
                                    +      $02,$0e,$26,$02,$01,$0d,$25,$02,$02,$0e,$26,$02,$01,$0d,$25,$02
                                    +      $02,$0e,$26,$02,$01,$0d,$25,$02,$02,$0e,$26,$02,$01,$0d,$25,$02
                                    +      $02,$0e,$26,$02,$01,$0d,$25,$02,$02,$0e,$26,$02,$01,$0d,$25,$02
                                    +      $02,$0e,$26,$03,$20,$25,$29,$03,$20,$25,$28,$1e,$00,$00,$00,$00
                   ; 
                   ; Music sequence $02: enter time portal.
470f: 40 01        music_02        .dd2    $0140
4711: 00 00                        .dd2    $0000
4713: 22 2a 2e 03                  .bulk   $22,$2a,$2e,$03
4717: 24 2c 30 03                  .bulk   $24,$2c,$30,$03
471b: 05 2e 31 1e                  .bulk   $05,$2e,$31,$1e
471f: 2a 2d 33 0c                  .bulk   $2a,$2d,$33,$0c
4723: 2c 31 35 06                  .bulk   $2c,$31,$35,$06
4727: 2a 33 36 06                  .bulk   $2a,$33,$36,$06
472b: 2c 31 38 18                  .bulk   $2c,$31,$38,$18
472f: 00 00 00 00                  .bulk   $00,$00,$00,$00
                   ; 
                   ; Music sequence $03: enemy base destroyed.
4733: 38 00        music_03        .dd2    $0038
4735: 00 00                        .dd2    $0000
4737: 2a 2a 2a 01                  .bulk   $2a,$2a,$2a,$01
473b: 29 29 29 01                  .bulk   $29,$29,$29,$01
473f: 27 27 27 01                  .bulk   $27,$27,$27,$01
4743: 25 25 25 01                  .bulk   $25,$25,$25,$01
4747: 24 24 24 01                  .bulk   $24,$24,$24,$01
474b: 22 22 22 01                  .bulk   $22,$22,$22,$01
474f: 20 20 20 01                  .bulk   $20,$20,$20,$01
4753: 1e 1e 1e 01                  .bulk   $1e,$1e,$1e,$01
4757: 1d 1d 1d 01                  .bulk   $1d,$1d,$1d,$01
475b: 1b 1b 1b 01                  .bulk   $1b,$1b,$1b,$01
475f: 19 19 19 01                  .bulk   $19,$19,$19,$01
4763: 00 00 00 00                  .bulk   $00,$00,$00,$00
                   ; 
                   ; Music sequence $04: fly through friendly base.
4767: f4 01        music_04        .dd2    $01f4
4769: 00 00                        .dd2    $0000
476b: 20 25 29 03                  .bulk   $20,$25,$29,$03
476f: 25 2a 2e 09                  .bulk   $25,$2a,$2e,$09
4773: 00 00 00 00                  .bulk   $00,$00,$00,$00
                   ; 
                   ; Music sequence $00: game over (not high score).
4777: 40 01 00 00  music_00        .bulk   $40,$01,$00,$00
477b: 01 0d 19 18                  .bulk   $01,$0d,$19,$18
477f: 01 14 20 18                  .bulk   $01,$14,$20,$18
4783: 01 0d 25 2d                  .bulk   $01,$0d,$25,$2d
4787: 20 25 29 03                  .bulk   $20,$25,$29,$03
478b: 25 2a 2e 30                  .bulk   $25,$2a,$2e,$30
478f: 00 00 00 00                  .bulk   $00,$00,$00,$00
                   ********************************************************************************
                   * Shape definitions.  Shapes are organized into classes, e.g. all enemy ships  *
                   * are in one class, all enemy bases are in another.  For each region of space  *
                   * there is a limit to the number of objects from a given class.  Only shapes   *
                   * from classes 0-7 can be spawned; classes 8-10 are used for player            *
                   * projectiles and explosions.                                                  *
                   *                                                                              *
                   * The data here is only referenced when an object is created.  At creation     *
                   * time it's "unpacked" into various tables.                                    *
                   *                                                                              *
                   * The first byte of the class definition is an AND mask that is applied to the *
                   * shape index.  It determines the maximum number of variants that there can be *
                   * in the table, and can be used to get an odd/even effect.  The second byte is *
                   * unused.  This is followed by a series of 16-bit offsets (from $4000) that    *
                   * specify the start of the shapes.                                             *
                   *                                                                              *
                   * Each shape begins with a 24-byte header:                                     *
                   *  +$00: number of elements in shape                                           *
                   *  +$01: lifespan, used for explosion flares and one of the chunks             *
                   *  +$02: score class (1-7, or 0 if not enemy ship or base)                     *
                   *  +$03: unique identifier (e.g. time warp is $6f)                             *
                   *  +$04: activity class: 0 for most things, 1 for player projectiles and       *
                   * explosion flares, 2 for explosion chunks, 3 for enemy ships (not bases)      *
                   *  +$05: 4 for player projectiles, 0 for everything else                       *
                   *  +$06: nonzero for enemy ships; affects how frequently they can change       *
                   * direction                                                                    *
                   *  +$07: determines method of selecting initial position; value is $00 for     *
                   * ships/bases/stars, $01/02 for enemy projectiles, $7e for explosion chunks,   *
                   * $7f for portal boundaries, $ff for Epoch logo and player projectile          *
                   *  +$08-09: minimum initial Z position                                         *
                   *  +$0a-0b: maximum initial Z position                                         *
                   *  +$0c-0e: unused, almost always zero                                         *
                   *  +$0f-10: hitbox size; also used as initial position modifier, when creating *
                   * object not at edge                                                           *
                   *  +$11-12: maximum Z speed                                                    *
                   *  +$13-14: maximum X speed, only nonzero for explosions/flare                 *
                   *  +$15-16: maximum Y speed, only nonzero for explosions/flare                 *
                   *  +$17: unused, always zero                                                   *
                   *                                                                              *
                   * The shape header is followed by the elements, 16 bytes each:                 *
                   *  +$00: element type                                                          *
                   *    $00=point                                                                 *
                   *    $01=horizontal line                                                       *
                   *    $80=rect                                                                  *
                   *    $ff=vertical line                                                         *
                   *  +$01: color A                                                               *
                   *  +$02: color B                                                               *
                   *    $00=black                                                                 *
                   *    $10=white (single-pixel)                                                  *
                   *    $20=green                                                                 *
                   *    $30=purple                                                                *
                   *    $40=orange                                                                *
                   *    $50=blue                                                                  *
                   *    $60=white (double-pixel)                                                  *
                   *    >=$80 ($ff) = do not draw                                                 *
                   *  +$03: color change frequency; 0=only color A used                           *
                   *  +$04-05: Z offset, +value away from viewer (16-bit signed)                  *
                   *  +$06-07: left (16-bit signed)                                               *
                   *  +$08-09: top (16-bit signed)                                                *
                   *  +$0a-0b: right (16-bit signed)                                              *
                   *  +$0c-0d: bottom (16-bit signed)                                             *
                   *  +$0e-0f: unused, always zero                                                *
                   *                                                                              *
                   * All coordinates are inclusive.  Negative values are up and to the left.      *
                   *                                                                              *
                   * Color values are used as the high nibble of an index into a color table with *
                   * $70 entries.                                                                 *
                   ********************************************************************************
4793: 00 00                        .junk   2
                   ; 
                   ; Shape class $00: EPOCH logo.
                   ; 
                   ; All of the elements have a +$1000 Z offset, which moves everything farther
                   ; from the viewer.
                   ; 
4795: 00           shape_00        .dd1    %00000000         ;1 entry
4796: 00                           .dd1    $00
4797: 99 07                        .dd2    shape_00_0-$4000

                   vis
4799: 13 00 00 01+ shape_00_0      .bulk   $13,$00,$00,$01,$00,$00,$00,$ff,$00,$0f,$00,$10,$00,$00,$00,$c0
                                    +      $01,$00,$00,$00,$00,$00,$00,$00
47b1: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$10,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
47c1: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$80,$fc,$00,$ff,$c0,$fc,$00,$01,$00,$00
47d1: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$c0,$fc,$00,$ff,$80,$fd,$40,$ff,$00,$00
47e1: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$c0,$fc,$e0,$ff,$40,$fd,$20,$00,$00,$00
47f1: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$c0,$fc,$c0,$00,$80,$fd,$00,$01,$00,$00
4801: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$00,$fe,$00,$ff,$40,$fe,$00,$01,$00,$00
4811: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$c0,$fe,$00,$ff,$00,$ff,$00,$00,$00,$00 ;'P' right vertical ($481d should be $20?)
4821: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$40,$fe,$e0,$ff,$c0,$fe,$20,$00,$00,$00 ;'P' lower horizontal
4831: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$40,$fe,$00,$ff,$c0,$fe,$40,$ff,$00,$00
4841: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$80,$ff,$00,$ff,$c0,$ff,$00,$01,$00,$00
4851: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$40,$00,$00,$ff,$80,$00,$00,$01,$00,$00
4861: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$c0,$ff,$00,$ff,$40,$00,$40,$ff,$00,$00
4871: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$c0,$ff,$c0,$00,$40,$00,$00,$01,$00,$00
4881: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$00,$01,$00,$ff,$40,$01,$00,$01,$00,$00 ;'C' vertical
4891: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$40,$01,$00,$ff,$00,$02,$40,$ff,$00,$00
48a1: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$40,$01,$c0,$00,$00,$02,$00,$01,$00,$00
48b1: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$80,$02,$00,$ff,$c0,$02,$00,$01,$00,$00
48c1: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$40,$03,$00,$ff,$80,$03,$00,$01,$00,$00
48d1: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$10,$c0,$02,$e0,$ff,$40,$03,$20,$00,$00,$00 ;'H' horizontal ($48d7 should be $80?)
                   ; 
                   ; Shape class $01: enemy bases.
                   ; 
                   ; There are more entries for the 300-point base, which makes it more likely to
                   ; appear.
                   ; 
48e1: 03           shape_01        .dd1    %00000011         ;4 entries
48e2: 00                           .dd1    $00
48e3: b9 09                        .dd2    shape_01_1-$4000
48e5: f1 08                        .dd2    shape_01_0-$4000
48e7: b9 09                        .dd2    shape_01_1-$4000
48e9: b9 09                        .dd2    shape_01_1-$4000
48eb: 00 00 00 00+                 .junk   6

                   vis
48f1: 0b 00 07 11+ shape_01_0      .bulk   $0b,$00,$07,$11,$00,$00,$00,$00,$00,$10,$00,$70,$00,$00,$00,$0f
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
4909: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4919: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$00,$00,$80,$fe,$d0,$ff,$80,$01,$d0,$ff,$00,$00
4929: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$00,$00,$80,$fe,$e8,$ff,$80,$01,$e8,$ff,$00,$00
4939: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$00,$00,$80,$fe,$00,$00,$80,$01,$00,$00,$00,$00
4949: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$00,$00,$80,$fe,$18,$00,$80,$01,$18,$00,$00,$00
4959: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$00,$00,$80,$fe,$30,$00,$80,$01,$30,$00,$00,$00
4969: ff 60 00 00+                 .bulk   $ff,$60,$00,$00,$00,$00,$00,$ff,$a0,$ff,$00,$ff,$60,$00,$00,$00
4979: ff 60 00 00+                 .bulk   $ff,$60,$00,$00,$00,$00,$00,$01,$a0,$ff,$00,$01,$60,$00,$00,$00
4989: 01 60 00 00+                 .bulk   $01,$60,$00,$00,$00,$00,$00,$ff,$a0,$ff,$00,$01,$a0,$ff,$00,$00
4999: 01 60 00 00+                 .bulk   $01,$60,$00,$00,$00,$00,$00,$ff,$60,$00,$00,$01,$60,$00,$00,$00
49a9: 80 60 00 01+                 .bulk   $80,$60,$00,$01,$00,$00,$e0,$ff,$e0,$ff,$20,$00,$20,$00,$00,$00

                   vis
49b9: 0a 00 06 12+ shape_01_1      .bulk   $0a,$00,$06,$12,$00,$00,$00,$00,$00,$10,$00,$50,$00,$00,$00,$10
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
49d1: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
49e1: 80 60 00 01+                 .bulk   $80,$60,$00,$01,$00,$00,$e0,$ff,$e0,$ff,$20,$00,$20,$00,$00,$00
49f1: 80 20 00 00+                 .bulk   $80,$20,$00,$00,$00,$00,$b0,$fe,$b0,$ff,$80,$ff,$50,$00,$00,$00
4a01: 80 20 00 00+                 .bulk   $80,$20,$00,$00,$00,$00,$80,$00,$b0,$ff,$50,$01,$50,$00,$00,$00
4a11: ff 50 00 00+                 .bulk   $ff,$50,$00,$00,$00,$00,$00,$00,$a0,$ff,$00,$00,$60,$00,$00,$00
4a21: 80 50 00 00+                 .bulk   $80,$50,$00,$00,$00,$00,$60,$fe,$00,$ff,$a0,$01,$b0,$ff,$00,$00
4a31: 80 50 00 00+                 .bulk   $80,$50,$00,$00,$00,$00,$60,$fe,$50,$00,$a0,$01,$00,$01,$00,$00
4a41: ff 40 00 00+                 .bulk   $ff,$40,$00,$00,$00,$00,$00,$00,$00,$01,$00,$00,$80,$01,$00,$00
4a51: 01 40 00 02+                 .bulk   $01,$40,$00,$02,$00,$00,$20,$ff,$60,$01,$e0,$00,$60,$01,$00,$00
4a61: 01 40 00 01+                 .bulk   $01,$40,$00,$01,$00,$00,$40,$ff,$30,$01,$c0,$00,$30,$01,$00,$00
                   ; 
                   ; Shape class $02: enemy ships + time portal.
                   ; 
4a71: 07           shape_02        .dd1    %00000111         ;8 entries
4a72: 00                           .dd1    $00
4a73: 91 0a                        .dd2    shape_02_0-$4000
4a75: 29 0b                        .dd2    shape_02_1-$4000
4a77: d9 0b                        .dd2    shape_02_3-$4000
4a79: 29 0b                        .dd2    shape_02_1-$4000
4a7b: 31 0c                        .dd2    shape_02_4-$4000
4a7d: d9 0b                        .dd2    shape_02_3-$4000
4a7f: 81 0b                        .dd2    shape_02_2-$4000
4a81: 81 0b                        .dd2    shape_02_2-$4000
4a83: 00 00 00 00+                 .junk   14

                   ; The second rect/line set has a small Z offset, which moves it farther from the
                   ; viewer.  This seems backward, since those parts are drawn last.
                   vis
4a91: 08 00 05 e1+ shape_02_0      .bulk   $08,$00,$05,$e1,$03,$00,$0f,$00,$00,$01,$00,$20,$00,$00,$00,$00
                                    +      $01,$00,$04,$00,$00,$00,$00,$00
4aa9: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4ab9: 80 30 00 00+                 .bulk   $80,$30,$00,$00,$00,$00,$a0,$ff,$a0,$ff,$60,$00,$60,$00,$00,$00
4ac9: 80 30 00 00+                 .bulk   $80,$30,$00,$00,$60,$00,$a0,$ff,$a0,$ff,$60,$00,$60,$00,$00,$00
4ad9: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$00,$00,$00,$ff,$a0,$ff,$00,$01,$a0,$ff,$00,$00
4ae9: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$00,$00,$00,$ff,$60,$00,$00,$01,$60,$00,$00,$00
4af9: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$60,$00,$00,$ff,$a0,$ff,$00,$01,$60,$00,$00,$00
4b09: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$60,$00,$00,$ff,$60,$00,$00,$01,$60,$00,$00,$00
4b19: 00 60 00 01+                 .bulk   $00,$60,$00,$01,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00

                   vis
4b29: 04 00 02 21+ shape_02_1      .bulk   $04,$00,$02,$21,$03,$00,$19,$00 ;$00-07
4b31: 00 04                        .dd2    $0400             ;$08-09
4b33: 00 20                        .dd2    $2000             ;$0a-0b
4b35: 00 00 00                     .bulk   $00,$00,$00       ;$0c-0e
4b38: c0 01                        .dd2    $01c0             ;$0f-10
4b3a: 00 03                        .dd2    $0300             ;$11-12
4b3c: 00 00                        .dd2    $0000             ;$13-14
4b3e: 00 00                        .dd2    $0000             ;$15-16
4b40: 00                           .dd1    $00               ;$17
4b41: 80 50 00 00+                 .bulk   $80,$50,$00,$00,$00,$00,$a0,$ff,$90,$ff,$60,$00,$70,$00,$00,$00
4b51: ff 20 00 00+                 .bulk   $ff,$20,$00,$00,$00,$00,$00,$ff,$60,$ff,$00,$ff,$a0,$00,$00,$00
4b61: ff 20 00 00+                 .bulk   $ff,$20,$00,$00,$00,$00,$00,$01,$60,$ff,$00,$01,$a0,$00,$00,$00
4b71: 01 20 00 00+                 .bulk   $01,$20,$00,$00,$00,$00,$00,$ff,$00,$00,$00,$01,$00,$00,$00,$00

                   vis
4b81: 04 00 03 22+ shape_02_2      .bulk   $04,$00,$03,$22,$03,$00,$14,$00,$00,$04,$00,$20,$00,$00,$00,$40
                                    +      $01,$00,$03,$00,$00,$00,$00,$00
4b99: 80 30 00 00+                 .bulk   $80,$30,$00,$00,$00,$00,$a0,$ff,$90,$ff,$60,$00,$70,$00,$00,$00
4ba9: ff 40 00 00+                 .bulk   $ff,$40,$00,$00,$00,$00,$00,$00,$60,$ff,$00,$00,$a0,$00,$00,$00
4bb9: 01 40 00 00+                 .bulk   $01,$40,$00,$00,$00,$00,$c0,$fe,$60,$ff,$40,$01,$60,$ff,$00,$00
4bc9: 01 40 00 00+                 .bulk   $01,$40,$00,$00,$00,$00,$c0,$fe,$a0,$00,$40,$01,$a0,$00,$00,$00

                   vis
4bd9: 04 00 04 23+ shape_02_3      .bulk   $04,$00,$04,$23,$03,$00,$28,$00,$00,$04,$00,$30,$00,$00,$00,$20
                                    +      $01,$00,$02,$00,$00,$00,$00,$00
4bf1: 80 50 00 00+                 .bulk   $80,$50,$00,$00,$00,$00,$a0,$ff,$c0,$ff,$60,$00,$40,$00,$00,$00
4c01: 80 40 00 01+                 .bulk   $80,$40,$00,$01,$00,$00,$e0,$fe,$d0,$ff,$40,$ff,$30,$00,$00,$00
4c11: 80 40 00 01+                 .bulk   $80,$40,$00,$01,$00,$00,$c0,$00,$d0,$ff,$20,$01,$30,$00,$00,$00
4c21: 01 50 00 00+                 .bulk   $01,$50,$00,$00,$00,$00,$00,$ff,$00,$00,$00,$01,$00,$00,$00,$00

                   vis
4c31: 05 00 00 6f+ shape_02_4      .bulk   $05,$00,$00,$6f,$00,$00,$00,$00,$00,$10,$00,$60,$00,$00,$00,$20
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
4c49: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4c59: 80 30 50 01+                 .bulk   $80,$30,$50,$01,$00,$00,$80,$ff,$c0,$fe,$e0,$ff,$40,$01,$00,$00
4c69: 80 40 20 02+                 .bulk   $80,$40,$20,$02,$00,$00,$20,$00,$c0,$fe,$80,$00,$40,$01,$00,$00
4c79: 80 20 10 01+                 .bulk   $80,$20,$10,$01,$00,$00,$c0,$fe,$80,$ff,$40,$01,$e0,$ff,$00,$00
4c89: 80 50 10 03+                 .bulk   $80,$50,$10,$03,$00,$00,$c0,$fe,$20,$00,$40,$01,$80,$00,$00,$00
                   ; 
                   ; Shape class $03: enemy projectiles.
                   ; 
                   ; The value at +$07 is matched with the ship class when matching projectiles
                   ; with enemies, so the flashing orange/white object is fired by bases, and the
                   ; solid orange object is fired by ships.
                   ; 
4c99: 02           shape_03        .dd1    %00000010         ;4 entries, even only
4c9a: 00                           .dd1    $00
4c9b: a9 0c                        .dd2    shape_03_0-$4000
4c9d: d1 0c                        .dd2    shape_03_1-$4000  ;(unused)
4c9f: d1 0c                        .dd2    shape_03_1-$4000
4ca1: d1 0c                        .dd2    shape_03_1-$4000  ;(unused)
4ca3: 00 00 00 00+                 .junk   6

                   vis
4ca9: 01 00 00 31+ shape_03_0      .bulk   $01,$00,$00,$31,$03,$00,$00,$01,$00,$02,$00,$40,$00,$00,$00,$20
                                    +      $00,$00,$08,$00,$00,$00,$00,$00
4cc1: 80 40 10 01+                 .bulk   $80,$40,$10,$01,$00,$00,$e0,$ff,$e0,$ff,$20,$00,$20,$00,$00,$00

                   vis
4cd1: 01 00 00 32+ shape_03_1      .bulk   $01,$00,$00,$32,$03,$00,$00,$02,$00,$02,$00,$40,$00,$00,$00,$20
                                    +      $00,$60,$07,$00,$00,$00,$00,$00
4ce9: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$00,$e0,$ff,$e0,$ff,$20,$00,$20,$00,$00,$00
                   ; 
                   ; Shape class $04: reference back to shape $01_1 (300pt enemy base).
                   ; 
                   ; This doesn't appear to be used -- the per-region limit tables at $708c all
                   ; have zero for the 4th entry.
                   ; 
4cf9: 00           shape_04        .dd1    %00000000         ;1 entry
4cfa: 00                           .dd1    $00
4cfb: b9 09                        .dd2    shape_01_1-$4000
4cfd: 00 00 00 00+                 .junk   12
                   ; 
                   ; Shape class $05: time portal travel bounds.
                   ; 
4d09: 07           shape_05        .dd1    %00000111         ;8 entries
4d0a: 00                           .dd1    $00
4d0b: 29 0d                        .dd2    shape_05_0-$4000
4d0d: 71 0d                        .dd2    shape_05_1-$4000
4d0f: b9 0d                        .dd2    shape_05_2-$4000
4d11: 01 0e                        .dd2    shape_05_3-$4000
4d13: a9 0e                        .dd2    shape_05_4-$4000
4d15: f1 0e                        .dd2    shape_05_5-$4000
4d17: 39 0f                        .dd2    shape_05_6-$4000
4d19: 71 0d                        .dd2    shape_05_1-$4000
4d1b: 00 00 00 00+                 .junk   14

                   vis
4d29: 03 00 00 51+ shape_05_0      .bulk   $03,$00,$00,$51,$00,$00,$00,$7f,$00,$20,$00,$24,$00,$00,$00,$a0
                                    +      $02,$00,$00,$00,$00,$00,$00,$00
4d41: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4d51: 01 20 50 01+                 .bulk   $01,$20,$50,$01,$00,$00,$b0,$fd,$90,$fd,$90,$02,$90,$fd,$00,$00
4d61: 01 40 00 00+                 .bulk   $01,$40,$00,$00,$a0,$00,$70,$fd,$a0,$02,$80,$02,$a0,$02,$00,$00

                   vis
4d71: 03 00 00 52+ shape_05_1      .bulk   $03,$00,$00,$52,$00,$00,$00,$7f,$00,$20,$00,$24,$00,$00,$00,$e0
                                    +      $02,$00,$00,$00,$00,$00,$00,$00
4d89: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4d99: 01 50 10 01+                 .bulk   $01,$50,$10,$01,$00,$00,$e0,$fd,$40,$fd,$e0,$02,$40,$fd,$00,$00
4da9: 01 30 00 00+                 .bulk   $01,$30,$00,$00,$c0,$00,$20,$fd,$30,$02,$f0,$02,$30,$02,$00,$00

                   vis
4db9: 03 00 00 53+ shape_05_2      .bulk   $03,$00,$00,$53,$00,$00,$00,$7f,$00,$20,$00,$24,$00,$00,$00,$e0
                                    +      $02,$00,$00,$00,$00,$00,$00,$00
4dd1: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4de1: 01 50 20 01+                 .bulk   $01,$50,$20,$01,$00,$00,$00,$fe,$d0,$fd,$e0,$02,$d0,$fd,$00,$00
4df1: 80 30 00 01+                 .bulk   $80,$30,$00,$01,$a0,$00,$b0,$fd,$40,$02,$90,$02,$c7,$02,$00,$00

                   vis
4e01: 09 00 00 54+ shape_05_3      .bulk   $09,$00,$00,$54,$00,$00,$00,$7f,$00,$20,$00,$24,$00,$00,$00,$a0
                                    +      $02,$00,$00,$00,$00,$00,$00,$00
4e19: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4e29: 00 20 00 00+                 .bulk   $00,$20,$00,$00,$00,$00,$d0,$fd,$a0,$fd,$00,$00,$00,$00,$00,$00
4e39: 00 20 30 01+                 .bulk   $00,$20,$30,$01,$00,$02,$c0,$ff,$c0,$fd,$00,$00,$00,$00,$00,$00
4e49: 00 20 00 00+                 .bulk   $00,$20,$00,$00,$50,$01,$35,$02,$70,$fd,$00,$00,$00,$00,$00,$00
4e59: 00 20 40 05+                 .bulk   $00,$20,$40,$05,$00,$01,$bb,$fd,$60,$02,$00,$00,$00,$00,$00,$00
4e69: 00 20 00 00+                 .bulk   $00,$20,$00,$00,$50,$00,$e0,$ff,$83,$02,$00,$00,$00,$00,$00,$00
4e79: 00 60 00 01+                 .bulk   $00,$60,$00,$01,$00,$00,$48,$02,$a0,$fd,$00,$00,$00,$00,$00,$00
4e89: 00 20 00 00+                 .bulk   $00,$20,$00,$00,$70,$00,$66,$02,$20,$00,$00,$00,$00,$00,$00,$00
4e99: 00 20 00 00+                 .bulk   $00,$20,$00,$00,$30,$01,$8e,$fd,$dd,$ff,$00,$00,$00,$00,$00,$00

                   vis
4ea9: 03 00 00 55+ shape_05_4      .bulk   $03,$00,$00,$55,$00,$00,$00,$7f,$00,$20,$00,$24,$00,$00,$00,$00
                                    +      $03,$00,$00,$00,$00,$00,$00,$00
4ec1: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4ed1: ff 30 40 01+                 .bulk   $ff,$30,$40,$01,$20,$00,$20,$fd,$00,$fe,$20,$fd,$b0,$02,$00,$00
4ee1: ff 20 00 00+                 .bulk   $ff,$20,$00,$00,$90,$01,$f0,$02,$30,$fd,$f0,$02,$60,$02,$00,$00

                   ; Weird colors.
                   vis
4ef1: 03 00 00 56+ shape_05_5      .bulk   $03,$00,$00,$56,$00,$00,$00,$7f,$00,$20,$00,$24,$00,$00,$00,$b0
                                    +      $02,$00,$00,$00,$00,$00,$00,$00
4f09: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4f19: ff 06 00 00+                 .bulk   $ff,$06,$00,$00,$00,$00,$c0,$fd,$50,$fd,$c0,$fd,$20,$02,$00,$00
4f29: ff 03 00 00+                 .bulk   $ff,$03,$00,$00,$20,$02,$b0,$02,$e0,$fe,$b0,$02,$70,$03,$00,$00

                   vis
4f39: 03 00 00 57+ shape_05_6      .bulk   $03,$00,$00,$57,$00,$00,$00,$7f,$00,$20,$00,$24,$00,$00,$00,$00
                                    +      $03,$00,$00,$00,$00,$00,$00,$00
4f51: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
4f61: 80 20 50 02+                 .bulk   $80,$20,$50,$02,$00,$00,$89,$fd,$a0,$fd,$e0,$fd,$50,$02,$00,$00
4f71: 80 40 20 01+                 .bulk   $80,$40,$20,$01,$90,$00,$44,$02,$b0,$fd,$00,$03,$e0,$01,$00,$00
                   ; 
                   ; Shape class $06: friendly base.
                   ; 
4f81: 00           shape_06        .dd1    %00000000         ;1 entry
4f82: 00                           .dd1    $00
4f83: 91 0f                        .dd2    shape_06_0-$4000
4f85: 00 00 00 00+                 .junk   12

                   ; Left window: 4x orange, 4x black
                   ; Middle window: purple, white, white, green, black, black ("it's complicated")
                   ; Right window: 2x white, 2x black
                   vis
4f91: 08 00 00 61+ shape_06_0      .bulk   $08,$00,$00,$61,$00,$00,$00,$00,$00,$10,$00,$40,$00,$00,$00,$20
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
4fa9: 00 50 00 00+                 .bulk   $00,$50,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00 ;fly-through point
4fb9: 80 20 00 00+                 .bulk   $80,$20,$00,$00,$00,$00,$f0,$fe,$e0,$fe,$a0,$01,$e0,$ff,$00,$00
4fc9: 80 20 00 00+                 .bulk   $80,$20,$00,$00,$00,$00,$70,$ff,$20,$00,$90,$00,$60,$00,$00,$00
4fd9: 80 20 00 00+                 .bulk   $80,$20,$00,$00,$00,$00,$90,$ff,$e0,$ff,$e0,$ff,$20,$00,$00,$00
4fe9: 80 20 00 00+                 .bulk   $80,$20,$00,$00,$00,$00,$20,$00,$e0,$ff,$70,$00,$20,$00,$00,$00
4ff9: 80 40 00 03+                 .bulk   $80,$40,$00,$03,$00,$00,$60,$ff,$40,$ff,$a0,$ff,$90,$ff,$00,$00 ;left
5009: 80 30 00 02+                 .bulk   $80,$30,$00,$02,$00,$00,$20,$00,$40,$ff,$50,$00,$90,$ff,$00,$00 ;middle
5019: 80 10 00 01+                 .bulk   $80,$10,$00,$01,$00,$00,$e0,$00,$40,$ff,$10,$01,$90,$ff,$00,$00 ;right
                   ; 
                   ; Shape class $07: stars.
                   ; 
5029: 07           shape_07        .dd1    %00000111         ;1 entry
502a: 00                           .dd1    $00
502b: 49 10                        .dd2    shape_07_0-$4000
502d: 71 10                        .dd2    shape_07_1-$4000
502f: 99 10                        .dd2    shape_07_2-$4000
5031: c1 10                        .dd2    shape_07_3-$4000
5033: e9 10                        .dd2    shape_07_4-$4000
5035: 11 11                        .dd2    shape_07_5-$4000
5037: e9 10                        .dd2    shape_07_4-$4000
5039: 71 10                        .dd2    shape_07_1-$4000
503b: 00 00 00 00+                 .junk   14

                   vis
5049: 01 00 00 71+ shape_07_0      .bulk   $01,$00,$00,$71,$00,$00,$00,$00,$40,$00,$00,$0a,$00,$00,$00,$01
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
5061: 00 60 00 00+                 .bulk   $00,$60,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00

                   vis
5071: 01 00 00 72+ shape_07_1      .bulk   $01,$00,$00,$72,$00,$00,$00,$00,$40,$00,$00,$40,$00,$00,$00,$01
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
5089: 00 50 00 00+                 .bulk   $00,$50,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00

                   vis
5099: 01 00 00 73+ shape_07_2      .bulk   $01,$00,$00,$73,$00,$00,$00,$00,$40,$00,$00,$28,$00,$00,$00,$01
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
50b1: 00 40 00 01+                 .bulk   $00,$40,$00,$01,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00

                   vis
50c1: 01 00 00 74+ shape_07_3      .bulk   $01,$00,$00,$74,$00,$00,$00,$00,$40,$00,$00,$10,$00,$00,$00,$01
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
50d9: 00 30 00 00+                 .bulk   $00,$30,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00

                   vis
50e9: 01 00 00 75+ shape_07_4      .bulk   $01,$00,$00,$75,$00,$00,$00,$00,$40,$00,$00,$70,$00,$00,$00,$01
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
5101: 00 20 00 02+                 .bulk   $00,$20,$00,$02,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00

                   ; This one is a rect, not a point.
                   vis
5111: 01 00 00 76+ shape_07_5      .bulk   $01,$00,$00,$76,$00,$00,$00,$00,$40,$00,$00,$70,$00,$00,$00,$01
                                    +      $00,$00,$00,$00,$00,$00,$00,$00
5129: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$00,$00,$e2,$ff,$e2,$ff,$1e,$00,$1e,$00,$00,$00
                   ; 
                   ; Shape class $08: projectile fired by player.  Note the element has a small Z
                   ; offset.
                   ; 
5139: 00           shape_08        .dd1    %00000000         ;1 entry
513a: 00                           .dd1    $00
513b: 49 11                        .dd2    shape_08_0-$4000
513d: 00 00 00 00+                 .junk   12

                   vis
5149: 01 00 00 81+ shape_08_0      .bulk   $01,$00,$00,$81,$01,$04,$00,$ff,$10,$00,$b0,$00,$00,$00,$00,$30
                                    +      $00,$00,$08,$00,$00,$00,$00,$00
5161: 80 10 ff 00+                 .bulk   $80,$10,$ff,$00,$80,$00,$c0,$ff,$c0,$ff,$40,$00,$40,$00,$00,$00
                   ; 
                   ; Shape class $09: explosion chunks.
                   ; 
5171: 07           shape_09        .dd1    %00000111         ;8 entries
5172: 00                           .dd1    $00
5173: 91 11                        .dd2    shape_09_0-$4000
5175: b9 11                        .dd2    shape_09_1-$4000
5177: e1 11                        .dd2    shape_09_2-$4000
5179: 09 12                        .dd2    shape_09_3-$4000
517b: 31 12                        .dd2    shape_09_4-$4000
517d: 59 12                        .dd2    shape_09_5-$4000
517f: 91 11                        .dd2    shape_09_0-$4000
5181: b9 11                        .dd2    shape_09_1-$4000
5183: 00 00 00 00+                 .junk   14

                   vis
5191: 01 00 00 91+ shape_09_0      .bulk   $01,$00,$00,$91,$02,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$20
                                    +      $00,$1a,$00,$1a,$00,$1a,$00,$00
51a9: 80 20 00 00+                 .bulk   $80,$20,$00,$00,$00,$00,$e9,$ff,$ec,$ff,$0b,$00,$09,$00,$00,$00

                   ; Limited lifespan.
                   vis
51b9: 01 20 00 92+ shape_09_1      .bulk   $01,$20,$00,$92,$02,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$20
                                    +      $00,$0a,$00,$0a,$00,$0a,$00,$00
51d1: 80 30 ff 01+                 .bulk   $80,$30,$ff,$01,$00,$00,$fa,$ff,$f6,$ff,$15,$00,$16,$00,$00,$00

                   vis
51e1: 01 00 00 93+ shape_09_2      .bulk   $01,$00,$00,$93,$02,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$20
                                    +      $00,$0a,$00,$0a,$00,$0f,$00,$00
51f9: 80 50 ff 01+                 .bulk   $80,$50,$ff,$01,$00,$00,$f9,$ff,$fb,$ff,$08,$00,$03,$00,$00,$00

                   vis
5209: 01 00 00 94+ shape_09_3      .bulk   $01,$00,$00,$94,$02,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$20
                                    +      $00,$0a,$00,$0a,$00,$0a,$00,$00
5221: 80 10 ff 01+                 .bulk   $80,$10,$ff,$01,$00,$00,$f2,$ff,$f9,$ff,$0a,$00,$0b,$00,$00,$00

                   vis
5231: 01 00 00 95+ shape_09_4      .bulk   $01,$00,$00,$95,$02,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$18
                                    +      $00,$0a,$00,$0a,$00,$18,$00,$00
5249: 80 40 30 01+                 .bulk   $80,$40,$30,$01,$00,$00,$fb,$ff,$fb,$ff,$10,$00,$11,$00,$00,$00

                   vis
5259: 01 00 00 96+ shape_09_5      .bulk   $01,$00,$00,$96,$02,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$20
                                    +      $00,$0a,$00,$0a,$00,$0a,$00,$00
5271: 80 50 00 00+                 .bulk   $80,$50,$00,$00,$00,$00,$da,$ff,$de,$ff,$19,$00,$1b,$00,$00,$00
                   ; 
                   ; Shape class $0a: enemy ship explosion flare.
                   ; 
                   ; All of these have nonzero values for the counter at +$01, which limits their
                   ; lifespan.
                   ; 
5281: 03           shape_0a        .dd1    %00000011         ;4 entries
5282: 00                           .dd1    $00
5283: 91 12                        .dd2    shape_0a_0-$4000
5285: c9 12                        .dd2    shape_0a_1-$4000
5287: 51 13                        .dd2    shape_0a_2-$4000
5289: 99 13                        .dd2    shape_0a_3-$4000
528b: 00 00 00 00+                 .junk   6

                   vis
5291: 02 02 00 01+ shape_0a_0      .bulk   $02,$02,$00,$01,$01,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$90
                                    +      $00,$40,$00,$40,$00,$40,$00,$00
52a9: 80 20 50 01+                 .bulk   $80,$20,$50,$01,$00,$00,$a0,$fe,$d0,$fe,$80,$00,$90,$00,$00,$00
52b9: 80 40 30 01+                 .bulk   $80,$40,$30,$01,$00,$00,$a0,$fd,$20,$ff,$80,$00,$c0,$01,$00,$00

                   vis
52c9: 07 06 00 02+ shape_0a_1      .bulk   $07,$06,$00,$02,$01,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$80
                                    +      $00,$20,$00,$20,$00,$20,$00,$00
52e1: 00 60 00 01+                 .bulk   $00,$60,$00,$01,$00,$00,$00,$ff,$70,$ff,$00,$00,$00,$00,$00,$00
52f1: 00 60 00 00+                 .bulk   $00,$60,$00,$00,$00,$00,$c0,$ff,$b0,$00,$00,$00,$00,$00,$00,$00
5301: 00 60 00 00+                 .bulk   $00,$60,$00,$00,$00,$00,$90,$01,$20,$01,$00,$00,$00,$00,$00,$00
5311: 00 60 00 01+                 .bulk   $00,$60,$00,$01,$00,$00,$a0,$00,$10,$02,$00,$00,$00,$00,$00,$00
5321: 00 60 00 00+                 .bulk   $00,$60,$00,$00,$00,$00,$d0,$00,$b1,$01,$00,$00,$00,$00,$00,$00
5331: 00 60 00 00+                 .bulk   $00,$60,$00,$00,$00,$00,$f0,$00,$d0,$fe,$00,$00,$00,$00,$00,$00
5341: 00 60 00 00+                 .bulk   $00,$60,$00,$00,$00,$00,$20,$01,$20,$ff,$00,$00,$00,$00,$00,$00

                   vis
5351: 03 01 00 03+ shape_0a_2      .bulk   $03,$01,$00,$03,$01,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$60
                                    +      $00,$80,$00,$80,$00,$80,$00,$00
5369: 80 10 00 00+                 .bulk   $80,$10,$00,$00,$00,$00,$90,$fc,$b0,$fe,$90,$00,$15,$02,$00,$00
5379: 80 40 00 00+                 .bulk   $80,$40,$00,$00,$90,$01,$b0,$ff,$70,$ff,$c0,$01,$30,$02,$00,$00
5389: 80 30 00 00+                 .bulk   $80,$30,$00,$00,$00,$02,$d0,$fd,$e0,$ff,$60,$00,$20,$02,$00,$00

                   vis
5399: 04 04 00 03+ shape_0a_3      .bulk   $04,$04,$00,$03,$01,$00,$00,$7e,$10,$00,$00,$01,$00,$00,$00,$60
                                    +      $00,$80,$00,$80,$00,$80,$00,$00
53b1: 01 20 ff 00+                 .bulk   $01,$20,$ff,$00,$00,$00,$a0,$fe,$fb,$ff,$60,$00,$05,$00,$00,$00
53c1: 01 20 30 01+                 .bulk   $01,$20,$30,$01,$00,$00,$b0,$ff,$00,$00,$40,$01,$00,$00,$00,$00
53d1: 01 50 ff 00+                 .bulk   $01,$50,$ff,$00,$00,$00,$d0,$fe,$20,$00,$60,$00,$20,$00,$00,$00
53e1: 01 10 00 01+                 .bulk   $01,$10,$00,$01,$00,$00,$90,$ff,$c0,$ff,$40,$01,$c0,$ff,$00,$00
                   ; 
                   ; Offsets to shape class definitions.  The 16-bit values are added to $4000.
                   ; 
                   ; The location of this table is identified by an offset stored at $4000.
                   ; 
                   ; Used by code at $760f.
53f1: 95 07        shape_cls_offs  .dd2    shape_00-$4000    ;$00
53f3: e1 08                        .dd2    shape_01-$4000    ;$01
53f5: 71 0a                        .dd2    shape_02-$4000    ;$02
53f7: 99 0c                        .dd2    shape_03-$4000    ;$03
53f9: f9 0c                        .dd2    shape_04-$4000    ;$04
53fb: 09 0d                        .dd2    shape_05-$4000    ;$05
53fd: 81 0f                        .dd2    shape_06-$4000    ;$06
53ff: 29 10                        .dd2    shape_07-$4000    ;$07
5401: 39 11                        .dd2    shape_08-$4000    ;$08
5403: 71 11                        .dd2    shape_09-$4000    ;$09
5405: 81 12                        .dd2    shape_0a-$4000    ;$0a
5407: 95 07                        .dd2    shape_00-$4000    ;$0b ($00)
5409: 3d 3d 3d 3d+                 .align  $0100 (247 bytes)
                   ; 
                   ; High byte of address of unrolled AND instructions.  Low byte of address comes
                   ; out of table at $b700.
                   unroll_and_addr_hi
5500: a6 a6 a6 a6+                 .bulk   $a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6
                                    +      $a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6,$a6
                                    +      $a6,$a6,$a6,$a6,$a6,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7
                                    +      $a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7
                                    +      $a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a7,$a8,$a8,$a8,$a8,$a8,$a8
                                    +      $a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8
                                    +      $a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a9,$a9
                                    +      $a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9
                                    +      $a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9,$a9
                                    +      $a9,$a9,$a9,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa
                                    +      $aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa,$aa
                                    +      $aa,$aa,$aa,$aa,$aa,$aa,$aa,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab
                                    +      $ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab
                                    +      $ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab
                                    +      $ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab
                                    +      $ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab,$ab
                   ; 
                   ; Low/high address of unrolled STA instructions.
5600: 00 03 06 09+ unroll_sta_lo   .bulk   $00,$03,$06,$09,$0c,$0f,$12,$15,$18,$1b,$1e,$21,$24,$27,$2a,$2d
                                    +      $30,$33,$36,$39,$3c,$3f,$42,$45,$48,$4b,$4e,$51,$54,$57,$5a,$5d
                                    +      $60,$63,$66,$69,$6c,$6f,$72,$75,$78,$7b,$7e,$81,$84,$87,$8a,$8d
                                    +      $90,$93,$96,$99,$9c,$9f,$a2,$a5,$a8,$ab,$ae,$b1,$b4,$b7,$ba,$bd
                                    +      $c0,$c3,$c6,$c9,$cc,$cf,$d2,$d5,$d8,$db,$de,$e1,$e4,$e7,$ea,$ed
                                    +      $f0,$f3,$f6,$f9,$fc,$ff,$02,$05,$08,$0b,$0e,$11,$14,$17,$1a,$1d
                                    +      $20,$23,$26,$29,$2c,$2f,$32,$35,$38,$3b,$3e,$41,$44,$47,$4a,$4d
                                    +      $50,$53,$56,$59,$5c,$5f,$62,$65,$68,$6b,$6e,$71,$74,$77,$7a,$7d
                                    +      $80,$83,$86,$89,$8c,$8f,$92,$95,$98,$9b,$9e,$a1,$a4,$a7,$aa,$ad
                                    +      $b0,$b3,$b6,$b9,$bc,$bf,$c2,$c5,$c8,$cb,$ce,$d1,$d4,$d7,$da,$dd
                                    +      $e0,$e3,$e6,$e9,$ec,$ef,$f2,$f5,$f8,$fb,$fe,$01,$04,$07,$0a,$0d
                                    +      $10,$13,$16,$19,$1c,$1f,$22,$25,$28,$2b,$2e,$31,$34,$37,$3a,$3d
                                    +      $3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d
                                    +      $3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d
                                    +      $3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d
                                    +      $3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d,$3d
5700: 58 58 58 58+ unroll_sta_hi   .bulk   $58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58
                                    +      $58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58
                                    +      $58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58
                                    +      $58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58
                                    +      $58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58,$58
                                    +      $58,$58,$58,$58,$58,$58,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59
                                    +      $59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59
                                    +      $59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59
                                    +      $59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59
                                    +      $59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59
                                    +      $59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$59,$5a,$5a,$5a,$5a,$5a
                                    +      $5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a
                                    +      $5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a
                                    +      $5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a
                                    +      $5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a
                                    +      $5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a,$5a

                   ; 
                   ; Draws a byte-wide vertical stripe.
                   ; 
                   ; This is generally not called directly.  A lookup table ($5600/5700) converts
                   ; line numbers to addresses, which are then used as an indirect jump (for the
                   ; top) or as a location to store an RTS (for the bottom).
                   ; 
                   ; On entry:
                   ;   A-reg: pixel byte value (adjusted for odd/even)
                   ;   Y-reg: horizontal offset (0-39)
                   ; 
5800: 99 00 20     UnrolledSTA     sta     HIRES_P1,y
5803: 99 00 24                     sta     HIRES_P1+$400,y
5806: 99 00 28                     sta     HIRES_P1+$800,y
5809: 99 00 2c                     sta     HIRES_P1+$c00,y
580c: 99 00 30                     sta     HIRES_P1+$1000,y
580f: 99 00 34                     sta     HIRES_P1+$1400,y
5812: 99 00 38                     sta     HIRES_P1+$1800,y
5815: 99 00 3c                     sta     HIRES_P1+$1c00,y
5818: 99 80 20                     sta     HIRES_P1+128,y
581b: 99 80 24                     sta     HIRES_P1+$480,y
581e: 99 80 28                     sta     HIRES_P1+$880,y
5821: 99 80 2c                     sta     HIRES_P1+$c80,y
5824: 99 80 30                     sta     HIRES_P1+$1080,y
5827: 99 80 34                     sta     HIRES_P1+$1480,y
582a: 99 80 38                     sta     HIRES_P1+$1880,y
582d: 99 80 3c                     sta     HIRES_P1+$1c80,y
5830: 99 00 21                     sta     HIRES_P1+$100,y
5833: 99 00 25                     sta     HIRES_P1+$500,y
5836: 99 00 29                     sta     HIRES_P1+$900,y
5839: 99 00 2d                     sta     HIRES_P1+$d00,y
583c: 99 00 31                     sta     HIRES_P1+$1100,y
583f: 99 00 35                     sta     HIRES_P1+$1500,y
5842: 99 00 39                     sta     HIRES_P1+$1900,y
5845: 99 00 3d                     sta     HIRES_P1+$1d00,y
5848: 99 80 21                     sta     HIRES_P1+$180,y
584b: 99 80 25                     sta     HIRES_P1+$580,y
584e: 99 80 29                     sta     HIRES_P1+$980,y
5851: 99 80 2d                     sta     HIRES_P1+$d80,y
5854: 99 80 31                     sta     HIRES_P1+$1180,y
5857: 99 80 35                     sta     HIRES_P1+$1580,y
585a: 99 80 39                     sta     HIRES_P1+$1980,y
585d: 99 80 3d                     sta     HIRES_P1+$1d80,y
5860: 99 00 22                     sta     HIRES_P1+$200,y
5863: 99 00 26                     sta     HIRES_P1+$600,y
5866: 99 00 2a                     sta     HIRES_P1+$a00,y
5869: 99 00 2e                     sta     HIRES_P1+$e00,y
586c: 99 00 32                     sta     HIRES_P1+$1200,y
586f: 99 00 36                     sta     HIRES_P1+$1600,y
5872: 99 00 3a                     sta     HIRES_P1+$1a00,y
5875: 99 00 3e                     sta     HIRES_P1+$1e00,y
5878: 99 80 22                     sta     HIRES_P1+$280,y
587b: 99 80 26                     sta     HIRES_P1+$680,y
587e: 99 80 2a                     sta     HIRES_P1+$a80,y
5881: 99 80 2e                     sta     HIRES_P1+$e80,y
5884: 99 80 32                     sta     HIRES_P1+$1280,y
5887: 99 80 36                     sta     HIRES_P1+$1680,y
588a: 99 80 3a                     sta     HIRES_P1+$1a80,y
588d: 99 80 3e                     sta     HIRES_P1+$1e80,y
5890: 99 00 23                     sta     HIRES_P1+$300,y
5893: 99 00 27                     sta     HIRES_P1+$700,y
5896: 99 00 2b                     sta     HIRES_P1+$b00,y
5899: 99 00 2f                     sta     HIRES_P1+$f00,y
589c: 99 00 33                     sta     HIRES_P1+$1300,y
589f: 99 00 37                     sta     HIRES_P1+$1700,y
58a2: 99 00 3b                     sta     HIRES_P1+$1b00,y
58a5: 99 00 3f                     sta     HIRES_P1+$1f00,y
58a8: 99 80 23                     sta     HIRES_P1+$380,y
58ab: 99 80 27                     sta     HIRES_P1+$780,y
58ae: 99 80 2b                     sta     HIRES_P1+$b80,y
58b1: 99 80 2f                     sta     HIRES_P1+$f80,y
58b4: 99 80 33                     sta     HIRES_P1+$1380,y
58b7: 99 80 37                     sta     HIRES_P1+$1780,y
58ba: 99 80 3b                     sta     HIRES_P1+$1b80,y
58bd: 99 80 3f                     sta     HIRES_P1+$1f80,y
58c0: 99 28 20                     sta     HIRES_P1+40,y
58c3: 99 28 24                     sta     HIRES_P1+$428,y
58c6: 99 28 28                     sta     HIRES_P1+$828,y
58c9: 99 28 2c                     sta     HIRES_P1+$c28,y
58cc: 99 28 30                     sta     HIRES_P1+$1028,y
58cf: 99 28 34                     sta     HIRES_P1+$1428,y
58d2: 99 28 38                     sta     HIRES_P1+$1828,y
58d5: 99 28 3c                     sta     HIRES_P1+$1c28,y
58d8: 99 a8 20                     sta     HIRES_P1+168,y
58db: 99 a8 24                     sta     HIRES_P1+$4a8,y
58de: 99 a8 28                     sta     HIRES_P1+$8a8,y
58e1: 99 a8 2c                     sta     HIRES_P1+$ca8,y
58e4: 99 a8 30                     sta     HIRES_P1+$10a8,y
58e7: 99 a8 34                     sta     HIRES_P1+$14a8,y
58ea: 99 a8 38                     sta     HIRES_P1+$18a8,y
58ed: 99 a8 3c                     sta     HIRES_P1+$1ca8,y
58f0: 99 28 21                     sta     HIRES_P1+$128,y
58f3: 99 28 25                     sta     HIRES_P1+$528,y
58f6: 99 28 29                     sta     HIRES_P1+$928,y
58f9: 99 28 2d                     sta     HIRES_P1+$d28,y
58fc: 99 28 31                     sta     HIRES_P1+$1128,y
58ff: 99 28 35                     sta     HIRES_P1+$1528,y
5902: 99 28 39                     sta     HIRES_P1+$1928,y
5905: 99 28 3d                     sta     HIRES_P1+$1d28,y
5908: 99 a8 21                     sta     HIRES_P1+$1a8,y
590b: 99 a8 25                     sta     HIRES_P1+$5a8,y
590e: 99 a8 29                     sta     HIRES_P1+$9a8,y
5911: 99 a8 2d                     sta     HIRES_P1+$da8,y
5914: 99 a8 31                     sta     HIRES_P1+$11a8,y
5917: 99 a8 35                     sta     HIRES_P1+$15a8,y
591a: 99 a8 39                     sta     HIRES_P1+$19a8,y
591d: 99 a8 3d                     sta     HIRES_P1+$1da8,y
5920: 99 28 22                     sta     HIRES_P1+$228,y
5923: 99 28 26                     sta     HIRES_P1+$628,y
5926: 99 28 2a                     sta     HIRES_P1+$a28,y
5929: 99 28 2e                     sta     HIRES_P1+$e28,y
592c: 99 28 32                     sta     HIRES_P1+$1228,y
592f: 99 28 36                     sta     HIRES_P1+$1628,y
5932: 99 28 3a                     sta     HIRES_P1+$1a28,y
5935: 99 28 3e                     sta     HIRES_P1+$1e28,y
5938: 99 a8 22                     sta     HIRES_P1+$2a8,y
593b: 99 a8 26                     sta     HIRES_P1+$6a8,y
593e: 99 a8 2a                     sta     HIRES_P1+$aa8,y
5941: 99 a8 2e                     sta     HIRES_P1+$ea8,y
5944: 99 a8 32                     sta     HIRES_P1+$12a8,y
5947: 99 a8 36                     sta     HIRES_P1+$16a8,y
594a: 99 a8 3a                     sta     HIRES_P1+$1aa8,y
594d: 99 a8 3e                     sta     HIRES_P1+$1ea8,y
5950: 99 28 23                     sta     HIRES_P1+$328,y
5953: 99 28 27                     sta     HIRES_P1+$728,y
5956: 99 28 2b                     sta     HIRES_P1+$b28,y
5959: 99 28 2f                     sta     HIRES_P1+$f28,y
595c: 99 28 33                     sta     HIRES_P1+$1328,y
595f: 99 28 37                     sta     HIRES_P1+$1728,y
5962: 99 28 3b                     sta     HIRES_P1+$1b28,y
5965: 99 28 3f                     sta     HIRES_P1+$1f28,y
5968: 99 a8 23                     sta     HIRES_P1+$3a8,y
596b: 99 a8 27                     sta     HIRES_P1+$7a8,y
596e: 99 a8 2b                     sta     HIRES_P1+$ba8,y
5971: 99 a8 2f                     sta     HIRES_P1+$fa8,y
5974: 99 a8 33                     sta     HIRES_P1+$13a8,y
5977: 99 a8 37                     sta     HIRES_P1+$17a8,y
597a: 99 a8 3b                     sta     HIRES_P1+$1ba8,y
597d: 99 a8 3f                     sta     HIRES_P1+$1fa8,y
5980: 99 50 20                     sta     HIRES_P1+80,y
5983: 99 50 24                     sta     HIRES_P1+$450,y
5986: 99 50 28                     sta     HIRES_P1+$850,y
5989: 99 50 2c                     sta     HIRES_P1+$c50,y
598c: 99 50 30                     sta     HIRES_P1+$1050,y
598f: 99 50 34                     sta     HIRES_P1+$1450,y
5992: 99 50 38                     sta     HIRES_P1+$1850,y
5995: 99 50 3c                     sta     HIRES_P1+$1c50,y
5998: 99 d0 20                     sta     HIRES_P1+208,y
599b: 99 d0 24                     sta     HIRES_P1+$4d0,y
599e: 99 d0 28                     sta     HIRES_P1+$8d0,y
59a1: 99 d0 2c                     sta     HIRES_P1+$cd0,y
59a4: 99 d0 30                     sta     HIRES_P1+$10d0,y
59a7: 99 d0 34                     sta     HIRES_P1+$14d0,y
59aa: 99 d0 38                     sta     HIRES_P1+$18d0,y
59ad: 99 d0 3c                     sta     HIRES_P1+$1cd0,y
59b0: 99 50 21                     sta     HIRES_P1+$150,y
59b3: 99 50 25                     sta     HIRES_P1+$550,y
59b6: 99 50 29                     sta     HIRES_P1+$950,y
59b9: 99 50 2d                     sta     HIRES_P1+$d50,y
59bc: 99 50 31                     sta     HIRES_P1+$1150,y
59bf: 99 50 35                     sta     HIRES_P1+$1550,y
59c2: 99 50 39                     sta     HIRES_P1+$1950,y
59c5: 99 50 3d                     sta     HIRES_P1+$1d50,y
59c8: 99 d0 21                     sta     HIRES_P1+$1d0,y
59cb: 99 d0 25                     sta     HIRES_P1+$5d0,y
59ce: 99 d0 29                     sta     HIRES_P1+$9d0,y
59d1: 99 d0 2d                     sta     HIRES_P1+$dd0,y
59d4: 99 d0 31                     sta     HIRES_P1+$11d0,y
59d7: 99 d0 35                     sta     HIRES_P1+$15d0,y
59da: 99 d0 39                     sta     HIRES_P1+$19d0,y
59dd: 99 d0 3d                     sta     HIRES_P1+$1dd0,y
59e0: 99 50 22                     sta     HIRES_P1+$250,y
59e3: 99 50 26                     sta     HIRES_P1+$650,y
59e6: 99 50 2a                     sta     HIRES_P1+$a50,y
59e9: 99 50 2e                     sta     HIRES_P1+$e50,y
59ec: 99 50 32                     sta     HIRES_P1+$1250,y
59ef: 99 50 36                     sta     HIRES_P1+$1650,y
59f2: 99 50 3a                     sta     HIRES_P1+$1a50,y
59f5: 99 50 3e                     sta     HIRES_P1+$1e50,y
59f8: 99 d0 22                     sta     HIRES_P1+$2d0,y
59fb: 99 d0 26                     sta     HIRES_P1+$6d0,y
59fe: 99 d0 2a                     sta     HIRES_P1+$ad0,y
5a01: 99 d0 2e                     sta     HIRES_P1+$ed0,y
5a04: 99 d0 32                     sta     HIRES_P1+$12d0,y
5a07: 99 d0 36                     sta     HIRES_P1+$16d0,y
5a0a: 99 d0 3a                     sta     HIRES_P1+$1ad0,y
5a0d: 99 d0 3e                     sta     HIRES_P1+$1ed0,y
5a10: 99 50 23                     sta     HIRES_P1+$350,y
5a13: 99 50 27                     sta     HIRES_P1+$750,y
5a16: 99 50 2b                     sta     HIRES_P1+$b50,y
5a19: 99 50 2f                     sta     HIRES_P1+$f50,y
5a1c: 99 50 33                     sta     HIRES_P1+$1350,y
5a1f: 99 50 37                     sta     HIRES_P1+$1750,y
5a22: 99 50 3b                     sta     HIRES_P1+$1b50,y
5a25: 99 50 3f                     sta     HIRES_P1+$1f50,y
5a28: 99 d0 23                     sta     HIRES_P1+$3d0,y
5a2b: 99 d0 27                     sta     HIRES_P1+$7d0,y
5a2e: 99 d0 2b                     sta     HIRES_P1+$bd0,y
5a31: 99 d0 2f                     sta     HIRES_P1+$fd0,y
5a34: 99 d0 33                     sta     HIRES_P1+$13d0,y
5a37: 99 d0 37                     sta     HIRES_P1+$17d0,y
5a3a: 99 d0 3b                     sta     HIRES_P1+$1bd0,y
5a3d: 99 d0 3f                     sta     HIRES_P1+$1fd0,y
5a40: 60                           rts

5a41: d0 3f 60 00+                 .junk   47

                   ; 
                   ; Redraws the crosshairs after we erase a rect.
                   ; 
                   ; Note we do the draw *before* restoring the instruction we overwrote during the
                   ; erase, but since rect erase uses STA or AND, and crosshair draw uses ORA, they
                   ; don't interfere with each other.
                   ; 
                   • Clear variables
                   ]restore_index  .var    $8a    {addr/1}

5a70: 20 80 5a     AfterEraseRect  jsr     DrawCrosshairs
5a73: a6 64                        ldx     cur_elem_index
5a75: a4 8a                        ldy     ]restore_index
5a77: 4c 4e 8e                     jmp     AfterEraseRect1

5a7a: 00 00 00 00+                 .junk   5
5a7f: 7e           :saved_xreg     .dd1    $7e

                   ; 
                   ; Draws the crosshairs at the center of the screen.
                   ; 
                   ; On exit:
                   ;   X-reg preserved
                   ; 
5a80: 8e 7f 5a     DrawCrosshairs  stx     :saved_xreg
5a83: a9 60                        lda     #INSTR_RTS
5a85: 8d 8b 1a                     sta     OraSeq_93         ;stop at line 93
5a88: a2 03                        ldx     #$03              ;two pixels of white
5a8a: a0 14                        ldy     #20               ;column 20 (center of screen)
5a8c: 20 53 1a                     jsr     OraSeq_85         ;draw vertical line, from line 85 to 92
5a8f: a9 8a                        lda     #INSTR_TXA
5a91: 8d 8b 1a                     sta     OraSeq_93         ;restore
5a94: a9 60                        lda     #INSTR_RTS
5a96: 8d f4 1a                     sta     OraSeq_108        ;stop at line 108
5a99: 20 bc 1a                     jsr     OraSeq_100        ;draw vertical line, from line 100 to 107
5a9c: a9 8a                        lda     #INSTR_TXA
5a9e: 8d f4 1a                     sta     OraSeq_108        ;restore
5aa1: ea                           nop
5aa2: ad 3a 22                     lda     HIRES_P1+$23a     ;draw the horizontal parts with a few stores
5aa5: 09 7e                        ora     #$7e
5aa7: 8d 3a 22                     sta     HIRES_P1+$23a
5aaa: ad 0b 22                     lda     HIRES_P1+$20b
5aad: 09 07                        ora     #$07
5aaf: 8d 3b 22                     sta     HIRES_P1+$23b
5ab2: ad 3c 22                     lda     HIRES_P1+$23c
5ab5: 09 60                        ora     #$60
5ab7: 8d 3c 22                     sta     HIRES_P1+$23c
5aba: ad 3d 22                     lda     HIRES_P1+$23d
5abd: 09 7f                        ora     #$7f
5abf: 8d 3d 22                     sta     HIRES_P1+$23d
5ac2: ae 7f 5a                     ldx     :saved_xreg
5ac5: 60                           rts

5ac6: 00 00 00 00+                 .align  $0100 (58 bytes)

                                   .org    $5e00
5e00: 00 00 00 00+                 .junk   69

                   ; 
                   ; Adjusts position of next time portal boundary object.
                   ; 
                   ; On entry:
                   ;   $ce-cf: portal boundary X coord modifier
                   ;   $d0-d1: portal boundary Y coord modifier
                   ; 
                   ; On exit:
                   ;   X-reg unmodified
                   ;   $ce-cf / $d0-d1 updated
                   ; 
                   • Clear variables
                   ]portal_zc?     .var    $86    {addr/2}
                   ]math2_val?     .var    $8a    {addr/1}
                   ]lz_count       .var    $8b    {addr/1}
                   ]joy_effect     .var    $8c    {addr/2}
                   ]portal_delta_yc .var   $96    {addr/2}

                   UpdatePortalPosn
5e45: ea                           nop
5e46: a9 00                        lda     #$00              ;set Z coord to $2400
5e48: 85 86                        sta     ]portal_zc?
5e4a: a9 24                        lda     #$24
5e4c: 85 87                        sta     ]portal_zc?+1
5e4e: d0 18                        bne     :Cont             ;(always)

5e50: a4 86 b9 00+ unref_5e50?     .junk   24                ;dead code

5e68: 85 87        :Cont           sta     ]portal_zc?+1
5e6a: a8                           tay
5e6b: b9 00 b9                     lda     clz_table,y       ;count leading zeroes ($24 -> 2)
5e6e: a8                           tay
5e6f: 85 8b                        sta     ]lz_count
5e71: 18                           clc
5e72: 69 ac                        adc     #>math_tab2_base?
5e74: 85 13                        sta     math_tab_ptr12+1
5e76: a5 86                        lda     ]portal_zc?
5e78: 39 d5 00                     and     bit_mask_left9,y
5e7b: 05 87                        ora     ]portal_zc?+1
5e7d: a8                           tay
5e7e: b1 12                        lda     (math_tab_ptr12),y
5e80: 85 8a                        sta     ]math2_val?
5e82: ea                           nop
5e83: 18                           clc
5e84: a4 8a                        ldy     ]math2_val?
5e86: b9 00 b5                     lda     turn_map_lo?,y
5e89: 65 9a                        adc     joy_yaw_angle
5e8b: 85 8c                        sta     ]joy_effect
5e8d: a5 9b                        lda     joy_yaw_angle+1
5e8f: e5 8b                        sbc     ]lz_count
5e91: 30 25                        bmi     L5EB8
5e93: 85 8d                        sta     ]joy_effect+1
5e95: 38                           sec
5e96: ea                           nop
5e97: 69 ac                        adc     #>math_tab2_base?
5e99: 85 15                        sta     math_tab_ptr14+1
5e9b: a4 8c                        ldy     ]joy_effect
5e9d: b9 00 17                     lda     math_tab1_lastpg?,y ;$80 - $ff
5ea0: a8                           tay
5ea1: b1 14                        lda     (math_tab_ptr14),y
5ea3: 85 95                        sta     portal_delta_xc+1
5ea5: a4 8d                        ldy     ]joy_effect+1
5ea7: 39 ef 00                     and     bit_mask_left8,y
5eaa: 45 9c                        eor     joy_yaw_sign
5eac: 85 94                        sta     portal_delta_xc
5eae: a5 95                        lda     portal_delta_xc+1
5eb0: 39 e7 00                     and     bit_mask_right8,y
5eb3: 45 9c                        eor     joy_yaw_sign
5eb5: 4c d4 5e                     jmp     L5ED4

5eb8: ea           L5EB8           nop
5eb9: 18                           clc
5eba: 69 08                        adc     #$08
5ebc: 30 12                        bmi     L5ED0
5ebe: 18                           clc
5ebf: 69 10                        adc     #>math_tab1_base?
5ec1: 85 15                        sta     math_tab_ptr14+1
5ec3: a4 8c                        ldy     ]joy_effect
5ec5: a5 9c                        lda     joy_yaw_sign
5ec7: 85 95                        sta     portal_delta_xc+1
5ec9: 51 14                        eor     (math_tab_ptr14),y
5ecb: 85 94                        sta     portal_delta_xc
5ecd: 4c d6 5e                     jmp     L5ED6

5ed0: a9 00        L5ED0           lda     #$00
5ed2: 85 94                        sta     portal_delta_xc
5ed4: 85 95        L5ED4           sta     portal_delta_xc+1
                   ; 
5ed6: ea           L5ED6           nop
5ed7: 18                           clc
5ed8: a4 8a                        ldy     ]math2_val?
5eda: b9 00 b5                     lda     turn_map_lo?,y
5edd: 65 9d                        adc     joy_pitch_angle
5edf: 85 8c                        sta     ]joy_effect
5ee1: a5 9e                        lda     joy_pitch_angle+1
5ee3: e5 8b                        sbc     ]lz_count
5ee5: 30 25                        bmi     L5F0C
5ee7: 85 8d                        sta     ]joy_effect+1
5ee9: 38                           sec
5eea: ea                           nop
5eeb: 69 ac                        adc     #>math_tab2_base?
5eed: 85 15                        sta     math_tab_ptr14+1
5eef: a4 8c                        ldy     ]joy_effect
5ef1: b9 00 17                     lda     math_tab1_lastpg?,y
5ef4: a8                           tay
5ef5: b1 14                        lda     (math_tab_ptr14),y
5ef7: 85 97                        sta     ]portal_delta_yc+1
5ef9: a4 8d                        ldy     ]joy_effect+1
5efb: 39 ef 00                     and     bit_mask_left8,y
5efe: 45 9f                        eor     joy_pitch_sign
5f00: 85 96                        sta     ]portal_delta_yc
5f02: a5 97                        lda     ]portal_delta_yc+1
5f04: 39 e7 00                     and     bit_mask_right8,y
5f07: 45 9f                        eor     joy_pitch_sign
5f09: 4c 28 5f                     jmp     L5F28

5f0c: ea           L5F0C           nop
5f0d: 18                           clc
5f0e: 69 08                        adc     #$08
5f10: 30 12                        bmi     L5F24
5f12: 18                           clc
5f13: 69 10                        adc     #>math_tab1_base?
5f15: 85 15                        sta     math_tab_ptr14+1
5f17: a4 8c                        ldy     ]joy_effect
5f19: a5 9f                        lda     joy_pitch_sign
5f1b: 85 97                        sta     ]portal_delta_yc+1
5f1d: 51 14                        eor     (math_tab_ptr14),y
5f1f: 85 96                        sta     ]portal_delta_yc
5f21: 4c 2a 5f                     jmp     L5F2A

5f24: a9 00        L5F24           lda     #$00
5f26: 85 96                        sta     ]portal_delta_yc
5f28: 85 97        L5F28           sta     ]portal_delta_yc+1
5f2a: ea           L5F2A           nop
                   ; Update output values.
5f2b: a0 02                        ldy     #$02
5f2d: b9 ce 00     :Loop           lda     portal_next_xc,y
5f30: 18                           clc
5f31: 79 94 00                     adc     portal_delta_xc,y ;coordinate delta
5f34: 99 ce 00                     sta     portal_next_xc,y
5f37: b9 cf 00                     lda     portal_next_xc+1,y
5f3a: 79 95 00                     adc     portal_delta_xc+1,y
5f3d: 99 cf 00                     sta     portal_next_xc+1,y
5f40: c9 12                        cmp     #$12              ;high byte >= 18?
5f42: 30 08                        bmi     :InPosRange       ;no, branch
5f44: a9 12                        lda     #$12              ;yes, clamp to 18
5f46: 99 cf 00                     sta     portal_next_xc+1,y
5f49: 4c 55 5f                     jmp     :Next

5f4c: c9 ed        :InPosRange     cmp     #$ed              ;high byte < -19?
5f4e: 10 05                        bpl     :Next             ;no, branch
5f50: a9 ed                        lda     #$ed              ;yes, clamp to -19
5f52: 99 cf 00                     sta     portal_next_xc+1,y
5f55: 88           :Next           dey
5f56: 88                           dey
5f57: 10 d4                        bpl     :Loop
5f59: 60                           rts

5f5a: 3d 3d 3d 3d+                 .junk   12

                   ; 
                   ; Updates object movement vector.
                   ; 
                   ; Some objects, like enemy ships, update their movement periodically.  Others,
                   ; like explosion chunks, have their vector set to random values.
                   ; 
                   ; If the player is turning, we need to update the vector so that things behave
                   ; as if we were rotating rather than sliding.
                   ; 
                   ; On entry:
                   ;   X-reg: object index
                   ; 
                   ; On exit:
                   ;   $64 and X-reg: index of first element
                   ; 
                   • Clear variables

5f66: 18           UpdateObject    clc                       ;do sound stuff
5f67: a5 b2                        lda     engine_sound_ctr?+1
5f69: 69 05                        adc     #$05
5f6b: 85 b2                        sta     engine_sound_ctr?+1
5f6d: 90 0f                        bcc     :NoSound
5f6f: e6 b3                        inc     engine_sound_ctr?+2
5f71: a5 cc                        lda     engine_sound_enable
5f73: f0 09                        beq     :NoSound
5f75: a5 b3                        lda     engine_sound_ctr?+2
5f77: 25 b1                        and     engine_sound_ctr?
5f79: d0 03                        bne     :NoSound
5f7b: ad 30 c0                     lda     SPKR
                   ; 
5f7e: a9 00        :NoSound        lda     #$00
5f80: 85 b4                        sta     wronly_b4?        ;init to zero
5f82: bd a0 9a                     lda     obj_shape_uid,x   ;get shape unique ID
5f85: 29 f0                        and     #$f0
5f87: c9 f0                        cmp     #$f0              ;check for $Fx (never happens?)
5f89: d0 02                        bne     :NotFn
5f8b: 85 b4                        sta     wronly_b4?        ;set $b4 to #$f0 (never happens?)
5f8d: a9 90        :NotFn          lda     #$90
5f8f: 85 c6                        sta     prev_zpos+1       ;init "previous zpos", an optimization used in
5f91: 85 c5                        sta     prev_zpos         ; UpdateElement
5f93: a9 00                        lda     #$00
5f95: 85 72                        sta     no_draw_obj_flag  ;init flags and counters
5f97: 85 f8                        sta     elem_collision_flag
5f99: 85 a4                        sta     wronly_a4?
5f9b: 85 a1                        sta     drawn_elem_count
5f9d: 85 a5                        sta     wronly_a5?
5f9f: 20 7f 7f                     jsr     Return7f7f
5fa2: bd 28 9a                     lda     obj_lifetime_ctr,x ;get object lifetime counter
5fa5: f0 10                        beq     :NotExpired       ;zero, object lives forever
5fa7: de 28 9a                     dec     obj_lifetime_ctr,x ;decrement
5faa: d0 0b                        bne     :NotExpired       ;not yet zero, continue
5fac: a9 ff                        lda     #$ff
5fae: 9d 18 9b                     sta     obj_activity_state,x ;mark object as expired
5fb1: e6 72                        inc     no_draw_obj_flag
5fb3: ea                           nop
5fb4: 4c 42 64                     jmp     GetFirstElemIndex ;copy first element index into $64 and return

5fb7: bd 18 9b     :NotExpired     lda     obj_activity_state,x ;check object activity state (0-3 or > $80)
5fba: 30 06                        bmi     :NoDraw           ;not valid, don't draw it
5fbc: d0 09                        bne     :Branch_SetBB     ;nonzero, branch
5fbe: ea                           nop                       ;zero for things that don't fly toward player
5fbf: 4c 42 64                     jmp     GetFirstElemIndex ;get first element index, and return

5fc2: e6 72        :NoDraw         inc     no_draw_obj_flag
5fc4: 4c 42 64                     jmp     GetFirstElemIndex

5fc7: 10 06        :Branch_SetBB   bpl     :SetBB            ;(always)

5fc9: e6 72 ea 4c+ unref_5fc9      .junk   6

5fcf: 38           :SetBB          sec                       ;A-reg currently 1-3
5fd0: e9 01                        sbc     #$01              ;subtract 1 so it's 0-2
5fd2: 85 bb                        sta     update_mvmt_flag  ;save as movement flag (nonzero for enemy ships)
5fd4: f0 05                        beq     :NoVelChange      ;zero for things with constant velocity; branch
5fd6: de 90 9b                     dec     vel_change_ctr,x  ;decrement the velocity-change countdown
5fd9: f0 03                        beq     :DoVelChange      ;reached zero, do the change
5fdb: 4c 8d 60     :NoVelChange    jmp     :MoveStuff

5fde: a5 bb        :DoVelChange    lda     update_mvmt_flag
5fe0: 29 02                        and     #$02              ;check for 2 (enemy ships)
5fe2: f0 09                        beq     :AddRandom        ;no, must be 1; branch to apply randomness
5fe4: 20 06 7d                     jsr     UpdateObjectVelocity
5fe7: 20 7f 7f                     jsr     Return7f7f
5fea: 4c 69 60                     jmp     :ResetVelChgCtr

                   ; Add some randomness.  We should only get here for explosion chunks.  Note that
                   ; chunks and flares are the only things that have nonzero values for X/Y speed.
                   ]rng_limit      .var    $86    {addr/2}
                   ]rng_limit_mode .var    $88    {addr/1}
                   ]rng_result     .var    $8a    {addr/2}

5fed: a9 01        :AddRandom      lda     #$01
5fef: 85 88                        sta     ]rng_limit_mode   ;set mode to +/-
5ff1: bd 20 9d                     lda     obj_spdlim_z_lo,x ;get Z speed limit
5ff4: 85 86                        sta     ]rng_limit
5ff6: bd 48 9d                     lda     obj_spdlim_z_hi,x
5ff9: 85 87                        sta     ]rng_limit+1
5ffb: 20 b0 7b                     jsr     GenRandom         ;generate random value
5ffe: bd 30 9c                     lda     obj_move_zc2_lo,x ;modify value in object table, adding the
6001: 18                           clc                       ; random value to the existing value
6002: 65 8a                        adc     ]rng_result
6004: 9d 10 9e                     sta     obj_move_zc_lo,x
6007: bd 58 9c                     lda     obj_move_zc2_hi,x
600a: 65 8b                        adc     ]rng_result+1
600c: 9d 38 9e                     sta     obj_move_zc_hi,x
600f: ea                           nop
6010: bd 70 9d                     lda     obj_spdlim_x_lo,x ;repeat for X speed
6013: 85 86                        sta     ]rng_limit
6015: bd 98 9d                     lda     obj_spdlim_x_hi,x
6018: 85 87                        sta     ]rng_limit+1
601a: 20 b0 7b                     jsr     GenRandom
601d: bd 80 9c                     lda     obj_move_xc2_lo,x
6020: 18                           clc
6021: 65 8a                        adc     ]rng_result
6023: 9d 60 9e                     sta     obj_move_xc_lo,x
6026: bd a8 9c                     lda     obj_move_xc2_hi,x
6029: 65 8b                        adc     ]rng_result+1
602b: 9d 88 9e                     sta     obj_move_xc_hi,x
602e: ea                           nop
602f: bd c0 9d                     lda     obj_spdlim_y_lo,x ;repeat for Y speed
6032: 85 86                        sta     ]rng_limit
6034: bd e8 9d                     lda     obj_spdlim_y_hi,x
6037: 85 87                        sta     ]rng_limit+1
6039: 20 b0 7b                     jsr     GenRandom
603c: bd d0 9c                     lda     obj_move_yc2_lo,x
603f: 18                           clc
6040: 65 8a                        adc     ]rng_result
6042: 9d b0 9e                     sta     obj_move_yc_lo,x
6045: bd f8 9c                     lda     obj_move_yc2_hi,x
6048: 65 8b                        adc     ]rng_result+1
604a: 9d d8 9e                     sta     obj_move_yc_hi,x
604d: ea                           nop
                   ; 
604e: 18                           clc                       ;do sound stuff
604f: a5 b2                        lda     engine_sound_ctr?+1
6051: 69 2c                        adc     #$2c
6053: 85 b2                        sta     engine_sound_ctr?+1
6055: 90 0f                        bcc     :NoSound
6057: e6 b3                        inc     engine_sound_ctr?+2
6059: a5 cc                        lda     engine_sound_enable
605b: f0 09                        beq     :NoSound
605d: a5 b3                        lda     engine_sound_ctr?+2
605f: 25 b1                        and     engine_sound_ctr?
6061: d0 03                        bne     :NoSound
6063: ad 30 c0                     lda     SPKR
6066: 20 7f 7f     :NoSound        jsr     Return7f7f
                   ; Reset the velocity-change counter, and update the state so that we don't try
                   ; to change the velocity again if this isn't a ship.
6069: bd 68 9b     :ResetVelChgCtr lda     vel_change_intvl_max,x
606c: d0 09                        bne     :IsShip           ;nonzero for enemy ships
606e: a9 01                        lda     #$01
6070: 9d 18 9b                     sta     obj_activity_state,x ;not enemy ship, mark as "don't update velocity"
6073: ea                           nop
6074: 4c 8d 60                     jmp     :MoveStuff

6077: 85 86        :IsShip         sta     ]rng_limit        ;use value as RNG limit
6079: a9 00                        lda     #$00
607b: 85 87                        sta     ]rng_limit+1
607d: 85 88                        sta     ]rng_limit_mode
607f: 20 b0 7b                     jsr     GenRandom         ;get value in $8a-8b
6082: 18                           clc
6083: a5 8a                        lda     ]rng_result
6085: 69 02                        adc     #$02              ;add 2
6087: 9d 90 9b                     sta     vel_change_ctr,x  ;set counter
608a: 20 7f 7f                     jsr     Return7f7f
                   ; 
                   ; Calculate object movement.
                   ; 
                   ]move_abs       .var    $86    {addr/2}
                   ]table2_val2?   .var    $88    {addr/2}
                   ]table2_val1?   .var    $8a    {addr/1}
                   ]lz_count       .var    $8b    {addr/1}
                   ]turn_angle?    .var    $8c    {addr/2}

608d: bd 88 9e     :MoveStuff      lda     obj_move_xc_hi,x  ;get high byte of X move
6090: 10 10                        bpl     :IsPosX           ;positive, branch
6092: 38                           sec
6093: a9 00                        lda     #$00              ;compute absolute value (0 - value)
6095: fd 60 9e                     sbc     obj_move_xc_lo,x
6098: 85 86                        sta     ]move_abs
609a: a9 00                        lda     #$00
609c: fd 88 9e                     sbc     obj_move_xc_hi,x
609f: 4c aa 60                     jmp     :ContX

60a2: bc 60 9e     :IsPosX         ldy     obj_move_xc_lo,x  ;copy low byte
60a5: 84 86                        sty     ]move_abs
60a7: bd 88 9e                     lda     obj_move_xc_hi,x  ;set flags for high byte
60aa: ea           :ContX          nop
60ab: d0 18                        bne     :BigX             ;high byte nonzero, branch
60ad: a4 86                        ldy     ]move_abs         ;get low byte
60af: b9 00 b9                     lda     clz_table,y       ;count leading zeroes
60b2: 18                           clc
60b3: 69 08                        adc     #$08              ;add 8 for the high byte
60b5: 85 8b                        sta     ]lz_count         ;save leading zero count
60b7: 69 a4                        adc     #>math_tab2_base?-$800 ;compute pointer (without the +8)
60b9: 85 13                        sta     math_tab_ptr12+1
60bb: a4 86                        ldy     ]move_abs         ;(?)
60bd: b1 12                        lda     (math_tab_ptr12),y ;get value from table
60bf: 85 8a                        sta     ]table2_val1?
60c1: ea                           nop
60c2: 4c df 60                     jmp     :GotThingX

60c5: 85 87        :BigX           sta     ]move_abs+1       ;save high byte
60c7: a8                           tay
60c8: b9 00 b9                     lda     clz_table,y       ;count leading zeroes
60cb: a8                           tay
60cc: 85 8b                        sta     ]lz_count         ;save leading zero count
60ce: 18                           clc
60cf: 69 ac                        adc     #>math_tab2_base? ;compute pointer
60d1: 85 13                        sta     math_tab_ptr12+1
60d3: a5 86                        lda     ]move_abs         ;get low byte
60d5: 39 d5 00                     and     bit_mask_left9,y  ;mask off overlapping bits
60d8: 05 87                        ora     ]move_abs+1       ;merge with high byte
60da: a8                           tay                       ;use as index
60db: b1 12                        lda     (math_tab_ptr12),y ;get value from table
60dd: 85 8a                        sta     ]table2_val1?
60df: ea           :GotThingX      nop
60e0: 18                           clc
60e1: a4 8a                        ldy     ]table2_val1?
60e3: b9 00 b5                     lda     turn_map_lo?,y
60e6: 65 9a                        adc     joy_yaw_angle     ;add joystick yaw magnitude
60e8: 85 8c                        sta     ]turn_angle?
60ea: a5 9b                        lda     joy_yaw_angle+1
60ec: e5 8b                        sbc     ]lz_count
60ee: 30 21                        bmi     :SlowYaw
60f0: 85 8d                        sta     ]turn_angle?+1
60f2: 38                           sec
60f3: ea                           nop
60f4: 69 ac                        adc     #>math_tab2_base?
60f6: 85 15                        sta     math_tab_ptr14+1
60f8: a4 8c                        ldy     ]turn_angle?
60fa: b9 00 17                     lda     math_tab1_lastpg?,y
60fd: a8                           tay
60fe: b1 14                        lda     (math_tab_ptr14),y
6100: 85 89                        sta     ]table2_val2?+1
6102: a4 8d                        ldy     ]turn_angle?+1
6104: 39 ef 00                     and     bit_mask_left8,y
6107: 85 88                        sta     ]table2_val2?
6109: a5 89                        lda     ]table2_val2?+1
610b: 39 e7 00                     and     bit_mask_right8,y
610e: 4c 2d 61                     jmp     L612D

6111: ea           :SlowYaw        nop
6112: 18                           clc
6113: 69 08                        adc     #$08
6115: 30 12                        bmi     :NoYaw
6117: 18                           clc
6118: 69 10                        adc     #>math_tab1_base?
611a: 85 15                        sta     math_tab_ptr14+1
611c: a4 8c                        ldy     ]turn_angle?
611e: a9 00                        lda     #$00
6120: 85 89                        sta     ]table2_val2?+1
6122: b1 14                        lda     (math_tab_ptr14),y
6124: 85 88                        sta     ]table2_val2?
6126: 4c 2f 61                     jmp     L612F

6129: a9 00        :NoYaw          lda     #$00
612b: 85 88                        sta     ]table2_val2?
612d: 85 89        L612D           sta     ]table2_val2?+1
                   ; Update Z movement with results.
612f: ea           L612F           nop
6130: bd 88 9e                     lda     obj_move_xc_hi,x
6133: 45 9c                        eor     joy_yaw_sign
6135: 10 2a                        bpl     L6161
6137: 18                           clc
6138: bd 10 9e                     lda     obj_move_zc_lo,x
613b: 65 88                        adc     ]table2_val2?
613d: 9d 10 9e                     sta     obj_move_zc_lo,x
6140: bd 38 9e                     lda     obj_move_zc_hi,x
6143: 65 89                        adc     ]table2_val2?+1
6145: 9d 38 9e                     sta     obj_move_zc_hi,x
6148: a5 bb                        lda     update_mvmt_flag
614a: f0 3c                        beq     :CalcY
614c: 18                           clc
614d: bd 30 9c                     lda     obj_move_zc2_lo,x
6150: 65 88                        adc     ]table2_val2?
6152: 9d 30 9c                     sta     obj_move_zc2_lo,x
6155: bd 58 9c                     lda     obj_move_zc2_hi,x
6158: 65 89                        adc     ]table2_val2?+1
615a: 9d 58 9c                     sta     obj_move_zc2_hi,x
615d: ea                           nop
615e: 4c 88 61                     jmp     :CalcY

6161: 38           L6161           sec
6162: bd 10 9e                     lda     obj_move_zc_lo,x
6165: e5 88                        sbc     ]table2_val2?
6167: 9d 10 9e                     sta     obj_move_zc_lo,x
616a: bd 38 9e                     lda     obj_move_zc_hi,x
616d: e5 89                        sbc     ]table2_val2?+1
616f: 9d 38 9e                     sta     obj_move_zc_hi,x
6172: a5 bb                        lda     update_mvmt_flag  ;object changes direction sometimes?
6174: f0 12                        beq     :CalcY            ;no, skip this next part
6176: 38                           sec
6177: bd 30 9c                     lda     obj_move_zc2_lo,x
617a: e5 88                        sbc     ]table2_val2?
617c: 9d 30 9c                     sta     obj_move_zc2_lo,x
617f: bd 58 9c                     lda     obj_move_zc2_hi,x
6182: e5 89                        sbc     ]table2_val2?+1
6184: 9d 58 9c                     sta     obj_move_zc2_hi,x
6187: ea                           nop
                   ; 
                   ; Repeat for Y coordinate.
                   ; 
6188: bd d8 9e     :CalcY          lda     obj_move_yc_hi,x
618b: 10 10                        bpl     :PosY
618d: 38                           sec
618e: a9 00                        lda     #$00
6190: fd b0 9e                     sbc     obj_move_yc_lo,x
6193: 85 86                        sta     ]move_abs
6195: a9 00                        lda     #$00
6197: fd d8 9e                     sbc     obj_move_yc_hi,x
619a: 4c a5 61                     jmp     :ContY

619d: bc b0 9e     :PosY           ldy     obj_move_yc_lo,x
61a0: 84 86                        sty     ]move_abs
61a2: bd d8 9e                     lda     obj_move_yc_hi,x
61a5: ea           :ContY          nop
61a6: d0 18                        bne     L61C0
61a8: a4 86                        ldy     ]move_abs
61aa: b9 00 b9                     lda     clz_table,y
61ad: 18                           clc
61ae: 69 08                        adc     #$08
61b0: 85 8b                        sta     ]lz_count
61b2: 69 a4                        adc     #>math_tab2_base?-$800
61b4: 85 13                        sta     math_tab_ptr12+1
61b6: a4 86                        ldy     ]move_abs
61b8: b1 12                        lda     (math_tab_ptr12),y
61ba: 85 8a                        sta     ]table2_val1?
61bc: ea                           nop
61bd: 4c da 61                     jmp     L61DA

61c0: 85 87        L61C0           sta     ]move_abs+1
61c2: a8                           tay
61c3: b9 00 b9                     lda     clz_table,y
61c6: a8                           tay
61c7: 85 8b                        sta     ]lz_count
61c9: 18                           clc
61ca: 69 ac                        adc     #>math_tab2_base?
61cc: 85 13                        sta     math_tab_ptr12+1
61ce: a5 86                        lda     ]move_abs
61d0: 39 d5 00                     and     bit_mask_left9,y
61d3: 05 87                        ora     ]move_abs+1
61d5: a8                           tay
61d6: b1 12                        lda     (math_tab_ptr12),y
61d8: 85 8a                        sta     ]table2_val1?
61da: ea           L61DA           nop
61db: 18                           clc
61dc: a4 8a                        ldy     ]table2_val1?
61de: b9 00 b5                     lda     turn_map_lo?,y
61e1: 65 9d                        adc     joy_pitch_angle
61e3: 85 8c                        sta     ]turn_angle?
61e5: a5 9e                        lda     joy_pitch_angle+1
61e7: e5 8b                        sbc     ]lz_count
61e9: 30 21                        bmi     :SlowPitch
61eb: 85 8d                        sta     ]turn_angle?+1
61ed: 38                           sec
61ee: ea                           nop
61ef: 69 ac                        adc     #>math_tab2_base?
61f1: 85 15                        sta     math_tab_ptr14+1
61f3: a4 8c                        ldy     ]turn_angle?
61f5: b9 00 17                     lda     math_tab1_lastpg?,y
61f8: a8                           tay
61f9: b1 14                        lda     (math_tab_ptr14),y
61fb: 85 89                        sta     ]table2_val2?+1
61fd: a4 8d                        ldy     ]turn_angle?+1
61ff: 39 ef 00                     and     bit_mask_left8,y
6202: 85 88                        sta     ]table2_val2?
6204: a5 89                        lda     ]table2_val2?+1
6206: 39 e7 00                     and     bit_mask_right8,y
6209: 4c 28 62                     jmp     L6228

620c: ea           :SlowPitch      nop
620d: 18                           clc
620e: 69 08                        adc     #$08
6210: 30 12                        bmi     :NoPitch
6212: 18                           clc
6213: 69 10                        adc     #>math_tab1_base?
6215: 85 15                        sta     math_tab_ptr14+1
6217: a4 8c                        ldy     ]turn_angle?
6219: a9 00                        lda     #$00
621b: 85 89                        sta     ]table2_val2?+1
621d: b1 14                        lda     (math_tab_ptr14),y
621f: 85 88                        sta     ]table2_val2?
6221: 4c 2a 62                     jmp     L622A

6224: a9 00        :NoPitch        lda     #$00
6226: 85 88                        sta     ]table2_val2?
6228: 85 89        L6228           sta     ]table2_val2?+1
                   ; Update Z movement with results.
622a: ea           L622A           nop
622b: bd d8 9e                     lda     obj_move_yc_hi,x
622e: 45 9f                        eor     joy_pitch_sign
6230: 10 2a                        bpl     L625C
6232: 18                           clc
6233: bd 10 9e                     lda     obj_move_zc_lo,x
6236: 65 88                        adc     ]table2_val2?
6238: 9d 10 9e                     sta     obj_move_zc_lo,x
623b: bd 38 9e                     lda     obj_move_zc_hi,x
623e: 65 89                        adc     ]table2_val2?+1
6240: 9d 38 9e                     sta     obj_move_zc_hi,x
6243: a5 bb                        lda     update_mvmt_flag
6245: f0 3c                        beq     L6283
6247: 18                           clc
6248: bd 30 9c                     lda     obj_move_zc2_lo,x
624b: 65 88                        adc     ]table2_val2?
624d: 9d 30 9c                     sta     obj_move_zc2_lo,x
6250: bd 58 9c                     lda     obj_move_zc2_hi,x
6253: 65 89                        adc     ]table2_val2?+1
6255: 9d 58 9c                     sta     obj_move_zc2_hi,x
6258: ea                           nop
6259: 4c 83 62                     jmp     L6283

625c: 38           L625C           sec
625d: bd 10 9e                     lda     obj_move_zc_lo,x
6260: e5 88                        sbc     ]table2_val2?
6262: 9d 10 9e                     sta     obj_move_zc_lo,x
6265: bd 38 9e                     lda     obj_move_zc_hi,x
6268: e5 89                        sbc     ]table2_val2?+1
626a: 9d 38 9e                     sta     obj_move_zc_hi,x
626d: a5 bb                        lda     update_mvmt_flag
626f: f0 12                        beq     L6283
6271: 38                           sec
6272: bd 30 9c                     lda     obj_move_zc2_lo,x
6275: e5 88                        sbc     ]table2_val2?
6277: 9d 30 9c                     sta     obj_move_zc2_lo,x
627a: bd 58 9c                     lda     obj_move_zc2_hi,x
627d: e5 89                        sbc     ]table2_val2?+1
627f: 9d 58 9c                     sta     obj_move_zc2_hi,x
6282: ea                           nop
                   ; 
                   ; Repeat for Z coordinate.
                   ; 
6283: bd 38 9e     L6283           lda     obj_move_zc_hi,x
6286: 10 10                        bpl     L6298
6288: 38                           sec
6289: a9 00                        lda     #$00
628b: fd 10 9e                     sbc     obj_move_zc_lo,x
628e: 85 86                        sta     ]move_abs
6290: a9 00                        lda     #$00
6292: fd 38 9e                     sbc     obj_move_zc_hi,x
6295: 4c a0 62                     jmp     L62A0

6298: bc 10 9e     L6298           ldy     obj_move_zc_lo,x
629b: 84 86                        sty     ]move_abs
629d: bd 38 9e                     lda     obj_move_zc_hi,x
62a0: ea           L62A0           nop
62a1: d0 18                        bne     L62BB
62a3: a4 86                        ldy     ]move_abs
62a5: b9 00 b9                     lda     clz_table,y
62a8: 18                           clc
62a9: 69 08                        adc     #$08
62ab: 85 8b                        sta     ]lz_count
62ad: 69 a4                        adc     #>math_tab2_base?-$800
62af: 85 13                        sta     math_tab_ptr12+1
62b1: a4 86                        ldy     ]move_abs
62b3: b1 12                        lda     (math_tab_ptr12),y
62b5: 85 8a                        sta     ]table2_val1?
62b7: ea                           nop
62b8: 4c d5 62                     jmp     L62D5

62bb: 85 87        L62BB           sta     ]move_abs+1
62bd: a8                           tay
62be: b9 00 b9                     lda     clz_table,y
62c1: a8                           tay
62c2: 85 8b                        sta     ]lz_count
62c4: 18                           clc
62c5: 69 ac                        adc     #>math_tab2_base?
62c7: 85 13                        sta     math_tab_ptr12+1
62c9: a5 86                        lda     ]move_abs
62cb: 39 d5 00                     and     bit_mask_left9,y
62ce: 05 87                        ora     ]move_abs+1
62d0: a8                           tay
62d1: b1 12                        lda     (math_tab_ptr12),y
62d3: 85 8a                        sta     ]table2_val1?
62d5: ea           L62D5           nop
62d6: 18                           clc
62d7: a4 8a                        ldy     ]table2_val1?
62d9: b9 00 b5                     lda     turn_map_lo?,y
62dc: 65 9a                        adc     joy_yaw_angle
62de: 85 8c                        sta     ]turn_angle?
62e0: a5 9b                        lda     joy_yaw_angle+1
62e2: e5 8b                        sbc     ]lz_count
62e4: 30 21                        bmi     :SlowYaw
62e6: 85 8d                        sta     ]turn_angle?+1
62e8: 38                           sec
62e9: ea                           nop
62ea: 69 ac                        adc     #>math_tab2_base?
62ec: 85 15                        sta     math_tab_ptr14+1
62ee: a4 8c                        ldy     ]turn_angle?
62f0: b9 00 17                     lda     math_tab1_lastpg?,y
62f3: a8                           tay
62f4: b1 14                        lda     (math_tab_ptr14),y
62f6: 85 89                        sta     ]table2_val2?+1
62f8: a4 8d                        ldy     ]turn_angle?+1
62fa: 39 ef 00                     and     bit_mask_left8,y
62fd: 85 88                        sta     ]table2_val2?
62ff: a5 89                        lda     ]table2_val2?+1
6301: 39 e7 00                     and     bit_mask_right8,y
6304: 4c 23 63                     jmp     L6323

6307: ea           :SlowYaw        nop
6308: 18                           clc
6309: 69 08                        adc     #$08
630b: 30 12                        bmi     :NoYaw
630d: 18                           clc
630e: 69 10                        adc     #>math_tab1_base?
6310: 85 15                        sta     math_tab_ptr14+1
6312: a4 8c                        ldy     ]turn_angle?
6314: a9 00                        lda     #$00
6316: 85 89                        sta     ]table2_val2?+1
6318: b1 14                        lda     (math_tab_ptr14),y
631a: 85 88                        sta     ]table2_val2?
631c: 4c 25 63                     jmp     L6325

631f: a9 00        :NoYaw          lda     #$00
6321: 85 88                        sta     ]table2_val2?
6323: 85 89        L6323           sta     ]table2_val2?+1
                   ; Update X/Y movement with results.
6325: ea           L6325           nop
6326: bd 38 9e                     lda     obj_move_zc_hi,x
6329: 45 9c                        eor     joy_yaw_sign
632b: 30 2a                        bmi     L6357
632d: 18                           clc
632e: bd 60 9e                     lda     obj_move_xc_lo,x
6331: 65 88                        adc     ]table2_val2?
6333: 9d 60 9e                     sta     obj_move_xc_lo,x
6336: bd 88 9e                     lda     obj_move_xc_hi,x
6339: 65 89                        adc     ]table2_val2?+1
633b: 9d 88 9e                     sta     obj_move_xc_hi,x
633e: a5 bb                        lda     update_mvmt_flag
6340: f0 3c                        beq     L637E
6342: 18                           clc
6343: bd 80 9c                     lda     obj_move_xc2_lo,x
6346: 65 88                        adc     ]table2_val2?
6348: 9d 80 9c                     sta     obj_move_xc2_lo,x
634b: bd a8 9c                     lda     obj_move_xc2_hi,x
634e: 65 89                        adc     ]table2_val2?+1
6350: 9d a8 9c                     sta     obj_move_xc2_hi,x
6353: ea                           nop
6354: 4c 7e 63                     jmp     L637E

6357: 38           L6357           sec
6358: bd 60 9e                     lda     obj_move_xc_lo,x
635b: e5 88                        sbc     ]table2_val2?
635d: 9d 60 9e                     sta     obj_move_xc_lo,x
6360: bd 88 9e                     lda     obj_move_xc_hi,x
6363: e5 89                        sbc     ]table2_val2?+1
6365: 9d 88 9e                     sta     obj_move_xc_hi,x
6368: a5 bb                        lda     update_mvmt_flag
636a: f0 12                        beq     L637E
636c: 38                           sec
636d: bd 80 9c                     lda     obj_move_xc2_lo,x
6370: e5 88                        sbc     ]table2_val2?
6372: 9d 80 9c                     sta     obj_move_xc2_lo,x
6375: bd a8 9c                     lda     obj_move_xc2_hi,x
6378: e5 89                        sbc     ]table2_val2?+1
637a: 9d a8 9c                     sta     obj_move_xc2_hi,x
637d: ea                           nop
637e: 18           L637E           clc
637f: 18                           clc
6380: a4 8a                        ldy     ]table2_val1?
6382: b9 00 b5                     lda     turn_map_lo?,y
6385: 65 9d                        adc     joy_pitch_angle
6387: 85 8c                        sta     ]turn_angle?
6389: a5 9e                        lda     joy_pitch_angle+1
638b: e5 8b                        sbc     ]lz_count
638d: 30 21                        bmi     :SlowPitch
638f: 85 8d                        sta     ]turn_angle?+1
6391: 38                           sec
6392: ea                           nop
6393: 69 ac                        adc     #>math_tab2_base?
6395: 85 15                        sta     math_tab_ptr14+1
6397: a4 8c                        ldy     ]turn_angle?
6399: b9 00 17                     lda     math_tab1_lastpg?,y
639c: a8                           tay
639d: b1 14                        lda     (math_tab_ptr14),y
639f: 85 89                        sta     ]table2_val2?+1
63a1: a4 8d                        ldy     ]turn_angle?+1
63a3: 39 ef 00                     and     bit_mask_left8,y
63a6: 85 88                        sta     ]table2_val2?
63a8: a5 89                        lda     ]table2_val2?+1
63aa: 39 e7 00                     and     bit_mask_right8,y
63ad: 4c cc 63                     jmp     L63CC

63b0: ea           :SlowPitch      nop
63b1: 18                           clc
63b2: 69 08                        adc     #$08
63b4: 30 12                        bmi     :NoPitch
63b6: 18                           clc
63b7: 69 10                        adc     #>math_tab1_base?
63b9: 85 15                        sta     math_tab_ptr14+1
63bb: a4 8c                        ldy     ]turn_angle?
63bd: a9 00                        lda     #$00
63bf: 85 89                        sta     ]table2_val2?+1
63c1: b1 14                        lda     (math_tab_ptr14),y
63c3: 85 88                        sta     ]table2_val2?
63c5: 4c ce 63                     jmp     L63CE

63c8: a9 00        :NoPitch        lda     #$00
63ca: 85 88                        sta     ]table2_val2?
63cc: 85 89        L63CC           sta     ]table2_val2?+1
63ce: ea           L63CE           nop
63cf: bd 38 9e                     lda     obj_move_zc_hi,x
63d2: 45 9f                        eor     joy_pitch_sign
63d4: 30 2a                        bmi     L6400
63d6: 18                           clc
63d7: bd b0 9e                     lda     obj_move_yc_lo,x
63da: 65 88                        adc     ]table2_val2?
63dc: 9d b0 9e                     sta     obj_move_yc_lo,x
63df: bd d8 9e                     lda     obj_move_yc_hi,x
63e2: 65 89                        adc     ]table2_val2?+1
63e4: 9d d8 9e                     sta     obj_move_yc_hi,x
63e7: a5 bb                        lda     update_mvmt_flag
63e9: f0 3c                        beq     L6427
63eb: 18                           clc
63ec: bd d0 9c                     lda     obj_move_yc2_lo,x
63ef: 65 88                        adc     ]table2_val2?
63f1: 9d d0 9c                     sta     obj_move_yc2_lo,x
63f4: bd f8 9c                     lda     obj_move_yc2_hi,x
63f7: 65 89                        adc     ]table2_val2?+1
63f9: 9d f8 9c                     sta     obj_move_yc2_hi,x
63fc: ea                           nop
63fd: 4c 27 64                     jmp     L6427

6400: 38           L6400           sec
6401: bd b0 9e                     lda     obj_move_yc_lo,x
6404: e5 88                        sbc     ]table2_val2?
6406: 9d b0 9e                     sta     obj_move_yc_lo,x
6409: bd d8 9e                     lda     obj_move_yc_hi,x
640c: e5 89                        sbc     ]table2_val2?+1
640e: 9d d8 9e                     sta     obj_move_yc_hi,x
6411: a5 bb                        lda     update_mvmt_flag
6413: f0 12                        beq     L6427
6415: 38                           sec
6416: bd d0 9c                     lda     obj_move_yc2_lo,x
6419: e5 88                        sbc     ]table2_val2?
641b: 9d d0 9c                     sta     obj_move_yc2_lo,x
641e: bd f8 9c                     lda     obj_move_yc2_hi,x
6421: e5 89                        sbc     ]table2_val2?+1
6423: 9d f8 9c                     sta     obj_move_yc2_hi,x
6426: ea                           nop
6427: 20 7f 7f     L6427           jsr     Return7f7f
642a: 18                           clc                       ;do sound stuff
642b: a5 b2                        lda     engine_sound_ctr?+1
642d: 69 30                        adc     #$30
642f: 85 b2                        sta     engine_sound_ctr?+1
6431: 90 0f                        bcc     GetFirstElemIndex
6433: e6 b3                        inc     engine_sound_ctr?+2
6435: a5 cc                        lda     engine_sound_enable
6437: f0 09                        beq     GetFirstElemIndex
6439: a5 b3                        lda     engine_sound_ctr?+2
643b: 25 b1                        and     engine_sound_ctr?
643d: d0 03                        bne     GetFirstElemIndex
643f: ad 30 c0                     lda     SPKR
                   ; 
                   ; Extracts the index of an object's first element into X-reg and ZP.
                   ; 
                   ; On entry:
                   ;   X-reg: object index
                   ; 
                   ; On exit:
                   ;   $64 and X-reg: element index
                   ; 
                   GetFirstElemIndex
6442: bd 00 9a                     lda     obj_first_elem_index,x
6445: aa                           tax
6446: 85 64                        sta     cur_elem_index
6448: 60                           rts

6449: 3d 3d 3d 3d+                 .junk   12

                   ; 
                   ; Updates element coordinates with object movement vector, and generates screen
                   ; coordinates for use by the render functions.
                   ; 
                   ; Player movement -- pitch/yaw and forward speed -- are applied evenly to all
                   ; element coordinates here.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ; 
                   ; On exit:
                   ;   $70: new value for modified element type
                   ;   $7e: screen top (0-191)
                   ;   $80: screen bottom (0-191)
                   ;   $82: abs value of screen left (0-139)
                   ;   $84: abs value of screen right (0-139)
                   ;   X-reg preserved
                   ; 
                   ; (Not all coordinates may be set, e.g. points only need top/left.)
                   ; 
                   • Clear variables
                   ]new_zpos       .var    $86    {addr/2}
                   ]zpos_sign      .var    $8c    {addr/1}

6455: a9 00        UpdateElement   lda     #$00
6457: 85 7c                        sta     no_draw_elem_flag? ;clear flag
6459: 85 70                        sta     mod_elem_type     ;set mod type to point
645b: 85 76                        sta     clamped_lr_count  ;init counters
645d: 85 78                        sta     clamped_tb_count
645f: 85 7a                        sta     elem_bad_z_flag?  ;clear flag
6461: a5 c8                        lda     sound_counters
6463: f0 03                        beq     :NoSound
6465: ad 30 c0                     lda     SPKR
6468: a9 ad        :NoSound        lda     #INSTR_LDA_ABS
646a: 20 4c 7b                     jsr     ModDrwEraVrtRct   ;suppress drawing (why?)
646d: a5 72                        lda     no_draw_obj_flag  ;check flag
646f: f0 0e                        beq     :DoDraw           ;not set, branch
6471: e6 7c                        inc     no_draw_elem_flag?
6473: 4c 93 6b                     jmp     :RestoreRts

                   ; Element crossed "far" plane ($8000), do not draw.
6476: e6 7a        :NoDrawZC       inc     elem_bad_z_flag?
6478: e6 7c                        inc     no_draw_elem_flag?
647a: e6 72                        inc     no_draw_obj_flag
647c: 4c 93 6b                     jmp     :RestoreRts

                   ; Update Z coordinate with object and player movement.  +Z is away from viewer. 
                   ; If the Z coordinate is >= $8000, it has disappeared into the distance.  If
                   ; it's <= 0, we've flown past it or into it.
                   ; 
                   ; Note this does not take joystick angles into account.
647f: 18           :DoDraw         clc
6480: a4 62                        ldy     cur_obj_index     ;get object index
6482: bd 40 a1                     lda     elem_zpos_lo,x    ;get current Z position
6485: 79 10 9e                     adc     obj_move_zc_lo,y  ;add object movement
6488: 85 86                        sta     ]new_zpos         ;save in ZP
648a: bd 80 a1                     lda     elem_zpos_hi,x
648d: 85 8c                        sta     ]zpos_sign        ;sign of zpos; note does not include player movement
648f: 79 38 9e                     adc     obj_move_zc_hi,y  ;repeat for high byte
6492: 70 e2                        bvs     :NoDrawZC         ;branch if we passed $8000 (signed overflow)
6494: 85 87                        sta     ]new_zpos+1
6496: a5 86                        lda     ]new_zpos         ;subtract player's speed
6498: 38                           sec
6499: e5 98                        sbc     adj_fwd_speed
649b: 9d 40 a1                     sta     elem_zpos_lo,x    ;update value in table
649e: 85 86                        sta     ]new_zpos         ;update value in ZP
64a0: a8                           tay
64a1: a5 87                        lda     ]new_zpos+1
64a3: e5 99                        sbc     adj_fwd_speed+1   ;repeat for high byte
64a5: 70 cf                        bvs     :NoDrawZC         ;branch if we passed $8000 (shouldn't be possible
64a7: 9d 80 a1                     sta     elem_zpos_hi,x    ; unless we can move backward)
64aa: ea                           nop
64ab: 85 87                        sta     ]new_zpos+1
64ad: 30 03                        bmi     :CheckFlewInto    ;if high byte negative, it's behind us
64af: 4c df 64                     jmp     :CheckZZero       ;object somewhere in front of us, continue on

64b2: a5 8c        :CheckFlewInto  lda     ]zpos_sign        ;check the Z position before the player moved
64b4: 10 06                        bpl     :FlewInto         ;was positive, player flew into element plane; branch
64b6: 20 7f 7f                     jsr     Return7f7f        ;was negative, object flew into player... distinction
64b9: 4c aa 69                     jmp     :ObjectBehind     ; w/o a diff, but we know it's not base/portal

64bc: a4 62        :FlewInto       ldy     cur_obj_index     ;get index of object we may have flown into
64be: 20 7f 7f                     jsr     Return7f7f
64c1: a9 00                        lda     #$00
64c3: 8d 98 6d                     sta     time_portal_fail_ctr ;reset time portal fail counter
64c6: b9 a0 9a                     lda     obj_shape_uid,y   ;get shape unique ID
64c9: 29 f0                        and     #$f0
64cb: c9 f0                        cmp     #$f0              ;(not used by game?)
64cd: f0 0d                        beq     :NotHostile
64cf: c9 50                        cmp     #$50              ;time portal boundary?
64d1: f0 09                        beq     :NotHostile       ;yes, branch
64d3: c9 60                        cmp     #$60              ;friendly base or time portal?
64d5: f0 05                        beq     :NotHostile       ;yes, branch
64d7: e6 f8                        inc     elem_collision_flag ;possibly bumped an enemy ship, base, or projectile
64d9: 20 7f 7f                     jsr     Return7f7f
64dc: 4c aa 69     :NotHostile     jmp     :ObjectBehind

64df: d0 12        :CheckZZero     bne     :CheckSameZ       ;high byte nonzero, branch
64e1: a4 86                        ldy     ]new_zpos         ;get low byte
64e3: d0 0e                        bne     :CheckSameZ       ;nonzero, branch
64e5: e6 7c                        inc     no_draw_elem_flag? ;we're at Z=0, don't draw this element
64e7: a9 ff                        lda     #$ff
64e9: 85 86                        sta     ]new_zpos         ;set Z position to -1
64eb: 85 87                        sta     ]new_zpos+1
64ed: 20 7f 7f                     jsr     Return7f7f
64f0: 4c bc 64                     jmp     :FlewInto         ;jump to "we flew into something" code

                   ; Object is in front of us.
                   ; 
                   ; Check to see if the previous element we processed had the same Z coordinate. 
                   ; If so, we can avoid repeating some of the calculations.
64f3: 20 7f 7f     :CheckSameZ     jsr     Return7f7f
64f6: c5 c6                        cmp     prev_zpos+1       ;does high byte of new_zpos match previous?
64f8: d0 0b                        bne     :MismatchHi       ;no, branch
64fa: c4 c5                        cpy     prev_zpos         ;does low byte match?
64fc: d0 09                        bne     :MismatchLo       ;no, branch
64fe: a5 be                        lda     prev_scale_tab_ptr11 ;match; get previous pointer value
6500: 85 13                        sta     math_tab_ptr12+1  ; and store in pointer
6502: 4c 13 66                     jmp     :SkipZCalc        ;skip the following calculation

                   ; Previous Z coord didn't match, perform calculations.
                   ; 
                   ; Remember that all movement is calculated as deltas, not absolutes, and that
                   ; everything is in eye space.  If an enemy ship moved 10 units to the left, we
                   ; shift it 10 units, regardless of position.  If we rotated 5 degrees, however,
                   ; the distance from the viewer determines how many units it moves.
                   ; 
                   ; The amount of movement is the same for all points with the same Z coordinate. 
                   ; In a "true" 3D system that wouldn't be the case, but Epoch keeps all elements
                   ; parallel to the view plane.  So when we rotate left, the elements move right,
                   ; and effectively rotate away from the viewer to maintain their parallel
                   ; orientation.
6505: 85 c6        :MismatchHi     sta     prev_zpos+1       ;save new_zpos+1
6507: 84 c5        :MismatchLo     sty     prev_zpos         ;save new_zpos
6509: a5 87                        lda     ]new_zpos+1
650b: d0 20                        bne     :BigZ
650d: a4 86                        ldy     ]new_zpos
650f: b9 00 b9                     lda     clz_table,y
6512: a8                           tay
6513: 18                           clc
6514: 69 08                        adc     #$08
6516: 85 bd                        sta     zcoord_clz
6518: 69 a4                        adc     #>math_tab2_base?-$800
651a: 85 13                        sta     math_tab_ptr12+1
651c: ad a7 6d                     lda     speed_fraction
651f: 39 d5 00                     and     bit_mask_left9,y
6522: 05 86                        ora     ]new_zpos
6524: a8                           tay
6525: b1 12                        lda     (math_tab_ptr12),y
6527: 85 bc                        sta     zcoord_factor
6529: ea                           nop
652a: 4c 47 65                     jmp     :CalcYaw

652d: 85 87        :BigZ           sta     ]new_zpos+1
652f: a8                           tay
6530: b9 00 b9                     lda     clz_table,y
6533: a8                           tay
6534: 85 bd                        sta     zcoord_clz
6536: 18                           clc
6537: 69 ac                        adc     #>math_tab2_base?
6539: 85 13                        sta     math_tab_ptr12+1
653b: a5 86                        lda     ]new_zpos
653d: 39 d5 00                     and     bit_mask_left9,y
6540: 05 87                        ora     ]new_zpos+1
6542: a8                           tay
6543: b1 12                        lda     (math_tab_ptr12),y
6545: 85 bc                        sta     zcoord_factor
                   ; Compute movement delta (in eye coordinates) caused by player yaw (joystick
                   ; horizontal axis).
                   ]yaw_thing?     .var    $8c    {addr/2}
                   ]yaw_move       .var    $94    {addr/2}

6547: ea           :CalcYaw        nop
6548: 20 7f 7f                     jsr     Return7f7f
654b: a5 13                        lda     math_tab_ptr12+1
654d: 85 be                        sta     prev_scale_tab_ptr11
654f: 18                           clc
6550: a4 bc                        ldy     zcoord_factor
6552: b9 00 b5                     lda     turn_map_lo?,y
6555: 65 9a                        adc     joy_yaw_angle
6557: 85 8c                        sta     ]yaw_thing?
6559: a5 9b                        lda     joy_yaw_angle+1
655b: e5 bd                        sbc     zcoord_clz
655d: 30 25                        bmi     :SlowYaw
655f: 85 8d                        sta     ]yaw_thing?+1
6561: 38                           sec
6562: ea                           nop
6563: 69 ac                        adc     #>math_tab2_base?
6565: 85 15                        sta     math_tab_ptr14+1
6567: a4 8c                        ldy     ]yaw_thing?
6569: b9 00 17                     lda     math_tab1_lastpg?,y
656c: a8                           tay
656d: b1 14                        lda     (math_tab_ptr14),y
656f: 85 95                        sta     ]yaw_move+1
6571: a4 8d                        ldy     ]yaw_thing?+1
6573: 39 ef 00                     and     bit_mask_left8,y
6576: 45 9c                        eor     joy_yaw_sign
6578: 85 94                        sta     ]yaw_move
657a: a5 95                        lda     ]yaw_move+1
657c: 39 e7 00                     and     bit_mask_right8,y
657f: 45 9c                        eor     joy_yaw_sign
6581: 4c a0 65                     jmp     L65A0

6584: ea           :SlowYaw        nop
6585: 18                           clc
6586: 69 08                        adc     #$08
6588: 30 12                        bmi     :NoYaw
658a: 18                           clc
658b: 69 10                        adc     #>math_tab1_base?
658d: 85 15                        sta     math_tab_ptr14+1
658f: a4 8c                        ldy     ]yaw_thing?
6591: a5 9c                        lda     joy_yaw_sign
6593: 85 95                        sta     ]yaw_move+1
6595: 51 14                        eor     (math_tab_ptr14),y
6597: 85 94                        sta     ]yaw_move
6599: 4c a2 65                     jmp     :CalcPitch

659c: a9 00        :NoYaw          lda     #$00
659e: 85 94                        sta     ]yaw_move
65a0: 85 95        L65A0           sta     ]yaw_move+1
                   ; Compute movement delta (in eye coordinates) caused by player pitch (joystick
                   ; vertical axis).
                   ]pitch_thing?   .var    $8c    {addr/2}
                   ]pitch_move     .var    $96    {addr/2}

65a2: ea           :CalcPitch      nop
65a3: 18                           clc
65a4: 18                           clc
65a5: a4 bc                        ldy     zcoord_factor
65a7: b9 00 b5                     lda     turn_map_lo?,y
65aa: 65 9d                        adc     joy_pitch_angle
65ac: 85 8c                        sta     ]pitch_thing?
65ae: a5 9e                        lda     joy_pitch_angle+1
65b0: e5 bd                        sbc     zcoord_clz
65b2: 30 25                        bmi     :SlowPitch
65b4: 85 8d                        sta     ]pitch_thing?+1
65b6: 38                           sec
65b7: ea                           nop
65b8: 69 ac                        adc     #>math_tab2_base?
65ba: 85 15                        sta     math_tab_ptr14+1
65bc: a4 8c                        ldy     ]pitch_thing?
65be: b9 00 17                     lda     math_tab1_lastpg?,y
65c1: a8                           tay
65c2: b1 14                        lda     (math_tab_ptr14),y
65c4: 85 97                        sta     ]pitch_move+1
65c6: a4 8d                        ldy     ]pitch_thing?+1
65c8: 39 ef 00                     and     bit_mask_left8,y
65cb: 45 9f                        eor     joy_pitch_sign
65cd: 85 96                        sta     ]pitch_move
65cf: a5 97                        lda     ]pitch_move+1
65d1: 39 e7 00                     and     bit_mask_right8,y
65d4: 45 9f                        eor     joy_pitch_sign
65d6: 4c f5 65                     jmp     L65F5

65d9: ea           :SlowPitch      nop
65da: 18                           clc
65db: 69 08                        adc     #$08
65dd: 30 12                        bmi     :NoPitch
65df: 18                           clc
65e0: 69 10                        adc     #>math_tab1_base?
65e2: 85 15                        sta     math_tab_ptr14+1
65e4: a4 8c                        ldy     ]pitch_thing?
65e6: a5 9f                        lda     joy_pitch_sign
65e8: 85 97                        sta     ]pitch_move+1
65ea: 51 14                        eor     (math_tab_ptr14),y
65ec: 85 96                        sta     ]pitch_move
65ee: 4c f7 65                     jmp     L65F7

65f1: a9 00        :NoPitch        lda     #$00
65f3: 85 96                        sta     ]pitch_move
65f5: 85 97        L65F5           sta     ]pitch_move+1
65f7: ea           L65F7           nop
                   ; 
65f8: 20 7f 7f                     jsr     Return7f7f
65fb: 18                           clc                       ;do sound stuff
65fc: a5 b2                        lda     engine_sound_ctr?+1
65fe: 69 0d                        adc     #$0d
6600: 85 b2                        sta     engine_sound_ctr?+1
6602: 90 0f                        bcc     :SkipZCalc
6604: e6 b3                        inc     engine_sound_ctr?+2
6606: a5 cc                        lda     engine_sound_enable
6608: f0 09                        beq     :SkipZCalc
660a: a5 b3                        lda     engine_sound_ctr?+2
660c: 25 b1                        and     engine_sound_ctr?
660e: d0 03                        bne     :SkipZCalc
6610: ad 30 c0                     lda     SPKR
                   ; Jump here if the previous element had the same Z coord.
6613: 18           :SkipZCalc      clc                       ;do sound stuff
6614: a5 b2                        lda     engine_sound_ctr?+1
6616: 69 23                        adc     #$23
6618: 85 b2                        sta     engine_sound_ctr?+1
661a: 90 0f                        bcc     :NoSound2
661c: e6 b3                        inc     engine_sound_ctr?+2
661e: a5 cc                        lda     engine_sound_enable
6620: f0 09                        beq     :NoSound2
6622: a5 b3                        lda     engine_sound_ctr?+2
6624: 25 b1                        and     engine_sound_ctr?
6626: d0 03                        bne     :NoSound2
6628: ad 30 c0                     lda     SPKR
                   ; 
                   ; Update element coordinates, and calculate screen coordinates.  Start with the
                   ; left.
                   ; 
                   ]scrn_yc_top    .var    $7e    {addr/1}
                   ]scrn_yc_btm    .var    $80    {addr/1}
                   ]scrn_xc_lft_abs .var   $82    {addr/1}
                   ]scrn_xc_rgt_abs .var   $84    {addr/1}
                   ]updated_coord? .var    $8c    {addr/2}

662b: 18           :NoSound2       clc
662c: bd c0 a1                     lda     elem_left_lo,x    ;get left coordinate, low byte
662f: 65 94                        adc     ]yaw_move         ;add movement from joystick
6631: a8                           tay                       ;hold in Y-reg
6632: bd 00 a2                     lda     elem_left_hi,x    ;get high byte
6635: 65 95                        adc     ]yaw_move+1       ;add joystick movement
6637: 85 8f                        sta     move_tmp+1
6639: 70 32                        bvs     :OffScreenLeft
663b: 18                           clc
663c: 98                           tya
663d: a4 62                        ldy     cur_obj_index
663f: 79 60 9e                     adc     obj_move_xc_lo,y
6642: 9d c0 a1                     sta     elem_left_lo,x
6645: 85 8c                        sta     ]updated_coord?
6647: a5 8f                        lda     move_tmp+1
6649: 79 88 9e                     adc     obj_move_xc_hi,y
664c: 70 1f                        bvs     :OffScreenLeft
664e: 9d 00 a2                     sta     elem_left_hi,x
6651: 30 2c                        bmi     :NegLeft
6653: a4 7c                        ldy     no_draw_elem_flag?
6655: d0 1b                        bne     :ZeroLeft1
6657: 85 8d                        sta     ]updated_coord?+1
6659: ea                           nop
665a: a5 8c                        lda     ]updated_coord?
665c: c5 86                        cmp     ]new_zpos
665e: a5 8d                        lda     ]updated_coord?+1
6660: e5 87                        sbc     ]new_zpos+1
6662: ea                           nop
6663: 30 12                        bmi     :Jmp_LeftBoundsOk ;good, branch
6665: e6 76        :LeftBoundsBad  inc     clamped_lr_count
6667: a9 8a                        lda     #138              ;clamp to left edge of screen
6669: a4 7a                        ldy     elem_bad_z_flag?  ;are we drawing this at all?
666b: f0 07                        beq     :ConstLeft        ;yes, use constant value
666d: e6 72        :OffScreenLeft  inc     no_draw_obj_flag  ;no, inc some flags and set to zero
666f: e6 7c                        inc     no_draw_elem_flag?
6671: ea                           nop
6672: a9 00        :ZeroLeft1      lda     #$00
6674: 4c e5 66     :ConstLeft      jmp     :GotLeft

                   :Jmp_LeftBoundsOk
6677: 4c a8 66                     jmp     :LeftBoundsOk

667a: a9 00        :ZeroLeft2      lda     #$00
667c: 4c e5 66                     jmp     :GotLeft

667f: a5 7c        :NegLeft        lda     no_draw_elem_flag?
6681: d0 ef                        bne     :ZeroLeft1
6683: 38                           sec
6684: a9 00                        lda     #$00
6686: e5 8c                        sbc     ]updated_coord?
6688: 85 8c                        sta     ]updated_coord?
668a: a9 00                        lda     #$00
668c: fd 00 a2                     sbc     elem_left_hi,x
668f: 85 8d                        sta     ]updated_coord?+1
6691: a5 8c                        lda     ]updated_coord?
6693: c5 86                        cmp     ]new_zpos
6695: a5 8d                        lda     ]updated_coord?+1
6697: e5 87                        sbc     ]new_zpos+1
6699: ea                           nop
669a: 30 0c                        bmi     :LeftBoundsOk
669c: 4c 65 66                     jmp     :LeftBoundsBad

669f: a5 8c        :CheckLeftZero  lda     ]updated_coord?   ;high byte is zero, check low byte
66a1: d0 14                        bne     :LeftSmall        ;nonzero, branch
66a3: a9 00                        lda     #$00              ;left coord is zero, so screen coord is zero
66a5: 4c e5 66                     jmp     :GotLeft

66a8: a5 87        :LeftBoundsOk   lda     ]new_zpos+1
66aa: f0 f3                        beq     :CheckLeftZero
66ac: a4 bd                        ldy     zcoord_clz
66ae: a5 8c                        lda     ]updated_coord?
66b0: 39 d5 00                     and     bit_mask_left9,y
66b3: 05 8d                        ora     ]updated_coord?+1
66b5: f0 c3                        beq     :ZeroLeft2
66b7: a8           :LeftSmall      tay
66b8: b1 12                        lda     (math_tab_ptr12),y
66ba: a8                           tay
66bb: 18                           clc
66bc: b9 00 b5                     lda     turn_map_lo?,y
66bf: 69 1c                        adc     #$1c
66c1: 85 8e                        sta     move_tmp
66c3: b9 00 b6                     lda     turn_map_hi?,y
66c6: 69 07                        adc     #$07
66c8: 85 8f                        sta     move_tmp+1
66ca: 38                           sec
66cb: a5 8e                        lda     move_tmp
66cd: a4 bc                        ldy     zcoord_factor
66cf: f9 00 b5                     sbc     turn_map_lo?,y
66d2: 85 8e                        sta     move_tmp
66d4: a5 8f                        lda     move_tmp+1
66d6: f9 00 b6                     sbc     turn_map_hi?,y
66d9: ea                           nop
66da: 30 9e                        bmi     :ZeroLeft2
66dc: 38                           sec                       ;+1
66dd: 69 0f                        adc     #>math_tab1_base?-$100
66df: 85 15                        sta     math_tab_ptr14+1
66e1: a4 8e                        ldy     move_tmp
66e3: b1 14                        lda     (math_tab_ptr14),y
66e5: ea           :GotLeft        nop
66e6: 85 82                        sta     ]scrn_xc_lft_abs
                   ; Calculate top coordinate.
66e8: 18                           clc
66e9: bd 40 a2                     lda     elem_top_lo,x
66ec: 65 96                        adc     ]pitch_move
66ee: a8                           tay
66ef: bd 80 a2                     lda     elem_top_hi,x
66f2: 65 97                        adc     ]pitch_move+1
66f4: 85 8f                        sta     move_tmp+1
66f6: 70 32                        bvs     :OffScreenTop
66f8: 18                           clc
66f9: 98                           tya
66fa: a4 62                        ldy     cur_obj_index
66fc: 79 b0 9e                     adc     obj_move_yc_lo,y
66ff: 9d 40 a2                     sta     elem_top_lo,x
6702: 85 8c                        sta     ]updated_coord?
6704: a5 8f                        lda     move_tmp+1
6706: 79 d8 9e                     adc     obj_move_yc_hi,y
6709: 70 1f                        bvs     :OffScreenTop
670b: 9d 80 a2                     sta     elem_top_hi,x
670e: 30 2c                        bmi     :NegTop
6710: a4 7c                        ldy     no_draw_elem_flag?
6712: d0 1b                        bne     :ZeroTop1
6714: 85 8d                        sta     ]updated_coord?+1
6716: ea                           nop
6717: a5 8c                        lda     ]updated_coord?
6719: c5 86                        cmp     ]new_zpos
671b: a5 8d                        lda     ]updated_coord?+1
671d: e5 87                        sbc     ]new_zpos+1
671f: ea                           nop
6720: 30 12                        bmi     :Jmp_TopBoundsOk
6722: e6 78        :TopBoundsBad   inc     clamped_tb_count
6724: a9 5e                        lda     #94
6726: a4 7a                        ldy     elem_bad_z_flag?
6728: f0 07                        beq     :ConstTop
672a: e6 72        :OffScreenTop   inc     no_draw_obj_flag
672c: e6 7c                        inc     no_draw_elem_flag?
672e: ea                           nop
672f: a9 00        :ZeroTop1       lda     #$00
6731: 4c a2 67     :ConstTop       jmp     :GotTop

                   :Jmp_TopBoundsOk
6734: 4c 65 67                     jmp     :TopBoundsOk

6737: a9 00        :ZeropTop2      lda     #$00
6739: 4c a2 67                     jmp     :GotTop

673c: a5 7c        :NegTop         lda     no_draw_elem_flag?
673e: d0 ef                        bne     :ZeroTop1
6740: 38                           sec
6741: a9 00                        lda     #$00
6743: e5 8c                        sbc     ]updated_coord?
6745: 85 8c                        sta     ]updated_coord?
6747: a9 00                        lda     #$00
6749: fd 80 a2                     sbc     elem_top_hi,x
674c: 85 8d                        sta     ]updated_coord?+1
674e: a5 8c                        lda     ]updated_coord?
6750: c5 86                        cmp     ]new_zpos
6752: a5 8d                        lda     ]updated_coord?+1
6754: e5 87                        sbc     ]new_zpos+1
6756: ea                           nop
6757: 30 0c                        bmi     :TopBoundsOk
6759: 4c 22 67                     jmp     :TopBoundsBad

675c: a5 8c        :CheckTopZero   lda     ]updated_coord?
675e: d0 14                        bne     :TopSmall
6760: a9 00                        lda     #$00
6762: 4c a2 67                     jmp     :GotTop

6765: a5 87        :TopBoundsOk    lda     ]new_zpos+1
6767: f0 f3                        beq     :CheckTopZero
6769: a4 bd                        ldy     zcoord_clz
676b: a5 8c                        lda     ]updated_coord?
676d: 39 d5 00                     and     bit_mask_left9,y
6770: 05 8d                        ora     ]updated_coord?+1
6772: f0 c3                        beq     :ZeropTop2
6774: a8           :TopSmall       tay
6775: b1 12                        lda     (math_tab_ptr12),y
6777: a8                           tay
6778: 18                           clc
6779: b9 00 b5                     lda     turn_map_lo?,y
677c: 69 8e                        adc     #142              ;center?
677e: 85 8e                        sta     move_tmp
6780: b9 00 b6                     lda     turn_map_hi?,y
6783: 69 06                        adc     #$06
6785: 85 8f                        sta     move_tmp+1
6787: 38                           sec
6788: a5 8e                        lda     move_tmp
678a: a4 bc                        ldy     zcoord_factor
678c: f9 00 b5                     sbc     turn_map_lo?,y
678f: 85 8e                        sta     move_tmp
6791: a5 8f                        lda     move_tmp+1
6793: f9 00 b6                     sbc     turn_map_hi?,y
6796: ea                           nop
6797: 30 9e                        bmi     :ZeropTop2
6799: 38                           sec                       ;+1
679a: 69 0f                        adc     #>math_tab1_base?-$100
679c: 85 15                        sta     math_tab_ptr14+1
679e: a4 8e                        ldy     move_tmp
67a0: b1 14                        lda     (math_tab_ptr14),y
67a2: ea           :GotTop         nop
67a3: 20 7f 7f                     jsr     Return7f7f
67a6: bc 80 a2                     ldy     elem_top_hi,x
67a9: 30 08                        bmi     :NegTop2
67ab: 18                           clc
67ac: 69 60                        adc     #96               ;center?
67ae: 85 7e                        sta     ]scrn_yc_top
67b0: 4c ba 67                     jmp     :Cont

67b3: 49 ff        :NegTop2        eor     #$ff              ;invert
67b5: 18                           clc
67b6: 69 61                        adc     #97               ;center? (+1 because of negation)
67b8: 85 7e                        sta     ]scrn_yc_top
67ba: a5 c9        :Cont           lda     sound_counters+1  ;do sound stuff
67bc: f0 03                        beq     :NoSound
67be: ad 30 c0                     lda     SPKR              ;click for sfx (player cannon, ship explosion)
67c1: bd c0 9f     :NoSound        lda     elem_types,x      ;get declared element type
67c4: d0 0b                        bne     :NotPoint
                   ; This is a point, so we only need left/top.  Confirm we're visible and bail.
67c6: a5 76                        lda     clamped_lr_count
67c8: 05 78                        ora     clamped_tb_count
67ca: f0 02                        beq     :NoIncFlag
67cc: e6 7c                        inc     no_draw_elem_flag?
67ce: 4c 90 6b     :NoIncFlag      jmp     :RestoreRts1

67d1: 30 03        :NotPoint       bmi     :RectOrVl
67d3: 4c ca 68                     jmp     :DoHorizLine      ;horizontal line

                   ; This is a rectangle or vertical line.  Calculate bottom coordinate.
67d6: 85 91        :RectOrVl       sta     orig_elem_type    ;save element type in ZP
67d8: 18                           clc
67d9: bd 40 a3                     lda     elem_bottom_lo,x
67dc: 65 96                        adc     ]pitch_move
67de: a8                           tay
67df: bd 80 a3                     lda     elem_bottom_hi,x
67e2: 65 97                        adc     ]pitch_move+1
67e4: 85 8f                        sta     move_tmp+1
67e6: 70 32                        bvs     :OffScreenBot
67e8: 18                           clc
67e9: 98                           tya
67ea: a4 62                        ldy     cur_obj_index
67ec: 79 b0 9e                     adc     obj_move_yc_lo,y
67ef: 9d 40 a3                     sta     elem_bottom_lo,x
67f2: 85 8c                        sta     ]updated_coord?
67f4: a5 8f                        lda     move_tmp+1
67f6: 79 d8 9e                     adc     obj_move_yc_hi,y
67f9: 70 1f                        bvs     :OffScreenBot
67fb: 9d 80 a3                     sta     elem_bottom_hi,x
67fe: 30 2c                        bmi     :NegBot
6800: a4 7c                        ldy     no_draw_elem_flag?
6802: d0 1b                        bne     :ZeroBot1
6804: 85 8d                        sta     ]updated_coord?+1
6806: ea                           nop
6807: a5 8c                        lda     ]updated_coord?
6809: c5 86                        cmp     ]new_zpos
680b: a5 8d                        lda     ]updated_coord?+1
680d: e5 87                        sbc     ]new_zpos+1
680f: ea                           nop
6810: 30 12                        bmi     :Jump_BotBoundsOk
6812: e6 78        :BotBoundsBad   inc     clamped_tb_count
6814: a9 5e                        lda     #94               ;(used later)
6816: a4 7a                        ldy     elem_bad_z_flag?
6818: f0 07                        beq     :ConstBot
681a: e6 72        :OffScreenBot   inc     no_draw_obj_flag
681c: e6 7c                        inc     no_draw_elem_flag?
681e: ea                           nop
681f: a9 00        :ZeroBot1       lda     #$00
6821: 4c 92 68     :ConstBot       jmp     :GotBottom

                   :Jump_BotBoundsOk
6824: 4c 55 68                     jmp     :BotBoundsOk

6827: a9 00        :ZeroBot2       lda     #$00
6829: 4c 92 68                     jmp     :GotBottom

682c: a5 7c        :NegBot         lda     no_draw_elem_flag?
682e: d0 ef                        bne     :ZeroBot1
6830: 38                           sec
6831: a9 00                        lda     #$00
6833: e5 8c                        sbc     ]updated_coord?
6835: 85 8c                        sta     ]updated_coord?
6837: a9 00                        lda     #$00
6839: fd 80 a3                     sbc     elem_bottom_hi,x
683c: 85 8d                        sta     ]updated_coord?+1
683e: a5 8c                        lda     ]updated_coord?
6840: c5 86                        cmp     ]new_zpos
6842: a5 8d                        lda     ]updated_coord?+1
6844: e5 87                        sbc     ]new_zpos+1
6846: ea                           nop
6847: 30 0c                        bmi     :BotBoundsOk
6849: 4c 12 68                     jmp     :BotBoundsBad

684c: a5 8c        :CheckBotZero   lda     ]updated_coord?
684e: d0 14                        bne     :BotSmall
6850: a9 00                        lda     #$00
6852: 4c 92 68                     jmp     :GotBottom

6855: a5 87        :BotBoundsOk    lda     ]new_zpos+1
6857: f0 f3                        beq     :CheckBotZero
6859: a4 bd                        ldy     zcoord_clz
685b: a5 8c                        lda     ]updated_coord?
685d: 39 d5 00                     and     bit_mask_left9,y
6860: 05 8d                        ora     ]updated_coord?+1
6862: f0 c3                        beq     :ZeroBot2
6864: a8           :BotSmall       tay
6865: b1 12                        lda     (math_tab_ptr12),y
6867: a8                           tay
6868: 18                           clc
6869: b9 00 b5                     lda     turn_map_lo?,y
686c: 69 8e                        adc     #142
686e: 85 8e                        sta     move_tmp
6870: b9 00 b6                     lda     turn_map_hi?,y
6873: 69 06                        adc     #$06
6875: 85 8f                        sta     move_tmp+1
6877: 38                           sec
6878: a5 8e                        lda     move_tmp
687a: a4 bc                        ldy     zcoord_factor
687c: f9 00 b5                     sbc     turn_map_lo?,y
687f: 85 8e                        sta     move_tmp
6881: a5 8f                        lda     move_tmp+1
6883: f9 00 b6                     sbc     turn_map_hi?,y
6886: ea                           nop
6887: 30 9e                        bmi     :ZeroBot2
6889: 38                           sec                       ;+1
688a: 69 0f                        adc     #>math_tab1_base?-$100
688c: 85 15                        sta     math_tab_ptr14+1
688e: a4 8e                        ldy     move_tmp
6890: b1 14                        lda     (math_tab_ptr14),y
6892: ea           :GotBottom      nop
6893: 20 7f 7f                     jsr     Return7f7f
6896: bc 80 a3                     ldy     elem_bottom_hi,x
6899: 30 08                        bmi     :BotNeg
689b: 18                           clc
689c: 69 60                        adc     #96
689e: 85 80                        sta     ]scrn_yc_btm      ;bottom Y coord for vertical line?
68a0: 4c aa 68                     jmp     :BotCont

68a3: 49 ff        :BotNeg         eor     #$ff
68a5: 18                           clc
68a6: 69 61                        adc     #97
68a8: 85 80                        sta     ]scrn_yc_btm
68aa: c5 7e        :BotCont        cmp     ]scrn_yc_top      ;compare top to bottom
68ac: f0 08                        beq     :IsHline
68ae: a9 80                        lda     #$80
68b0: 85 70                        sta     mod_elem_type     ;set type to vline
68b2: ea                           nop
68b3: 4c bc 68                     jmp     :BotTbOk

68b6: a5 78        :IsHline        lda     clamped_tb_count
68b8: f0 02                        beq     :BotTbOk
68ba: e6 7c                        inc     no_draw_elem_flag?
68bc: 06 91        :BotTbOk        asl     orig_elem_type    ;shift left to test ($80 for rect, $ff for vline)
68be: ea                           nop
68bf: 10 0f                        bpl     :CalcRight
68c1: a5 76                        lda     clamped_lr_count  ;vertical line
68c3: f0 02                        beq     :NoIncFlag
68c5: e6 7c                        inc     no_draw_elem_flag?
68c7: 4c 90 6b     :NoIncFlag      jmp     :RestoreRts1

68ca: a5 78        :DoHorizLine    lda     clamped_tb_count
68cc: f0 02                        beq     :CalcRight
68ce: e6 7c                        inc     no_draw_elem_flag?
                   ; Horizontal line or rect.  Calculate right coordinate.
68d0: 18           :CalcRight      clc
68d1: bd c0 a2                     lda     elem_right_lo,x
68d4: 65 94                        adc     ]yaw_move
68d6: a8                           tay
68d7: bd 00 a3                     lda     elem_right_hi,x
68da: 65 95                        adc     ]yaw_move+1
68dc: 85 8f                        sta     move_tmp+1
68de: 70 32                        bvs     :OffScreenRgt
68e0: 18                           clc
68e1: 98                           tya
68e2: a4 62                        ldy     cur_obj_index
68e4: 79 60 9e                     adc     obj_move_xc_lo,y
68e7: 9d c0 a2                     sta     elem_right_lo,x
68ea: 85 8c                        sta     ]updated_coord?
68ec: a5 8f                        lda     move_tmp+1
68ee: 79 88 9e                     adc     obj_move_xc_hi,y
68f1: 70 1f                        bvs     :OffScreenRgt
68f3: 9d 00 a3                     sta     elem_right_hi,x
68f6: 30 2c                        bmi     :NegRgt
68f8: a4 7c                        ldy     no_draw_elem_flag?
68fa: d0 1b                        bne     :ZeroRgt1
68fc: 85 8d                        sta     ]updated_coord?+1
68fe: ea                           nop
68ff: a5 8c                        lda     ]updated_coord?
6901: c5 86                        cmp     ]new_zpos
6903: a5 8d                        lda     ]updated_coord?+1
6905: e5 87                        sbc     ]new_zpos+1
6907: ea                           nop
6908: 30 12                        bmi     :Jmp_RgtBoundsOk
690a: e6 76        :RgtBoundsBad   inc     clamped_lr_count
690c: a9 8a                        lda     #138
690e: a4 7a                        ldy     elem_bad_z_flag?
6910: f0 07                        beq     :ConstRgt
6912: e6 72        :OffScreenRgt   inc     no_draw_obj_flag
6914: e6 7c                        inc     no_draw_elem_flag?
6916: ea                           nop
6917: a9 00        :ZeroRgt1       lda     #$00
6919: 4c 8a 69     :ConstRgt       jmp     :GotRgt

                   :Jmp_RgtBoundsOk
691c: 4c 4d 69                     jmp     :RgtBoundsOk

691f: a9 00        :ZeroRgt2       lda     #$00
6921: 4c 8a 69                     jmp     :GotRgt

6924: a5 7c        :NegRgt         lda     no_draw_elem_flag?
6926: d0 ef                        bne     :ZeroRgt1
6928: 38                           sec
6929: a9 00                        lda     #$00
692b: e5 8c                        sbc     ]updated_coord?
692d: 85 8c                        sta     ]updated_coord?
692f: a9 00                        lda     #$00
6931: fd 00 a3                     sbc     elem_right_hi,x
6934: 85 8d                        sta     ]updated_coord?+1
6936: a5 8c                        lda     ]updated_coord?
6938: c5 86                        cmp     ]new_zpos
693a: a5 8d                        lda     ]updated_coord?+1
693c: e5 87                        sbc     ]new_zpos+1
693e: ea                           nop
693f: 30 0c                        bmi     :RgtBoundsOk
6941: 4c 0a 69                     jmp     :RgtBoundsBad

6944: a5 8c        :CheckRgtZero   lda     ]updated_coord?
6946: d0 14                        bne     :RgtSmall
6948: a9 00                        lda     #$00
694a: 4c 8a 69                     jmp     :GotRgt

694d: a5 87        :RgtBoundsOk    lda     ]new_zpos+1
694f: f0 f3                        beq     :CheckRgtZero
6951: a4 bd                        ldy     zcoord_clz
6953: a5 8c                        lda     ]updated_coord?
6955: 39 d5 00                     and     bit_mask_left9,y
6958: 05 8d                        ora     ]updated_coord?+1
695a: f0 c3                        beq     :ZeroRgt2
695c: a8           :RgtSmall       tay
695d: b1 12                        lda     (math_tab_ptr12),y
695f: a8                           tay
6960: 18                           clc
6961: b9 00 b5                     lda     turn_map_lo?,y
6964: 69 1c                        adc     #$1c
6966: 85 8e                        sta     move_tmp
6968: b9 00 b6                     lda     turn_map_hi?,y
696b: 69 07                        adc     #$07
696d: 85 8f                        sta     move_tmp+1
696f: 38                           sec
6970: a5 8e                        lda     move_tmp
6972: a4 bc                        ldy     zcoord_factor
6974: f9 00 b5                     sbc     turn_map_lo?,y
6977: 85 8e                        sta     move_tmp
6979: a5 8f                        lda     move_tmp+1
697b: f9 00 b6                     sbc     turn_map_hi?,y
697e: ea                           nop
697f: 30 9e                        bmi     :ZeroRgt2
6981: 38                           sec                       ;+1
6982: 69 0f                        adc     #>math_tab1_base?-$100
6984: 85 15                        sta     math_tab_ptr14+1
6986: a4 8e                        ldy     move_tmp
6988: b1 14                        lda     (math_tab_ptr14),y
698a: ea           :GotRgt         nop
698b: 20 7f 7f                     jsr     Return7f7f
698e: 85 84                        sta     ]scrn_xc_rgt_abs  ;set right coordinate
6990: c5 82                        cmp     ]scrn_xc_lft_abs  ;same as left?
6992: d0 11                        bne     :LftNeRgt         ;no, branch
6994: bd 00 a3                     lda     elem_right_hi,x   ;absolute value is equal; compare signs
6997: 5d 00 a2                     eor     elem_left_hi,x
699a: 30 09                        bmi     :LftNeRgt         ;signs not equal, branch
699c: a5 76                        lda     clamped_lr_count
699e: f0 02                        beq     :NoIncFlag
69a0: e6 7c                        inc     no_draw_elem_flag?
69a2: 4c 90 6b     :NoIncFlag      jmp     :RestoreRts1

69a5: e6 70        :LftNeRgt       inc     mod_elem_type     ;vline->rect
69a7: 4c 90 6b                     jmp     :RestoreRts1

                   ; 
                   ; Transform object that is behind us (Z is negative).
                   ; 
                   ; This marks the element as "do not draw", then calculates the position of the
                   ; element as if the Z coordinate were at (0-Z).  Since there's no need to update
                   ; the position for an element we're not drawing, my guess is that the
                   ; calculations are performed for the benefit of collision detection vs. the
                   ; player (but if that's the case, why worry about right/bottom coords?).
                   ; 
                   ]scale1_val?    .var    $8a    {addr/1}
                   ]scale2_base?   .var    $8b    {addr/1}

69aa: 18           :ObjectBehind   clc                       ;do sound stuff
69ab: a5 b2                        lda     engine_sound_ctr?+1
69ad: 69 18                        adc     #$18
69af: 85 b2                        sta     engine_sound_ctr?+1
69b1: 90 0f                        bcc     :NoSound
69b3: e6 b3                        inc     engine_sound_ctr?+2
69b5: a5 cc                        lda     engine_sound_enable
69b7: f0 09                        beq     :NoSound
69b9: a5 b3                        lda     engine_sound_ctr?+2
69bb: 25 b1                        and     engine_sound_ctr?
69bd: d0 03                        bne     :NoSound
69bf: ad 30 c0                     lda     SPKR
69c2: a9 0e        :NoSound        lda     #$0e
69c4: 85 72                        sta     no_draw_obj_flag  ;set flag to suppress rendering of object
69c6: e6 7a                        inc     elem_bad_z_flag?
69c8: e6 7c                        inc     no_draw_elem_flag?
69ca: 38                           sec
69cb: a9 00                        lda     #$00
69cd: e5 86                        sbc     ]new_zpos
69cf: 85 86                        sta     ]new_zpos
69d1: a9 00                        lda     #$00
69d3: e5 87                        sbc     ]new_zpos+1
69d5: 85 87                        sta     ]new_zpos+1
69d7: a9 fc                        lda     #$fc
69d9: 85 c6                        sta     prev_zpos+1       ;set to -$0400 (invalid)
69db: a5 87                        lda     ]new_zpos+1
69dd: d0 18                        bne     L69F7
69df: a4 86                        ldy     ]new_zpos
69e1: b9 00 b9                     lda     clz_table,y
69e4: 18                           clc
69e5: 69 08                        adc     #$08
69e7: 85 8b                        sta     ]scale2_base?
69e9: 69 a4                        adc     #>math_tab2_base?-$800
69eb: 85 13                        sta     math_tab_ptr12+1
69ed: a4 86                        ldy     ]new_zpos
69ef: b1 12                        lda     (math_tab_ptr12),y
69f1: 85 8a                        sta     ]scale1_val?
69f3: ea                           nop
69f4: 4c 11 6a                     jmp     L6A11

69f7: 85 87        L69F7           sta     ]new_zpos+1
69f9: a8                           tay
69fa: b9 00 b9                     lda     clz_table,y
69fd: a8                           tay
69fe: 85 8b                        sta     ]scale2_base?
6a00: 18                           clc
6a01: 69 ac                        adc     #>math_tab2_base?
6a03: 85 13                        sta     math_tab_ptr12+1
6a05: a5 86                        lda     ]new_zpos
6a07: 39 d5 00                     and     bit_mask_left9,y
6a0a: 05 87                        ora     ]new_zpos+1
6a0c: a8                           tay
6a0d: b1 12                        lda     (math_tab_ptr12),y
6a0f: 85 8a                        sta     ]scale1_val?
6a11: ea           L6A11           nop
6a12: 18                           clc
6a13: a4 8a                        ldy     ]scale1_val?
6a15: b9 00 b5                     lda     turn_map_lo?,y
6a18: 65 9a                        adc     joy_yaw_angle
6a1a: 85 8c                        sta     ]updated_coord?
6a1c: a5 9b                        lda     joy_yaw_angle+1
6a1e: e5 8b                        sbc     ]scale2_base?
6a20: 30 25                        bmi     L6A47
6a22: 85 8d                        sta     ]updated_coord?+1
6a24: 38                           sec
6a25: ea                           nop
6a26: 69 ac                        adc     #>math_tab2_base?
6a28: 85 15                        sta     math_tab_ptr14+1
6a2a: a4 8c                        ldy     ]updated_coord?
6a2c: b9 00 17                     lda     math_tab1_lastpg?,y
6a2f: a8                           tay
6a30: b1 14                        lda     (math_tab_ptr14),y
6a32: 85 95                        sta     ]yaw_move+1
6a34: a4 8d                        ldy     ]updated_coord?+1
6a36: 39 ef 00                     and     bit_mask_left8,y
6a39: 45 9c                        eor     joy_yaw_sign
6a3b: 85 94                        sta     ]yaw_move
6a3d: a5 95                        lda     ]yaw_move+1
6a3f: 39 e7 00                     and     bit_mask_right8,y
6a42: 45 9c                        eor     joy_yaw_sign
6a44: 4c 63 6a                     jmp     L6A63

6a47: ea           L6A47           nop
6a48: 18                           clc
6a49: 69 08                        adc     #$08
6a4b: 30 12                        bmi     L6A5F
6a4d: 18                           clc
6a4e: 69 10                        adc     #>math_tab1_base?
6a50: 85 15                        sta     math_tab_ptr14+1
6a52: a4 8c                        ldy     ]updated_coord?
6a54: a5 9c                        lda     joy_yaw_sign
6a56: 85 95                        sta     ]yaw_move+1
6a58: 51 14                        eor     (math_tab_ptr14),y
6a5a: 85 94                        sta     ]yaw_move
6a5c: 4c 65 6a                     jmp     L6A65

6a5f: a9 00        L6A5F           lda     #$00
6a61: 85 94                        sta     ]yaw_move
6a63: 85 95        L6A63           sta     ]yaw_move+1
6a65: ea           L6A65           nop
6a66: 18                           clc
6a67: a4 8a                        ldy     ]scale1_val?
6a69: b9 00 b5                     lda     turn_map_lo?,y
6a6c: 65 9d                        adc     joy_pitch_angle
6a6e: 85 8c                        sta     ]updated_coord?
6a70: a5 9e                        lda     joy_pitch_angle+1
6a72: e5 8b                        sbc     ]scale2_base?
6a74: 30 25                        bmi     L6A9B
6a76: 85 8d                        sta     ]updated_coord?+1
6a78: 38                           sec
6a79: ea                           nop
6a7a: 69 ac                        adc     #>math_tab2_base?
6a7c: 85 15                        sta     math_tab_ptr14+1
6a7e: a4 8c                        ldy     ]updated_coord?
6a80: b9 00 17                     lda     math_tab1_lastpg?,y
6a83: a8                           tay
6a84: b1 14                        lda     (math_tab_ptr14),y
6a86: 85 97                        sta     ]pitch_move+1
6a88: a4 8d                        ldy     ]updated_coord?+1
6a8a: 39 ef 00                     and     bit_mask_left8,y
6a8d: 45 9f                        eor     joy_pitch_sign
6a8f: 85 96                        sta     ]pitch_move
6a91: a5 97                        lda     ]pitch_move+1
6a93: 39 e7 00                     and     bit_mask_right8,y
6a96: 45 9f                        eor     joy_pitch_sign
6a98: 4c b7 6a                     jmp     L6AB7

6a9b: ea           L6A9B           nop
6a9c: 18                           clc
6a9d: 69 08                        adc     #$08
6a9f: 30 12                        bmi     L6AB3
6aa1: 18                           clc
6aa2: 69 10                        adc     #>math_tab1_base?
6aa4: 85 15                        sta     math_tab_ptr14+1
6aa6: a4 8c                        ldy     ]updated_coord?
6aa8: a5 9f                        lda     joy_pitch_sign
6aaa: 85 97                        sta     ]pitch_move+1
6aac: 51 14                        eor     (math_tab_ptr14),y
6aae: 85 96                        sta     ]pitch_move
6ab0: 4c b9 6a                     jmp     L6AB9

6ab3: a9 00        L6AB3           lda     #$00
6ab5: 85 96                        sta     ]pitch_move
6ab7: 85 97        L6AB7           sta     ]pitch_move+1
6ab9: ea           L6AB9           nop
6aba: 18                           clc                       ;do sound stuff
6abb: a5 b2                        lda     engine_sound_ctr?+1
6abd: 69 0d                        adc     #$0d
6abf: 85 b2                        sta     engine_sound_ctr?+1
6ac1: 90 0f                        bcc     :NoSound
6ac3: e6 b3                        inc     engine_sound_ctr?+2
6ac5: a5 cc                        lda     engine_sound_enable
6ac7: f0 09                        beq     :NoSound
6ac9: a5 b3                        lda     engine_sound_ctr?+2
6acb: 25 b1                        and     engine_sound_ctr?
6acd: d0 03                        bne     :NoSound
6acf: ad 30 c0                     lda     SPKR
6ad2: 38           :NoSound        sec
6ad3: bd c0 a1                     lda     elem_left_lo,x
6ad6: e5 94                        sbc     ]yaw_move
6ad8: a8                           tay
6ad9: bd 00 a2                     lda     elem_left_hi,x
6adc: e5 95                        sbc     ]yaw_move+1
6ade: 85 8f                        sta     move_tmp+1
6ae0: 70 17                        bvs     L6AF9
6ae2: 18                           clc
6ae3: 98                           tya
6ae4: a4 62                        ldy     cur_obj_index
6ae6: 79 60 9e                     adc     obj_move_xc_lo,y
6ae9: 9d c0 a1                     sta     elem_left_lo,x
6aec: a5 8f                        lda     move_tmp+1
6aee: 79 88 9e                     adc     obj_move_xc_hi,y
6af1: 70 06                        bvs     L6AF9
6af3: 9d 00 a2                     sta     elem_left_hi,x
6af6: 4c fd 6a                     jmp     L6AFD

6af9: e6 72        L6AF9           inc     no_draw_obj_flag
6afb: e6 7c                        inc     no_draw_elem_flag?
6afd: ea           L6AFD           nop
6afe: 38                           sec
6aff: bd 40 a2                     lda     elem_top_lo,x
6b02: e5 96                        sbc     ]pitch_move
6b04: a8                           tay
6b05: bd 80 a2                     lda     elem_top_hi,x
6b08: e5 97                        sbc     ]pitch_move+1
6b0a: 85 8f                        sta     move_tmp+1
6b0c: 70 17                        bvs     L6B25
6b0e: 18                           clc
6b0f: 98                           tya
6b10: a4 62                        ldy     cur_obj_index
6b12: 79 b0 9e                     adc     obj_move_yc_lo,y
6b15: 9d 40 a2                     sta     elem_top_lo,x
6b18: a5 8f                        lda     move_tmp+1
6b1a: 79 d8 9e                     adc     obj_move_yc_hi,y
6b1d: 70 06                        bvs     L6B25
6b1f: 9d 80 a2                     sta     elem_top_hi,x
6b22: 4c 29 6b                     jmp     L6B29

6b25: e6 72        L6B25           inc     no_draw_obj_flag
6b27: e6 7c                        inc     no_draw_elem_flag?
6b29: ea           L6B29           nop
6b2a: bd c0 9f                     lda     elem_types,x      ;get original element type
6b2d: 85 91                        sta     orig_elem_type    ;copy to ZP
6b2f: 10 33                        bpl     :PtOrHlin
6b31: 38                           sec                       ;rect or vline
6b32: bd 40 a3                     lda     elem_bottom_lo,x
6b35: e5 96                        sbc     ]pitch_move
6b37: a8                           tay
6b38: bd 80 a3                     lda     elem_bottom_hi,x
6b3b: e5 97                        sbc     ]pitch_move+1
6b3d: 85 8f                        sta     move_tmp+1
6b3f: 70 17                        bvs     L6B58
6b41: 18                           clc
6b42: 98                           tya
6b43: a4 62                        ldy     cur_obj_index
6b45: 79 b0 9e                     adc     obj_move_yc_lo,y
6b48: 9d 40 a3                     sta     elem_bottom_lo,x
6b4b: a5 8f                        lda     move_tmp+1
6b4d: 79 d8 9e                     adc     obj_move_yc_hi,y
6b50: 70 06                        bvs     L6B58
6b52: 9d 80 a3                     sta     elem_bottom_hi,x
6b55: 4c 5c 6b                     jmp     L6B5C

6b58: e6 72        L6B58           inc     no_draw_obj_flag
6b5a: e6 7c                        inc     no_draw_elem_flag?
6b5c: ea           L6B5C           nop
6b5d: 06 91                        asl     orig_elem_type    ;test low bits
6b5f: 10 03                        bpl     :PtOrHlin         ;was rect, branch
6b61: 4c 90 6b                     jmp     :RestoreRts1

6b64: 38           :PtOrHlin       sec                       ;point, hline, or rect
6b65: bd c0 a2                     lda     elem_right_lo,x
6b68: e5 94                        sbc     ]yaw_move
6b6a: a8                           tay
6b6b: bd 00 a3                     lda     elem_right_hi,x
6b6e: e5 95                        sbc     ]yaw_move+1
6b70: 85 8f                        sta     move_tmp+1
6b72: 70 17                        bvs     L6B8B
6b74: 18                           clc
6b75: 98                           tya
6b76: a4 62                        ldy     cur_obj_index
6b78: 79 60 9e                     adc     obj_move_xc_lo,y
6b7b: 9d c0 a2                     sta     elem_right_lo,x
6b7e: a5 8f                        lda     move_tmp+1
6b80: 79 88 9e                     adc     obj_move_xc_hi,y
6b83: 70 06                        bvs     L6B8B
6b85: 9d 00 a3                     sta     elem_right_hi,x
6b88: 4c 8f 6b                     jmp     :RestoreRts2

6b8b: e6 72        L6B8B           inc     no_draw_obj_flag
6b8d: e6 7c                        inc     no_draw_elem_flag?
6b8f: ea           :RestoreRts2    nop
6b90: 20 7f 7f     :RestoreRts1    jsr     Return7f7f
6b93: a9 20        :RestoreRts     lda     #INSTR_JSR_ABS    ;restore draw/erase of vertical lines and rects
6b95: 20 4c 7b                     jsr     ModDrwEraVrtRct
6b98: 60                           rts

6b99: 3d 3d 3d 3d+                 .junk   293
                   logo_region_toggle
6cbe: ff                           .dd1    $ff               ;bool 00/ff: select logo region for title screen?
                   demo_logo_progress
6cbf: 0a                           .dd1    $0a               ;initial value for forward progress when showing logo
6cc0: 86 00        demo_logo_speed .dd2    $0086             ;foward speed when showing logo in demo (1340)
6cc2: 00 00 00 00                  .junk   4
                   ; 
                   ; Counter used with random number generation (0-54).  Incremented every time the
                   ; function is called.
6cc6: 12           rng_counter     .junk   1
                   ; 
                   ; Register spill.
6cc7: 1f           saved_xreg_7bb0 .junk   1
                   ; 
                   ; This big pile of bytes appears to hold the state for random number generation
                   ; (function at $7bb0).  Some of the bytes are tweaked directly by certain
                   ; functions, possibly to add entropy.
6cc8: 26 e0 eb f4+ rng_state1      .bulk   $26,$e0,$eb,$f4,$50,$6e,$8f,$a7,$73,$3c,$48,$57,$d4,$c7,$8d,$df ;55 elements
                                    +      $33,$ea,$25,$27,$eb,$6e,$ac,$a3,$7a,$ec,$79,$61,$b5,$30,$e5,$78
                                    +      $01,$59,$b9,$6b,$6b,$76,$d7,$9b,$e5,$a8,$2d,$14,$a9,$f7,$12,$7c
                                    +      $d8,$ba,$04,$b3,$b2,$11,$1e
6cff: 13 2b 7b 7c+ rng_state2      .bulk   $13,$2b,$7b,$7c,$3d,$72,$38,$7e,$5d,$44,$cf,$d1,$df,$13,$0f,$bc ;55 elements
                                    +      $f5,$dc,$27,$2e,$f2,$53,$2f,$44,$7d,$5a,$35,$4d,$84,$93,$41,$65
                                    +      $c5,$b1,$79,$ca,$43,$04,$53,$b4,$d6,$b7,$7e,$f8,$99,$81,$57,$5e
                                    +      $af,$4b,$3c,$80,$cd,$9a,$88
6d36: 00 00 00 00+                 .junk   5
                   game_active_flag
6d3b: 00                           .dd1    $00               ;bool 00/ff: is game being played?
6d3c: 00           wronly_6d3c     .dd1    $00               ;written, never read
6d3d: 01           rng_update_flag .dd1    $01               ;if zero, invoke the RNG several times
6d3e: 00                           .junk   1
                   end_game_msg_ctr
6d3f: 00 00                        .dd2    $0000             ;holds "out of ____" on screen during demo for a bit
                   title_text_draw_index
6d41: 00                           .dd1    $00               ;index into title text string
6d42: 03           rsrc_draw_index .dd1    $03               ;index into $70dc/$70e1 (0-4)
6d43: 00           game_over_music .dd1    $00               ;1=not high score, 5=high score, 0=music done
6d44: 00           horiz_axis_mod  .dd1    $00               ;horizontal joystick axis modifier (00/ff)
6d45: 00 00                        .junk   2
6d47: 00           vert_axis_mod   .dd1    $00               ;vertical joystick axis modifier (00/ff)
                   sound_disab_flag
6d48: 00                           .dd1    $00               ;bool 00/01: is sound disabled?
                   ; 
                   ; $6d49-6dbc zeroed out during game init ($8152).
                   ; 
6d49: 00           tmp_xmove_lo    .dd1    $00
6d4a: 00           tmp_xmove_hi    .dd1    $00
6d4b: 00           tmp_ymove_lo    .dd1    $00
6d4c: 00           tmp_ymove_hi    .dd1    $00
6d4d: 00           tmp_zmove_lo    .dd1    $00
6d4e: 00           tmp_zmove_hi    .dd1    $00
6d4f: 00 00                        .junk   2
6d51: 00 00        max_z_spd_copy  .dd2    $0000
6d53: 00 00 00     portal_xmod0    .dd3    $000000           ;portal boundary position modifier
6d56: 00 00 00     portal_ymod0    .dd3    $000000           ;portal boundary position modifier
6d59: 00 00 00     portal_xmod1    .dd3    $000000           ;portal boundary position modifier
6d5c: 00 00 00     portal_ymod1    .dd3    $000000           ;portal boundary position modifier
6d5f: 00           fuel_this_frame .dd1    $00               ;# of units of fuel we burned this frame
6d60: 00                           .junk   1
                   ; 
                   ; Region progress counter, updated every frame.  When this reaches zero, we
                   ; update the region number.
                   region_progress_ctr
6d61: e5 09                        .dd2    $09e5
                   ; 
                   ; Region of space (0-7).  Determines what sorts of things are created here,
                   ; based on the contents of the table at $708c.
6d63: 06           space_region    .dd1    $06
                   ; 
                   ; Counter used when deciding whether to create multiple objects in one frame. 
                   ; Initially set to 0-28, then reduced by class-specific values at $707f.
6d64: fe           create_mult_ctr .dd1    $fe
                   ; 
                   ; Counter used to pick the class of a shape to create.  This is incremented,
                   ; ANDed with #$07, and checked against the list of shapes valid in this region.
6d65: 27           shape_cl_ctr    .dd1    $27
6d66: 00                           .junk   1
                   ; 
                   ; Points to region limit table for the current region.  This is set to the value
                   ; from the region table base ptr ($70cc) plus (region * 8).
6d67: bc 70        region_tab_ptr  .dd2    region_class_max+48
                   ; 
                   ; Active object count, by class.  The Nth entry is incremented when an object of
                   ; class N is created, and decremented when it's destroyed.  This is used to
                   ; enforce the per-region limits.
                   ; 
                   ; (Like everything else nearby, this is zeroed out by the loop at $8152.)
                   active_class_ctrs
6d69: 01 00 00 00+                 .bulk   $01,$00,$00,$00,$00,$00,$00,$04,$00,$00,$00,$00,$00,$00,$00,$00
                   ; 
                   ; Copy of shape header, used by object creator.  $6d79-6d8a are copied from
                   ; header +$08 to +$11.
6d79: 00           element_count   .dd1    $00               ;hdr +$00 element count
6d7a: 00 00 00                     .bulk   $00,$00,$00       ;hdr +$01-03 (unused)
6d7d: 00           shape_act_type  .dd1    $00               ;hdr +$04: activity type
6d7e: 00 00 00                     .bulk   $00,$00,$00       ;hdr +$05-07 (unused)
6d81: 40 00        shape_zmin      .dd2    $0040             ;hdr +$08-09: minimum initial value for Z
6d83: 00 10        shape_zmax      .dd2    $1000             ;hdr +$0a-0b: maximum initial value for Z
6d85: 00 00 00                     .bulk   $00,$00,$00       ;hdr +$0c-0e (unused)
6d88: 01 00        shape_hitbox    .dd2    $0001             ;hdr +$0f-10: size of hitbox
6d8a: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00 ;hdr +$11-17 (unused)
                   ; 
6d91: 00           shot_delay_ctr  .dd1    $00               ;paces shots when buttons held down
6d92: 00           btns_down_flag  .dd1    $00               ;bool 00/80: both buttons down (or spacebar hit)?
                   btns_0_down_flag
6d93: 00                           .dd1    $00               ;bool 00/80: button 0 down?
                   btns_1_down_flag
6d94: 00                           .dd1    $00               ;bool 00/80: button 1 down?
                   time_in_portal_ctr
6d95: 00 00                        .dd2    $0000             ;counts time spent in portal
6d97: 00           wronly_6d97?    .dd1    $00               ;incremented, never read
                   time_portal_fail_ctr
6d98: 00                           .dd1    $00               ;increases when flying outside time portal
                   entered_portal_flag
6d99: 00                           .dd1    $00               ;bool 00/nz: did we just enter a time portal?
6d9a: 00                           .junk   1
6d9b: 00 00 00 00+ wronly_6d9b?    .fill   6,$00             ;written, updated, never read
6da1: 00 00 00                     .junk   3
6da4: 00 00 00     forward_speed   .dd3    $000000           ;16.8: speed/10 (so "2600"=$00 04 01)
6da7: 00           speed_fraction  .dd1    $00               ;fractional speed tracking
6da8: 00 00                        .junk   2
6daa: 00           joystick_x_mag  .dd1    $00               ;joystick X axis magnitude ($00-65 or 5b)
6dab: 00           joy_mag_sum     .dd1    $00               ;sum of joystick magnitudes
                   joy_mag_plus_spd
6dac: 08                           .dd1    $08               ;sum of joystick magnitudes and a speed thing
6dad: 00           joystick_y_mag  .dd1    $00               ;joystick Y axis magnitude ($00-65 or 5b)
                   portal_bound_limit
6dae: 00 00                        .dd2    $0000             ;RNG limit when positioning portal boundaries
6db0: 00           wronly_6db0?    .dd1    $00               ;written, never read
6db1: 00 00 00 00+                 .junk   12
                   ; (end of zeroed-out area)
                   ; 
                   ; -----
                   ; 
                   ; Player resource state.
                   ; 
                   ; Modified via indirect access; see $7c68 and $7ca0.
                   ; 
                   ; $6dbd-6dcf (19 bytes) are initialized from $6dd7.
6dbd: 00           resource_state  .dd1    $00
6dbe: 00 00 00     cur_score       .dd3    $000000           ;24-bit BCD: current score
6dc1: 00                           .dd1    $00               ;(last byte ignored)
6dc2: 99 99        time_left       .dd2    $9999             ;16-bit BCD: amount of time left
6dc4: 00                           .dd1    $00
6dc5: 00 90        fuel_left       .dd2    $9000             ;16-bit BCD: amount of fuel left
6dc7: 00                           .dd1    $00
6dc8: 00 01        amun_left       .dd2    $0100             ;16-bit BCD: amount of ammo left
6dca: 00 00        cur_speed       .dd2    $0000             ;16-bit BCD: current speed
6dcc: 00                           .dd1    $00
6dcd: 0c           frame_counter   .dd1    $0c
                   status_line_index
6dce: 14                           .dd1    $14
6dcf: 00                           .dd1    $00
                   ; 
6dd0: 00                           .junk   1
6dd1: 00 00 00     high_score      .dd3    $000000           ;24-bit BCD: high score
6dd4: 00 00 00                     .junk   3
                   ; 
                   ; Initial ship loadout: 0 score, 9999 time, 9000 fuel, 100 ammo, 0 speed.
6dd7: 00 00 00 00+ initial_loadout .bulk   $00,$00,$00,$00,$00,$99,$99,$00,$00,$90,$00,$00,$01,$00,$00,$00
                                    +      $00,$00,$00
6dea: 00 00 00 00+                 .junk   75
                   ; 
                   ; Text shown during title sequence.
                   text_sirius_pres
6e35: 53 49 52 49+                 .str    ‘SIRIUS SOFTWARE PRESENTS ’
6e4e: 43 4f 50 59+ text_copyright  .str    ‘COPYRIGHT 1981’
6e5c: 42 59 20 20+ text_larry_spc  .str    ‘BY  LARRY MILLER    HIT SPACEBAR TO START’
                   ; 
                   ; The next 3 items form the top 40-char row of the status area.
6e85: 20 20 48 49+ text_score_time .str    ‘  HIGH  SCORE  TIME  FUEL  AMUN ’
                   text_axis_status
6ea5: 20                           .dd1    ‘ ’               ;value from $7345-7348 (' ','H','V','\')
6ea6: 34 20 53 50+ text_joy_sens   .str    ‘4 SPEED’         ;first char set to '1' - '5'
                   ; 
                   ; Unused.
6ead: 41 42 4f 56+ text_position   .str    ‘ABOVEBELOWRIGHTLEFT ’
                   ; 
                   ; Text shown at end of game.
6ec1: 4f 55 54 20+ text_out_of     .str    ‘OUT OF ’
                   text_time_fuel_amun
6ec8: 54 49 4d 45+                 .str    ‘TIMEFUELAMUN*RES’ ;printed after "OUT OF"
6ed8: 52 41 54 49+ text_rating     .str    ‘RATING  ’
                   ; 
                   ; Secret key sequence.  Type "NOTICE" while playing to pop up a copyright
                   ; notice.
                   secret_key_index
6ee0: 00                           .dd1    $00               ;current position in sequence
6ee1: 0e           secret_key_seq  .dd1    $0e               ;'N' - $40
6ee2: 0f                           .dd1    $0f               ;'O' - $40
6ee3: 14                           .dd1    $14               ;'T' - $40
6ee4: 09                           .dd1    $09               ;'I' - $40
6ee5: 03                           .dd1    $03               ;'C' - $40
6ee6: 05                           .dd1    $05               ;'E' - $40
                   ; 
                   ; Score ratings.  5 entries, 16 bytes each.  Determined by score thresholds
                   ; defined at $70e6.
                   text_rating_labels
6ee7: 4e 4f 56 49+                 .str    ‘NOVICE          PILOT           CAPTAIN         FLEET COMMANDE’
                                    +      ‘R GALACTIC EMPEROR’

                   vis
6f37: 11 11 11 1f+ font_glyphs     .bulk   $11,$11,$11,$1f,$11,$0a,$04,$00 ;'A'
6f3f: 0f 11 11 0f+                 .bulk   $0f,$11,$11,$0f,$11,$11,$0f,$00
6f47: 0e 11 01 01+                 .bulk   $0e,$11,$01,$01,$01,$11,$0e,$00
6f4f: 0f 11 11 11+                 .bulk   $0f,$11,$11,$11,$11,$11,$0f,$00
6f57: 1f 01 01 0f+                 .bulk   $1f,$01,$01,$0f,$01,$01,$1f,$00
6f5f: 01 01 01 0f+                 .bulk   $01,$01,$01,$0f,$01,$01,$1f,$00
6f67: 1e 11 11 19+                 .bulk   $1e,$11,$11,$19,$01,$11,$0e,$00
6f6f: 11 11 11 1f+                 .bulk   $11,$11,$11,$1f,$11,$11,$11,$00
6f77: 0e 04 04 04+                 .bulk   $0e,$04,$04,$04,$04,$04,$0e,$00
6f7f: 06 09 09 08+                 .bulk   $06,$09,$09,$08,$08,$08,$1c,$00
6f87: 11 09 05 03+                 .bulk   $11,$09,$05,$03,$05,$09,$11,$00
6f8f: 1f 01 01 01+                 .bulk   $1f,$01,$01,$01,$01,$01,$01,$00
6f97: 11 11 11 15+                 .bulk   $11,$11,$11,$15,$15,$1b,$11,$00
6f9f: 11 19 19 15+                 .bulk   $11,$19,$19,$15,$13,$13,$11,$00
6fa7: 0e 11 11 11+                 .bulk   $0e,$11,$11,$11,$11,$11,$0e,$00
6faf: 01 01 01 0f+                 .bulk   $01,$01,$01,$0f,$11,$11,$0f,$00
6fb7: 10 0e 15 11+                 .bulk   $10,$0e,$15,$11,$11,$11,$0e,$00
6fbf: 11 09 05 0f+                 .bulk   $11,$09,$05,$0f,$11,$11,$0f,$00
6fc7: 0e 11 10 0e+                 .bulk   $0e,$11,$10,$0e,$01,$11,$0e,$00
6fcf: 04 04 04 04+                 .bulk   $04,$04,$04,$04,$04,$04,$1f,$00
6fd7: 0e 11 11 11+                 .bulk   $0e,$11,$11,$11,$11,$11,$11,$00
6fdf: 04 0a 11 11+                 .bulk   $04,$0a,$11,$11,$11,$11,$11,$00
6fe7: 11 1b 15 15+                 .bulk   $11,$1b,$15,$15,$11,$11,$11,$00
6fef: 11 11 0a 04+                 .bulk   $11,$11,$0a,$04,$0a,$11,$11,$00
6ff7: 04 04 04 0e+                 .bulk   $04,$04,$04,$0e,$11,$11,$11,$00
6fff: 1f 01 02 04+                 .bulk   $1f,$01,$02,$04,$08,$10,$1f,$00 ;'Z'
7007: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00 ;' '
700f: 09 0f 09 09+                 .bulk   $09,$0f,$09,$09,$04,$0a,$11,$00 ;'V' + 'H', shown when both joystick axes are flipped
                   ; Digits start here.
                   font_glyph_digits
7017: 0e 11 11 11+                 .bulk   $0e,$11,$11,$11,$11,$11,$0e,$00 ;'0'
701f: 0e 04 04 04+                 .bulk   $0e,$04,$04,$04,$04,$06,$04,$00
7027: 1f 01 06 08+                 .bulk   $1f,$01,$06,$08,$10,$11,$0e,$00
702f: 0e 11 10 1c+                 .bulk   $0e,$11,$10,$1c,$08,$10,$0f,$00
7037: 08 08 3f 09+                 .bulk   $08,$08,$3f,$09,$0a,$0c,$08,$00
703f: 0e 11 10 10+                 .bulk   $0e,$11,$10,$10,$0f,$01,$1f,$00
7047: 0e 11 11 0f+                 .bulk   $0e,$11,$11,$0f,$01,$02,$1c,$00
704f: 02 02 02 04+                 .bulk   $02,$02,$02,$04,$08,$10,$1f,$00
7057: 0e 11 11 0e+                 .bulk   $0e,$11,$11,$0e,$11,$11,$0e,$00
705f: 07 08 10 1e+                 .bulk   $07,$08,$10,$1e,$11,$11,$0e,$00 ;'9'
7067: 00 04 04 1f+                 .bulk   $00,$04,$04,$1f,$04,$04,$00,$00 ;'+'
706f: 00 00 00 1f+                 .bulk   $00,$00,$00,$1f,$00,$00,$00,$00 ;'-'
7077: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$00,$00,$00 ;' '
                   ; 
                   ; Table of values used to update the "create multiple shapes in one frame"
                   ; counter at $6d64.
707f: 30 18 10 0c+ create_mult_tab .bulk   $30,$18,$10,$0c,$0c,$30,$18,$02
7087: 08 0c 0c 01+                 .junk   5
                   ; 
                   ; Determines which classes of objects are spawned in this region of space.  Take
                   ; the region index from $6d63, multiply by 8, and use that as an index.  Each
                   ; row of 8 specifies the maximum number of objects of that class that can be
                   ; created here.
                   ; 
                   ; The shape classes are:
                   ;   0: Epoch logo
                   ;   1: enemy bases
                   ;   2: enemy ships + time portal
                   ;   3: enemy projectiles
                   ;   4: enemy base (300pt version only); unused below
                   ;   5: time portal boundaries
                   ;   6: friendly base
                   ;   7: stars
                   ; (time portals are in the same set as enemy ships)
                   ; 
                   ; Classes 8-10 are used for player projectiles and enemy ship explosions.
                   region_class_max
708c: 00 01 01 01+                 .bulk   $00,$01,$01,$01,$00,$00,$00,$0c ;$01: 1 base, 1 ship, 1 projectile, 12 stars
7094: 00 01 01 00+                 .bulk   $00,$01,$01,$00,$00,$00,$00,$0f ;$02: 1 base, 1 ship, 15 stars
709c: 00 00 02 02+                 .bulk   $00,$00,$02,$02,$00,$00,$00,$0b ;$03: 2 ships, 2 projectiles, 11 stars
70a4: 00 00 00 00+                 .bulk   $00,$00,$00,$00,$00,$0c,$00,$00 ;$03: traveling through time portal
70ac: 00 01 00 01+                 .bulk   $00,$01,$00,$01,$00,$00,$01,$0c ;$04: 1 base, 1 projectile, 1 friendly, 12 stars
70b4: 00 00 01 00+                 .bulk   $00,$00,$01,$00,$00,$00,$00,$20 ;$05: 1 ship, 32 stars (my god, it's full of)
70bc: 01 00 00 00+                 .bulk   $01,$00,$00,$00,$00,$00,$00,$08 ;$06: title sequence
70c4: 00 01 01 00+                 .bulk   $00,$01,$01,$00,$00,$00,$01,$09 ;$07: 1 base, 1 ship, 1 friendly, 9 stars
70cc: 8c 70        region_tab_base .dd2    region_class_max  ;points to the region table
                   ; 
                   ; Lo-res color values.  Used to set the color on lo-res page 2, which is flashed
                   ; on certain events (e.g. getting hit).
70ce: 06 0c 0d 0f+ lo_res_color    .bulk   $06,$0c,$0d,$0f,$09,$01,$0e,$0d ;m.blu, l.grn, yell, wht, orng, red, aqu, yell
70d6: 00 00 00 00+                 .junk   6
                   ; 
                   ; Screen columns for status line items: score, time, fuel, amun, high.
70dc: 07 0f 15 1b+ rsrc_print_col  .bulk   $07,$0f,$15,$1b,$00
                   ; 
                   ; Index into $6dbd: score, time, fuel, amun, high.  This is the index of the
                   ; *last* byte, since that's what we want to print first (little-endian).
                   status_val_index
70e1: 03 06 09 0c+                 .bulk   $03,$06,$09,$0c,$16
                   ; 
                   ; Score rating thresholds (24-bit little-endian BCD):
                   ;       0 -  800 : novice
                   ;     800 - 2499 : pilot
                   ;    2500 - 7999 : captain
                   ;   8000 - 24999 : fleet commander
                   ;        > 25000 : galactic emperor
                   rating_thresholds
70e6: 00 08 00                     .dd3    $000800
70e9: 00 25 00                     .dd3    $002500
70ec: 00 80 00                     .dd3    $008000
70ef: 00 50 02                     .dd3    $025000
70f2: 00 00 00                     .junk   3
70f5: 08 00        time_rate       .dd2    $0008             ;-8 units per tick
70f7: 20 00        speed_rate      .dd2    $0020             ;+20 per tick while button held (cf. $7349)
                   time_portal_rate
70f9: 00 00                        .dd2    $0000             ;+N time restored (based on speed)
70fb: 01 00        amun_rate       .dd2    $0001             ;-1 per shot
                   ; Enemy ship point values.
                   enemy_point_values
70fd: 00 05 00 00                  .dd4    $00000500         ;+5 (not used?)
7101: 00 10 00 00                  .dd4    $00001000         ;+10 (not used?)
7105: 00 30 00 00                  .dd4    $00003000         ;+30 for alien: |-#-|
7109: 00 40 00 00                  .dd4    $00004000         ;+40 for alien: (rotated H)
710d: 00 60 00 00                  .dd4    $00006000         ;+60 for alien: =-##-=
7111: 00 00 01 00                  .dd4    $00010000         ;+100 for alien: two rotated H
7115: 00 00 03 00                  .dd4    $00030000         ;+300 for base #1 (block)
7119: 00 00 05 00                  .dd4    $00050000         ;+500 for base #2 (wide/thin)
711d: 00 03        fuel_rate_1     .dd2    $0300             ;-300 (collision)
711f: 02 00        fuel_rate_2     .dd2    $0002             ;-2 (maneuvers)
7121: 00 00 00 5a+                 .junk   80
                   ; 
                   ; Sound effect tables (function at $7cda).  Table 0 is for player cannon fire,
                   ; table 1 is for an enemy ship explosion.  Five bytes are copied into $c8-cc. 
                   ; The last byte (which acts as an "enabled" flag) is always zero.
7171: 01 02 03 03+ sfx_table_0     .bulk   $01,$02,$03,$03,$00
7176: 02 03 04 06+                 .bulk   $02,$03,$04,$06,$00
717b: 03 05 07 09+                 .bulk   $03,$05,$07,$09,$00
7180: 05 08 0a 0d+                 .bulk   $05,$08,$0a,$0d,$00
7185: 0a 0a 0c 14+                 .bulk   $0a,$0a,$0c,$14,$00
718a: 0a 0c 0e 18+                 .bulk   $0a,$0c,$0e,$18,$00
718f: 0a 10 18 24+                 .bulk   $0a,$10,$18,$24,$00
7194: 00 01 00 09+                 .bulk   $00,$01,$00,$09,$00
7199: 00 00 02 03+ sfx_table_1     .bulk   $00,$00,$02,$03,$00
719e: 00 00 03 06+                 .bulk   $00,$00,$03,$06,$00
71a3: 00 00 06 0a+                 .bulk   $00,$00,$06,$0a,$00
71a8: 00 00 0c 10+                 .bulk   $00,$00,$0c,$10,$00
71ad: 00 00 0e 10+                 .bulk   $00,$00,$0e,$10,$00
71b2: 00 00 0a 14+                 .bulk   $00,$00,$0a,$14,$00
71b7: 00 00 07 10+                 .bulk   $00,$00,$07,$10,$00
71bc: 00 00 0a 14+                 .bulk   $00,$00,$0a,$14,$00
                   joystick_sens_mod
71c1: ff fd                        .dd2    $fdff             ;$faff, $fbff, ... $feff
                   ; 
                   ; Color pixel bit masks.  The index is formed by taking the element color value
                   ; ($00=black, $10=white, ...$60=white) and ORing it with a value (0-6,7-14) for
                   ; the pixel we want to draw or erase.
                   ; 
                   ; Hi-res bytes have 7 pixels (with a little hand-waving), so the last entry in
                   ; each set of 8 is ignored.  There are 16 bytes per color, rather than 8,
                   ; because the colors change for odd/even columns.
                   color_bit_masks_thin
71c3: 01 02 04 08+                 .bulk   $01,$02,$04,$08,$10,$20,$40,$40 ;$00 black (handled specially)
71cb: 01 02 04 08+                 .bulk   $01,$02,$04,$08,$10,$20,$40,$40
71d3: 01 02 04 08+                 .bulk   $01,$02,$04,$08,$10,$20,$40,$40 ;$10 white (single pixel)
71db: 01 02 04 08+                 .bulk   $01,$02,$04,$08,$10,$20,$40,$40
71e3: 02 02 08 08+                 .bulk   $02,$02,$08,$08,$20,$20,$20,$20 ;$20 green
71eb: 01 01 04 04+                 .bulk   $01,$01,$04,$04,$10,$10,$40,$40
71f3: 01 01 04 04+                 .bulk   $01,$01,$04,$04,$10,$10,$40,$40 ;$30 purple
71fb: 02 02 08 08+                 .bulk   $02,$02,$08,$08,$20,$20,$20,$20
7203: 82 82 88 88+                 .bulk   $82,$82,$88,$88,$a0,$a0,$a0,$a0 ;$40 orange
720b: 81 81 84 84+                 .bulk   $81,$81,$84,$84,$90,$90,$c0,$c0
7213: 81 81 84 84+                 .bulk   $81,$81,$84,$84,$90,$90,$c0,$c0 ;$50 blue
721b: 82 82 88 88+                 .bulk   $82,$82,$88,$88,$a0,$a0,$a0,$a0
7223: 03 03 06 0c+                 .bulk   $03,$03,$06,$0c,$18,$30,$60,$60 ;$60 white (double pixel)
722b: 03 03 06 0c+                 .bulk   $03,$03,$06,$0c,$18,$30,$60,$60
                   ; 
                   ; Secret message: "COPYRIGHT BY LARRY R. MILLER 1981    noo".  40 bytes are
                   ; decoded to a secondary buffer, but only 36 are printed.
                   secret_copyright
7233: 23 2f 30 39+                 .bulk   $23,$2f,$30,$39,$32,$29,$27,$28,$34,$00,$22,$39,$00,$2c,$21,$32
                                    +      $32,$39,$00,$32,$0e,$00,$2d,$29,$2c,$2c,$25,$32,$00,$11,$19,$18
                                    +      $11,$00,$00,$00,$00,$4e,$4f,$4f
725b: 0d 18 11 0e+                 .junk   8
                   ; 
                   ; See comments for $71c3, above.
                   ; 
                   ; These pixels are for the left edge of something that extends to the right,
                   ; starting in pixel N.  If it starts in pixel 0 the entire byte is filled, if it
                   ; starts in pixel 6 only the last bit is set.  We always set a color in this
                   ; byte though, so if the color pattern sets bits 1/3/5, and we're starting in
                   ; pixel 6, we'll actually set pixel 5.
                   ; 
                   ; When drawing the middle parts of something, we just use index 0/8 to fill the
                   ; whole byte.
                   color_bit_masks_left
7263: 7f 7e 7c 78+                 .bulk   $7f,$7e,$7c,$78,$70,$60,$40,$40 ;$00 black (handled specially)
726b: 7f 7e 7c 78+                 .bulk   $7f,$7e,$7c,$78,$70,$60,$40,$40
7273: 7f 7e 7c 78+                 .bulk   $7f,$7e,$7c,$78,$70,$60,$40,$40 ;$10 white (single pixel)
727b: 7f 7e 7c 78+                 .bulk   $7f,$7e,$7c,$78,$70,$60,$40,$40
7283: 2a 2a 28 28+                 .bulk   $2a,$2a,$28,$28,$20,$20,$20,$20 ;$20 green
728b: 55 55 54 54+                 .bulk   $55,$55,$54,$54,$50,$50,$40,$40
7293: 55 55 54 54+                 .bulk   $55,$55,$54,$54,$50,$50,$40,$40 ;$30 purple
729b: 2a 2a 28 28+                 .bulk   $2a,$2a,$28,$28,$20,$20,$20,$20
72a3: aa aa a8 a8+                 .bulk   $aa,$aa,$a8,$a8,$a0,$a0,$a0,$a0 ;$40 orange
72ab: d5 d5 d4 d4+                 .bulk   $d5,$d5,$d4,$d4,$d0,$d0,$c0,$c0
72b3: d5 d5 d4 d4+                 .bulk   $d5,$d5,$d4,$d4,$d0,$d0,$c0,$c0 ;$50 blue
72bb: aa aa a8 a8+                 .bulk   $aa,$aa,$a8,$a8,$a0,$a0,$a0,$a0
72c3: 7f 7f 7e 7c+                 .bulk   $7f,$7f,$7e,$7c,$78,$70,$60,$60 ;$60 white (double pixel)
72cb: 7f 7f 7e 7c+                 .bulk   $7f,$7f,$7e,$7c,$78,$70,$60,$60
                   ; 
                   ; See comments for $71c3, above.
                   ; 
                   ; Same basic idea as the previous table, but for the right side of something
                   ; that extends to the left.
                   color_bit_masks_right
72d3: 01 03 07 0f+                 .bulk   $01,$03,$07,$0f,$1f,$3f,$7f,$7f ;$00 black (handled specially)
72db: 01 03 07 0f+                 .bulk   $01,$03,$07,$0f,$1f,$3f,$7f,$7f
72e3: 01 03 07 0f+                 .bulk   $01,$03,$07,$0f,$1f,$3f,$7f,$7f ;$10 white (single pixel)
72eb: 01 03 07 0f+                 .bulk   $01,$03,$07,$0f,$1f,$3f,$7f,$7f
72f3: 02 02 0a 0a+                 .bulk   $02,$02,$0a,$0a,$2a,$2a,$2a,$2a ;$20 green
72fb: 01 01 05 05+                 .bulk   $01,$01,$05,$05,$15,$15,$55,$55
7303: 01 01 05 05+                 .bulk   $01,$01,$05,$05,$15,$15,$55,$55 ;$30 purple
730b: 02 02 0a 0a+                 .bulk   $02,$02,$0a,$0a,$2a,$2a,$2a,$2a
7313: 82 82 8a 8a+                 .bulk   $82,$82,$8a,$8a,$aa,$aa,$aa,$aa ;$40 orange
731b: 81 81 85 85+                 .bulk   $81,$81,$85,$85,$95,$95,$d5,$d5
7323: 81 81 85 85+                 .bulk   $81,$81,$85,$85,$95,$95,$d5,$d5 ;$50 blue
732b: 82 82 8a 8a+                 .bulk   $82,$82,$8a,$8a,$aa,$aa,$aa,$aa
7333: 03 03 07 0f+                 .bulk   $03,$03,$07,$0f,$1f,$3f,$7f,$7f ;$60 white (double pixel)
733b: 03 03 07 0f+                 .bulk   $03,$03,$07,$0f,$1f,$3f,$7f,$7f
7343: 00 07                        .junk   2
                   ; 
                   ; Joystick axis flip chars, for UI.  ' '=normal, 'H'=horiz flip, 'V'=vert flip,
                   ; '\'=both (displays as a glyph with both 'H' and 'V').
7345: 20 48 56 5c  axis_flip_chars .str    ‘ HV\’
                   ; 
                   ; This is an 8.8 number that specifies how rapidly our speed increases or
                   ; decreases in a frame.
                   ; 
                   ; This is independent of (but equal to) the speed change that we display on-
                   ; screen, which is specified by a 16-bit value at $70f7.
7349: 00 02        delta_speed     .dd2    $0200             ;8.8: speed change per frame
734b: 3d 3d 3d 3d+                 .junk   26

                   ; 
                   ; Draws one of the numeric status values (score, time, fuel, amun, speed). 
                   ; Leading zeroes are replaced with spaces, unless the value is zero.
                   ; 
                   ; Values for X/Y:
                   ;   $24/$0e: speed in column 36
                   ;   $0f/$06: time in column 6
                   ; 
                   ; On entry:
                   ;   X-reg: horizontal offset (0-39)
                   ;   Y-reg: offset to resource to print
                   ;   $86: number of BCD bytes in value
                   ; 
                   • Clear variables
                   ]bcd_byte_cnt   .var    $86    {addr/1}
                   ]nonzero_flag   .var    $87    {addr/1}
                   ]byte_counter   .var    $88    {addr/1}
                   ]rsrc_index     .var    $89    {addr/1}

7365: a5 86        DrawStatusNum   lda     ]bcd_byte_cnt
7367: 85 88                        sta     ]byte_counter     ;number of two-digit BCD bytes to print
7369: a9 00                        lda     #$00
736b: 85 87                        sta     ]nonzero_flag     ;clear flag
736d: 84 89                        sty     ]rsrc_index
736f: b9 bd 6d     :Loop           lda     resource_state,y  ;get value
7372: 29 f0                        and     #$f0              ;strip low nibble
7374: d0 0e                        bne     :HiNonzero        ;nonzero, print it
7376: a5 87                        lda     ]nonzero_flag     ;have we seen a nonzero value before?
7378: d0 05                        bne     :HiPrint0         ;yes, print '0'
737a: a9 60                        lda     #$60              ;no, print ' '
737c: 4c 87 73                     jmp     :HiPrint

737f: a9 00        :HiPrint0       lda     #$00              ;'0'
7381: 4c 87 73                     jmp     :HiPrint

7384: e6 87        :HiNonzero      inc     ]nonzero_flag     ;set flag
7386: 4a                           lsr     A                 ;divide by 2 to get value * 8
7387: 20 df 75     :HiPrint        jsr     PrintDigitLine9   ;print the digit
738a: a4 89                        ldy     ]rsrc_index
738c: b9 bd 6d                     lda     resource_state,y  ;get same byte
738f: 29 0f                        and     #$0f              ;strip the high nibble
7391: d0 14                        bne     :LoNonzero        ;nonzero, print it
7393: a5 87                        lda     ]nonzero_flag     ;have we seen a nonzero value before?
7395: d0 0b                        bne     :LoPrint0         ;yes, print '0'
7397: a5 88                        lda     ]byte_counter     ;get bytes remaining
7399: c9 02                        cmp     #$02              ;is it < 2?
739b: 30 05                        bmi     :LoPrint0         ;yes, this is last digit; branch
739d: a9 60                        lda     #$60              ;print ' '
739f: 4c ac 73                     jmp     :LoPrint

73a2: a9 00        :LoPrint0       lda     #$00              ;print '0'
73a4: 4c ac 73                     jmp     :LoPrint

73a7: e6 87        :LoNonzero      inc     ]nonzero_flag     ;set flag
73a9: 0a                           asl     A                 ;multiply by 8
73aa: 0a                           asl     A
73ab: 0a                           asl     A
73ac: 20 df 75     :LoPrint        jsr     PrintDigitLine9   ;print the digit
73af: c6 89                        dec     ]rsrc_index       ;decrement to next little-endian digit
73b1: a4 89                        ldy     ]rsrc_index
73b3: c6 88                        dec     ]byte_counter     ;decrement counter
73b5: d0 b8                        bne     :Loop             ;not done, loop
73b7: ea                           nop
73b8: 60                           rts

                   ; 
                   ; Prints a character on line 0.
                   ; 
                   ; On entry:
                   ;   A-reg: ASCII character value
                   ;   X-reg: horizontal offset (0-39)
                   ; 
                   ; On exit:
                   ;   X-reg: (+1)
                   ; 
73b9: 38           PrintCharLine0  sec
73ba: e9 41                        sbc     #‘A’              ;subtract so 'A' is zero
73bc: 10 39                        bpl     :PrintLetter      ;still >= 0, print it
73be: 18                           clc
73bf: 69 11                        adc     #$11              ;add ('A' - '0') so '0' is zero
73c1: 30 32                        bmi     :PrintSpace       ;still negative, print ' '
73c3: 0a                           asl     A                 ;multiply by 8 to get index
73c4: 0a                           asl     A
73c5: 0a                           asl     A
73c6: a8                           tay
73c7: b9 1d 70                     lda     font_glyph_digits+6,y ;read pixels from bottom line
73ca: 9d 00 20                     sta     HIRES_P1,x        ;line 0
73cd: b9 1c 70                     lda     font_glyph_digits+5,y
73d0: 9d 00 24                     sta     HIRES_P1+$400,x
73d3: b9 1b 70                     lda     font_glyph_digits+4,y
73d6: 9d 00 28                     sta     HIRES_P1+$800,x
73d9: b9 1a 70                     lda     font_glyph_digits+3,y
73dc: 9d 00 2c                     sta     HIRES_P1+$c00,x
73df: b9 19 70                     lda     font_glyph_digits+2,y
73e2: 9d 00 30                     sta     HIRES_P1+$1000,x
73e5: b9 18 70                     lda     font_glyph_digits+1,y
73e8: 9d 00 34                     sta     HIRES_P1+$1400,x
73eb: b9 17 70                     lda     font_glyph_digits,y
73ee: 9d 00 38                     sta     HIRES_P1+$1800,x
73f1: e8                           inx
73f2: 4c 26 74                     jmp     :Return

73f5: a9 1a        :PrintSpace     lda     #$1a              ;blank glyph
73f7: 0a           :PrintLetter    asl     A
73f8: 0a                           asl     A
73f9: 0a                           asl     A
73fa: a8                           tay
73fb: b9 3d 6f                     lda     font_glyphs+6,y
73fe: 9d 00 20                     sta     HIRES_P1,x
7401: b9 3c 6f                     lda     font_glyphs+5,y
7404: 9d 00 24                     sta     HIRES_P1+$400,x
7407: b9 3b 6f                     lda     font_glyphs+4,y
740a: 9d 00 28                     sta     HIRES_P1+$800,x
740d: b9 3a 6f                     lda     font_glyphs+3,y
7410: 9d 00 2c                     sta     HIRES_P1+$c00,x
7413: b9 39 6f                     lda     font_glyphs+2,y
7416: 9d 00 30                     sta     HIRES_P1+$1000,x
7419: b9 38 6f                     lda     font_glyphs+1,y
741c: 9d 00 34                     sta     HIRES_P1+$1400,x
741f: b9 37 6f                     lda     font_glyphs,y
7422: 9d 00 38                     sta     HIRES_P1+$1800,x
7425: e8                           inx
7426: 60           :Return         rts

                   ; 
                   ; Prints a character on line 9 (not 8).
                   ; 
                   ; On entry:
                   ;   A-reg: ASCII character value
                   ;   X-reg: horizontal offset (0-39)
                   ; 
                   ; On exit:
                   ;   X-reg: (+1)
                   ; 
7427: 38           PrintCharLine9  sec
7428: e9 41                        sbc     #‘A’
742a: 10 39                        bpl     :PrintLetter
742c: 18                           clc
742d: 69 11                        adc     #$11
742f: 30 32                        bmi     :PrintSpace
7431: 0a                           asl     A
7432: 0a                           asl     A
7433: 0a                           asl     A
7434: a8                           tay
7435: b9 1d 70                     lda     font_glyph_digits+6,y
7438: 9d 80 24                     sta     HIRES_P1+$480,x   ;line 9
743b: b9 1c 70                     lda     font_glyph_digits+5,y
743e: 9d 80 28                     sta     HIRES_P1+$880,x
7441: b9 1b 70                     lda     font_glyph_digits+4,y
7444: 9d 80 2c                     sta     HIRES_P1+$c80,x
7447: b9 1a 70                     lda     font_glyph_digits+3,y
744a: 9d 80 30                     sta     HIRES_P1+$1080,x
744d: b9 19 70                     lda     font_glyph_digits+2,y
7450: 9d 80 34                     sta     HIRES_P1+$1480,x
7453: b9 18 70                     lda     font_glyph_digits+1,y
7456: 9d 80 38                     sta     HIRES_P1+$1880,x
7459: b9 17 70                     lda     font_glyph_digits,y
745c: 9d 80 3c                     sta     HIRES_P1+$1c80,x
745f: e8                           inx
7460: 4c 94 74                     jmp     L7494

7463: a9 1a        :PrintSpace     lda     #$1a              ;blank glyph
7465: 0a           :PrintLetter    asl     A
7466: 0a                           asl     A
7467: 0a                           asl     A
7468: a8                           tay
7469: b9 3d 6f                     lda     font_glyphs+6,y
746c: 9d 80 24                     sta     HIRES_P1+$480,x
746f: b9 3c 6f                     lda     font_glyphs+5,y
7472: 9d 80 28                     sta     HIRES_P1+$880,x
7475: b9 3b 6f                     lda     font_glyphs+4,y
7478: 9d 80 2c                     sta     HIRES_P1+$c80,x
747b: b9 3a 6f                     lda     font_glyphs+3,y
747e: 9d 80 30                     sta     HIRES_P1+$1080,x
7481: b9 39 6f                     lda     font_glyphs+2,y
7484: 9d 80 34                     sta     HIRES_P1+$1480,x
7487: b9 38 6f                     lda     font_glyphs+1,y
748a: 9d 80 38                     sta     HIRES_P1+$1880,x
748d: b9 37 6f                     lda     font_glyphs,y
7490: 9d 80 3c                     sta     HIRES_P1+$1c80,x
7493: e8                           inx
7494: 60           L7494           rts

                   ; 
                   ; Prints a character on line 32.
                   ; 
                   ; On entry:
                   ;   A-reg: ASCII character value
                   ;   X-reg: horizontal offset (0-39)
                   ; 
                   ; On exit:
                   ;   X-reg: (+1)
                   ; 
7495: 38           PrintCharLine32 sec
7496: e9 41                        sbc     #‘A’
7498: 10 39                        bpl     :PrintLetter
749a: 18                           clc
749b: 69 11                        adc     #$11
749d: 30 32                        bmi     :PrintSpace
749f: 0a                           asl     A
74a0: 0a                           asl     A
74a1: 0a                           asl     A
74a2: a8                           tay
74a3: b9 1d 70                     lda     font_glyph_digits+6,y
74a6: 9d 00 22                     sta     HIRES_P1+$200,x   ;line 32
74a9: b9 1c 70                     lda     font_glyph_digits+5,y
74ac: 9d 00 26                     sta     HIRES_P1+$600,x
74af: b9 1b 70                     lda     font_glyph_digits+4,y
74b2: 9d 00 2a                     sta     HIRES_P1+$a00,x
74b5: b9 1a 70                     lda     font_glyph_digits+3,y
74b8: 9d 00 2e                     sta     HIRES_P1+$e00,x
74bb: b9 19 70                     lda     font_glyph_digits+2,y
74be: 9d 00 32                     sta     HIRES_P1+$1200,x
74c1: b9 18 70                     lda     font_glyph_digits+1,y
74c4: 9d 00 36                     sta     HIRES_P1+$1600,x
74c7: b9 17 70                     lda     font_glyph_digits,y
74ca: 9d 00 3a                     sta     HIRES_P1+$1a00,x
74cd: e8                           inx
74ce: 4c 02 75                     jmp     L7502

74d1: a9 1a        :PrintSpace     lda     #$1a              ;blank glyph
74d3: 0a           :PrintLetter    asl     A
74d4: 0a                           asl     A
74d5: 0a                           asl     A
74d6: a8                           tay
74d7: b9 3d 6f                     lda     font_glyphs+6,y
74da: 9d 00 22                     sta     HIRES_P1+$200,x
74dd: b9 3c 6f                     lda     font_glyphs+5,y
74e0: 9d 00 26                     sta     HIRES_P1+$600,x
74e3: b9 3b 6f                     lda     font_glyphs+4,y
74e6: 9d 00 2a                     sta     HIRES_P1+$a00,x
74e9: b9 3a 6f                     lda     font_glyphs+3,y
74ec: 9d 00 2e                     sta     HIRES_P1+$e00,x
74ef: b9 39 6f                     lda     font_glyphs+2,y
74f2: 9d 00 32                     sta     HIRES_P1+$1200,x
74f5: b9 38 6f                     lda     font_glyphs+1,y
74f8: 9d 00 36                     sta     HIRES_P1+$1600,x
74fb: b9 37 6f                     lda     font_glyphs,y
74fe: 9d 00 3a                     sta     HIRES_P1+$1a00,x
7501: e8                           inx
7502: 60           L7502           rts

                   ; 
                   ; Prints a character on line 160.
                   ; 
                   ; On entry:
                   ;   A-reg: ASCII character value
                   ;   X-reg: horizontal offset (0-39)
                   ; 
                   ; On exit:
                   ;   X-reg: (+1)
                   ; 
                   PrintCharLine160
7503: 38                           sec
7504: e9 41                        sbc     #‘A’              ;subtract so 'A' is zero
7506: 10 39                        bpl     :PrintLetter      ;still >= 0, print it
7508: 18                           clc
7509: 69 11                        adc     #$11              ;add ('A' - '0') so '0' is zero
750b: 30 32                        bmi     :PrintSpace       ;still negative, must be ' '
750d: 0a                           asl     A                 ;multiply by 8 to get index
750e: 0a                           asl     A
750f: 0a                           asl     A
7510: a8                           tay
7511: b9 1d 70                     lda     font_glyph_digits+6,y
7514: 9d 50 22                     sta     HIRES_P1+$250,x   ;line 160
7517: b9 1c 70                     lda     font_glyph_digits+5,y
751a: 9d 50 26                     sta     HIRES_P1+$650,x
751d: b9 1b 70                     lda     font_glyph_digits+4,y
7520: 9d 50 2a                     sta     HIRES_P1+$a50,x
7523: b9 1a 70                     lda     font_glyph_digits+3,y
7526: 9d 50 2e                     sta     HIRES_P1+$e50,x
7529: b9 19 70                     lda     font_glyph_digits+2,y
752c: 9d 50 32                     sta     HIRES_P1+$1250,x
752f: b9 18 70                     lda     font_glyph_digits+1,y
7532: 9d 50 36                     sta     HIRES_P1+$1650,x
7535: b9 17 70                     lda     font_glyph_digits,y
7538: 9d 50 3a                     sta     HIRES_P1+$1a50,x
753b: e8                           inx
753c: 4c 70 75                     jmp     :Return

753f: a9 1a        :PrintSpace     lda     #$1a              ;blank glyph
7541: 0a           :PrintLetter    asl     A                 ;multiply by 8 to get index
7542: 0a                           asl     A
7543: 0a                           asl     A
7544: a8                           tay
7545: b9 3d 6f                     lda     font_glyphs+6,y
7548: 9d 50 22                     sta     HIRES_P1+$250,x   ;line 160
754b: b9 3c 6f                     lda     font_glyphs+5,y
754e: 9d 50 26                     sta     HIRES_P1+$650,x
7551: b9 3b 6f                     lda     font_glyphs+4,y
7554: 9d 50 2a                     sta     HIRES_P1+$a50,x
7557: b9 3a 6f                     lda     font_glyphs+3,y
755a: 9d 50 2e                     sta     HIRES_P1+$e50,x
755d: b9 39 6f                     lda     font_glyphs+2,y
7560: 9d 50 32                     sta     HIRES_P1+$1250,x
7563: b9 38 6f                     lda     font_glyphs+1,y
7566: 9d 50 36                     sta     HIRES_P1+$1650,x
7569: b9 37 6f                     lda     font_glyphs,y
756c: 9d 50 3a                     sta     HIRES_P1+$1a50,x
756f: e8                           inx
7570: 60           :Return         rts

                   ; 
                   ; Prints a character on line 176.
                   ; 
                   ; On entry:
                   ;   A-reg: ASCII character value
                   ;   X-reg: horizontal offset (0-39)
                   ; 
                   ; On exit:
                   ;   X-reg: (+1)
                   ; 
                   PrintCharLine176
7571: 38                           sec
7572: e9 41                        sbc     #‘A’
7574: 10 39                        bpl     :PrintLetter
7576: 18                           clc
7577: 69 11                        adc     #$11
7579: 30 32                        bmi     :PrintSpace
757b: 0a                           asl     A
757c: 0a                           asl     A
757d: 0a                           asl     A
757e: a8                           tay
757f: b9 1d 70                     lda     font_glyph_digits+6,y
7582: 9d 50 23                     sta     HIRES_P1+$350,x   ;line 176
7585: b9 1c 70                     lda     font_glyph_digits+5,y
7588: 9d 50 27                     sta     HIRES_P1+$750,x
758b: b9 1b 70                     lda     font_glyph_digits+4,y
758e: 9d 50 2b                     sta     HIRES_P1+$b50,x
7591: b9 1a 70                     lda     font_glyph_digits+3,y
7594: 9d 50 2f                     sta     HIRES_P1+$f50,x
7597: b9 19 70                     lda     font_glyph_digits+2,y
759a: 9d 50 33                     sta     HIRES_P1+$1350,x
759d: b9 18 70                     lda     font_glyph_digits+1,y
75a0: 9d 50 37                     sta     HIRES_P1+$1750,x
75a3: b9 17 70                     lda     font_glyph_digits,y
75a6: 9d 50 3b                     sta     HIRES_P1+$1b50,x
75a9: e8                           inx
75aa: 4c de 75                     jmp     :Return

75ad: a9 1a        :PrintSpace     lda     #$1a              ;blank glyph
75af: 0a           :PrintLetter    asl     A
75b0: 0a                           asl     A
75b1: 0a                           asl     A
75b2: a8                           tay
75b3: b9 3d 6f                     lda     font_glyphs+6,y
75b6: 9d 50 23                     sta     HIRES_P1+$350,x
75b9: b9 3c 6f                     lda     font_glyphs+5,y
75bc: 9d 50 27                     sta     HIRES_P1+$750,x
75bf: b9 3b 6f                     lda     font_glyphs+4,y
75c2: 9d 50 2b                     sta     HIRES_P1+$b50,x
75c5: b9 3a 6f                     lda     font_glyphs+3,y
75c8: 9d 50 2f                     sta     HIRES_P1+$f50,x
75cb: b9 39 6f                     lda     font_glyphs+2,y
75ce: 9d 50 33                     sta     HIRES_P1+$1350,x
75d1: b9 38 6f                     lda     font_glyphs+1,y
75d4: 9d 50 37                     sta     HIRES_P1+$1750,x
75d7: b9 37 6f                     lda     font_glyphs,y
75da: 9d 50 3b                     sta     HIRES_P1+$1b50,x
75dd: e8                           inx
75de: 60           :Return         rts

                   ; 
                   ; Prints a numeric digit, '+', '-', or ' ' on line 9.  Used for scores, time,
                   ; fuel, ammo, and forward speed.  Unlike the other functions, the digit argument
                   ; must already be multiplied by 8.
                   ; 
                   ; On entry:
                   ;   A-reg: digit * 8
                   ;   X-reg: horizontal offset (0-39)
                   ; 
                   ; On exit:
                   ;   X-reg: (+1)
                   ; 
75df: a8           PrintDigitLine9 tay
75e0: b9 1d 70                     lda     font_glyph_digits+6,y
75e3: 9d 80 24                     sta     HIRES_P1+$480,x
75e6: b9 1c 70                     lda     font_glyph_digits+5,y
75e9: 9d 80 28                     sta     HIRES_P1+$880,x
75ec: b9 1b 70                     lda     font_glyph_digits+4,y
75ef: 9d 80 2c                     sta     HIRES_P1+$c80,x
75f2: b9 1a 70                     lda     font_glyph_digits+3,y
75f5: 9d 80 30                     sta     HIRES_P1+$1080,x
75f8: b9 19 70                     lda     font_glyph_digits+2,y
75fb: 9d 80 34                     sta     HIRES_P1+$1480,x
75fe: b9 18 70                     lda     font_glyph_digits+1,y
7601: 9d 80 38                     sta     HIRES_P1+$1880,x
7604: b9 17 70                     lda     font_glyph_digits,y
7607: 9d 80 3c                     sta     HIRES_P1+$1c80,x
760a: e8                           inx
760b: 60                           rts

760c: 09                           .junk   1
760d: 26           copy_prot_const .dd1    $26
760e: 07           :saved_yreg     .dd1    $07

                   ; 
                   ; Creates a new instance of a shape.  Chooses a random shape from the requested
                   ; shape class.
                   ; 
                   ; If we don't have enough room, this returns without creating anything.
                   ; 
                   ; On entry:
                   ;   Y-reg: shape class index (0-11)
                   ; 
                   ; On exit:
                   ;   $62: index of newly-created object
                   ; 
                   • Clear variables
                   ]shape_cls_ptr  .var    $16    {addr/2}
                   ]offset_tab_ptr .var    $18    {addr/2}
                   ]rng_limit_mode .var    $88    {addr/1}
                   ]rng_result     .var    $8a    {addr/2}

760f: ea           CreateObject    nop
7610: 8c 0e 76                     sty     :saved_yreg
7613: 84 a3                        sty     shape_cl_index
7615: 98                           tya
7616: 0a                           asl     A                 ;double it
7617: a8                           tay                       ;keep it in Y-reg
7618: ad 00 40                     lda     shape_data_offset ;create a pointer to $53f1
761b: 85 18                        sta     ]offset_tab_ptr
761d: 18                           clc
761e: ad 01 40                     lda     shape_data_offset+1
7621: 69 40                        adc     #>DATA_AREA
7623: 85 19                        sta     ]offset_tab_ptr+1 ;$18-19 is now a pointer to shape class offset table
7625: b1 18                        lda     (]offset_tab_ptr),y ;look up value specified by Y-reg
7627: 85 16                        sta     ]shape_cls_ptr    ;store in $16-17
7629: 18                           clc
762a: c8                           iny
762b: b1 18                        lda     (]offset_tab_ptr),y
762d: 69 40                        adc     #>DATA_AREA
762f: 85 17                        sta     ]shape_cls_ptr+1  ;$16-17 is now pointer to shape_NN
                   ]shape_ptr      .var    $18    {addr/2}

7631: a9 ff                        lda     #$ff
7633: 85 88                        sta     ]rng_limit_mode   ;don't limit RNG result
7635: ea                           nop
7636: 20 b0 7b                     jsr     GenRandom         ;sets $8a-8b
7639: a5 8b                        lda     ]rng_result+1     ;get semi-random value
763b: a0 00                        ldy     #$00
763d: 31 16                        and     (]shape_cls_ptr),y ;AND with shape's item AND mask
763f: 0a                           asl     A                 ;double it
7640: 69 02                        adc     #$02              ;add 2 to skip header (mask + unused byte)
7642: a8                           tay
7643: b1 16                        lda     (]shape_cls_ptr),y ;get offset to shape entry
7645: 85 18                        sta     ]shape_ptr        ;set pointer
7647: c8                           iny
7648: b1 16                        lda     (]shape_cls_ptr),y
764a: ac 0d 76                     ldy     copy_prot_const   ;Y-reg=$26
764d: 18                           clc
764e: 69 40                        adc     #>DATA_AREA
7650: 85 19                        sta     ]shape_ptr+1      ;$18-19 is now pointer to shape_NN_X
7652: 20 7f 7f                     jsr     Return7f7f
                   ; Copy-protection booby-trap.  Loads a constant value from $760d and uses it to
                   ; load a constant value from $0037.  If the value at $0037 isn't $25, the code
                   ; below executes, stomping on a semi-random memory location.  The game will
                   ; seize up after a couple of seconds.
7655: b9 11 00                     lda     $0011,y           ;get value from $0037
7658: c9 25                        cmp     #$25              ;is it $25?
765a: f0 14                        beq     :Okay             ;yes, all is well
765c: a5 8a                        lda     ]rng_result       ;no, perform random sabotage
765e: 29 7f                        and     #$7f
7660: 85 8a                        sta     ]rng_result
7662: b1 8a                        lda     (]rng_result),y
7664: a0 e7                        ldy     #$e7              ;write to an offset to be sneaky
7666: 91 8a                        sta     (]rng_result),y
7668: a9 00                        lda     #$00              ;overwrite the pointer
766a: 85 8a                        sta     ]rng_result
766c: a9 20                        lda     #$20
766e: 85 8b                        sta     ]rng_result+1
                   ; 
7670: a0 00        :Okay           ldy     #$00
7672: b1 18                        lda     (]shape_ptr),y    ;get number of elements in shape
7674: 8d 79 6d                     sta     element_count
7677: c5 6e                        cmp     free_elem_count   ;do we have room?
7679: 30 03                        bmi     :HaveRoom         ;yes, branch
767b: f0 01                        beq     :HaveRoom
767d: 60                           rts

767e: a6 66        :HaveRoom       ldx     avail_obj_index   ;get next available slot num
7680: 86 62                        stx     cur_obj_index     ;use as slot num
7682: 10 02                        bpl     :HaveSlot         ;branch if slot number okay
7684: ea                           nop
7685: 60                           rts

7686: bd 00 9a     :HaveSlot       lda     obj_first_elem_index,x ;check the head of the element list
7689: 30 03                        bmi     :SlotGood         ;entry is unused as expected; branch
768b: 4c 5c 81                     jmp     PartialRestart    ;list is bad, reset state

768e: bc 50 9a     :SlotGood       ldy     obj_next_obj,x    ;get index of next object
7691: 84 66                        sty     avail_obj_index   ;remember it for next time
7693: a5 6a                        lda     head_obj_index    ;get previous obj list head index
7695: 86 6a                        stx     head_obj_index    ;set new object as head of list
7697: 9d 50 9a                     sta     obj_next_obj,x    ;put previous head in "next" pointer
                   ; Copy data from +$08-11 in shape header (zmin, zmax, hitbox).
769a: a0 11                        ldy     #$11
769c: b1 18        :Copy8Loop      lda     (]shape_ptr),y
769e: 99 79 6d                     sta     element_count,y
76a1: 88                           dey
76a2: b1 18                        lda     (]shape_ptr),y
76a4: 99 79 6d                     sta     element_count,y
76a7: 88                           dey
76a8: c0 08                        cpy     #$08
76aa: 10 f0                        bpl     :Copy8Loop
                   ; 
76ac: c6 6d                        dec     free_obj_count    ;decrement number of free object slots
76ae: a5 a3                        lda     shape_cl_index    ;get the shape class index
76b0: 9d 08 9c                     sta     obj_shape_cl_index,x ;store
76b3: ac 0e 76                     ldy     :saved_yreg       ;get the shape class index, from a different place
76b6: b9 69 6d                     lda     active_class_ctrs,y ;get the by-class active object count
76b9: 18                           clc
76ba: 69 01                        adc     #$01              ;increment it
                   ; Copy some more values out of the shape header.  Set various object entries.
76bc: 99 69 6d                     sta     active_class_ctrs,y
76bf: a0 00                        ldy     #$00
76c1: c8                           iny                       ;Y=$01
76c2: b1 18                        lda     (]shape_ptr),y    ;get object lifetime
76c4: 9d 28 9a                     sta     obj_lifetime_ctr,x
76c7: c8                           iny                       ;Y=$02
76c8: b1 18                        lda     (]shape_ptr),y    ;get enemy score class
76ca: 9d 78 9a                     sta     obj_score_class,x
76cd: ea                           nop
76ce: f0 13                        beq     :NoPoints         ;if not an enemy ship or base, branch
76d0: a9 dd                        lda     #$dd
76d2: 9d f0 9a                     sta     obj_next_enemy_index,x ;set next-enemy index to "none"
76d5: a5 6c                        lda     head_enemy_obj_index ;get previous enemy index
76d7: 86 6c                        stx     head_enemy_obj_index ;replace previous enemy index with ourselves
76d9: 9d c8 9a                     sta     obj_prev_enemy_index,x ;set our "previous enemy" link
76dc: a8                           tay                       ;was the previous-enemy index valid?
76dd: 30 04                        bmi     :NoPoints         ;no, branch
76df: 8a                           txa                       ;A-reg = our new object index
76e0: 99 f0 9a                     sta     obj_next_enemy_index,y ;yes, set previous object's next-enemy link to us
76e3: a0 02        :NoPoints       ldy     #$02
76e5: c8                           iny                       ;Y=$03
76e6: b1 18                        lda     (]shape_ptr),y
76e8: 9d a0 9a                     sta     obj_shape_uid,x
76eb: c8                           iny                       ;Y=$04
76ec: b1 18                        lda     (]shape_ptr),y
76ee: 9d 18 9b                     sta     obj_activity_state,x
76f1: 8d 7d 6d                     sta     shape_act_type
76f4: c8                           iny                       ;Y=$05
76f5: b1 18                        lda     (]shape_ptr),y
76f7: 9d 40 9b                     sta     obj_plyr_proj_flag,x
76fa: c8                           iny                       ;Y=$06
76fb: b1 18                        lda     (]shape_ptr),y
76fd: 9d 68 9b                     sta     vel_change_intvl_max,x
7700: a0 0e                        ldy     #$0e
7702: c8                           iny                       ;Y=$0f
7703: b1 18                        lda     (]shape_ptr),y
7705: 9d b8 9b                     sta     hitbox_size_lo,x
7708: c8                           iny                       ;Y=$10
7709: b1 18                        lda     (]shape_ptr),y
770b: 9d e0 9b                     sta     hitbox_size_hi,x
770e: 20 7f 7f                     jsr     Return7f7f
                   ; Set initial position.
7711: a0 07                        ldy     #$07
7713: b1 18                        lda     (]shape_ptr),y    ;get shape header +$07
7715: f0 21                        beq     :Jmp_SetPosGeneral ;value is $00 for most shapes
7717: 30 2e                        bmi     :SetPosnCenter    ;$ff for player projectiles and Epoch logo
7719: c9 7f                        cmp     #$7f              ;$7f for portal boundaries
771b: f0 1e                        beq     :Jmp_SetBoundPosn
771d: c9 7e                        cmp     #$7e              ;$7e for explosion flare and chunks
771f: f0 1d                        beq     :SetPosnExpl
                   ; A-reg=$ff (logo, player projectile) or $01/$02 (enemy projectile).  We look
                   ; for an object whose ship class matches the projectile type (1=base, 2=ship). 
                   ; If we find it, we set the projectile's position to match.  (This is why time
                   ; portals can shoot at you.)
7721: a4 6a                        ldy     head_obj_index
7723: ea                           nop                       ;A-reg=$ff (logo, plyr proj) or $01/$02 (enemy proj)
7724: d9 08 9c     :FindLoop       cmp     obj_shape_cl_index,y ;compare to shape class (0-11)
7727: f0 32                        beq     :CopyPrev         ;(found ship that fired projectile?)
7729: be 50 9a                     ldx     obj_next_obj,y    ;get index of next object
772c: 30 0a                        bmi     :Jmp_SetPosGeneral ;reached end of list, do general positioning
772e: dd 08 9c                     cmp     obj_shape_cl_index,x ;compare to shape class (0-11)
7731: f0 2d                        beq     :CopyObjPosn      ;(found ship that fired projectile?)
7733: bc 50 9a                     ldy     obj_next_obj,x    ;get index of next object
7736: 10 ec                        bpl     :FindLoop         ;if not done, loop
                   :Jmp_SetPosGeneral
7738: 4c 8d 77                     jmp     :SetPosnGeneral

                   :Jmp_SetBoundPosn
773b: 4c 06 79                     jmp     :SetBoundaryPosn

                   ]rng_limit      .var    $86    {addr/2}
                   ]initial_zpos   .var    $8c    {addr/2}
                   ]src_obj_index  .var    $8e    {addr/1}

773e: a5 a2        :SetPosnExpl    lda     linked_obj_index  ;get index of object that exploded
7740: 29 3f                        and     #$3f              ;(value is $00-27, not sure what this is for)
7742: 85 8e                        sta     ]src_obj_index
7744: 4c 62 77                     jmp     :CopyObjPosn1

                   ; Sets the initial object position to the center of the screen.  Useful for
                   ; player projectiles and the Epoch logo.
7747: a9 00        :SetPosnCenter  lda     #$00
7749: 85 bf                        sta     initial_xpos
774b: 85 c0                        sta     initial_xpos+1
774d: 85 c1                        sta     initial_ypos
774f: 85 c2                        sta     initial_ypos+1
7751: 85 8c                        sta     ]initial_zpos
7753: 85 8d                        sta     ]initial_zpos+1
7755: 20 7f 7f                     jsr     Return7f7f
7758: 4c 2a 79                     jmp     :InitPosnRdy

775b: 84 8e        :CopyPrev       sty     ]src_obj_index
775d: 4c 62 77                     jmp     :CopyObjPosn1

                   ; Copy position from existing object.  The top/left coordinate of the first
                   ; element is used.
7760: 86 8e        :CopyObjPosn    stx     ]src_obj_index
7762: a4 8e        :CopyObjPosn1   ldy     ]src_obj_index
7764: be 00 9a                     ldx     obj_first_elem_index,y ;get index of first element
7767: bd c0 a1                     lda     elem_left_lo,x    ;copy left to X
776a: 85 bf                        sta     initial_xpos
776c: bd 00 a2                     lda     elem_left_hi,x
776f: 85 c0                        sta     initial_xpos+1
7771: bd 40 a2                     lda     elem_top_lo,x     ;copy top to Y
7774: 85 c1                        sta     initial_ypos
7776: bd 80 a2                     lda     elem_top_hi,x
7779: 85 c2                        sta     initial_ypos+1
777b: bd 40 a1                     lda     elem_zpos_lo,x    ;copy Z
777e: 85 8c                        sta     ]initial_zpos
7780: bd 80 a1                     lda     elem_zpos_hi,x
7783: 85 8d                        sta     ]initial_zpos+1
7785: a6 62                        ldx     cur_obj_index
7787: 20 7f 7f                     jsr     Return7f7f
778a: 4c 2a 79                     jmp     :InitPosnRdy

                   ; Sets initial position for ships, bases, stars.
778d: a6 62        :SetPosnGeneral ldx     cur_obj_index
778f: 18                           clc                       ;do sound stuff
7790: a5 b2                        lda     engine_sound_ctr?+1
7792: 69 1a                        adc     #$1a
7794: 85 b2                        sta     engine_sound_ctr?+1
7796: 90 0f                        bcc     :NoSound
7798: e6 b3                        inc     engine_sound_ctr?+2
779a: a5 cc                        lda     engine_sound_enable
779c: f0 09                        beq     :NoSound
779e: a5 b3                        lda     engine_sound_ctr?+2
77a0: 25 b1                        and     engine_sound_ctr?
77a2: d0 03                        bne     :NoSound
77a4: ad 30 c0                     lda     SPKR
                   ; Perform some calculations on linear and angular speed to form the limit we
                   ; pass to the RNG, then generate a random value.
77a7: ad aa 6d     :NoSound        lda     joystick_x_mag    ;sum up the joystick axis magnitudes
77aa: 18                           clc
77ab: 6d ad 6d                     adc     joystick_y_mag
77ae: 8d ab 6d                     sta     joy_mag_sum
77b1: a5 99                        lda     adj_fwd_speed+1   ;get high byte of forward speed
77b3: 29 0f                        and     #%00001111        ;(max speed is $0384 (9000), so this does nothing)
77b5: 85 8c                        sta     ]initial_zpos
77b7: a5 98                        lda     adj_fwd_speed     ;get low byte
77b9: 29 f0                        and     #%11110000        ;strip low nibble
77bb: 05 8c                        ora     ]initial_zpos     ;blend with low nibble of high byte
77bd: a8                           tay
77be: b9 00 b0                     lda     speed_table?,y    ;get value from table
77c1: a4 99                        ldy     adj_fwd_speed+1   ;get high byte of forward speed
77c3: 10 03                        bpl     :IsPos            ;branch if positive (always)
77c5: 49 ff                        eor     #$ff              ;(perhaps at one time the player could go backwards?)
77c7: ea                           nop
77c8: 18           :IsPos          clc
77c9: 6d ab 6d                     adc     joy_mag_sum       ;add the sum of the joystick magnitudes
77cc: 8d ac 6d                     sta     joy_mag_plus_spd
77cf: 09 02                        ora     #%00000010        ;set bit 1 (why?)
77d1: 85 86                        sta     ]rng_limit
77d3: a9 00                        lda     #$00
77d5: 85 88                        sta     ]rng_limit_mode   ;limit range
77d7: 85 87                        sta     ]rng_limit+1      ;high byte is zero
77d9: 90 03                        bcc     :NoInc
77db: e6 87                        inc     ]rng_limit+1      ;or, rarely, 1
77dd: ea                           nop
77de: 20 b0 7b     :NoInc          jsr     GenRandom
77e1: a5 8b                        lda     ]rng_result+1     ;get the high byte of the result
77e3: ea                           nop
77e4: f0 03                        beq     :WasZero          ;if zero, branch; this is most common case
77e6: 4c b1 78     :Jmp_PosnInside jmp     :SetPosnInside

                   ]random_val     .var    $8e    {addr/1}

77e9: a5 8a        :WasZero        lda     ]rng_result       ;get the low byte of the result
77eb: 85 8e                        sta     ]random_val       ;save for later
77ed: cd ab 6d                     cmp     joy_mag_sum       ;compare to the joystick sum
77f0: ea                           nop
77f1: b0 f3                        bcs     :Jmp_PosnInside   ;was >=, take less-common path
                   ; 
77f3: 18                           clc                       ;do sound stuff
77f4: a5 b2                        lda     engine_sound_ctr?+1
77f6: 69 26                        adc     #$26
77f8: 85 b2                        sta     engine_sound_ctr?+1
77fa: 90 0f                        bcc     :NoSound
77fc: e6 b3                        inc     engine_sound_ctr?+2
77fe: a5 cc                        lda     engine_sound_enable
7800: f0 09                        beq     :NoSound
7802: a5 b3                        lda     engine_sound_ctr?+2
7804: 25 b1                        and     engine_sound_ctr?
7806: d0 03                        bne     :NoSound
7808: ad 30 c0                     lda     SPKR
780b: 38           :NoSound        sec
                   ; Generate initial position, placing the object at one edge of the screen.
                   ; 
                   ; The distance calculation generates two random numbers and keeps the larger
                   ; one, probably as a way to bias the initial placement toward greater distance.
780c: ad 83 6d                     lda     shape_zmax        ;get max initial Z position for this shape
780f: ed 81 6d                     sbc     shape_zmin        ;subtract minimum position
7812: 85 86                        sta     ]rng_limit        ;save delta
7814: ad 84 6d                     lda     shape_zmax+1      ;repeat for high byte
7817: ed 82 6d                     sbc     shape_zmin+1
781a: 85 87                        sta     ]rng_limit+1
781c: 20 b0 7b                     jsr     GenRandom         ;generate random number between 0 and limit
781f: a5 8a                        lda     ]rng_result       ;copy value out
7821: 85 8c                        sta     ]initial_zpos
7823: a5 8b                        lda     ]rng_result+1
7825: 85 8d                        sta     ]initial_zpos+1
7827: 20 b0 7b                     jsr     GenRandom         ;generate a second random number
782a: a5 8a                        lda     ]rng_result
782c: c5 8c                        cmp     ]initial_zpos     ;compare new value to previous value
782e: a5 8b                        lda     ]rng_result+1
7830: e5 8d                        sbc     ]initial_zpos+1
7832: 10 08                        bpl     :KeepNew          ;new value bigger, keep it; branch
7834: a5 8c                        lda     ]initial_zpos     ;old value bigger, copy to RNG result
7836: 85 8a                        sta     ]rng_result
7838: a5 8d                        lda     ]initial_zpos+1
783a: 85 8b                        sta     ]rng_result+1
783c: 18           :KeepNew        clc
783d: a5 8a                        lda     ]rng_result       ;get result
783f: 6d 81 6d                     adc     shape_zmin        ;add minimum initial Z position
7842: 85 8c                        sta     ]initial_zpos     ;save as initial Z
7844: a5 8b                        lda     ]rng_result+1     ;same for high byte
7846: 6d 82 6d                     adc     shape_zmin+1
7849: 85 8d                        sta     ]initial_zpos+1
784b: 20 7f 7f                     jsr     Return7f7f
784e: a5 8c                        lda     ]initial_zpos     ;use full value as RNG limit
7850: 85 86                        sta     ]rng_limit
7852: a5 8d                        lda     ]initial_zpos+1
7854: 85 87                        sta     ]rng_limit+1
7856: a9 01                        lda     #$01
7858: 85 88                        sta     ]rng_limit_mode   ;set mode to return +/- value
785a: 20 b0 7b                     jsr     GenRandom         ;generate random value
785d: a5 8e                        lda     ]random_val       ;get the random number we generated earlier
785f: cd aa 6d                     cmp     joystick_x_mag    ;compare to joystick position
7862: ea                           nop
7863: 90 03                        bcc     :FasterYaw        ;branch if less (more likely if turning faster)
7865: 4c 8c 78                     jmp     :SlowerYaw

                   ; Set X/Y coordinates.  Assuming a 45-degree FOV, we can place an object at the
                   ; edge of the visible area by setting X=Z and/or Y=Z.
7868: a5 8a        :FasterYaw      lda     ]rng_result       ;set YC to random value, XC same as ZC
786a: 85 c1                        sta     initial_ypos      ; so it's at left or right edge
786c: a5 8b                        lda     ]rng_result+1
786e: 85 c2                        sta     initial_ypos+1
7870: a5 8c                        lda     ]initial_zpos
7872: 85 bf                        sta     initial_xpos
7874: a5 8d                        lda     ]initial_zpos+1
7876: 85 c0                        sta     initial_xpos+1
7878: a5 9c                        lda     joy_yaw_sign      ;which way are we turning?
787a: 30 0d                        bmi     :RightTurn        ;turning right, create ship on right edge; branch
787c: 38                           sec                       ;set X position to 0-X so it's on left edge
787d: a9 00                        lda     #$00
787f: e5 bf                        sbc     initial_xpos
7881: 85 bf                        sta     initial_xpos
7883: a9 00                        lda     #$00
7885: e5 c0                        sbc     initial_xpos+1
7887: 85 c0                        sta     initial_xpos+1
7889: 4c 2a 79     :RightTurn      jmp     :InitPosnRdy

788c: a5 8a        :SlowerYaw      lda     ]rng_result       ;set XC to random value, YC same as ZC
788e: 85 bf                        sta     initial_xpos      ; so it's at top or bottom edge
7890: a5 8b                        lda     ]rng_result+1
7892: 85 c0                        sta     initial_xpos+1
7894: a5 8c                        lda     ]initial_zpos
7896: 85 c1                        sta     initial_ypos
7898: a5 8d                        lda     ]initial_zpos+1
789a: 85 c2                        sta     initial_ypos+1
789c: ea                           nop
789d: a5 9f                        lda     joy_pitch_sign    ;which we are we turning?
789f: 30 0d                        bmi     :DownTurn         ;pitching downward, create at bottom; branch
78a1: 38                           sec                       ;set Y position to 0-Y so it's at top edge
78a2: a9 00                        lda     #$00
78a4: e5 c1                        sbc     initial_ypos
78a6: 85 c1                        sta     initial_ypos
78a8: a9 00                        lda     #$00
78aa: e5 c2                        sbc     initial_ypos+1
78ac: 85 c2                        sta     initial_ypos+1
78ae: 4c 2a 79     :DownTurn       jmp     :InitPosnRdy

                   ; Set the initial position somewhere in the middle of the view area, rather than
                   ; at the edge.  The 45 degree FOV means the Z coordinate defines the edges; we
                   ; reduce it by the size of the hitbox in an attempt to place it at least partly
                   ; on-screen.
78b1: ad 83 6d     :SetPosnInside  lda     shape_zmax        ;set Z position to max
78b4: 85 8c                        sta     ]initial_zpos
78b6: ad 84 6d                     lda     shape_zmax+1
78b9: 85 8d                        sta     ]initial_zpos+1
78bb: 38                           sec                       ;set RNG limit to max Z minus header tweak
78bc: a5 8c                        lda     ]initial_zpos
78be: ed 88 6d                     sbc     shape_hitbox
78c1: 85 86                        sta     ]rng_limit
78c3: a5 8d                        lda     ]initial_zpos+1
78c5: ed 89 6d                     sbc     shape_hitbox+1
78c8: 85 87                        sta     ]rng_limit+1
78ca: a9 01                        lda     #$01
78cc: 85 88                        sta     ]rng_limit_mode   ;set RNG to return +/-
78ce: ea                           nop
78cf: ad 3b 6d                     lda     game_active_flag  ;are we in demo mode?
78d2: d0 18                        bne     :NotDemo          ;no, branch
                   ; Tweaks to improve the appearance of ships in the title demo.  Does not affect
                   ; stars or projectiles.
78d4: a5 8a                        lda     ]rng_result
78d6: 29 0f                        and     #$0f
78d8: d0 12                        bne     :NotDemo          ;skip this next bit 15 out of 16 times
78da: a5 a3                        lda     shape_cl_index    ;get shape class index
78dc: c9 02                        cmp     #$02              ;enemy ship?
78de: f0 08                        beq     :IsDemoShip       ;yes, branch
78e0: c9 06                        cmp     #$06              ;friendly base?
78e2: f0 04                        beq     :IsDemoShip       ;yes, branch
78e4: c9 01                        cmp     #$01              ;enemy base?
78e6: d0 04                        bne     :NotDemo          ;no, skip this
78e8: a9 01        :IsDemoShip     lda     #$01
78ea: 85 87                        sta     ]rng_limit+1      ;set upper limit so things are near the center
78ec: 20 b0 7b     :NotDemo        jsr     GenRandom         ;generate random value
78ef: a5 8a                        lda     ]rng_result       ;save as X position
78f1: 85 bf                        sta     initial_xpos
78f3: a5 8b                        lda     ]rng_result+1
78f5: 85 c0                        sta     initial_xpos+1
78f7: 20 b0 7b                     jsr     GenRandom         ;generate another random value
78fa: a5 8a                        lda     ]rng_result       ;save as Y position
78fc: 85 c1                        sta     initial_ypos
78fe: a5 8b                        lda     ]rng_result+1
7900: 85 c2                        sta     initial_ypos+1
7902: ea                           nop
7903: 4c 2a 79                     jmp     :InitPosnRdy      ;continue

                   ; Sets the position of a time portal boundary object.  This was computed
                   ; earlier.
                   :SetBoundaryPosn
7906: a5 ce                        lda     portal_next_xc    ;copy $ce-d1 to $bf-c2
7908: 85 bf                        sta     initial_xpos
790a: a5 cf                        lda     portal_next_xc+1
790c: 85 c0                        sta     initial_xpos+1
790e: a5 d0                        lda     portal_next_yc
7910: 85 c1                        sta     initial_ypos
7912: a5 d1                        lda     portal_next_yc+1
7914: 85 c2                        sta     initial_ypos+1
7916: ad 83 6d                     lda     shape_zmax        ;set initial Z position to max ($2400 for all)
7919: 85 8c                        sta     ]initial_zpos
791b: ad 84 6d                     lda     shape_zmax+1
791e: 85 8d                        sta     ]initial_zpos+1
7920: a5 8d                        lda     ]initial_zpos+1   ;check high byte
7922: c9 20                        cmp     #$20              ;>= $20?  (time portal bounds are $24)
7924: 10 04                        bpl     :InitPosnRdy      ;yes, branch
7926: a9 20                        lda     #$20
7928: 85 8d                        sta     ]initial_zpos+1   ;ensure it's at least $20
                   ; 
                   ; Initial position is set.  Finish creation.  (Multiple things branch here.)
                   ; 
792a: 20 7f 7f     :InitPosnRdy    jsr     Return7f7f
792d: a5 8c                        lda     ]initial_zpos     ;add 2 to initial Z position (why... to
792f: 18                           clc                       ; prevent player projectiles at Z=0?)
7930: 69 02                        adc     #$02
7932: 85 8c                        sta     ]initial_zpos
7934: 90 02                        bcc     :NoInc
7936: e6 8d                        inc     ]initial_zpos+1
                   ; Initialize object slot.
7938: a9 00        :NoInc          lda     #$00
793a: 9d 10 9e                     sta     obj_move_zc_lo,x
793d: 9d 38 9e                     sta     obj_move_zc_hi,x
7940: 9d 60 9e                     sta     obj_move_xc_lo,x
7943: 9d 88 9e                     sta     obj_move_xc_hi,x
7946: 9d b0 9e                     sta     obj_move_yc_lo,x
7949: 9d d8 9e                     sta     obj_move_yc_hi,x
794c: 9d 20 9d                     sta     obj_spdlim_z_lo,x
794f: 9d 48 9d                     sta     obj_spdlim_z_hi,x
7952: 9d 70 9d                     sta     obj_spdlim_x_lo,x
7955: 9d 98 9d                     sta     obj_spdlim_x_hi,x
7958: 9d c0 9d                     sta     obj_spdlim_y_lo,x
795b: 9d e8 9d                     sta     obj_spdlim_y_hi,x
795e: 9d 30 9c                     sta     obj_move_zc2_lo,x
7961: 9d 58 9c                     sta     obj_move_zc2_hi,x
7964: 9d 80 9c                     sta     obj_move_xc2_lo,x
7967: 9d a8 9c                     sta     obj_move_xc2_hi,x
796a: 9d d0 9c                     sta     obj_move_yc2_lo,x
796d: 9d f8 9c                     sta     obj_move_yc2_hi,x
7970: a9 01                        lda     #$01
7972: 9d 90 9b                     sta     vel_change_ctr,x  ;queue a velocity change
                   ; Shape hdr +$04: 0 for most things, 1 for player projectiles and explosion
                   ; flares, 2 for explosion chunks, 3 for enemy ships (not bases)
7975: ad 7d 6d                     lda     shape_act_type
7978: f0 3f                        beq     :Jmp_DoneWithHdr
797a: c9 01                        cmp     #$01              ;player projectile or explosion flare?
797c: f0 31                        beq     :PlyrProjOrFlare  ;yes, branch
797e: a0 10                        ldy     #$10
7980: c8                           iny                       ;Y=$11
7981: b1 18                        lda     (]shape_ptr),y
7983: 9d 20 9d                     sta     obj_spdlim_z_lo,x
7986: c8                           iny
7987: b1 18                        lda     (]shape_ptr),y
7989: 9d 48 9d                     sta     obj_spdlim_z_hi,x
798c: c8                           iny
798d: b1 18                        lda     (]shape_ptr),y
798f: 9d 70 9d                     sta     obj_spdlim_x_lo,x
7992: c8                           iny
7993: b1 18                        lda     (]shape_ptr),y
7995: 9d 98 9d                     sta     obj_spdlim_x_hi,x
7998: c8                           iny
7999: b1 18                        lda     (]shape_ptr),y
799b: 9d c0 9d                     sta     obj_spdlim_y_lo,x
799e: c8                           iny                       ;Y=$16
799f: b1 18                        lda     (]shape_ptr),y
79a1: 9d e8 9d                     sta     obj_spdlim_y_hi,x
79a4: ea                           nop
79a5: a4 a2                        ldy     linked_obj_index  ;are we linked to another object?
79a7: 10 13                        bpl     :CreateLinked     ;yes, branch
79a9: a9 00                        lda     #$00              ;(?)
79ab: ea                           nop
79ac: 4c 39 7a                     jmp     :DoneWithHdr

                   :PlyrProjOrFlare
79af: a4 a2                        ldy     linked_obj_index  ;is a linked object specified?
79b1: 10 09                        bpl     :CreateLinked     ;yes, branch
79b3: a9 00                        lda     #$00
79b5: 9d 18 9b                     sta     obj_activity_state,x ;mark as non-moving
79b8: ea                           nop
                   :Jmp_DoneWithHdr
79b9: 4c 39 7a                     jmp     :DoneWithHdr

79bc: c0 7f        :CreateLinked   cpy     #$7f              ;player projectile?
79be: f0 3b                        beq     :PrepPlayerProj?  ;yes, branch
79c0: ea                           nop                       ;no, explosion flare or chunk
79c1: b9 10 9e                     lda     obj_move_zc_lo,y  ;copy object movement vectors
79c4: 9d 10 9e                     sta     obj_move_zc_lo,x
79c7: 9d 30 9c                     sta     obj_move_zc2_lo,x
79ca: b9 38 9e                     lda     obj_move_zc_hi,y
79cd: 9d 38 9e                     sta     obj_move_zc_hi,x
79d0: 9d 58 9c                     sta     obj_move_zc2_hi,x
79d3: b9 60 9e                     lda     obj_move_xc_lo,y
79d6: 9d 60 9e                     sta     obj_move_xc_lo,x
79d9: 9d 80 9c                     sta     obj_move_xc2_lo,x
79dc: b9 88 9e                     lda     obj_move_xc_hi,y
79df: 9d 88 9e                     sta     obj_move_xc_hi,x
79e2: 9d a8 9c                     sta     obj_move_xc2_hi,x
79e5: b9 b0 9e                     lda     obj_move_yc_lo,y
79e8: 9d b0 9e                     sta     obj_move_yc_lo,x
79eb: 9d d0 9c                     sta     obj_move_yc2_lo,x
79ee: b9 d8 9e                     lda     obj_move_yc_hi,y
79f1: 9d d8 9e                     sta     obj_move_yc_hi,x
79f4: 9d f8 9c                     sta     obj_move_yc2_hi,x
79f7: ea                           nop
79f8: 4c 39 7a                     jmp     :DoneWithHdr

                   ; Prepare player projectile.
                   :PrepPlayerProj?
79fb: a0 11                        ldy     #$11
79fd: b1 18                        lda     (]shape_ptr),y    ;get projectile max Z velocity
79ff: 18                           clc
7a00: 65 98                        adc     adj_fwd_speed     ;add to ship's forward speed
7a02: 9d 30 9c                     sta     obj_move_zc2_lo,x ;store in object movement table
7a05: 9d 10 9e                     sta     obj_move_zc_lo,x
7a08: c8                           iny                       ;Y=$12
7a09: b1 18                        lda     (]shape_ptr),y
7a0b: 65 99                        adc     adj_fwd_speed+1   ;repeat for high byte
7a0d: 9d 58 9c                     sta     obj_move_zc2_hi,x
7a10: 9d 38 9e                     sta     obj_move_zc_hi,x
7a13: ea                           nop
7a14: c8                           iny                       ;Y=$13
7a15: b1 18                        lda     (]shape_ptr),y    ;load zeroes for the rest of the movement
7a17: 9d 60 9e                     sta     obj_move_xc_lo,x
7a1a: 9d 80 9c                     sta     obj_move_xc2_lo,x
7a1d: c8                           iny                       ;Y=$14
7a1e: b1 18                        lda     (]shape_ptr),y
7a20: 9d 88 9e                     sta     obj_move_xc_hi,x
7a23: 9d a8 9c                     sta     obj_move_xc2_hi,x
7a26: c8                           iny                       ;Y=$15
7a27: b1 18                        lda     (]shape_ptr),y
7a29: 9d b0 9e                     sta     obj_move_yc_lo,x
7a2c: 9d d0 9c                     sta     obj_move_yc2_lo,x
7a2f: c8                           iny                       ;Y=$16
7a30: b1 18                        lda     (]shape_ptr),y
7a32: 9d d8 9e                     sta     obj_move_yc_hi,x
7a35: 9d f8 9c                     sta     obj_move_yc2_hi,x
7a38: ea                           nop
7a39: 18           :DoneWithHdr    clc                       ;do sound stuff
7a3a: a5 b2                        lda     engine_sound_ctr?+1
7a3c: 69 1d                        adc     #$1d
7a3e: 85 b2                        sta     engine_sound_ctr?+1
7a40: 90 0f                        bcc     :NoSound
7a42: e6 b3                        inc     engine_sound_ctr?+2
7a44: a5 cc                        lda     engine_sound_enable
7a46: f0 09                        beq     :NoSound
7a48: a5 b3                        lda     engine_sound_ctr?+2
7a4a: 25 b1                        and     engine_sound_ctr?
7a4c: d0 03                        bne     :NoSound
7a4e: ad 30 c0                     lda     SPKR
                   ; Advance to first element.
7a51: a5 18        :NoSound        lda     ]shape_ptr        ;get shape pointer
7a53: 18                           clc
7a54: 69 18                        adc     #24               ;24 bytes in shape header
7a56: 85 18                        sta     ]shape_ptr
7a58: 90 02                        bcc     :NoInc
7a5a: e6 19                        inc     ]shape_ptr+1
                   ]elem_ptr       .var    $18    {addr/2}

7a5c: a5 68        :NoInc          lda     avail_elem_index  ;get next available index
7a5e: 85 64                        sta     cur_elem_index    ;save as current index
7a60: 9d 00 9a                     sta     obj_first_elem_index,x ;set as first element in object's list
7a63: ea                           nop
7a64: a6 64        :NextElement    ldx     cur_elem_index    ;get index of next element
7a66: bd 00 9f                     lda     elem_obj_index,x  ;see if something is here
7a69: 30 03                        bmi     :IndexOkay        ;unused, we're good; branch
7a6b: 4c 5c 81                     jmp     PartialRestart    ;unexpected, reset state

7a6e: bd 40 9f     :IndexOkay      lda     elem_next_elem,x  ;get index of next element in list
7a71: 85 68                        sta     avail_elem_index  ;update next-available element index
7a73: 18                           clc                       ;do sound stuff
7a74: a5 b2                        lda     engine_sound_ctr?+1
7a76: 69 12                        adc     #$12
7a78: 85 b2                        sta     engine_sound_ctr?+1
7a7a: 90 0f                        bcc     :NoSound
7a7c: e6 b3                        inc     engine_sound_ctr?+2
7a7e: a5 cc                        lda     engine_sound_enable
7a80: f0 09                        beq     :NoSound
7a82: a5 b3                        lda     engine_sound_ctr?+2
7a84: 25 b1                        and     engine_sound_ctr?
7a86: d0 03                        bne     :NoSound
7a88: ad 30 c0                     lda     SPKR
7a8b: c6 6e        :NoSound        dec     free_elem_count
7a8d: a5 62                        lda     cur_obj_index     ;get the object index
7a8f: 9d 00 9f                     sta     elem_obj_index,x  ;set as back-ref in element table
7a92: a0 00                        ldy     #$00
7a94: b1 18                        lda     (]elem_ptr),y     ;get element type
7a96: 9d c0 9f                     sta     elem_types,x
7a99: c8                           iny
7a9a: b1 18                        lda     (]elem_ptr),y     ;get color A
7a9c: 9d 00 a0                     sta     elem_colorsA,x
7a9f: 9d 80 a0                     sta     elem_cur_colors,x
7aa2: c8                           iny
7aa3: b1 18                        lda     (]elem_ptr),y     ;get color B
7aa5: 9d 40 a0                     sta     elem_colorsB,x
7aa8: c8                           iny
7aa9: b1 18                        lda     (]elem_ptr),y     ;color change freq
7aab: 9d c0 a0                     sta     elem_colorchanges,x
7aae: 9d 00 a1                     sta     elem_colorchange_ctrs,x
7ab1: ea                           nop
                   ; Copy the element coordinates, adjusting them for the initial position computed
                   ; earlier.
7ab2: c8                           iny                       ;Y=$04
7ab3: b1 18                        lda     (]elem_ptr),y     ;get Z offset
7ab5: 18                           clc
7ab6: 65 8c                        adc     ]initial_zpos
7ab8: 9d 40 a1                     sta     elem_zpos_lo,x
7abb: c8                           iny
7abc: b1 18                        lda     (]elem_ptr),y
7abe: 65 8d                        adc     ]initial_zpos+1
7ac0: 9d 80 a1                     sta     elem_zpos_hi,x
7ac3: c8                           iny
7ac4: b1 18                        lda     (]elem_ptr),y     ;get left coord
7ac6: 18                           clc
7ac7: 65 bf                        adc     initial_xpos
7ac9: 9d c0 a1                     sta     elem_left_lo,x
7acc: c8                           iny
7acd: b1 18                        lda     (]elem_ptr),y
7acf: 65 c0                        adc     initial_xpos+1
7ad1: 9d 00 a2                     sta     elem_left_hi,x
7ad4: c8                           iny
7ad5: b1 18                        lda     (]elem_ptr),y     ;get top coord
7ad7: 18                           clc
7ad8: 65 c1                        adc     initial_ypos
7ada: 9d 40 a2                     sta     elem_top_lo,x
7add: c8                           iny
7ade: b1 18                        lda     (]elem_ptr),y
7ae0: 65 c2                        adc     initial_ypos+1
7ae2: 9d 80 a2                     sta     elem_top_hi,x
7ae5: c8                           iny
7ae6: b1 18                        lda     (]elem_ptr),y     ;get right coord
7ae8: 18                           clc
7ae9: 65 bf                        adc     initial_xpos
7aeb: 9d c0 a2                     sta     elem_right_lo,x
7aee: c8                           iny
7aef: b1 18                        lda     (]elem_ptr),y
7af1: 65 c0                        adc     initial_xpos+1
7af3: 9d 00 a3                     sta     elem_right_hi,x
7af6: c8                           iny
7af7: b1 18                        lda     (]elem_ptr),y     ;get bottom coord
7af9: 18                           clc
7afa: 65 c1                        adc     initial_ypos
7afc: 9d 40 a3                     sta     elem_bottom_lo,x
7aff: c8                           iny
7b00: b1 18                        lda     (]elem_ptr),y
7b02: 65 c2                        adc     initial_ypos+1
7b04: 9d 80 a3                     sta     elem_bottom_hi,x
7b07: ea                           nop
7b08: a9 00                        lda     #$00
7b0a: 9d 40 a5                     sta     elem_erase_6,x    ;init pixel bit mask?
7b0d: a9 83                        lda     #$83
7b0f: 9d 80 9f                     sta     elem_mod_types,x  ;flag as newly-created, not yet drawn
7b12: ce 79 6d                     dec     element_count     ;decrement the counter
7b15: f0 17                        beq     :Done             ;done, bail
7b17: a5 68                        lda     avail_elem_index  ;do we have room for another element?
7b19: 30 13                        bmi     :Done             ;no, bail with partial definition
7b1b: 85 64                        sta     cur_elem_index    ;set "next elem" as current
7b1d: 9d 40 9f                     sta     elem_next_elem,x  ;store it in element list as well
7b20: a5 18                        lda     ]elem_ptr         ;advance element pointer 16 bytes
7b22: 18                           clc
7b23: 69 10                        adc     #16
7b25: 85 18                        sta     ]elem_ptr
7b27: 90 02                        bcc     :NoInc
7b29: e6 19                        inc     ]elem_ptr+1       ;advance high byte
7b2b: 4c 64 7a     :NoInc          jmp     :NextElement

7b2e: a9 fc        :Done           lda     #$fc
7b30: 9d 40 9f                     sta     elem_next_elem,x  ;mark the end of the element list
7b33: ea                           nop
7b34: ea                           nop
7b35: 60                           rts

                   ; 
                   ; Draws the status line.  Each call here draws one character and increments the
                   ; index, so this must be called 40x to draw the whole thing.
                   ; 
7b36: ee ce 6d     DrawStatusLine  inc     status_line_index ;advance to next char
7b39: ae ce 6d                     ldx     status_line_index ;get current index
7b3c: e0 28                        cpx     #40               ;reached end of line?
7b3e: 30 05                        bmi     :NotEnd           ;not yet, branch
7b40: a2 00                        ldx     #$00
7b42: 8e ce 6d                     stx     status_line_index ;reset to start of line
7b45: bd 85 6e     :NotEnd         lda     text_score_time,x ;get one character
7b48: 20 b9 73                     jsr     PrintCharLine0    ;draw that character
7b4b: 60                           rts

                   ; 
                   ; Modifies the instructions that draw and erase vertical lines and rects.  Can
                   ; be used to prevent these two functions from modifying the hi-res screen.
                   ; 
                   ; (It's unclear what purpose this serves.  Might be an attempt to confuse
                   ; somebody disassembling a memory snapshot?  As far as I can tell, the
                   ; draw/erase functions are never actually called in "LDA mode".)
                   ; 
                   ; On entry:
                   ;   A-reg: opcode ($20 for JSR, $ad for LDA)
                   ; 
7b4c: 8d 98 90     ModDrwEraVrtRct sta     _CallOra0         ;draw vert line
7b4f: 8d a4 91                     sta     _CallOraSta1      ;draw rect
7b52: 8d c3 91                     sta     _CallOraSta2
7b55: 8d f1 91                     sta     _CallOraSta3
7b58: 8d 63 8d                     sta     _CallAnd0         ;erase vert line
7b5b: 8d 07 8e                     sta     _CallAnd1         ;erase rect
7b5e: 8d 2a 8e                     sta     _CallAnd2
7b61: 8d 47 8e                     sta     _CallAnd3
7b64: 60                           rts

7b65: 83 8c b4 97+                 .junk   75

                   ; 
                   ; Generates "random" values.
                   ; 
                   ; I'm not sure what the mathematical basis for this is.  It seems a bit ad hoc.
                   ; 
                   ; The return value can optionally be limited to a range.  When the mode is $00,
                   ; a limit of 100 produces a result in the range [0,100].  When the mode is $01,
                   ; odd results are negated, so the range becomes [-99,100] stepping by 2.
                   ; 
                   ; On entry:
                   ;   $86-87: max value (inclusive)
                   ;   $88: $00=limit range, $01=limit and pos/neg, $ff=no limit
                   ; 
                   ; On exit:
                   ;   $89: copy of $8b before attempts to limit value
                   ;   $8a-8b: "random" value
                   ;   X-reg preserved
                   ; 
                   • Clear variables
                   ]rng_limit      .var    $86    {addr/2}
                   ]rng_limit_mode .var    $88    {addr/1}
                   ]retval_unmod   .var    $89    {addr/1}
                   ]retval         .var    $8a    {addr/2}

7bb0: 8e c7 6c     GenRandom       stx     saved_xreg_7bb0   ;preserve X-reg
7bb3: 38           :Retry          sec
7bb4: ad c6 6c                     lda     rng_counter       ;get counter [0,54]
7bb7: e9 18                        sbc     #24               ;subtract 24 [-24,30]
7bb9: 10 03                        bpl     :Ge24             ;[0,30], branch
7bbb: 18                           clc                       ;now [-24,-1]
7bbc: 69 37                        adc     #55               ;add 55 [31,54]
7bbe: aa           :Ge24           tax                       ;X-reg now [0,54] but flipped around
7bbf: ac c6 6c                     ldy     rng_counter       ;get original counter in Y-reg
7bc2: 18                           clc
7bc3: b9 c8 6c                     lda     rng_state1,y      ;get first value
7bc6: 7d c8 6c                     adc     rng_state1,x      ;add to alternate value in same table
7bc9: 85 8a                        sta     ]retval           ;set as return value
7bcb: ea                           nop
7bcc: 99 c8 6c                     sta     rng_state1,y      ;update state
7bcf: b9 ff 6c                     lda     rng_state2,y      ;get second value
7bd2: 7d ff 6c                     adc     rng_state2,x      ;add to alternate value in same table
7bd5: 85 8b                        sta     ]retval+1
7bd7: 85 89                        sta     ]retval_unmod     ;return a copy
7bd9: 99 ff 6c                     sta     rng_state2,y      ;update state
7bdc: a8                           tay
7bdd: ea                           nop
                   ; Advance to the next set of "random" values.
7bde: ee c6 6c                     inc     rng_counter       ;increment index
7be1: ad c6 6c                     lda     rng_counter       ;check current value
7be4: c9 37                        cmp     #55               ;reached limit?
7be6: 30 06                        bmi     :CounterOk        ;no, branch
7be8: a9 00                        lda     #$00
7bea: 8d c6 6c                     sta     rng_counter       ;reset counter
7bed: ea                           nop
                   ; Check the mode to see if we need to limit the range.  If so, we generate a
                   ; mask for the argument and apply it to the result.  If the result is out of
                   ; range, retry.
7bee: a5 88        :CounterOk      lda     ]rng_limit_mode   ;is mode $ff?
7bf0: 30 4d                        bmi     :Return           ;yes, bail
7bf2: a4 87                        ldy     ]rng_limit+1      ;get high byte of limit
7bf4: f0 18                        beq     :ArgHiZero        ;it's zero, just check the low byte
7bf6: be 00 b9                     ldx     clz_table,y       ;count leading zeroes in arg
7bf9: b5 de                        lda     bit_mask_right9,x ;get mask that covers bits
7bfb: 25 8b                        and     ]retval+1         ;mask the return value byte with it
7bfd: 85 8b                        sta     ]retval+1         ;save it
7bff: c5 87                        cmp     ]rng_limit+1      ;compare to high byte of arg
7c01: ea                           nop                       ; in case arg is not (2^N)-1
7c02: f0 05                        beq     :CheckLow         ;matched, check low byte
7c04: 10 ad                        bpl     :Retry            ;larger than arg, try again
7c06: 4c 27 7c                     jmp     :GoodRange        ;smaller, value is fine

7c09: a5 8a        :CheckLow       lda     ]retval           ;get low byte of result
7c0b: 4c 20 7c                     jmp     :CheckLow2

7c0e: a9 00        :ArgHiZero      lda     #$00
7c10: 85 8b                        sta     ]retval+1         ;limit hi is zero, so result hi will be zero
7c12: a4 86                        ldy     ]rng_limit        ;get low byte of limit arg
7c14: f0 2e                        beq     :Return0          ;looks like they really want zero; branch
7c16: be 00 b9                     ldx     clz_table,y       ;count leading zeroes in arg
7c19: b5 de                        lda     bit_mask_right9,x ;get mask that covers bits
7c1b: 25 8a                        and     ]retval           ;mask return value byte with it
7c1d: 85 8a                        sta     ]retval           ;save low byte
7c1f: ea                           nop
7c20: c5 86        :CheckLow2      cmp     ]rng_limit        ;compare low byte of result to low byte of limit
7c22: ea                           nop
7c23: f0 02                        beq     :GoodRange        ;they match, accept it
7c25: b0 8c                        bcs     :Retry            ;return value too large, re-roll
7c27: a5 88        :GoodRange      lda     ]rng_limit_mode   ;check mode
7c29: f0 14                        beq     :Return           ;is zero, we're done
                   ; Generate a negative result half the time.
7c2b: a5 8a                        lda     ]retval
7c2d: 29 01                        and     #$01              ;is it odd or even?
7c2f: f0 0e                        beq     :Return           ;even, bail
7c31: 38                           sec                       ;odd, compute (0 - retval)
7c32: a9 00                        lda     #$00
7c34: e5 8a                        sbc     ]retval
7c36: 85 8a                        sta     ]retval
7c38: a9 00                        lda     #$00
7c3a: e5 8b                        sbc     ]retval+1
7c3c: 85 8b                        sta     ]retval+1
7c3e: ea                           nop
7c3f: ae c7 6c     :Return         ldx     saved_xreg_7bb0   ;restore X-reg
7c42: ea                           nop
7c43: 60                           rts

7c44: a9 00        :Return0        lda     #$00              ;set return value to zero
7c46: 85 8a                        sta     ]retval
7c48: 85 8b                        sta     ]retval+1
7c4a: ea                           nop
7c4b: 4c 3f 7c                     jmp     :Return

                   ; 
                   ; Sets the color of lo-res graphics page 2.
                   ; 
                   ; This takes 16 + (5*4 + 2 + 3) * 256 - 1 + 6 = 6421 cycles.
                   ; 
                   ; On entry:
                   ;   A-reg: color (0-15)
                   ; 
                   ]lr_color       .var    $8c    {addr/1}

7c4e: 85 8c        SetLoRes2       sta     ]lr_color         ;shift color so it's in both nibbles
7c50: 0a                           asl     A
7c51: 0a                           asl     A
7c52: 0a                           asl     A
7c53: 0a                           asl     A
7c54: 05 8c                        ora     ]lr_color
7c56: a0 00                        ldy     #$00
7c58: 99 00 08     :Loop           sta     $0800,y
7c5b: 99 00 09                     sta     $0900,y
7c5e: 99 00 0a                     sta     $0a00,y
7c61: 99 00 0b                     sta     $0b00,y
7c64: c8                           iny
7c65: d0 f1                        bne     :Loop
7c67: 60                           rts

                   ; 
                   ; Reduces the amount of a resource available to the player.  The resource counts
                   ; are stored as little-endian BCD values.
                   ; 
                   ; Possible values for X-reg/Y-reg:
                   ; 
                   ;   $05/$0f: $6dc2 (time), by 8
                   ;   $0b/$15: $6dc8 (amun), by 1
                   ;   $0d/$11: $6dca (speed), by 20
                   ;   $08/$39: $6dc5 (fuel), by 2
                   ;   $08/$37: $6dc5 (fuel), by 300
                   ; 
                   ; On entry:
                   ;   X-reg: index to resource counter (base $6dbd)
                   ;   Y-reg: index to increase amount (base $70e6)
                   ;   $8a: number of BCD bytes (2 digits per byte)
                   ; 
                   ; On exit:
                   ;   Carry set on underflow
                   ; 
                   • Clear variables
                   ]num_bytes      .var    $8a    {addr/1}
                   ]rsrc_index     .var    $8b    {addr/1}
                   ]digit_counter  .var    $8c    {addr/1}

7c68: ad 3b 6d     ReduceResource  lda     game_active_flag  ;game active?
7c6b: f0 2f                        beq     RsrcChangeOk      ;no, bail without changing
7c6d: a5 8a                        lda     ]num_bytes        ;get number of bytes to update
7c6f: 29 07                        and     #$07              ;limit to 0-7
7c71: 85 8c                        sta     ]digit_counter    ;save it
7c73: 86 8b                        stx     ]rsrc_index
7c75: f8                           sed                       ;switch to decimal mode
7c76: 38                           sec
7c77: bd bd 6d     :Loop           lda     resource_state,x  ;get resource digit
7c7a: f9 e6 70                     sbc     rating_thresholds,y ;subtract value
7c7d: 9d bd 6d                     sta     resource_state,x  ;save result
7c80: c8                           iny                       ;advance to next
7c81: e8                           inx
7c82: c6 8c                        dec     ]digit_counter    ;done with digits?
7c84: ea                           nop
7c85: d0 f0                        bne     :Loop             ;no, loop
7c87: b0 13                        bcs     RsrcChangeOk
                   ; Underflow, clamp to zero.  (Code also used for overflow.)
7c89: a9 00                        lda     #$00
7c8b: a4 8a        SetRsrcValue    ldy     ]num_bytes
7c8d: 88                           dey
7c8e: a6 8b                        ldx     ]rsrc_index
7c90: 9d bd 6d     :ZeroLoop       sta     resource_state,x  ;set all to zero
7c93: e8                           inx
7c94: 88                           dey
7c95: ea                           nop
7c96: 10 f8                        bpl     :ZeroLoop
7c98: d8                           cld
7c99: 38                           sec                       ;signal underflow
7c9a: ea                           nop
7c9b: 60                           rts

7c9c: 18           RsrcChangeOk    clc                       ;success
7c9d: d8                           cld
7c9e: ea                           nop
7c9f: 60                           rts

                   ; 
                   ; Increases the amount of a resource available to the player.  The resource
                   ; counts are stored as little-endian BCD values.
                   ; 
                   ; Possible values for X-reg/Y-reg:
                   ; 
                   ;   $05/$13: $6dc2 (time), by ($70f9)
                   ;   $0d/$11: $6dca (speed), by 20
                   ;   $00/$??: $6dbd (score), by shape-specific value
                   ; 
                   ; On entry:
                   ;   X-reg: index to resource counter (base $6dbd)
                   ;   Y-reg: index to increase amount (base $70e6)
                   ;   $8a: number of BCD bytes (2 digits per byte)
                   ; 
                   ; On exit:
                   ;   Carry set on underflow
                   ; 
                   IncreaseResource
7ca0: ad 3b 6d                     lda     game_active_flag  ;game active?
7ca3: f0 f7                        beq     RsrcChangeOk      ;no, bail without changing
7ca5: 86 8b                        stx     ]rsrc_index
7ca7: a5 8a                        lda     ]num_bytes        ;get number of bytes to update
7ca9: 85 8c                        sta     ]digit_counter
7cab: f8                           sed
7cac: 18                           clc
7cad: bd bd 6d     :Loop           lda     resource_state,x  ;get resource value
7cb0: 79 e6 70                     adc     rating_thresholds,y ;add increment value
7cb3: 9d bd 6d                     sta     resource_state,x  ;save it
7cb6: e8                           inx                       ;advance to next
7cb7: c8                           iny
7cb8: ea                           nop
7cb9: c6 8c                        dec     ]digit_counter    ;done with digits?
7cbb: d0 f0                        bne     :Loop             ;no, loop
7cbd: 90 dd                        bcc     RsrcChangeOk
                   ; Overflow.  Clamp to all 99s.
7cbf: a9 99                        lda     #$99
7cc1: ea                           nop
7cc2: 4c 8b 7c                     jmp     SetRsrcValue

                   ; 
7cc5: 4c a9 0f     Jmp_Memset      jmp     Memset

7cc8: ea a0 00 91+                 .junk   18

                   ; 
                   ; Sets up a sound to play over multiple frames.
                   ; 
                   ;  Y=$00 A=$00: player cannon fired
                   ;  Y=$02 A=(score class): enemy ship (non-base) destroyed
                   ; 
                   ; On entry:
                   ;   A-reg: sub-index (0-7)
                   ;   Y-reg: effect number ($00 or $02)
                   ;   X-reg preserved
                   ; 
                   • Clear variables
                   ]temp           .var    $86    {addr/1}
                   ]saved_xreg     .var    $87    {addr/1}

7cda: 86 87        InitiateSfx     stx     ]saved_xreg       ;preserve X-reg
7cdc: 85 86                        sta     ]temp
7cde: 0a                           asl     A                 ;multiply by 4
7cdf: 0a                           asl     A
7ce0: 18                           clc
7ce1: 65 86                        adc     ]temp             ;add to itself (multiply by 5)
7ce3: c0 02                        cpy     #$02              ;is Y-reg 0 or 1?
7ce5: 30 02                        bmi     :UseTable0        ;yes, branch
7ce7: 69 28                        adc     #40               ;add 40 so we're indexing table 1
7ce9: a0 00        :UseTable0      ldy     #$00
7ceb: aa                           tax
7cec: ad 48 6d                     lda     sound_disab_flag  ;sound disabled?
7cef: d0 11                        bne     :NoSound          ;yes, branch
7cf1: ad 3b 6d                     lda     game_active_flag
7cf4: f0 0c                        beq     :NoSound
7cf6: bd 71 71     :CopyLoop       lda     sfx_table_0,x     ;copy 5 bytes to $c8-cc
7cf9: 99 c8 00                     sta     sound_counters,y
7cfc: e8                           inx
7cfd: c8                           iny
7cfe: c0 05                        cpy     #$05
7d00: 30 f4                        bmi     :CopyLoop
7d02: a6 87        :NoSound        ldx     ]saved_xreg       ;restore X-reg
7d04: ea                           nop
7d05: 60                           rts

                   ; 
                   ; Updates the motion vector for an object.  Called on first update for enemy
                   ; ships and projectiles, and then called at random intervals for enemy ships.
                   ; 
                   ; Things generally move toward the player (at 0,0,0).
                   ; 
                   ; On entry:
                   ;   X-reg: object index
                   ; 
                   ; On exit:
                   ;   Object velocity values updated
                   ;   X-reg preserved
                   ; 
                   • Clear variables
                   ]left_coord     .var    $86    {addr/2}
                   ]top_coord      .var    $88    {addr/2}
                   ]z_coord        .var    $8a    {addr/2}
                   ]biggest_dim    .var    $8c    {addr/2}

                   UpdateObjectVelocity
7d06: 18                           clc                       ;do sound stuff
7d07: a5 b2                        lda     engine_sound_ctr?+1
7d09: 69 41                        adc     #$41
7d0b: 85 b2                        sta     engine_sound_ctr?+1
7d0d: 90 0f                        bcc     :NoSound
7d0f: e6 b3                        inc     engine_sound_ctr?+2
7d11: a5 cc                        lda     engine_sound_enable
7d13: f0 09                        beq     :NoSound
7d15: a5 b3                        lda     engine_sound_ctr?+2
7d17: 25 b1                        and     engine_sound_ctr?
7d19: d0 03                        bne     :NoSound
7d1b: ad 30 c0                     lda     SPKR
7d1e: bd 20 9d     :NoSound        lda     obj_spdlim_z_lo,x ;get maximum Z velocity
7d21: 8d 51 6d                     sta     max_z_spd_copy    ;save a copy
7d24: bd 48 9d                     lda     obj_spdlim_z_hi,x
7d27: 8d 52 6d                     sta     max_z_spd_copy+1
7d2a: bc 00 9a                     ldy     obj_first_elem_index,x ;get index of first element
7d2d: b9 c0 a1                     lda     elem_left_lo,y    ;copy element left/top/zc into DP storage
7d30: 85 86                        sta     ]left_coord
7d32: b9 00 a2                     lda     elem_left_hi,y
7d35: 85 87                        sta     ]left_coord+1
7d37: b9 40 a2                     lda     elem_top_lo,y
7d3a: 85 88                        sta     ]top_coord
7d3c: b9 80 a2                     lda     elem_top_hi,y
7d3f: 85 89                        sta     ]top_coord+1
7d41: b9 40 a1                     lda     elem_zpos_lo,y
7d44: 85 8a                        sta     ]z_coord
7d46: b9 80 a1                     lda     elem_zpos_hi,y
7d49: 85 8b                        sta     ]z_coord+1
                   ; Find the absolute value of the largest coordinate (left / top / zc) in the
                   ; first element in the object.  This is using the current object position, in
                   ; eye coordinates, so the largest coordinate is the point farthest from the
                   ; viewer.
                   ; 
                   ; (This code has a lot of redundancies, as if 16-bit signed comparison macros
                   ; got strung together.)
7d4b: a5 87                        lda     ]left_coord+1     ;get sign of left coordinate
7d4d: 10 0d                        bpl     :LeftPos1         ;positive, branch
7d4f: 49 ff                        eor     #$ff              ;negate, store absolute value
7d51: 85 8d                        sta     ]biggest_dim+1    ;(note invert w/o +1)
7d53: a5 86                        lda     ]left_coord
7d55: 49 ff                        eor     #$ff
7d57: 85 8c                        sta     ]biggest_dim
7d59: 4c 62 7d                     jmp     :LeftCont1

7d5c: 85 8d        :LeftPos1       sta     ]biggest_dim+1    ;copy left to "biggest"
7d5e: a5 86                        lda     ]left_coord
7d60: 85 8c                        sta     ]biggest_dim
7d62: a5 89        :LeftCont1      lda     ]top_coord+1      ;get high byte of top coordinate
7d64: 10 02                        bpl     :TopPos1
7d66: 49 ff                        eor     #$ff              ;negate
7d68: c5 8d        :TopPos1        cmp     ]biggest_dim+1    ;compare to low byte of left coordinate
7d6a: f0 06                        beq     :TopLeftSame      ;hi bytes match, check low byte
7d6c: 10 13                        bpl     :TopBiggerH
7d6e: 18                           clc                       ;force branch at jump destination
7d6f: 4c 8e 7d                     jmp     :FwdBiggerLeft    ;left is bigger

7d72: a5 88        :TopLeftSame    lda     ]top_coord        ;get low byte of top coordinate
7d74: a4 89                        ldy     ]top_coord+1      ;check sign
7d76: 10 02                        bpl     :TopPos2
7d78: 49 ff                        eor     #$ff              ;negate
7d7a: c5 8c        :TopPos2        cmp     ]biggest_dim      ;compare to low byte of left coordinate
7d7c: 90 10                        bcc     :FwdBiggerLeft    ;left is bigger
7d7e: 4c 8b 7d                     jmp     :TopBiggerL       ;top is bigger

                   ; Top coord is bigger than left.
7d81: 85 8d        :TopBiggerH     sta     ]biggest_dim+1    ;copy top coord to "biggest"
7d83: a5 88                        lda     ]top_coord
7d85: a4 89                        ldy     ]top_coord+1
7d87: 10 02                        bpl     :TopBiggerL
7d89: 49 ff                        eor     #$ff
7d8b: 85 8c        :TopBiggerL     sta     ]biggest_dim
7d8d: 38                           sec                       ;don't take next branch
7d8e: 90 47        :FwdBiggerLeft  bcc     :LeftBigger
7d90: a5 89                        lda     ]top_coord+1      ;copy top coord to "biggest" (again; negative)
7d92: 10 0d                        bpl     :TopPos3
7d94: 49 ff                        eor     #$ff
7d96: 85 8d                        sta     ]biggest_dim+1
7d98: a5 88                        lda     ]top_coord
7d9a: 49 ff                        eor     #$ff
7d9c: 85 8c                        sta     ]biggest_dim
7d9e: 4c a7 7d                     jmp     :TopCheckZ

7da1: 85 8d        :TopPos3        sta     ]biggest_dim+1    ;copy top coord to "biggest" (again; positive)
7da3: a5 88                        lda     ]top_coord
7da5: 85 8c                        sta     ]biggest_dim
                   ; Compare Z coordinate.
7da7: a5 8b        :TopCheckZ      lda     ]z_coord+1        ;get high byte of Z coord
7da9: 10 02                        bpl     :ZPos1T
7dab: 49 ff                        eor     #$ff              ;negate
7dad: c5 8d        :ZPos1T         cmp     ]biggest_dim+1    ;compare to high byte of "biggest"
7daf: f0 06                        beq     :ZSameT           ;equal, check low byte
7db1: 10 13                        bpl     :ZBiggerT         ;zc is bigger, use it
7db3: 18                           clc
7db4: 4c d3 7d                     jmp     :ZSmallerT        ;zc is smaller, jump to the jump

7db7: a5 8a        :ZSameT         lda     ]z_coord          ;get low byte
7db9: a4 8b                        ldy     ]z_coord+1        ;check sign
7dbb: 10 02                        bpl     :ZPos2T
7dbd: 49 ff                        eor     #$ff              ;negate
7dbf: c5 8c        :ZPos2T         cmp     ]biggest_dim      ;compare to low byte of "biggest"
7dc1: 90 10                        bcc     :ZSmallerT        ;zc is smaller, branch
7dc3: 4c d0 7d                     jmp     :ZPos3T           ;use zc instead

7dc6: 85 8d        :ZBiggerT       sta     ]biggest_dim+1    ;save high byte
7dc8: a5 8a                        lda     ]z_coord          ;get low byte
7dca: a4 8b                        ldy     ]z_coord+1        ;check sign
7dcc: 10 02                        bpl     :ZPos3T
7dce: 49 ff                        eor     #$ff
7dd0: 85 8c        :ZPos3T         sta     ]biggest_dim
7dd2: 38                           sec
7dd3: ea           :ZSmallerT      nop
7dd4: 4c 1a 7e                     jmp     :GotBiggest

                   ; Left coord is bigger than top.  (We already have the absolute value in
                   ; "biggest", but we copy it again.)
7dd7: a5 87        :LeftBigger     lda     ]left_coord+1
7dd9: 10 0d                        bpl     :LeftPos2
7ddb: 49 ff                        eor     #$ff
7ddd: 85 8d                        sta     ]biggest_dim+1
7ddf: a5 86                        lda     ]left_coord
7de1: 49 ff                        eor     #$ff
7de3: 85 8c                        sta     ]biggest_dim
7de5: 4c ee 7d                     jmp     :LeftCheckZ

7de8: 85 8d        :LeftPos2       sta     ]biggest_dim+1
7dea: a5 86                        lda     ]left_coord
7dec: 85 8c                        sta     ]biggest_dim
                   ; Compare Z coordinate.  (Duplicate of code above.)
7dee: a5 8b        :LeftCheckZ     lda     ]z_coord+1
7df0: 10 02                        bpl     :ZPos1L
7df2: 49 ff                        eor     #$ff
7df4: c5 8d        :ZPos1L         cmp     ]biggest_dim+1
7df6: f0 06                        beq     :ZSameL
7df8: 10 13                        bpl     :ZBiggerL
7dfa: 18                           clc
7dfb: 4c 1a 7e                     jmp     :GotBiggest

7dfe: a5 8a        :ZSameL         lda     ]z_coord
7e00: a4 8b                        ldy     ]z_coord+1
7e02: 10 02                        bpl     :ZPos2L
7e04: 49 ff                        eor     #$ff
7e06: c5 8c        :ZPos2L         cmp     ]biggest_dim
7e08: 90 10                        bcc     :GotBiggest
7e0a: 4c 17 7e                     jmp     :ZPos3L

7e0d: 85 8d        :ZBiggerL       sta     ]biggest_dim+1
7e0f: a5 8a                        lda     ]z_coord
7e11: a4 8b                        ldy     ]z_coord+1
7e13: 10 02                        bpl     :ZPos3L
7e15: 49 ff                        eor     #$ff
7e17: 85 8c        :ZPos3L         sta     ]biggest_dim
7e19: 38                           sec
                   ; We now have the biggest dimension value.  Use it to configure table lookups.
                   ]table_ptr1     .var    $10    {addr/2}
                   ]scale_tab_val  .var    $7e    {addr/1}
                   ]clz_value      .var    $80    {addr/1}

7e1a: ea           :GotBiggest     nop
7e1b: a5 8c                        lda     ]biggest_dim      ;add 2 to biggest dimension
7e1d: 18                           clc
7e1e: 69 02                        adc     #$02
7e20: 85 8c                        sta     ]biggest_dim
7e22: 90 02                        bcc     :NoInc
7e24: e6 8d                        inc     ]biggest_dim+1
7e26: a4 8d        :NoInc          ldy     ]biggest_dim+1    ;get high byte
7e28: d0 17                        bne     :BigHiNZ          ;nonzero, branch
                   ; Get scale factor when biggest dimension < 256.
7e2a: a4 8c                        ldy     ]biggest_dim
7e2c: b9 00 b9                     lda     clz_table,y       ;count leading zeroes [0,8]
7e2f: 18                           clc
7e30: 69 08                        adc     #$08              ;add 8 for the zero high byte [8,16]
7e32: 85 80                        sta     ]clz_value        ;save leading zero count
7e34: 69 a4                        adc     #>math_tab2_base?-$800 ;[$ac,$b4]
7e36: 85 11                        sta     ]table_ptr1+1     ;set as pointer high byte
7e38: a4 8c                        ldy     ]biggest_dim      ;use biggest dimension, low byte, as index
7e3a: b1 10                        lda     (]table_ptr1),y
7e3c: 85 7e                        sta     ]scale_tab_val
7e3e: 4c 58 7e                     jmp     :UpdateSpeeds

                   ; Get scale factor when biggest dimension >= 256.  The high and low bytes are
                   ; merged into a single byte, which is used to index into a table determined by
                   ; the high byte.  This is a clever way of implementing "use the leftmost 8 bits
                   ; of the 16-bit value as an index into the table".
7e41: b9 00 b9     :BigHiNZ        lda     clz_table,y       ;count leading zeroes in high byte
7e44: a8                           tay                       ;copy to Y-reg
7e45: 85 80                        sta     ]clz_value        ;save leading zero count
7e47: 18                           clc
7e48: 69 ac                        adc     #>math_tab2_base? ;[$ac,$b4]
7e4a: 85 11                        sta     ]table_ptr1+1     ;set as pointer high byte
7e4c: a5 8c                        lda     ]biggest_dim      ;get "biggest" low byte
7e4e: 39 d5 00                     and     bit_mask_left9,y  ;clear overlapping bits (leaves 0-8 hi bits set)
7e51: 05 8d                        ora     ]biggest_dim+1    ;merge with "biggest" high byte
7e53: a8                           tay                       ;use as index
7e54: b1 10                        lda     (]table_ptr1),y
7e56: 85 7e                        sta     ]scale_tab_val
                   ; 
                   ; Table pointer is configured.  Loop over X/Y/Z, using X-reg=$00/$02/$04.
                   ; 
                   ]table_ptr2     .var    $12    {addr/2}
                   ]ltmp_82?       .var    $82    {addr/1}
                   ]ltmp_84?       .var    $84    {addr/1}
                   ]speed_abs      .var    $8e    {addr/2}
                   ]z_spd_tmp      .var    $90    {addr/2}

7e58: ea           :UpdateSpeeds   nop
7e59: a2 00                        ldx     #$00
7e5b: b5 87        :CoordLoop      lda     ]left_coord+1,x   ;get absolute value of coordinate
7e5d: 10 11                        bpl     :IsPos
7e5f: 38                           sec                       ;compute (0 - coordinate)
7e60: a9 00                        lda     #$00
7e62: f5 86                        sbc     ]left_coord,x
7e64: 85 8e                        sta     ]speed_abs
7e66: a9 00                        lda     #$00
7e68: f5 87                        sbc     ]left_coord+1,x
7e6a: 85 8f                        sta     ]speed_abs+1
7e6c: ea                           nop
7e6d: 4c 77 7e                     jmp     L7E77

7e70: 85 8f        :IsPos          sta     ]speed_abs+1
7e72: b5 86                        lda     ]left_coord,x
7e74: ea                           nop
7e75: 85 8e                        sta     ]speed_abs
                   ; 
7e77: a4 8d        L7E77           ldy     ]biggest_dim+1    ;check high byte
7e79: f0 10                        beq     :HighZero
7e7b: a4 80                        ldy     ]clz_value
7e7d: a5 8e                        lda     ]speed_abs
7e7f: 39 d5 00                     and     bit_mask_left9,y
7e82: 05 8f                        ora     ]speed_abs+1
7e84: a8                           tay
7e85: b1 10                        lda     (]table_ptr1),y
7e87: ea                           nop
7e88: 4c 90 7e                     jmp     :Cont

7e8b: a4 8e        :HighZero       ldy     ]speed_abs
7e8d: b1 10                        lda     (]table_ptr1),y
7e8f: ea                           nop
                   ; 
7e90: a8           :Cont           tay
7e91: 85 82                        sta     ]ltmp_82?
7e93: b9 00 b5                     lda     turn_map_lo?,y
7e96: 38                           sec
7e97: a4 7e                        ldy     ]scale_tab_val
7e99: f9 00 b5                     sbc     turn_map_lo?,y
7e9c: 85 90                        sta     ]z_spd_tmp
7e9e: a4 82                        ldy     ]ltmp_82?
7ea0: b9 00 b6                     lda     turn_map_hi?,y
7ea3: a4 7e                        ldy     ]scale_tab_val
7ea5: f9 00 b6                     sbc     turn_map_hi?,y
7ea8: 85 91                        sta     ]z_spd_tmp+1
7eaa: 18                           clc
7eab: a5 90                        lda     ]z_spd_tmp
7ead: 6d 51 6d                     adc     max_z_spd_copy    ;add maximum Z velocity allowed for this object
7eb0: 85 90                        sta     ]z_spd_tmp
7eb2: a5 91                        lda     ]z_spd_tmp+1
7eb4: 6d 52 6d                     adc     max_z_spd_copy+1
7eb7: 85 91                        sta     ]z_spd_tmp+1
7eb9: a5 91                        lda     ]z_spd_tmp+1      ;get high byte
7ebb: 30 19                        bmi     :SetZero          ;went negative, clamp to zero
7ebd: c9 08                        cmp     #$08              ;is it >= 8?
7ebf: 10 20                        bpl     :Gt8              ;yes, branch
7ec1: 18                           clc
7ec2: 69 10                        adc     #>math_tab1_base?
7ec4: 85 13                        sta     ]table_ptr2+1
7ec6: a4 90                        ldy     ]z_spd_tmp
7ec8: b1 12                        lda     (]table_ptr2),y
7eca: 9d 49 6d                     sta     tmp_xmove_lo,x
7ecd: a9 00                        lda     #$00
7ecf: 9d 4a 6d                     sta     tmp_xmove_hi,x
7ed2: ea                           nop
7ed3: 4c 06 7f                     jmp     L7F06

7ed6: a9 00        :SetZero        lda     #$00
7ed8: 9d 49 6d                     sta     tmp_xmove_lo,x
7edb: 9d 4a 6d                     sta     tmp_xmove_hi,x
7ede: 4c 06 7f                     jmp     L7F06

7ee1: 38           :Gt8            sec
7ee2: e9 08                        sbc     #$08              ;reduce by 8
7ee4: 85 91                        sta     ]z_spd_tmp+1
7ee6: 18                           clc
7ee7: 69 ad                        adc     #>math_tab2_base?+$100
7ee9: 85 13                        sta     ]table_ptr2+1
7eeb: a4 90                        ldy     ]z_spd_tmp
7eed: b9 00 17                     lda     math_tab1_lastpg?,y
7ef0: a8                           tay
7ef1: b1 12                        lda     (]table_ptr2),y
7ef3: a4 91                        ldy     ]z_spd_tmp+1
7ef5: 85 84                        sta     ]ltmp_84?
7ef7: 39 e7 00                     and     bit_mask_right8,y
7efa: 9d 4a 6d                     sta     tmp_xmove_hi,x
7efd: a5 84                        lda     ]ltmp_84?
7eff: 39 ef 00                     and     bit_mask_left8,y
7f02: 9d 49 6d                     sta     tmp_xmove_lo,x
7f05: ea                           nop
                   ; 
7f06: b4 87        L7F06           ldy     ]left_coord+1,x
7f08: 30 12                        bmi     :IsPos
7f0a: 38                           sec
7f0b: a9 00                        lda     #$00
7f0d: fd 49 6d                     sbc     tmp_xmove_lo,x
7f10: 9d 49 6d                     sta     tmp_xmove_lo,x
7f13: a9 00                        lda     #$00
7f15: fd 4a 6d                     sbc     tmp_xmove_hi,x
7f18: 9d 4a 6d                     sta     tmp_xmove_hi,x
7f1b: ea                           nop
7f1c: e0 04        :IsPos          cpx     #$04              ;are working on Z?
7f1e: d0 2b                        bne     :NextCoord        ;no, branch to skip this next part
                   ; Modify Z velocity based on player speed.
7f20: a5 98                        lda     adj_fwd_speed     ;get forward speed
7f22: 85 8e                        sta     ]speed_abs
7f24: a5 99                        lda     adj_fwd_speed+1
7f26: 85 8f                        sta     ]speed_abs+1
7f28: 06 8e                        asl     ]speed_abs        ;double it
7f2a: 26 8f                        rol     ]speed_abs+1
7f2c: 18                           clc
7f2d: bd 49 6d                     lda     tmp_xmove_lo,x    ;add doubled speed to movement (which is negative)
7f30: 65 8e                        adc     ]speed_abs
7f32: bd 4a 6d                     lda     tmp_xmove_hi,x
7f35: 65 8f                        adc     ]speed_abs+1
7f37: 10 12                        bpl     :NextCoord        ;it became positive, don't do this
7f39: 18                           clc                       ;add (non-doubled) speed to Z movement
7f3a: bd 49 6d                     lda     tmp_xmove_lo,x
7f3d: 65 98                        adc     adj_fwd_speed
7f3f: 9d 49 6d                     sta     tmp_xmove_lo,x
7f42: bd 4a 6d                     lda     tmp_xmove_hi,x
7f45: 65 99                        adc     adj_fwd_speed+1
7f47: 9d 4a 6d                     sta     tmp_xmove_hi,x
7f4a: ea                           nop
7f4b: e8           :NextCoord      inx                       ;advance to next coordinate
7f4c: e8                           inx
7f4d: e0 06                        cpx     #$06              ;done yet?
7f4f: 10 03                        bpl     :All3Done         ;yes, branch
7f51: 4c 5b 7e                     jmp     :CoordLoop        ;no, loop

                   ; Copy results out to object data tables.
7f54: a6 62        :All3Done       ldx     cur_obj_index
7f56: ea                           nop
7f57: ad 49 6d                     lda     tmp_xmove_lo
7f5a: 9d 60 9e                     sta     obj_move_xc_lo,x
7f5d: ad 4a 6d                     lda     tmp_xmove_hi
7f60: 9d 88 9e                     sta     obj_move_xc_hi,x
7f63: ad 4b 6d                     lda     tmp_ymove_lo
7f66: 9d b0 9e                     sta     obj_move_yc_lo,x
7f69: ad 4c 6d                     lda     tmp_ymove_hi
7f6c: 9d d8 9e                     sta     obj_move_yc_hi,x
7f6f: ad 4d 6d                     lda     tmp_zmove_lo
7f72: 9d 10 9e                     sta     obj_move_zc_lo,x
7f75: ad 4e 6d                     lda     tmp_zmove_hi
7f78: 9d 38 9e                     sta     obj_move_zc_hi,x
7f7b: 20 7f 7f                     jsr     Return7f7f
7f7e: 60                           rts

                   ; 
                   ; Debugging thing?  Deleted sound routine?
                   ; 
7f7f: 60           Return7f7f      rts

7f80: 60 00 7a 3a+                 .junk   61
7fbd: 00           :saved_86       .dd1    $00
7fbe: 00           :saved_87       .dd1    $00
7fbf: 00           :saved_yreg     .dd1    $00
7fc0: 00           :saved_xreg     .dd1    $00
7fc1: 00                           .junk   1

                   ; 
                   ; Plays a musical sequence.
                   ; 
                   ;   $00: game-over music (not high score)
                   ;   $01: start game
                   ;   $02: enter time portal
                   ;   $03: (chirp) enemy base destroyed (either kind)
                   ;   $04: fly through friendly base
                   ;   $05: game-over music (high score)
                   ;   $06: exit time portal (max time)
                   ;   $07: (same as $03)
                   ; 
                   ; Hitting a key exits the sequence early.
                   ; 
                   ; On entry:
                   ;   A-reg: sequence number (0-7)
                   ; 
                   ; On exit:
                   ;   X/Y-reg preserved
                   ;   $86-87 preserved
                   ; 
                   • Clear variables
                   ]music_ptr      .var    $16    {addr/2}
                   ]note0          .var    $86    {addr/2}
                   ]note1          .var    $88    {addr/2}
                   ]note2          .var    $8a    {addr/2}
                   ]duration       .var    $8c    {addr/2}
                   ]rep_count      .var    $8f    {addr/1}
                   ]sound_num      .var    $91    {addr/1}
                   ]count0         .var    $aa    {addr/2}
                   ]count1         .var    $ac    {addr/2}
                   ]count2         .var    $ae    {addr/2}

7fc2: 85 91        PlayMusicSeq    sta     ]sound_num
7fc4: a5 86                        lda     ]note0            ;preserve previous contents of $86-87
7fc6: 8d bd 7f                     sta     :saved_86
7fc9: a5 87                        lda     ]note0+1
7fcb: 8d be 7f                     sta     :saved_87
7fce: 8c bf 7f                     sty     :saved_yreg       ;preserve X/Y-reg
7fd1: 8e c0 7f                     stx     :saved_xreg
7fd4: ac 48 6d                     ldy     sound_disab_flag  ;check whether sound is enabled
7fd7: f0 03                        beq     :SoundOn
7fd9: 4c 4f 80                     jmp     :Bail

7fdc: ac 10 c0     :SoundOn        ldy     KBDSTRB           ;clear keyboard strobe
7fdf: a5 91                        lda     ]sound_num        ;get sound number
7fe1: 29 07                        and     #$07              ;make sure it's 0-7
7fe3: 0a                           asl     A
7fe4: a8                           tay
7fe5: b9 02 40                     lda     music_offset,y    ;get pointer to music
7fe8: 85 16                        sta     ]music_ptr
7fea: b9 03 40                     lda     music_offset+1,y
7fed: 18                           clc
7fee: 69 40                        adc     #>DATA_AREA
7ff0: 85 17                        sta     ]music_ptr+1
7ff2: a0 00                        ldy     #$00              ;grab first two bytes, which affect how long
7ff4: b1 16                        lda     (]music_ptr),y    ; each note is played
7ff6: 85 8c                        sta     ]duration
7ff8: a0 01                        ldy     #$01
7ffa: b1 16                        lda     (]music_ptr),y
7ffc: 85 8d                        sta     ]duration+1
7ffe: a9 00                        lda     #$00              ;initialize counters
8000: 85 aa                        sta     ]count0
8002: 85 ab                        sta     ]count0+1
8004: 85 ac                        sta     ]count1
8006: 85 ad                        sta     ]count1+1
8008: 85 ae                        sta     ]count2
800a: 85 af                        sta     ]count2+1
                   ; Loop over all notes in sequence.
800c: a5 16        :MusicLoop      lda     ]music_ptr        ;advance pointer 4 bytes
800e: 18                           clc
800f: 69 04                        adc     #$04
8011: 85 16                        sta     ]music_ptr
8013: 90 02                        bcc     :NoInc
8015: e6 17                        inc     ]music_ptr+1
8017: a0 00        :NoInc          ldy     #$00              ;get first entry
8019: b1 16                        lda     (]music_ptr),y
801b: 0a                           asl     A
801c: aa                           tax
801d: bd 12 40                     lda     note_values,x     ;look up value from table
8020: 85 86                        sta     ]note0
8022: bd 13 40                     lda     note_values+1,x
8025: 85 87                        sta     ]note0+1
8027: a0 01                        ldy     #$01              ;get second entry
8029: b1 16                        lda     (]music_ptr),y
802b: 0a                           asl     A
802c: aa                           tax
802d: bd 12 40                     lda     note_values,x     ;look up value from table
8030: 85 88                        sta     ]note1
8032: bd 13 40                     lda     note_values+1,x
8035: 85 89                        sta     ]note1+1
8037: a0 02                        ldy     #$02              ;get third entry
8039: b1 16                        lda     (]music_ptr),y
803b: 0a                           asl     A
803c: aa                           tax
803d: bd 12 40                     lda     note_values,x     ;look up value from table
8040: 85 8a                        sta     ]note2
8042: bd 13 40                     lda     note_values+1,x
8045: 85 8b                        sta     ]note2+1
8047: a0 03                        ldy     #$03              ;get 4th entry
8049: b1 16                        lda     (]music_ptr),y
804b: 85 8f                        sta     ]rep_count
804d: d0 11                        bne     :PlayNotes        ;zero value here indicates end of list
804f: ad bd 7f     :Bail           lda     :saved_86
8052: 85 86                        sta     ]note0
8054: ad be 7f                     lda     :saved_87
8057: 85 87                        sta     ]note0+1
8059: ac bf 7f                     ldy     :saved_yreg
805c: ae c0 7f                     ldx     :saved_xreg
805f: 60                           rts

                   ]do_click       .var    $80    {addr/1}
                   ]duration_counter .var  $90    {addr/2}

8060: a5 8c        :PlayNotes      lda     ]duration         ;initialize global duration counter
8062: 85 90                        sta     ]duration_counter
8064: a5 8d                        lda     ]duration+1
8066: 85 91                        sta     ]duration_counter+1
8068: 18           :PlayLoop       clc
8069: a5 86                        lda     ]note0            ;advance counter #0
806b: 65 aa                        adc     ]count0
806d: 85 aa                        sta     ]count0
806f: a5 87                        lda     ]note0+1
8071: 65 ab                        adc     ]count0+1
8073: 85 ab                        sta     ]count0+1
8075: 10 35                        bpl     :Pos0             ;positive half, branch
8077: a5 86                        lda     ]note0            ;(pad timing?)
8079: 18                           clc
807a: a5 88                        lda     ]note1            ;advance counter #1
807c: 65 ac                        adc     ]count1
807e: 85 ac                        sta     ]count1
8080: a5 89                        lda     ]note1+1
8082: 65 ad                        adc     ]count1+1
8084: 85 ad                        sta     ]count1+1
8086: 10 12                        bpl     :Pos1             ;positive half, branch
8088: 18                           clc
8089: a5 8a                        lda     ]note2            ;advance counter #2
808b: 65 ae                        adc     ]count2
808d: 85 ae                        sta     ]count2
808f: a5 8b                        lda     ]note2+1
8091: 65 af                        adc     ]count2+1
8093: 85 af                        sta     ]count2+1
8095: a5 86                        lda     ]note0
8097: 4c cf 80                     jmp     :ClickIfOne_2

809a: 18           :Pos1           clc
809b: a5 8a                        lda     ]note2            ;advance counter #2
809d: 65 ae                        adc     ]count2
809f: 85 ae                        sta     ]count2
80a1: a5 8b                        lda     ]note2+1
80a3: 65 af                        adc     ]count2+1
80a5: 85 af                        sta     ]count2+1
80a7: 30 25                        bmi     :ClickIfOne_1     ;negative half, click if 1
80a9: 4c e4 80                     jmp     :ClickIfZero

80ac: ea           :Pos0           nop
80ad: 18                           clc
80ae: a5 88                        lda     ]note1            ;advance counter #1
80b0: 65 ac                        adc     ]count1
80b2: 85 ac                        sta     ]count1
80b4: a5 89                        lda     ]note1+1
80b6: 65 ad                        adc     ]count1+1
80b8: 85 ad                        sta     ]count1+1
80ba: 30 de                        bmi     :Pos1             ;negative half, branch
80bc: 18                           clc
80bd: a5 8a                        lda     ]note2
80bf: 65 ae                        adc     ]count2
80c1: 85 ae                        sta     ]count2
80c3: a5 8b                        lda     ]note2+1
80c5: 65 af                        adc     ]count2+1
80c7: 85 af                        sta     ]count2+1
80c9: a5 86                        lda     ]note0            ;(padding?)
80cb: 4c e4 80                     jmp     :ClickIfZero

80ce: ea           :ClickIfOne_1   nop
80cf: a5 80        :ClickIfOne_2   lda     ]do_click
80d1: f0 0a                        beq     :NotOne
80d3: a9 00                        lda     #$00
80d5: 85 80                        sta     ]do_click
80d7: ad 30 c0                     lda     SPKR              ;click
80da: 4c f9 80                     jmp     :LoopBottom

80dd: ea           :NotOne         nop                       ;pad for timing
80de: ea                           nop
80df: ea                           nop
80e0: ea                           nop
80e1: 4c f9 80                     jmp     :LoopBottom

80e4: a5 80        :ClickIfZero    lda     ]do_click
80e6: d0 0a                        bne     :NotZero
80e8: a9 01                        lda     #$01
80ea: 85 80                        sta     ]do_click
80ec: ad 30 c0                     lda     SPKR              ;click
80ef: 4c f9 80                     jmp     :LoopBottom

80f2: ea           :NotZero        nop
80f3: ea                           nop
80f4: ea                           nop
80f5: ea                           nop
80f6: 4c f9 80                     jmp     :LoopBottom

80f9: 38           :LoopBottom     sec                       ;decrement counter
80fa: a5 90                        lda     ]duration_counter
80fc: e9 01                        sbc     #$01
80fe: 85 90                        sta     ]duration_counter
8100: a5 91                        lda     ]duration_counter+1
8102: e9 00                        sbc     #$00              ;use SBC so cycle count is consistent
8104: 85 91                        sta     ]duration_counter+1
8106: 30 12                        bmi     :DurationExp
8108: ea                           nop
8109: ea                           nop
810a: ea                           nop
810b: ea                           nop
810c: ea                           nop
810d: ad 00 c0                     lda     KBD               ;check for player interrupting music
8110: 10 03                        bpl     :Cont             ;not yet, branch
8112: 4c 4f 80                     jmp     :Bail             ;yes, stop now (note: kbd strobe not cleared)

                   ]vestigial_8e?  .var    $8e    {addr/1}

8115: a5 8e        :Cont           lda     ]vestigial_8e?    ;(?)
8117: 4c 68 80                     jmp     :PlayLoop

811a: c6 8f        :DurationExp    dec     ]rep_count        ;decrement per-note repetition counter
811c: f0 03                        beq     :NextNote         ;if we hit zero, move on to next note
811e: 4c 60 80                     jmp     :PlayNotes        ;otherwise, keep playing this one

8121: 4c 0c 80     :NextNote       jmp     :MusicLoop

8124: cc                           .junk   1
8125: 96           high_code_page  .dd1    $96
8126: 00 3d 3d 3d+                 .junk   13

                   ; 
                   ; Game entry point.
                   ; 
                   ; We also jump here when R/Ctrl+R is hit.
                   ; 
8133: ad 10 c0     Start           lda     KBDSTRB           ;clear keyboard
8136: a9 00                        lda     #$00
8138: 8d 3b 6d                     sta     game_active_flag
813b: 8d 3c 6d                     sta     wronly_6d3c
813e: 8d 3d 6d                     sta     rng_update_flag
8141: 8d 3f 6d                     sta     end_game_msg_ctr
8144: 8d 40 6d                     sta     end_game_msg_ctr+1
                   ; Jump here when starting a new game, after playing the start-new-game music.
8147: a2 13        InitGame        ldx     #$13
8149: bd d7 6d     :CopyLoop       lda     initial_loadout,x ;set initial values for resources
814c: 9d bd 6d                     sta     resource_state,x  ; time, fuel, amun (multi-byte BCD)
814f: ca                           dex
8150: 10 f7                        bpl     :CopyLoop
                   ; Init $6d49-6dbb to zero.
8152: a9 00                        lda     #$00
8154: a2 72                        ldx     #$72
8156: 9d 49 6d     :ZLoop1         sta     tmp_xmove_lo,x
8159: ca                           dex
815a: 10 fa                        bpl     :ZLoop1
                   ; 
                   ; Reset a few things.  Various places jump here when the state of the world
                   ; appears to be screwed up.
                   ; 
                   • Clear variables
                   ]zero           .var    $00    {addr/1}

815c: a2 c0        PartialRestart  ldx     #$c0
815e: 9a                           txs                       ;init stack pointer
815f: ad 50 c0                     lda     TXTCLR            ;enable graphics
8162: ad 52 c0                     lda     MIXCLR            ;disable mixed-mode
8165: ad 57 c0                     lda     HIRES             ;enable hi-res graphics
8168: ad 54 c0                     lda     TXTPAGE1          ;enable page 1
816b: 20 7f 7f                     jsr     Return7f7f
                   ; Init $60-d1 to zero.
816e: a9 00                        lda     #$00
8170: a2 60                        ldx     #$60
8172: 95 00        :ZLoop2         sta     ]zero,x
8174: e8                           inx
8175: e0 d2                        cpx     #$d2
8177: d0 f9                        bne     :ZLoop2
                   ; Init a few variables.
8179: a9 00                        lda     #$00
817b: 85 10                        sta     ptr_10            ;set low bytes of these pointers
817d: 85 12                        sta     math_tab_ptr12
817f: 85 14                        sta     math_tab_ptr14
8181: 8d ae 6d                     sta     portal_bound_limit ;init these to zero
8184: 8d af 6d                     sta     portal_bound_limit+1
8187: 8d b0 6d                     sta     wronly_6db0?
818a: 8d 43 6d                     sta     game_over_music
                   ; Init hi-res page 1 ($2000-3fff), text page 1 ($0400-07ff), and storage from
                   ; $9700-a5ff to zero.
818d: a2 20                        ldx     #$20              ;start page
818f: a0 40                        ldy     #$40              ;end page
8191: a9 00                        lda     #$00              ;value
8193: 20 c5 7c                     jsr     Jmp_Memset        ;set $2000-3fff to $00
8196: a9 00                        lda     #$00              ;value
8198: a2 04                        ldx     #$04              ;start page
819a: a0 08                        ldy     #$08              ;end page
819c: 20 c5 7c                     jsr     Jmp_Memset        ;set $0400-07ff to $00
819f: ae 25 81                     ldx     high_code_page    ;#$96
81a2: e8                           inx
81a3: a0 a6                        ldy     #$a6
81a5: a9 00                        lda     #$00
81a7: 20 c5 7c                     jsr     Jmp_Memset        ;set $9700-a5ff to $00
                   ; 
81aa: a2 13                        ldx     #$13              ;(?)
81ac: a9 ef                        lda     #$ef              ;set object index trackers to "no value"
81ae: 85 6a                        sta     head_obj_index
81b0: 85 6c                        sta     head_enemy_obj_index
81b2: 8d 62 6d                     sta     region_progress_ctr+1 ;init value; gets replaced later
81b5: a9 28                        lda     #40
81b7: 85 6d                        sta     free_obj_count    ;room for 40 objects
81b9: a9 40                        lda     #64
81bb: 85 6e                        sta     free_elem_count   ;room for 64 elements
81bd: 20 7f 7f                     jsr     Return7f7f
                   ; Init $9a50-9a76 to ascending values $01-27, then set $9a77 to $ed.
                   ; Init $9a00-9a26 to $f7, then set $9a27 to $ed.
81c0: a2 00                        ldx     #$00
81c2: a0 01                        ldy     #$01
81c4: 98           :ObjLoop        tya
81c5: 9d 50 9a                     sta     obj_next_obj,x
81c8: a9 f7                        lda     #$f7
81ca: 9d 00 9a                     sta     obj_first_elem_index,x
81cd: c8                           iny
81ce: e8                           inx
81cf: e0 27                        cpx     #39
81d1: d0 f1                        bne     :ObjLoop
81d3: a9 ed                        lda     #$ed
81d5: 9d 50 9a                     sta     obj_next_obj,x    ;last entry gets end-of-list marker
81d8: 9d 00 9a                     sta     obj_first_elem_index,x
81db: 20 7f 7f                     jsr     Return7f7f
                   ; Init $9f40-9f7e to ascending values $01-3f, then set $9f7f to $ec.
                   ; Init $9f00-9f3e to $f6, then set $9f3f to $ec.
81de: a2 00                        ldx     #$00
81e0: a0 01                        ldy     #$01
81e2: 98           :ElemLoop       tya
81e3: 9d 40 9f                     sta     elem_next_elem,x  ;set "next" index to slot number + 1
81e6: a9 f6                        lda     #$f6
81e8: 9d 00 9f                     sta     elem_obj_index,x
81eb: c8                           iny
81ec: e8                           inx
81ed: e0 3f                        cpx     #$3f
81ef: d0 f1                        bne     :ElemLoop
81f1: a9 ec                        lda     #$ec
81f3: 9d 40 9f                     sta     elem_next_elem,x  ;mark the end of the list
81f6: 9d 00 9f                     sta     elem_obj_index,x
81f9: 20 7f 7f                     jsr     Return7f7f
                   ; 
                   • Clear variables
                   ]bcd_byte_cnt1  .var    $86    {addr/1}
                   ]bcd_byte_cnt2  .var    $8a    {addr/1}

81fc: 20 80 5a     MainLoop        jsr     DrawCrosshairs
81ff: 4c 23 82                     jmp     :MainLoop1

8202: ba 85 16 bd+                 .junk   33

8223: ee cd 6d     :MainLoop1      inc     frame_counter     ;increment the counter used for pacing
8226: a2 24                        ldx     #$24
8228: a0 0e                        ldy     #$0e
822a: a9 02                        lda     #$02
822c: 85 86                        sta     ]bcd_byte_cnt1    ;2-byte value
822e: 20 65 73                     jsr     DrawStatusNum     ;draw current speed
8231: ad 63 6d                     lda     space_region      ;get region
8234: c9 03                        cmp     #$03              ;are we flying through a time portal?
8236: d0 2e                        bne     :NoTimeIncr       ;no, branch
8238: ad 98 6d                     lda     time_portal_fail_ctr ;are we *successfully* flying through a time portal?
823b: d0 29                        bne     :NoTimeIncr       ;no, branch
                   ; Flying through the middle of a time portal.  Update time.
823d: ad cd 6d                     lda     frame_counter     ;get frame counter
8240: 29 01                        and     #$01              ;check odd/even frame
8242: d0 22                        bne     :NoTimeIncr       ;odd, skip this next bit
8244: a9 02                        lda     #$02
8246: 85 8a                        sta     ]bcd_byte_cnt2    ;update two-byte (4-digit) number
8248: ad cb 6d                     lda     cur_speed+1       ;get high BCD byte of speed
824b: 8d f9 70                     sta     time_portal_rate  ;use as low byte of increase
824e: a9 00                        lda     #$00
8250: 8d fa 70                     sta     time_portal_rate+1 ;set high byte of increase to zero
8253: a0 13                        ldy     #$13
8255: a2 05                        ldx     #$05
8257: 20 a0 7c                     jsr     IncreaseResource  ;increase time
825a: a9 02                        lda     #$02
825c: 85 86                        sta     ]bcd_byte_cnt1    ;draw two-byte (4-digit) number
825e: a2 0f                        ldx     #$0f
8260: a0 06                        ldy     #$06
8262: 20 65 73                     jsr     DrawStatusNum     ;draw time
8265: ea                           nop
                   ; 6-frame cycle: 0-4 draw resource count, 5 reduce time, advance progress in
                   ; region, and fall through to draw resource #0.
8266: ee 42 6d     :NoTimeIncr     inc     rsrc_draw_index
8269: ad 42 6d                     lda     rsrc_draw_index   ;get index
826c: c9 05                        cmp     #$05              ;< 5?
826e: 30 51                        bmi     :DrawRsrc         ;yes, draw a thing
8270: a9 00                        lda     #$00
8272: 8d 42 6d                     sta     rsrc_draw_index   ;reset index
8275: 20 7f 7f                     jsr     Return7f7f
8278: a9 02                        lda     #$02
827a: 85 8a                        sta     ]bcd_byte_cnt2    ;2-byte value
827c: a2 05                        ldx     #$05
827e: a0 0f                        ldy     #$0f
8280: 20 68 7c                     jsr     ReduceResource    ;update time remaining
                   • Clear variables
                   ]prog_factor    .var    $86    {addr/1}

8283: a9 0e                        lda     #$0e              ;default to 14
8285: 85 86                        sta     ]prog_factor
8287: ad 3b 6d                     lda     game_active_flag  ;are we showing the demo?
828a: f0 21                        beq     :GotFactor        ;yes, branch
828c: ad 63 6d                     lda     space_region      ;get region
828f: c9 03                        cmp     #$03              ;inside a time portal?
8291: f0 1a                        beq     :GotFactor        ;yes, branch (not speed-dependent inside portal)
8293: a9 09                        lda     #$09              ;reduce to 9
8295: 85 86                        sta     ]prog_factor
8297: ad cb 6d                     lda     cur_speed+1       ;check speed
829a: c9 05                        cmp     #$05              ;at least 500?
829c: 90 0f                        bcc     :GotFactor        ;no, branch
829e: a9 10                        lda     #$10              ;increase to 16
82a0: 85 86                        sta     ]prog_factor
82a2: ad cb 6d                     lda     cur_speed+1       ;check speed again
82a5: c9 10                        cmp     #$10              ;at least 1000?
82a7: 90 04                        bcc     :GotFactor        ;no, branch
82a9: a9 20                        lda     #$20              ;increase to 32
82ab: 85 86                        sta     ]prog_factor
82ad: 38           :GotFactor      sec
82ae: ad 61 6d                     lda     region_progress_ctr
82b1: e5 86                        sbc     ]prog_factor
82b3: 8d 61 6d                     sta     region_progress_ctr
82b6: b0 03                        bcs     :NoDec
82b8: ce 62 6d                     dec     region_progress_ctr+1
                   ]bcd_byte_cnt   .var    $86    {addr/1}

82bb: a9 03        :NoDec          lda     #$03
82bd: 85 86                        sta     ]bcd_byte_cnt     ;score is 3 bytes (6 digits)
82bf: a9 00                        lda     #$00              ;draw score
82c1: c9 04        :DrawRsrc       cmp     #$04              ;is index up to 4?
82c3: d0 06                        bne     :Not4             ;no, leave BCD byte count alone (== 2)
82c5: a9 03                        lda     #$03              ;yes, high scores are also 3 bytes
82c7: 85 86                        sta     ]bcd_byte_cnt
82c9: a9 04                        lda     #$04              ;draw #4 (high score)
82cb: a8           :Not4           tay
82cc: be dc 70                     ldx     rsrc_print_col,y  ;get screen column (0-39)
82cf: b9 e1 70                     lda     status_val_index,y ;get storage index of item
82d2: a8                           tay
82d3: 20 65 73                     jsr     DrawStatusNum     ;draw it
82d6: ea                           nop
                   ; Handle keyboard input.  This part is handled for the demo as well.
82d7: ad 00 c0                     lda     KBD               ;read keyboard
82da: 10 36                        bpl     :Jmp_83a2         ;no key hit, bail
82dc: c9 d6                        cmp     #“V”
82de: d0 0e                        bne     :NotV
82e0: ad 10 c0                     lda     KBDSTRB           ;clear keyboard strobe
82e3: ad 47 6d                     lda     vert_axis_mod
82e6: 49 ff                        eor     #$ff              ;flip vertical joystick axis
82e8: 8d 47 6d                     sta     vert_axis_mod
82eb: 4c fd 82                     jmp     :SetAxisChar

82ee: c9 c8        :NotV           cmp     #“H”              ;is it 'H'?
82f0: d0 23                        bne     :NotH             ;no, branch
82f2: ad 10 c0                     lda     KBDSTRB           ;clear keyboard strobe
82f5: ad 44 6d                     lda     horiz_axis_mod
82f8: 49 ff                        eor     #$ff              ;flip horizontal joystick axis
82fa: 8d 44 6d                     sta     horiz_axis_mod
                   ]joy_axis_adj   .var    $86    {addr/1}

82fd: ad 44 6d     :SetAxisChar    lda     horiz_axis_mod    ;00/ff
8300: 29 01                        and     #$01              ;00/01
8302: 85 86                        sta     ]joy_axis_adj
8304: ad 47 6d                     lda     vert_axis_mod     ;00/ff
8307: 29 02                        and     #$02              ;00/02
8309: 05 86                        ora     ]joy_axis_adj
830b: a8                           tay                       ;0/1/2/3
830c: b9 45 73                     lda     axis_flip_chars,y ;get char ('H', 'V', etc)
830f: 8d a5 6e                     sta     text_axis_status  ;set in status bar
8312: 4c a2 83     :Jmp_83a2       jmp     :GetInput1

8315: c9 93        :NotH           cmp     #$93              ;Ctrl+S?
8317: f0 04                        beq     :ToggleSound
8319: c9 d3                        cmp     #“S”              ;plain 'S' (same effect, not documented)?
831b: d0 1a                        bne     :NotS             ;no, continue
831d: a9 20        :ToggleSound    lda     #$20
831f: 8d 85 6e                     sta     text_score_time   ;set sound-enabled to "on" for now
8322: ad 48 6d                     lda     sound_disab_flag
8325: 49 01                        eor     #$01              ;toggle sound flag (00/01)
8327: 8d 48 6d                     sta     sound_disab_flag
832a: f0 05                        beq     :SoundEnabled
832c: a9 53                        lda     #‘S’
832e: 8d 85 6e                     sta     text_score_time   ;update text at top of screen to show sound disabled
8331: ad 10 c0     :SoundEnabled   lda     KBDSTRB           ;clear keyboard
8334: 4c a2 83                     jmp     :GetInput1

8337: 29 7f        :NotS           and     #$7f
8339: c9 31                        cmp     #‘1’              ;check for 1-5
833b: 30 15                        bmi     :NotDigit
833d: c9 36                        cmp     #‘6’
833f: b0 11                        bcs     :NotDigit         ;nope, continue
8341: 8d a6 6e                     sta     text_joy_sens     ;set value for display
8344: 29 07                        and     #$07              ;convert ['1','5'] to [1,5]
8346: 18                           clc
8347: 69 f9                        adc     #$f9              ;now [$fa,$fe]
8349: 8d c2 71                     sta     joystick_sens_mod+1
834c: ad 10 c0                     lda     KBDSTRB
834f: 4c a2 83                     jmp     :GetInput1

                   ; Check for "NOTICE" key sequence.
8352: 38           :NotDigit       sec
8353: e9 40                        sbc     #$40
8355: ac e0 6e                     ldy     secret_key_index
8358: d9 e1 6e                     cmp     secret_key_seq,y
835b: f0 08                        beq     :NoticeMatch
835d: a9 00                        lda     #$00              ;didn't match, reset sequence
835f: 8d e0 6e                     sta     secret_key_index
8362: 4c a2 83                     jmp     :GetInput1

                   ; Matched, show secret copyright message.
8365: ee e0 6e     :NoticeMatch    inc     secret_key_index
8368: ad 10 c0                     lda     KBDSTRB           ;clear keyboard strobe
836b: ad e0 6e                     lda     secret_key_index  ;get index
836e: c9 06                        cmp     #$06              ;all 5 chars typed?
8370: 30 30                        bmi     :GetInput1        ;not yet
8372: a0 27        :PrintCopyright ldy     #39               ;copy 40 bytes
8374: b9 33 72     :SecCopyrLoop   lda     secret_copyright,y
8377: 18                           clc
8378: 69 20                        adc     #$20              ;"decode" character
837a: 99 80 0f                     sta     copyright_msg,y
837d: 88                           dey
837e: 10 f4                        bpl     :SecCopyrLoop
8380: ad 50 c0                     lda     TXTCLR            ;enable graphics
8383: ad 57 c0                     lda     HIRES             ;enable hi-res graphics
8386: ad 54 c0                     lda     TXTPAGE1          ;enable page 1
                   ]counter        .var    $8c    {addr/1}

8389: a2 00                        ldx     #$00
838b: a9 00                        lda     #$00
838d: 85 8c                        sta     ]counter
838f: a4 8c        :PrintCopyrLoop ldy     ]counter
8391: b9 80 0f                     lda     copyright_msg,y
8394: 20 95 74                     jsr     PrintCharLine32
8397: e6 8c                        inc     ]counter
8399: e0 24                        cpx     #36               ;print 35 bytes
839b: ea                           nop
839c: 30 f1                        bmi     :PrintCopyrLoop
839e: ea                           nop
839f: 4c 72 83                     jmp     :PrintCopyright   ;loop forever

83a2: ad 3b 6d     :GetInput1      lda     game_active_flag  ;currently playing game?
83a5: f0 03                        beq     :NotPlaying       ;no, branch
83a7: 4c 05 84                     jmp     CheckRestart      ;yes, go read the joystick and check other keys

                   ; Read inputs while showing the title demo.
83aa: ad 00 c0     :NotPlaying     lda     KBD               ;read keyboard
83ad: 10 23                        bpl     :NoSpc            ;no key hit, branch
83af: 29 7f                        and     #%01111111        ;strip high bit
83b1: c9 20                        cmp     #‘ ’              ;was it spacebar?
83b3: d0 1d                        bne     :NoSpc            ;no, keep going
83b5: ad 10 c0                     lda     KBDSTRB           ;clear keyboard strobe
83b8: a9 04                        lda     #$04
83ba: 8d 3c 6d                     sta     wronly_6d3c       ;set useless thing to $04
83bd: a9 ff                        lda     #$ff
83bf: 8d 3b 6d                     sta     game_active_flag  ;now playing game
83c2: 8d 3c 6d                     sta     wronly_6d3c       ;set useless thing to $ff
83c5: a9 01                        lda     #$01
83c7: 20 c2 7f                     jsr     PlayMusicSeq      ;play "start game" music
83ca: a9 01                        lda     #$01              ;(?)
83cc: 20 f4 0f                     jsr     Return0ff4
83cf: 4c 47 81                     jmp     InitGame          ;start the game

83d2: a9 d0        :NoSpc          lda     #$d0              ;set a bunch of DP values
83d4: 85 9b                        sta     joy_yaw_angle+1
83d6: 85 9e                        sta     joy_pitch_angle+1
83d8: a9 00                        lda     #$00
83da: 85 9c                        sta     joy_yaw_sign      ;zero all this stuff out
83dc: 85 9f                        sta     joy_pitch_sign    ;(all of these get zeroed out when we start a new
83de: 85 9a                        sta     joy_yaw_angle     ; game, not sure why we do it here)
83e0: 85 9d                        sta     joy_pitch_angle
83e2: 85 ce                        sta     portal_next_xc
83e4: 85 cf                        sta     portal_next_xc+1
83e6: 85 d0                        sta     portal_next_yc
83e8: 85 d1                        sta     portal_next_yc+1
83ea: 8d aa 6d                     sta     joystick_x_mag
83ed: 8d ad 6d                     sta     joystick_y_mag
83f0: ad cf 6c                     lda     rng_state1+7      ;perturb RNG state
83f3: 18                           clc
83f4: 69 52                        adc     #$52
83f6: 8d cf 6c                     sta     rng_state1+7
83f9: ee 10 6d                     inc     rng_state2+17
83fc: 20 b0 7b                     jsr     GenRandom
83ff: 20 7f 7f                     jsr     Return7f7f
8402: 4c d0 84                     jmp     ReadJoystick      ;go read the joystick (for RNG state update?)

                   ; 
                   ; Check for restart key sequence and game-over conditions.
                   ; 
8405: ad 00 c0     CheckRestart    lda     KBD
8408: c9 d2                        cmp     #“R”              ;'R' hit (seems dangerous)?
840a: f0 04                        beq     :DoReset
840c: c9 92                        cmp     #$92              ;Ctrl+R
840e: d0 06                        bne     :NotR
8410: ad 10 c0     :DoReset        lda     KBDSTRB           ;clear keyboard strobe
8413: 4c 33 81                     jmp     Start             ;restart game

                   ; Check end-game conditions.
8416: ad c2 6d     :NotR           lda     time_left
8419: 0d c3 6d                     ora     time_left+1
841c: d0 05                        bne     :HaveTime
841e: a9 00                        lda     #$00              ;cause = no time
8420: 4c 3d 84                     jmp     GameOver

8423: ad c5 6d     :HaveTime       lda     fuel_left
8426: 0d c6 6d                     ora     fuel_left+1
8429: d0 08                        bne     :HaveFuel
842b: a9 04                        lda     #$04              ;cause = no fuel
842d: 4c 3d 84                     jmp     GameOver

8430: 4c d0 84     :HaveAmun       jmp     ReadJoystick

                   ]score_rating   .var    $91    {addr/1}

8433: ad c8 6d     :HaveFuel       lda     amun_left
8436: 0d c9 6d                     ora     amun_left+1
8439: d0 f5                        bne     :HaveAmun
                   ; 
                   ; We ran out of time/fuel/amun, game is over.
                   ; 
843b: a9 08                        lda     #$08              ;cause = no amun
843d: 85 b5        GameOver        sta     end_game_cause
                   ; Determine rating, based on score.
843f: a9 04                        lda     #$04              ;init rating to 4 (max)
8441: 85 91                        sta     ]score_rating
8443: a0 09                        ldy     #$09
8445: ea           :RatingLoop     nop
8446: f8                           sed
8447: ad be 6d                     lda     cur_score
844a: d9 e6 70                     cmp     rating_thresholds,y
844d: ad bf 6d                     lda     cur_score+1
8450: f9 e7 70                     sbc     rating_thresholds+1,y
8453: ad c0 6d                     lda     cur_score+2
8456: f9 e8 70                     sbc     rating_thresholds+2,y
8459: d8                           cld
845a: 10 08                        bpl     :GotRating
845c: c6 91                        dec     ]score_rating
845e: 88                           dey
845f: 88                           dey
8460: 88                           dey
8461: 10 e2                        bpl     :RatingLoop
8463: ea                           nop
8464: a5 91        :GotRating      lda     ]score_rating     ;get rating
8466: 0a                           asl     A                 ;16 chars per rating string
8467: 0a                           asl     A
8468: 0a                           asl     A
8469: 0a                           asl     A
846a: 85 b6                        sta     score_rating_index
                   ; 
846c: ad 10 c0                     lda     KBDSTRB           ;clear keyboard strobe
846f: a9 00                        lda     #$00
8471: 8d 3b 6d                     sta     game_active_flag  ;clear "playing game" flag
8474: a9 02                        lda     #$02
8476: 8d cd 6d                     sta     frame_counter
                   ; Zero out $9a-9f and $c8-cd.
8479: a2 05                        ldx     #$05
847b: a9 00                        lda     #$00
847d: 95 9a        :ZeroDpLoop     sta     joy_yaw_angle,x
847f: 95 c8                        sta     sound_counters,x
8481: ca                           dex
8482: 10 f9                        bpl     :ZeroDpLoop
8484: a9 01                        lda     #$01              ;set to $0104
8486: 8d 40 6d                     sta     end_game_msg_ctr+1
8489: a9 04                        lda     #$04
848b: 8d 3f 6d                     sta     end_game_msg_ctr
848e: a9 02                        lda     #$02              ;change it to $0180
8490: 8d 40 6d                     sta     end_game_msg_ctr+1
8493: a9 80                        lda     #$80
8495: 8d 3f 6d                     sta     end_game_msg_ctr
8498: a9 01                        lda     #$01
849a: 8d 43 6d                     sta     game_over_music
                   ; Compare high score to current score.
849d: f8                           sed
849e: ad d1 6d                     lda     high_score
84a1: cd be 6d                     cmp     cur_score
84a4: ad d2 6d                     lda     high_score+1
84a7: ed bf 6d                     sbc     cur_score+1
84aa: ad d3 6d                     lda     high_score+2
84ad: ed c0 6d                     sbc     cur_score+2
84b0: b0 17                        bcs     :NotHighScore
84b2: ad be 6d                     lda     cur_score
84b5: 8d d1 6d                     sta     high_score
84b8: ad bf 6d                     lda     cur_score+1
84bb: 8d d2 6d                     sta     high_score+1
84be: ad c0 6d                     lda     cur_score+2
84c1: 8d d3 6d                     sta     high_score+2
84c4: a9 05                        lda     #$05
84c6: 8d 43 6d                     sta     game_over_music   ;play full fanfare
84c9: d8           :NotHighScore   cld
84ca: 20 7f 7f                     jsr     Return7f7f
84cd: 4c fc 81                     jmp     MainLoop

                   ; 
                   ; Reads the joystick after checking for the pause key.
                   ; 
                   ; We do this whether or not we're playing a game.
                   ; 
                   • Clear variables
                   ]rng_limit_mode .var    $88    {addr/1}
                   ]pdl0           .var    $8a    {addr/1}
                   ]pdl1           .var    $8d    {addr/1}
                   ]counter        .var    $8e    {addr/1}

84d0: a9 00        ReadJoystick    lda     #$00
84d2: 8d 5f 6d                     sta     fuel_this_frame   ;init fuel consumption
84d5: 85 14                        sta     math_tab_ptr14    ;set low byte of pointers to zero
84d7: 85 12                        sta     math_tab_ptr12
84d9: 85 10                        sta     ptr_10
84db: ad 00 c0                     lda     KBD               ;check keyboard
84de: c9 9b                        cmp     #$9b              ;ESC?
84e0: d0 0e                        bne     DoReadJoystick
                   ; Pause mode.  Wait for key.
84e2: ad 10 c0                     lda     KBDSTRB           ;clear keyboard strobe
84e5: ad 00 c0     :PauseLoop      lda     KBD               ;check for key hit
84e8: 10 fb                        bpl     :PauseLoop        ;nothing hit, loop
84ea: ad 10 c0                     lda     KBDSTRB           ;clear keyboard strobe
84ed: 20 7f 7f                     jsr     Return7f7f
                   ; 
                   ; Read both joystick axes.
                   ; 
                   ; Paddles are normally read in an 11-cycle loop, so reading 0-255 requires 2816
                   ; cycles.  This routine requires 15 cycles per loop, theoretically yielding a
                   ; value from 0-187 in the same time frame for an ideal joystick.  (In practice,
                   ; it will be able to read a bit higher because the capacitor may continue to
                   ; charge past the point where the routine times out.)
                   ; 
                   ; We need to adjust the center point.  In theory this should be (256-188)/2=34,
                   ; but the code here biases the result by +50.  Under AppleWin's mouse emulation
                   ; I see 50-243 (0-193 unadjusted).  When PDL(n) is reporting 127 this code
                   ; returns 138, suggesting that the correct adjustment is actually +39.  However,
                   ; the code that handles movement uses 152 ($98) as the center point, so the
                   ; adjustment here should actually be +64 (confirmed in AppleWin).
                   ; 
                   ; This implementation offers better resolution than the 22-cycle variants, but
                   ; stretches the timing when one paddle finishes.
                   ; 
                   ; (For reference, PADDL0/PADDL1 become positive (<$80) when their capacitors
                   ; have recharged.)
                   ; 
84f0: ad 70 c0     DoReadJoystick  lda     PTRIG             ;trigger paddle discharge
84f3: a0 32                        ldy     #50               ;offset by +50
84f5: ad 64 c0     :ReadBothLoop   lda     PADDL0            ;4  (15 cycles/loop)
84f8: 2d 65 c0                     and     PADDL1            ;4
84fb: 10 0a                        bpl     :OneDone          ;2  one or both are done, branch
84fd: c8                           iny                       ;2
84fe: d0 f5                        bne     :ReadBothLoop     ;3  exit if we wrap around to zero
8500: 88                           dey                       ;both paddles done; decr to 255
8501: 84 8a                        sty     ]pdl0             ;save paddle 0 value
8503: ea                           nop
8504: 4c 2e 85                     jmp     :BothDone

8507: ad 64 c0     :OneDone        lda     PADDL0            ;is paddle 0 done?
850a: 10 14                        bpl     :P0Done           ;yes, branch
850c: 84 8d                        sty     ]pdl1             ;no, paddle 1 is done; save it
850e: ad 64 c0     :P0OnlyLoop     lda     PADDL0            ;read paddle 0
8511: 2d 64 c0                     and     PADDL0            ;4-cycle nop to balance timing
8514: 10 04                        bpl     :BothDone
8516: c8                           iny
8517: d0 f5                        bne     :P0OnlyLoop
8519: 88                           dey                       ;decrement to 255
851a: 84 8a        :BothDone       sty     ]pdl0
851c: ea                           nop
851d: 4c 30 85                     jmp     :JoystickDone

8520: 84 8a        :P0Done         sty     ]pdl0             ;save paddle 0 value
8522: ad 65 c0     :P1OnlyLoop     lda     PADDL1            ;read paddle 1
8525: 2d 65 c0                     and     PADDL1            ;4-cycle nop to balance timing
8528: 10 04                        bpl     :BothDone
852a: c8                           iny
852b: d0 f5                        bne     :P1OnlyLoop
852d: 88                           dey                       ;decrement to 255
852e: 84 8d        :BothDone       sty     ]pdl1             ;save paddle 1 value
                   ; Got joystick reading.
8530: 98           :JoystickDone   tya
8531: 65 b2                        adc     engine_sound_ctr?+1
8533: 85 b2                        sta     engine_sound_ctr?+1
8535: 90 0f                        bcc     :NoSound
8537: e6 b3                        inc     engine_sound_ctr?+2
8539: a5 cc                        lda     engine_sound_enable
853b: f0 09                        beq     :NoSound
853d: a5 b3                        lda     engine_sound_ctr?+2
853f: 25 b1                        and     engine_sound_ctr?
8541: d0 03                        bne     :NoSound
8543: ad 30 c0                     lda     SPKR
8546: 20 7f 7f     :NoSound        jsr     Return7f7f
8549: ad 3b 6d                     lda     game_active_flag  ;are we showing the demo?
854c: d0 3e                        bne     SetTurnRate       ;no, branch
                   ; Add entropy to the RNG by pulling in the joystick and button values.  This is
                   ; fairly ineffective, since a self-centering joystick will tend to return the
                   ; same values, and the "floating bus" effect will likely result in both buttons
                   ; returning the same value (unless one is pressed, which gets you one bit).
854e: ad 3d 6d                     lda     rng_update_flag   ;is update flag clear?
8551: d0 36                        bne     :Bail             ;no, bail
8553: ee 3d 6d                     inc     rng_update_flag   ;yes, inc so we don't do this again
8556: a5 8a                        lda     ]pdl0             ;perturb RNG state with joystick values
8558: 0a                           asl     A
8559: ea                           nop
855a: 4d d9 6c                     eor     rng_state1+17
855d: 8d d9 6c                     sta     rng_state1+17
8560: a5 8d                        lda     ]pdl1
8562: 0a                           asl     A
8563: 4d da 6c                     eor     rng_state1+18
8566: 8d da 6c                     sta     rng_state1+18
8569: ea                           nop
856a: a9 ff                        lda     #$ff
856c: 85 88                        sta     ]rng_limit_mode   ;no limit on result
856e: 85 8e                        sta     ]counter
8570: 20 b0 7b     :SpinLoop       jsr     GenRandom
8573: 20 b0 7b                     jsr     GenRandom
8576: ad 62 c0                     lda     BUTN1             ;perturb RNG state with button values
8579: 4d 61 c0                     eor     BUTN0             ;(this will most likely evaluate to $00)
857c: 0a                           asl     A
857d: 4d db 6c                     eor     rng_state1+19
8580: 8d db 6c                     sta     rng_state1+19
8583: c6 8e                        dec     ]counter
8585: a5 8e                        lda     ]counter
8587: d0 e7                        bne     :SpinLoop
8589: 4c 6f 89     :Bail           jmp     UpdateRegion

858c: a0 03        SetTurnRate     ldy     #$03              ;start with vertical axis
858e: b9 44 6d     :Loop           lda     horiz_axis_mod,y  ;get axis modifier ($00/$ff)
8591: 49 ff                        eor     #$ff              ;invert
8593: 99 9c 00                     sta     joy_yaw_sign,y    ;store in $9c/$9f
8596: 99 9c 00                     sta     joy_yaw_sign,y    ;(?)
8599: b9 8a 00                     lda     tmp_8a,y          ;get paddle read value ($8a/$8d)
859c: 38                           sec
859d: e9 98                        sbc     #$98              ;use $98 (152) as center point
859f: 10 0d                        bpl     :IsPos
85a1: aa                           tax                       ;preserve value in X-reg
85a2: b9 9c 00                     lda     joy_yaw_sign,y    ;joystick left/up (negative), invert sign
85a5: 49 ff                        eor     #$ff
85a7: 99 9c 00                     sta     joy_yaw_sign,y
85aa: 8a                           txa                       ;restore value
85ab: 49 ff                        eor     #$ff              ;invert it
85ad: ea                           nop
85ae: aa           :IsPos          tax                       ;copy magnitude to X-reg
85af: 99 aa 6d                     sta     joystick_x_mag,y  ;store for some odd uses
85b2: c9 08                        cmp     #$08              ;is magnitude < 8?
85b4: 90 03                        bcc     :SlowTurn         ;yes, turning slowly; branch
85b6: ee 5f 6d                     inc     fuel_this_frame   ;turning quickly, burn more fuel
85b9: 18           :SlowTurn       clc
85ba: bd 00 b5                     lda     turn_map_lo?,x    ;convert magnitude to 16-bit turn angle
85bd: 6d c1 71                     adc     joystick_sens_mod ;reduce by joystick sensitivity setting ($ff)
85c0: 99 9a 00                     sta     joy_yaw_angle,y   ;set the pitch or yaw rate
85c3: bd 00 b6                     lda     turn_map_hi?,x
85c6: 6d c2 71                     adc     joystick_sens_mod+1 ;add value in range [$fa,$fe], or [-6,-2], which
85c9: 99 9b 00                     sta     joy_yaw_angle+1,y ; reduces movement and widens center zone
85cc: e0 00                        cpx     #$00              ;is the joystick axis centered?
85ce: d0 09                        bne     :NoSub            ;no, branch
85d0: b9 9b 00                     lda     joy_yaw_angle+1,y ;yes, modify movement rate
85d3: 38                           sec
85d4: e9 0c                        sbc     #$0c              ;subtract 12 (ensures that object updater
85d6: 99 9b 00                     sta     joy_yaw_angle+1,y ; recognizes that we're not moving)
                   ; Do some peculiar things with state that nothing reads.  Perturb the RNG state.
85d9: b9 9c 00     :NoSub          lda     joy_yaw_sign,y
85dc: 99 9c 6d                     sta     wronly_6d9b?+1,y
85df: 59 aa 6d                     eor     joystick_x_mag,y
85e2: 99 9b 6d                     sta     wronly_6d9b?,y
85e5: 0a                           asl     A
85e6: 18                           clc
85e7: 79 cb 6c                     adc     rng_state1+3,y
85ea: 99 cb 6c                     sta     rng_state1+3,y
85ed: 98                           tya
85ee: aa                           tax
85ef: 1e 9b 6d                     asl     wronly_6d9b?,x    ;shift 16-bit value left, twice
85f2: 3e 9c 6d                     rol     wronly_6d9b?+1,x
85f5: 1e 9b 6d                     asl     wronly_6d9b?,x
85f8: 3e 9c 6d                     rol     wronly_6d9b?+1,x
                   ; Advance to the other axis.
85fb: 88                           dey
85fc: 88                           dey
85fd: ea                           nop
85fe: 88                           dey                       ;now Y-reg=0 or -3
85ff: 10 8d                        bpl     :Loop
8601: 20 7f 7f                     jsr     Return7f7f
                   ; 
                   ; Check to see if both buttons are down, or the space bar is hit.  If so, fire a
                   ; shot.
                   ; 
                   ; If the buttons are held down, we pace the shots more slowly than we would if
                   ; the player were pressing the button or spacebar rapidly.  If you hit the space
                   ; bar too rapidly, attempting to fire every frame, the game will throttle your
                   ; shots.  If you time it so the space bar is hit on alternate frames, you will
                   ; fire as quickly as possible.
                   ; 
8604: ad 61 c0                     lda     BUTN0             ;are both buttons down?
8607: 2d 62 c0                     and     BUTN1
860a: a8                           tay                       ;preserve in Y-reg
860b: 30 0c                        bmi     :BothDown         ;yes, branch
860d: ad 00 c0                     lda     KBD               ;check keyboard
8610: c9 a0                        cmp     #“ ”              ;spacebar hit?
8612: d0 48                        bne     CheckSpeedButtons ;no, go check for speed change
8614: ad 10 c0                     lda     KBDSTRB           ;yes, clear keyboard strobe
8617: a0 ff                        ldy     #$ff              ;set Y-reg to value with high bit set
8619: ea           :BothDown       nop
861a: ad 92 6d                     lda     btns_down_flag    ;were both buttons down before?
861d: 10 08                        bpl     :DoFire           ;no, branch
861f: 8c 92 6d                     sty     btns_down_flag    ;yes, save current state (up or down)
8622: ce 91 6d                     dec     shot_delay_ctr    ;decrement the inter-shot counter
8625: 10 32                        bpl     :NoFire           ;not ready to fire yet, bail
8627: 8c 92 6d     :DoFire         sty     btns_down_flag    ;set flag
862a: ea                           nop
                   ; Fire a shot if possible.
                   ]num_bytes      .var    $8a    {addr/1}

862b: a5 6e                        lda     free_elem_count   ;? testing to see if obj table is full?
862d: f0 2a                        beq     :NoFire
862f: a5 6d                        lda     free_obj_count
8631: f0 26                        beq     :NoFire
8633: a9 06                        lda     #$06
8635: 8d 91 6d                     sta     shot_delay_ctr    ;init shot delay (reduces shot spamming)
8638: a2 0b                        ldx     #$0b
863a: a9 02                        lda     #$02
863c: 85 8a                        sta     ]num_bytes
863e: a0 15                        ldy     #$15
8640: 20 68 7c                     jsr     ReduceResource    ;reduce ammunition by 1
8643: a9 7f                        lda     #$7f              ;special value, tested later
8645: 85 a2                        sta     linked_obj_index
8647: ea                           nop
8648: a0 08                        ldy     #$08              ;player projectile
864a: 20 0f 76                     jsr     CreateObject
864d: a0 00                        ldy     #$00              ;effect #0: player cannon fired
864f: a9 00                        lda     #$00
8651: 20 da 7c                     jsr     InitiateSfx       ;initiate the sound effect
8654: a9 00                        lda     #$00              ;(?)
8656: 20 f0 0f                     jsr     Return0ff0
8659: 4c f5 86     :NoFire         jmp     :AdjustSpeed

                   ; 
                   ; Speeds up or slows down based on whether a single button is being pushed.
                   ; 
                   ; The button read is ignored on the first frame, presumably to reduce the
                   ; instances where you speed up or slow down while trying to fire by hitting both
                   ; buttons.
                   ; 
                   ; Note the displayed speed value is updated independently of the actual forward
                   ; speed, using constants from two different locations.
                   ; 
                   • Clear variables
                   ]num_bytes      .var    $8a    {addr/1}

                   CheckSpeedButtons
865c: a9 00                        lda     #$00
865e: 8d 91 6d                     sta     shot_delay_ctr    ;reset shot delay counter to zero
8661: 8c 92 6d                     sty     btns_down_flag    ;save buttons-down flag value
8664: ad 61 c0                     lda     BUTN0             ;get button 0 (go slower)
8667: 10 4b                        bpl     :NoSlow           ;not pushed, bail
8669: ad 93 6d                     lda     btns_0_down_flag  ;was button 0 down before?
866c: 10 43                        bpl     :Jmp_AdjustSpeed  ;no, bail
866e: ad 92 6d                     lda     btns_down_flag    ;both buttons down?
8671: 30 3e                        bmi     :Jmp_AdjustSpeed  ;yes, bail
                   ; Slow down.
8673: ee 5f 6d                     inc     fuel_this_frame   ;increase fuel consumption
8676: a2 0d                        ldx     #$0d              ;reduce displayed speed by 20
8678: a0 11                        ldy     #$11
867a: a9 02                        lda     #$02              ;2-byte value
867c: 85 8a                        sta     ]num_bytes
867e: 20 68 7c                     jsr     ReduceResource    ;reduce speed
8681: b0 20                        bcs     :Underflow        ;reached zero
8683: 38                           sec
8684: ad a4 6d                     lda     forward_speed     ;adjust forward speed, which is a 16.8 value
8687: ed 49 73                     sbc     delta_speed       ;subtract per-frame delta, an 8.8 value
868a: 8d a4 6d                     sta     forward_speed
868d: ad a5 6d                     lda     forward_speed+1
8690: ed 4a 73                     sbc     delta_speed+1
8693: 8d a5 6d                     sta     forward_speed+1
8696: ad a6 6d                     lda     forward_speed+2
8699: e9 00                        sbc     #$00
869b: 8d a6 6d                     sta     forward_speed+2
869e: 20 7f 7f                     jsr     Return7f7f
86a1: 10 0e                        bpl     :Jmp_AdjustSpeed  ;if speed is still positive, branch
86a3: a9 00        :Underflow      lda     #$00              ;set desired speed to zero
86a5: 8d a4 6d                     sta     forward_speed
86a8: 8d a5 6d                     sta     forward_speed+1
86ab: 8d a6 6d                     sta     forward_speed+2
86ae: 20 7f 7f                     jsr     Return7f7f
                   :Jmp_AdjustSpeed
86b1: 4c f5 86                     jmp     :AdjustSpeed

86b4: ad 62 c0     :NoSlow         lda     BUTN1             ;get button 1 (go faster)
86b7: 10 f8                        bpl     :Jmp_AdjustSpeed  ;not pushed, bail
86b9: ad 92 6d                     lda     btns_down_flag    ;was button 1 down before?
86bc: 30 f3                        bmi     :Jmp_AdjustSpeed  ;no, bail
86be: ad 94 6d                     lda     btns_1_down_flag  ;both buttons down?
86c1: 10 ee                        bpl     :Jmp_AdjustSpeed  ;yes, bail
                   ; Speed up.
86c3: ee 5f 6d                     inc     fuel_this_frame   ;increase fuel consumption
86c6: ad cb 6d                     lda     cur_speed+1       ;get high byte of speed
86c9: c9 90                        cmp     #$90              ;have we reached 9000?
86cb: b0 27                        bcs     :NoFaster         ;yes, bail
86cd: a2 0d                        ldx     #$0d
86cf: a0 11                        ldy     #$11
86d1: a9 02                        lda     #$02
86d3: 85 8a                        sta     ]num_bytes
86d5: 20 a0 7c                     jsr     IncreaseResource  ;increase displayed speed by 20
86d8: b0 1a                        bcs     :NoFaster
86da: ad a4 6d                     lda     forward_speed     ;adjust forward speed, which is a 16.8 value
86dd: 6d 49 73                     adc     delta_speed       ;add per-frame delta, an 8.8 value
86e0: 8d a4 6d                     sta     forward_speed
86e3: ad a5 6d                     lda     forward_speed+1
86e6: 6d 4a 73                     adc     delta_speed+1
86e9: 8d a5 6d                     sta     forward_speed+1
86ec: 90 07                        bcc     :AdjustSpeed
86ee: ee a6 6d                     inc     forward_speed+2
86f1: 20 7f 7f                     jsr     Return7f7f
86f4: ea           :NoFaster       nop
                   ; Copy forward speed to DP variable, adjusting for fractional speed values
                   ; (which aren't used in this game).  A speed of 0.5 would be handled by setting
                   ; the speed to 0 or 1 on alternate frames.
                   ]sound_adj?     .var    $86    {addr/2}

86f5: ad 61 c0     :AdjustSpeed    lda     BUTN0             ;set button-down flags
86f8: 8d 93 6d                     sta     btns_0_down_flag
86fb: ad 62 c0                     lda     BUTN1
86fe: 8d 94 6d                     sta     btns_1_down_flag
8701: 18                           clc
8702: ad a7 6d                     lda     speed_fraction    ;track fractional value, updating every frame
8705: 6d a4 6d                     adc     forward_speed     ;not used in this game (always zero)
8708: 8d a7 6d                     sta     speed_fraction
870b: ad a5 6d                     lda     forward_speed+1
870e: 69 00                        adc     #$00
8710: 85 98                        sta     adj_fwd_speed
8712: 85 86                        sta     ]sound_adj?       ;used to adjust sound we don't actually play
8714: ad a6 6d                     lda     forward_speed+2   ; (presumably this is used to tweak the engine noise
8717: 69 00                        adc     #$00              ; when accelerating or decelerating, but the
8719: 85 99                        sta     adj_fwd_speed+1   ; engine noise is disabled)
871b: 85 87                        sta     ]sound_adj?+1
871d: 10 0d                        bpl     :IsPos
871f: 38                           sec                       ;we're moving backward, so use (0 - value) here
8720: a9 00                        lda     #$00              ;(not possible in this game)
8722: e5 86                        sbc     ]sound_adj?
8724: 85 86                        sta     ]sound_adj?
8726: a9 00                        lda     #$00
8728: e5 87                        sbc     ]sound_adj?+1
872a: 85 87                        sta     ]sound_adj?+1
872c: ce 5f 6d     :IsPos          dec     fuel_this_frame   ;have we fully deducted fuel for this frame?
872f: 30 0e                        bmi     :FuelDone         ;yes, branch
                   ; Update fuel.
8731: a2 08                        ldx     #$08              ;update current fuel by 2
8733: a0 39                        ldy     #$39
8735: a9 02                        lda     #$02              ;update 2-byte value
8737: 85 8a                        sta     ]num_bytes
8739: 20 68 7c                     jsr     ReduceResource    ;reduce value
873c: 4c 2c 87                     jmp     :IsPos

873f: ad 63 6d     :FuelDone       lda     space_region      ;get region?
8742: c9 03                        cmp     #$03              ;inside time portal?
8744: f0 57                        beq     :InPortal         ;yes, branch
8746: ad 95 6d                     lda     time_in_portal_ctr ;is the counter nonzero?
8749: 0d 96 6d                     ora     time_in_portal_ctr+1
874c: d0 03                        bne     :PostPortalReset? ;yes, we just left portal; reset state
874e: 4c 58 89                     jmp     :NotInPortal      ;no, continue

                   ; Reset portal-related state after leaving a portal.
                   :PostPortalReset?
8751: a9 00                        lda     #$00
8753: 85 ce                        sta     portal_next_xc
8755: 85 cf                        sta     portal_next_xc+1
8757: 85 d0                        sta     portal_next_yc
8759: 85 d1                        sta     portal_next_yc+1
875b: 8d 95 6d                     sta     time_in_portal_ctr
875e: 8d 96 6d                     sta     time_in_portal_ctr+1
8761: 8d 98 6d                     sta     time_portal_fail_ctr
8764: 8d 53 6d                     sta     portal_xmod0
8767: 8d 54 6d                     sta     portal_xmod0+1
876a: 8d 55 6d                     sta     portal_xmod0+2
876d: 8d 56 6d                     sta     portal_ymod0
8770: 8d 57 6d                     sta     portal_ymod0+1
8773: 8d 58 6d                     sta     portal_ymod0+2
8776: 8d 59 6d                     sta     portal_xmod1
8779: 8d 5a 6d                     sta     portal_xmod1+1
877c: 8d 5b 6d                     sta     portal_xmod1+2
877f: 8d 5c 6d                     sta     portal_ymod1
8782: 8d 5d 6d                     sta     portal_ymod1+1
8785: 8d 5e 6d                     sta     portal_ymod1+2
8788: 8d 9b 6d                     sta     wronly_6d9b?
878b: 8d 9c 6d                     sta     wronly_6d9b?+1
878e: 8d 9d 6d                     sta     wronly_6d9b?+2
8791: 8d 9e 6d                     sta     wronly_6d9b?+3
8794: 8d 9f 6d                     sta     wronly_6d9b?+4
8797: 8d a0 6d                     sta     wronly_6d9b?+5
879a: 4c 58 89                     jmp     :NotInPortal

                   ; 
                   ; Perturb the time portal position.
                   ; 
                   ]rng_limit      .var    $86    {addr/2}
                   ]rng_limit_mode .var    $88    {addr/1}
                   ]rng_retval     .var    $8a    {addr/2}
                   ]random_val     .var    $8e    {addr/3}

879d: ad 95 6d     :InPortal       lda     time_in_portal_ctr ;increment the time-in-portal counter
87a0: 18                           clc
87a1: 69 01                        adc     #$01
87a3: 8d 95 6d                     sta     time_in_portal_ctr
87a6: 90 03                        bcc     :NoInc
87a8: ee 96 6d                     inc     time_in_portal_ctr+1
87ab: ad ae 6d     :NoInc          lda     portal_bound_limit ;increment the limit, so portals get wilder over
87ae: 18                           clc                       ; time; value is only reset when game restarts
87af: 69 01                        adc     #$01
87b1: 8d ae 6d                     sta     portal_bound_limit
87b4: 90 03                        bcc     :NoInc
87b6: ee af 6d                     inc     portal_bound_limit+1
                   ; Start with the X coordinate.
87b9: ad ae 6d     :NoInc          lda     portal_bound_limit ;pass limit to RNG
87bc: 85 86                        sta     ]rng_limit
87be: ad af 6d                     lda     portal_bound_limit+1
87c1: 85 87                        sta     ]rng_limit+1
87c3: a9 01                        lda     #$01              ;limited range, positive/negative
87c5: 85 88                        sta     ]rng_limit_mode
87c7: 20 b0 7b                     jsr     GenRandom         ;get random number
87ca: a5 8a                        lda     ]rng_retval       ;copy the result out
87cc: 85 8e                        sta     ]random_val
87ce: a5 8b                        lda     ]rng_retval+1
87d0: 85 8f                        sta     ]random_val+1
87d2: 30 07                        bmi     :IsNeg
87d4: a9 00                        lda     #$00              ;sign-extend positive
87d6: 85 90                        sta     ]random_val+2
87d8: 4c df 87                     jmp     :Cont1

87db: a9 ff        :IsNeg          lda     #$ff              ;sign-extend negative
87dd: 85 90                        sta     ]random_val+2
                   ; Add the random value to the YC modifier.
                   ]shifted_copy   .var    $86    {addr/3}

87df: 18           :Cont1          clc
87e0: ad 53 6d                     lda     portal_xmod0
87e3: 65 8e                        adc     ]random_val
87e5: 8d 53 6d                     sta     portal_xmod0
87e8: ad 54 6d                     lda     portal_xmod0+1
87eb: 65 8f                        adc     ]random_val+1
87ed: 8d 54 6d                     sta     portal_xmod0+1
87f0: ad 55 6d                     lda     portal_xmod0+2
87f3: 65 90                        adc     ]random_val+2
87f5: 8d 55 6d                     sta     portal_xmod0+2
87f8: 20 7f 7f                     jsr     Return7f7f
                   ; Copy the value from $6d53 to ZP, essentially right-shifting 8x and sign-
                   ; extending.
87fb: ad 54 6d                     lda     portal_xmod0+1
87fe: 85 86                        sta     ]shifted_copy
8800: ad 55 6d                     lda     portal_xmod0+2
8803: 85 87                        sta     ]shifted_copy+1
8805: 10 05                        bpl     :IsPos
8807: a9 ff                        lda     #$ff
8809: 4c 0e 88                     jmp     :Cont2

880c: a9 00        :IsPos          lda     #$00
880e: 85 88        :Cont2          sta     ]shifted_copy+2
                   ; Modify the 24-bit value at $6d53, subtracting itself right-shifted 8x, so
                   ; bigger magnitudes beget bigger magnitudes (positive feedback loop).
8810: 38                           sec
8811: ad 53 6d                     lda     portal_xmod0
8814: e5 86                        sbc     ]shifted_copy
8816: 8d 53 6d                     sta     portal_xmod0
8819: ad 54 6d                     lda     portal_xmod0+1
881c: e5 87                        sbc     ]shifted_copy+1
881e: 8d 54 6d                     sta     portal_xmod0+1
8821: ad 55 6d                     lda     portal_xmod0+2
8824: e5 88                        sbc     ]shifted_copy+2
8826: 8d 55 6d                     sta     portal_xmod0+2
8829: 20 7f 7f                     jsr     Return7f7f
                   ; Modify the 24-bit value at $6d59, adding $6d53 right-shifted 8x.
882c: 18                           clc
882d: ad 59 6d                     lda     portal_xmod1
8830: 65 86                        adc     ]shifted_copy
8832: 8d 59 6d                     sta     portal_xmod1
8835: ad 5a 6d                     lda     portal_xmod1+1
8838: 65 87                        adc     ]shifted_copy+1
883a: 8d 5a 6d                     sta     portal_xmod1+1
883d: ad 5b 6d                     lda     portal_xmod1+2
8840: 65 88                        adc     ]shifted_copy+2
8842: 8d 5b 6d                     sta     portal_xmod1+2
                   ; Copy the value from $6d59 to ZP, essentially right-shifting 8x and sign-
                   ; extending.
8845: ad 5a 6d                     lda     portal_xmod1+1
8848: 85 86                        sta     ]shifted_copy
884a: ad 5b 6d                     lda     portal_xmod1+2
884d: 85 87                        sta     ]shifted_copy+1
884f: 10 05                        bpl     :IsPos
8851: a9 ff                        lda     #$ff
8853: 4c 58 88                     jmp     :Cont

8856: a9 00        :IsPos          lda     #$00
8858: 85 88        :Cont           sta     ]shifted_copy+2
885a: 20 7f 7f                     jsr     Return7f7f
                   ; Modify the 24-bit value at $6d59, subtracting itself right-shifted 8x.
885d: 38                           sec
885e: ad 59 6d                     lda     portal_xmod1
8861: e5 86                        sbc     ]shifted_copy
8863: 8d 59 6d                     sta     portal_xmod1
8866: ad 5a 6d                     lda     portal_xmod1+1
8869: e5 87                        sbc     ]shifted_copy+1
886b: 8d 5a 6d                     sta     portal_xmod1+1
886e: ad 5b 6d                     lda     portal_xmod1+2
8871: e5 88                        sbc     ]shifted_copy+2
8873: 8d 5b 6d                     sta     portal_xmod1+2
8876: ea                           nop
8877: ea                           nop
8878: ea                           nop
8879: ea                           nop
887a: 18                           clc                       ;update portal boundary X coordinate
887b: a5 ce                        lda     portal_next_xc
887d: 65 86                        adc     ]shifted_copy
887f: 85 ce                        sta     portal_next_xc
8881: a5 cf                        lda     portal_next_xc+1
8883: 65 87                        adc     ]shifted_copy+1
8885: 85 cf                        sta     portal_next_xc+1
                   ; 
                   ; Do it all again for Y coordinate.
                   ; 
                   ]rng_limit      .var    $86    {addr/2}
                   ]rng_limit_mode .var    $88    {addr/1}
                   ]random_val     .var    $8e    {addr/3}

8887: ad ae 6d                     lda     portal_bound_limit ;reset limit
888a: 85 86                        sta     ]rng_limit
888c: ad af 6d                     lda     portal_bound_limit+1
888f: 85 87                        sta     ]rng_limit+1
8891: a9 01                        lda     #$01
8893: 85 88                        sta     ]rng_limit_mode   ;generate +/-
8895: 20 b0 7b                     jsr     GenRandom         ;generate 16-bit random number
8898: a5 8a                        lda     ]rng_retval
889a: 85 8e                        sta     ]random_val
889c: a5 8b                        lda     ]rng_retval+1
889e: 85 8f                        sta     ]random_val+1
88a0: 30 07                        bmi     :IsNeg
88a2: a9 00                        lda     #$00
88a4: 85 90                        sta     ]random_val+2     ;sign-extend positive
88a6: 4c ad 88                     jmp     :Cont1

88a9: a9 ff        :IsNeg          lda     #$ff
88ab: 85 90                        sta     ]random_val+2     ;sign-extend negative
                   ; Add the random value to the XC modifier.
                   ]shifted_copy   .var    $86    {addr/3}

88ad: 18           :Cont1          clc
88ae: ad 56 6d                     lda     portal_ymod0      ;add random number
88b1: 65 8e                        adc     ]random_val
88b3: 8d 56 6d                     sta     portal_ymod0
88b6: ad 57 6d                     lda     portal_ymod0+1
88b9: 65 8f                        adc     ]random_val+1
88bb: 8d 57 6d                     sta     portal_ymod0+1
88be: ad 58 6d                     lda     portal_ymod0+2
88c1: 65 90                        adc     ]random_val+2
88c3: 8d 58 6d                     sta     portal_ymod0+2
88c6: 20 7f 7f                     jsr     Return7f7f
                   ; Copy the value from $6d56 to ZP, essentially right-shifting 8x and sign-
                   ; extending.
88c9: ad 57 6d                     lda     portal_ymod0+1
88cc: 85 86                        sta     ]shifted_copy
88ce: ad 58 6d                     lda     portal_ymod0+2
88d1: 85 87                        sta     ]shifted_copy+1
88d3: 10 05                        bpl     :IsPos
88d5: a9 ff                        lda     #$ff
88d7: 4c dc 88                     jmp     :Cont2

88da: a9 00        :IsPos          lda     #$00
88dc: 85 88        :Cont2          sta     ]shifted_copy+2
                   ; Modify the 24-bit value at $6d56, subtracting itself right-shifted 8x, so
                   ; bigger magnitudes beget bigger magnitudes (positive feedback loop).
88de: 38                           sec
88df: ad 56 6d                     lda     portal_ymod0
88e2: e5 86                        sbc     ]shifted_copy
88e4: 8d 56 6d                     sta     portal_ymod0
88e7: ad 57 6d                     lda     portal_ymod0+1
88ea: e5 87                        sbc     ]shifted_copy+1
88ec: 8d 57 6d                     sta     portal_ymod0+1
88ef: ad 58 6d                     lda     portal_ymod0+2
88f2: e5 88                        sbc     ]shifted_copy+2
88f4: 8d 58 6d                     sta     portal_ymod0+2
88f7: 20 7f 7f                     jsr     Return7f7f
                   ; Modify the 24-bit value at $6d5c, adding $6d56 right-shifted 8x.
88fa: 18                           clc
88fb: ad 5c 6d                     lda     portal_ymod1
88fe: 65 86                        adc     ]shifted_copy
8900: 8d 5c 6d                     sta     portal_ymod1
8903: ad 5d 6d                     lda     portal_ymod1+1
8906: 65 87                        adc     ]shifted_copy+1
8908: 8d 5d 6d                     sta     portal_ymod1+1
890b: ad 5e 6d                     lda     portal_ymod1+2
890e: 65 88                        adc     ]shifted_copy+2
8910: 8d 5e 6d                     sta     portal_ymod1+2
                   ; Copy the value from $6d5c to ZP, essentially right-shifting 8x and sign-
                   ; extending.
8913: ad 5d 6d                     lda     portal_ymod1+1
8916: 85 86                        sta     ]shifted_copy
8918: ad 5e 6d                     lda     portal_ymod1+2
891b: 85 87                        sta     ]shifted_copy+1
891d: 10 05                        bpl     :IsPos2
891f: a9 ff                        lda     #$ff
8921: 4c 26 89                     jmp     :Cont3

8924: a9 00        :IsPos2         lda     #$00
8926: 85 88        :Cont3          sta     ]shifted_copy+2
8928: 20 7f 7f                     jsr     Return7f7f
                   ; Modify the 24-bit value at $6d5c, subtracting itself right-shifted 8x.
892b: 38                           sec
892c: ad 5c 6d                     lda     portal_ymod1
892f: e5 86                        sbc     ]shifted_copy
8931: 8d 5c 6d                     sta     portal_ymod1
8934: ad 5d 6d                     lda     portal_ymod1+1
8937: e5 87                        sbc     ]shifted_copy+1
8939: 8d 5d 6d                     sta     portal_ymod1+1
893c: ad 5e 6d                     lda     portal_ymod1+2
893f: e5 88                        sbc     ]shifted_copy+2
8941: 8d 5e 6d                     sta     portal_ymod1+2
8944: ea                           nop
8945: ea                           nop
8946: ea                           nop
8947: ea                           nop
8948: 18                           clc
8949: a5 d0                        lda     portal_next_yc    ;update portal boundary Y coordinate
894b: 65 86                        adc     ]shifted_copy
894d: 85 d0                        sta     portal_next_yc
894f: a5 d1                        lda     portal_next_yc+1
8951: 65 87                        adc     ]shifted_copy+1
8953: 85 d1                        sta     portal_next_yc+1
8955: 20 45 5e                     jsr     UpdatePortalPosn  ;calculate next position
                   ; 
                   ; Decrement sound counters by one, unless already at zero.
                   ; 
8958: a5 87        :NotInPortal    lda     ]shifted_copy+1   ;(?)
895a: a0 04                        ldy     #$04
895c: b6 c8        :DecrLoop       ldx     sound_counters,y
895e: f0 05                        beq     :AlreadyZero
8960: ca                           dex
8961: 8a                           txa
8962: 99 c8 00                     sta     sound_counters,y
8965: 88           :AlreadyZero    dey
8966: ea                           nop
8967: 10 f3                        bpl     :DecrLoop
8969: a5 fa                        lda     impact_sound_flag ;decrement $fa to zero
896b: f0 02                        beq     UpdateRegion
896d: c6 fa                        dec     impact_sound_flag
                   ; 
                   ; Switches to a new region if appropriate.
                   ; 
                   • Clear variables

896f: ad 3b 6d     UpdateRegion    lda     game_active_flag  ;are we in demo mode?
8972: f0 2d                        beq     :Jmp_CheckRegion_1 ;yes, branch
8974: ad 63 6d                     lda     space_region      ;get region
8977: c9 03                        cmp     #$03              ;are we inside a time portal?
8979: d0 29                        bne     :Jmp_CheckRegion_2 ;no, branch
897b: ad c3 6d                     lda     time_left+1       ;check time left
897e: c9 99                        cmp     #$99              ;reached max?
8980: 90 08                        bcc     :StillInside      ;not yet, branch
8982: a9 06                        lda     #$06
8984: 20 c2 7f                     jsr     PlayMusicSeq      ;play "exit time portal" music
8987: 4c 9e 89                     jmp     :ChangeRegion     ;switch to a new region

898a: ad 96 6d     :StillInside    lda     time_in_portal_ctr+1 ;have we been inside for at least 500 ticks?
898d: d0 07                        bne     :Sub0500
898f: ad 95 6d                     lda     time_in_portal_ctr
8992: c9 05                        cmp     #$05
8994: 90 0b                        bcc     :Jmp_CheckRegion_1 ;haven't been inside long, skip button check
8996: ad 61 c0     :Sub0500        lda     BUTN0             ;are both buttons held down?
8999: 2d 62 c0                     and     BUTN1
899c: 10 03                        bpl     :Jmp_CheckRegion_1 ;no, branch
899e: 4c fd 89     :ChangeRegion   jmp     :RandRegion       ;exit the time portal to a new, random region

                   :Jmp_CheckRegion_1
89a1: 4c f0 89                     jmp     :CheckRegion

                   :Jmp_CheckRegion_2
89a4: 4c f0 89                     jmp     :CheckRegion

                   :EnterTimePortal
89a7: ee 97 6d                     inc     wronly_6d97?
89aa: ad 3b 6d                     lda     game_active_flag  ;are we in demo mode?
89ad: f0 28                        beq     :NoFanfare        ;yes, skip the fanfare
89af: a9 02                        lda     #$02
89b1: 20 c2 7f                     jsr     PlayMusicSeq      ;play "enter time portal" music
                   ; Erase status line, from left side to partway through fuel counter.
89b4: a2 00                        ldx     #$00
89b6: a9 00        :EraseLoop      lda     #$00
89b8: 9d 80 24                     sta     HIRES_P1+$480,x   ;line 9
89bb: 9d 80 28                     sta     HIRES_P1+$880,x
89be: 9d 80 2c                     sta     HIRES_P1+$c80,x
89c1: 9d 80 30                     sta     HIRES_P1+$1080,x
89c4: 9d 80 38                     sta     HIRES_P1+$1880,x
89c7: 9d 80 34                     sta     HIRES_P1+$1480,x
89ca: 9d 80 3c                     sta     HIRES_P1+$1c80,x  ;line 15
89cd: e8                           inx
89ce: e0 18                        cpx     #24               ;reached column 24 (last digit of fuel)?
89d0: 30 e4                        bmi     :EraseLoop
89d2: a9 02                        lda     #$02
89d4: 20 f4 0f                     jsr     Return0ff4
89d7: a9 00        :NoFanfare      lda     #$00
89d9: 8d 99 6d                     sta     entered_portal_flag ;clear "just entered" flag
89dc: a9 40                        lda     #$40
89de: 8d 62 6d                     sta     region_progress_ctr+1 ;configure max time in portal
89e1: ad 3b 6d                     lda     game_active_flag  ;are we in demo mode?
89e4: d0 05                        bne     :Playing          ;no, branch
89e6: a9 18                        lda     #$18
89e8: 8d 62 6d                     sta     region_progress_ctr+1 ;reduce max time in portal
89eb: a9 03        :Playing        lda     #$03              ;set space-region to 3 (inside portal)
89ed: 4c 55 8a                     jmp     :SetRegion

89f0: ad 99 6d     :CheckRegion    lda     entered_portal_flag ;did we just enter a time portal?
89f3: d0 b2                        bne     :EnterTimePortal  ;yes, do the intro bit
89f5: ad 62 6d                     lda     region_progress_ctr+1 ;check our progress in this region
89f8: 30 03                        bmi     :RandRegion       ;time for a new region, branch
89fa: 4c 7e 8a                     jmp     SpawnNewStuff

                   ; Pick a region at random.
                   • Clear variables
                   ]rng_limit_mode .var    $88    {addr/1}
                   ]rng_result     .var    $8a    {addr/2}

89fd: a9 ff        :RandRegion     lda     #$ff
89ff: 85 88                        sta     ]rng_limit_mode   ;no limit
8a01: 20 b0 7b                     jsr     GenRandom         ;generate random number
8a04: a5 8b                        lda     ]rng_result+1
8a06: 29 0f                        and     #$0f
8a08: 8d 62 6d                     sta     region_progress_ctr+1 ;init progress counter high byte to 0-15
8a0b: a5 8a                        lda     ]rng_result
8a0d: 8d 61 6d                     sta     region_progress_ctr ;init progress counter low byte
8a10: 29 07                        and     #$07              ;limit to 0-7
8a12: 8d 63 6d                     sta     space_region      ;use as region value
8a15: ac 3b 6d                     ldy     game_active_flag  ;are we playing the game?
8a18: d0 33                        bne     :InGame           ;yes, branch
                   ; Change the demo region.
8a1a: a5 8b                        lda     ]rng_result+1     ;not playing; set the forward speed
8a1c: 85 98                        sta     adj_fwd_speed
8a1e: 29 03                        and     #$03
8a20: 85 99                        sta     adj_fwd_speed+1   ;limit to 0-3 ($3ff is speed=10230)
8a22: ad be 6c                     lda     logo_region_toggle ;flip toggle
8a25: 49 ff                        eor     #$ff
8a27: 8d be 6c                     sta     logo_region_toggle
8a2a: 10 15                        bpl     :NotLogo          ;go into Epoch-logo mode every other time
8a2c: ad bf 6c                     lda     demo_logo_progress ;init progress to specific value for logo
8a2f: 8d 62 6d                     sta     region_progress_ctr+1 ; so it doesn't flip modes mid-logo-zoom
8a32: ad c0 6c                     lda     demo_logo_speed   ;set forward speed
8a35: 85 98                        sta     adj_fwd_speed
8a37: ad c1 6c                     lda     demo_logo_speed+1
8a3a: 85 99                        sta     adj_fwd_speed+1
8a3c: a9 06                        lda     #$06              ;set region to Epoch logo
8a3e: 4c 55 8a                     jmp     :SetRegion

8a41: ad 63 6d     :NotLogo        lda     space_region      ;get region
8a44: c9 06                        cmp     #$06              ;is it 6?
8a46: d0 0d                        bne     :SetRegion        ;no, branch
8a48: a9 03                        lda     #$03              ;don't show logo again; do time portal instead
8a4a: 4c 55 8a                     jmp     :SetRegion

8a4d: c9 03        :InGame         cmp     #$03              ;did we randomly pick time portal?
8a4f: f0 ac                        beq     :RandRegion       ;yes, re-roll
8a51: c9 06                        cmp     #$06              ;did we randomly pick Epoch logo?
8a53: f0 a8                        beq     :RandRegion       ;yes, re-roll
8a55: 8d 63 6d     :SetRegion      sta     space_region      ;set the new region
8a58: 0a                           asl     A                 ;multiply by 8
8a59: 0a                           asl     A
8a5a: 0a                           asl     A
8a5b: 18                           clc
8a5c: 6d cc 70                     adc     region_tab_base   ;add base pointer
8a5f: 8d 67 6d                     sta     region_tab_ptr    ;set pointer
8a62: ea                           nop
8a63: ad cd 70                     lda     region_tab_base+1
8a66: 69 00                        adc     #$00
8a68: 8d 68 6d                     sta     region_tab_ptr+1  ;set high byte
8a6b: ea                           nop
8a6c: ad 63 6d                     lda     space_region      ;get the region
8a6f: c9 03                        cmp     #$03              ;are we in a time portal?
8a71: d0 0b                        bne     SpawnNewStuff     ;no, branch
8a73: ad 62 6d                     lda     region_progress_ctr+1 ;reset region progress
8a76: 69 0e                        adc     #$0e
8a78: 8d 62 6d                     sta     region_progress_ctr+1
8a7b: 20 7f 7f                     jsr     Return7f7f
                   ; 
8a7e: a9 07        SpawnNewStuff   lda     #$07              ;get a "random" value from 0-7
8a80: 38                           sec
8a81: e5 b3                        sbc     engine_sound_ctr?+2
8a83: 30 4f                        bmi     :NoCreate         ;not in range, don't spawn this frame
8a85: 0a                           asl     A                 ;multiply by 4 (0-28)
8a86: 0a                           asl     A
8a87: 8d 64 6d                     sta     create_mult_ctr   ;put a limit on how much we create
8a8a: ad 63 6d                     lda     space_region      ;get the region
8a8d: c9 03                        cmp     #$03              ;are we in a time portal?
8a8f: d0 19                        bne     :TryCreateObj     ;no, branch
8a91: a4 6a                        ldy     head_obj_index
8a93: b9 08 9c                     lda     obj_shape_cl_index,y ;get shape class
8a96: c9 05                        cmp     #$05              ;is it a time portal boundary object?
8a98: d0 10                        bne     :TryCreateObj
8a9a: b9 00 9a                     lda     obj_first_elem_index,y
8a9d: 30 0b                        bmi     :TryCreateObj
8a9f: a8                           tay
8aa0: b9 80 a1                     lda     elem_zpos_hi,y
8aa3: c9 1f                        cmp     #$1f
8aa5: 90 03                        bcc     :TryCreateObj
8aa7: 4c ee 8a                     jmp     DrawStatus

                   ; Create a new object if there's room for it in the tables and it fits in the
                   ; objects-per-region limit.
                   ]region_ptr?    .var    $16    {addr/2}

8aaa: ad 67 6d     :TryCreateObj   lda     region_tab_ptr    ;get pointer to region limit table
8aad: 85 16                        sta     ]region_ptr?
8aaf: ad 68 6d                     lda     region_tab_ptr+1
8ab2: 85 17                        sta     ]region_ptr?+1
8ab4: ea                           nop
8ab5: a5 6d                        lda     free_obj_count    ;do we have room to create a new object?
8ab7: f0 1b                        beq     :NoCreate         ;no, branch
8ab9: a5 6e                        lda     free_elem_count   ;got space in element list?
8abb: f0 17                        beq     :NoCreate         ;no, branch
8abd: a2 07                        ldx     #$07              ;loop over 8 shape classes
8abf: ee 65 6d     :ChkClassLoop   inc     shape_cl_ctr      ;increment counter
8ac2: ad 65 6d                     lda     shape_cl_ctr      ;get counter
8ac5: 29 07                        and     #$07              ;reduce to 0-7
8ac7: a8                           tay
8ac8: b9 69 6d                     lda     active_class_ctrs,y ;get count of active objects of this class
8acb: d1 16                        cmp     (]region_ptr?),y  ;compare to max
8acd: 30 08                        bmi     :CreateObject     ;cur < max, create another
8acf: ca                           dex
8ad0: ea                           nop
8ad1: 10 ec                        bpl     :ChkClassLoop     ;try the next class
8ad3: ea                           nop
8ad4: 4c ee 8a     :NoCreate       jmp     DrawStatus        ;no luck, go on to the next thing

                   ; Create a new object.  Object class in Y-reg.
8ad7: a9 f7        :CreateObject   lda     #$f7
8ad9: 85 a2                        sta     linked_obj_index
8adb: ad 64 6d                     lda     create_mult_ctr   ;get counter
8ade: 38                           sec
8adf: f9 7f 70                     sbc     create_mult_tab,y ;subtract a class-specific value, so we can create
8ae2: 8d 64 6d                     sta     create_mult_ctr   ; lots of stars all at once, but just one base
8ae5: 20 0f 76                     jsr     CreateObject      ;create an object
8ae8: ea                           nop
8ae9: ad 64 6d                     lda     create_mult_ctr   ;check counter
8aec: 10 bc                        bpl     :TryCreateObj     ;we're in the "positive phase", so try for another
                   ; 
                   ; Draw status text a bit at a time.
                   ; 
8aee: 20 36 7b     DrawStatus      jsr     DrawStatusLine    ;draw one character of status line
8af1: 20 36 7b     :DrawStatus1    jsr     DrawStatusLine    ;draw one character of status line
8af4: 18                           clc                       ;do sound stuff
8af5: a5 b2                        lda     engine_sound_ctr?+1
8af7: 69 0b                        adc     #$0b
8af9: 85 b2                        sta     engine_sound_ctr?+1
8afb: 90 0f                        bcc     :NoSound
8afd: e6 b3                        inc     engine_sound_ctr?+2
8aff: a5 cc                        lda     engine_sound_enable
8b01: f0 09                        beq     :NoSound
8b03: a5 b3                        lda     engine_sound_ctr?+2
8b05: 25 b1                        and     engine_sound_ctr?
8b07: d0 03                        bne     :NoSound
8b09: ad 30 c0                     lda     SPKR              ;click
8b0c: a5 b3        :NoSound        lda     engine_sound_ctr?+2 ;load $b3
8b0e: a5 b3                        lda     engine_sound_ctr?+2 ;load $b3 again
8b10: 18                           clc
8b11: a5 b3                        lda     engine_sound_ctr?+2 ;load $b3 a third time
8b13: c9 09                        cmp     #$09              ;is it < 9?
8b15: 30 da                        bmi     :DrawStatus1      ;yes, draw another character
8b17: 20 7f 7f                     jsr     Return7f7f
8b1a: ad 3b 6d                     lda     game_active_flag  ;are we in demo mode?
8b1d: f0 03                        beq     :ShowOutOf        ;yes, branch
8b1f: 4c 2d 8c                     jmp     StartRedraw

                   ; After the game ends, we show "out of ____", and continue to display it for a
                   ; bit after the demo resumes.  We do this instead of the author/copyright text.
                   ]str_index      .var    $8c    {addr/1}

8b22: ad 40 6d     :ShowOutOf      lda     end_game_msg_ctr+1 ;has high byte of counter hit zero?
8b25: f0 7f                        beq     :NoShowOut        ;yes, branch
8b27: 38                           sec
8b28: ad 3f 6d                     lda     end_game_msg_ctr  ;decrement counter
8b2b: e9 01                        sbc     #$01
8b2d: 8d 3f 6d                     sta     end_game_msg_ctr
8b30: ad 40 6d                     lda     end_game_msg_ctr+1
8b33: e9 00                        sbc     #$00
8b35: 8d 40 6d                     sta     end_game_msg_ctr+1
                   ; Draw "OUT OF  ____" message.
8b38: a2 00                        ldx     #$00              ;column 0
8b3a: a9 00                        lda     #$00
8b3c: 85 8c                        sta     ]str_index
8b3e: a4 8c        :OutOfLoop      ldy     ]str_index
8b40: b9 c1 6e                     lda     text_out_of,y     ;get char from string
8b43: 20 03 75                     jsr     PrintCharLine160  ;print it
8b46: e6 8c                        inc     ]str_index
8b48: e0 06                        cpx     #$06              ;done yet? (6 chars in "OUT OF")
8b4a: ea                           nop
8b4b: 30 f1                        bmi     :OutOfLoop
8b4d: ea                           nop
8b4e: a2 08                        ldx     #$08              ;column 8
8b50: a5 b5                        lda     end_game_cause    ;get reason for ending game (0/4/8)
8b52: 85 8c                        sta     ]str_index        ;use as index into string
8b54: a4 8c        :RsrcLoop       ldy     ]str_index
8b56: b9 c8 6e                     lda     text_time_fuel_amun,y ;get char from string
8b59: 20 03 75                     jsr     PrintCharLine160  ;print it
8b5c: e6 8c                        inc     ]str_index
8b5e: e0 0c                        cpx     #$0c              ;reached column 12 (8+4)?
8b60: ea                           nop
8b61: 30 f1                        bmi     :RsrcLoop
8b63: ea                           nop
                   ; Draw "RATING  ______" message.
8b64: a2 10                        ldx     #16               ;column 16
8b66: a9 00                        lda     #$00
8b68: 85 8c                        sta     ]str_index
8b6a: a4 8c        :RatLoop        ldy     ]str_index
8b6c: b9 d8 6e                     lda     text_rating,y     ;get char from string
8b6f: 20 03 75                     jsr     PrintCharLine160  ;print it
8b72: e6 8c                        inc     ]str_index
8b74: e0 16                        cpx     #22               ;done yet? (6 chars in "RATING")
8b76: ea                           nop
8b77: 30 f1                        bmi     :RatLoop
8b79: ea                           nop
8b7a: a2 18                        ldx     #24               ;column 24
8b7c: a5 b6                        lda     score_rating_index ;index to rating string
8b7e: 85 8c                        sta     ]str_index
8b80: a4 8c        :RatLabelLoop   ldy     ]str_index
8b82: b9 e7 6e                     lda     text_rating_labels,y ;get char from string
8b85: 20 03 75                     jsr     PrintCharLine160  ;print it
8b88: e6 8c                        inc     ]str_index
8b8a: e0 28                        cpx     #40               ;reached column 40 (24+16)?
8b8c: ea                           nop
8b8d: 30 f1                        bmi     :RatLabelLoop
8b8f: ea                           nop
                   ; Play the music if we haven't yet.
8b90: ad 43 6d                     lda     game_over_music   ;have we played the music?
8b93: f0 0e                        beq     :MusicDone        ;yes, bail
8b95: c9 01                        cmp     #$01              ;is it the "not new high score" music?
8b97: d0 02                        bne     :PlayGameOver     ;no, play it
8b99: a9 00                        lda     #$00              ;yes, play the short game-over sequence
8b9b: 20 c2 7f     :PlayGameOver   jsr     PlayMusicSeq
8b9e: a9 00                        lda     #$00
8ba0: 8d 43 6d                     sta     game_over_music   ;record that we're done playing
8ba3: 4c 2d 8c     :MusicDone      jmp     StartRedraw       ;don't show author/copyright

8ba6: ea           :NoShowOut      nop
8ba7: ad 3f 6d                     lda     end_game_msg_ctr  ;did timer just expire?
8baa: f0 23                        beq     :DrawTitleText    ;no, skip
                   ; We show "out of ____" for a while after the game ends.  If the timer has just
                   ; expired, we want to erase the text.
8bac: a2 00                        ldx     #$00
8bae: a9 00        :ClearLoop      lda     #$00
8bb0: 9d 50 22                     sta     HIRES_P1+$250,x   ;line 160
8bb3: 9d 50 26                     sta     HIRES_P1+$650,x
8bb6: 9d 50 2a                     sta     HIRES_P1+$a50,x
8bb9: 9d 50 2e                     sta     HIRES_P1+$e50,x
8bbc: 9d 50 36                     sta     HIRES_P1+$1650,x
8bbf: 9d 50 32                     sta     HIRES_P1+$1250,x
8bc2: 9d 50 3a                     sta     HIRES_P1+$1a50,x
8bc5: e8                           inx
8bc6: e0 28                        cpx     #40
8bc8: 30 e4                        bmi     :ClearLoop
8bca: a9 00                        lda     #$00
8bcc: 8d 3f 6d                     sta     end_game_msg_ctr  ;zero this so we know erase is done
                   ; 
                   ; Draw the author/copyright strings.  We draw one per frame, rotating.
                   ; 
8bcf: ee 41 6d     :DrawTitleText  inc     title_text_draw_index ;inc index
8bd2: ad 41 6d                     lda     title_text_draw_index ;get index
8bd5: c9 03                        cmp     #$03              ;have we hit 3?
8bd7: 30 1e                        bmi     :Not3             ;not yet, branch
8bd9: a9 00                        lda     #$00
8bdb: 8d 41 6d                     sta     title_text_draw_index ;yes, reset index to zero
                   ; Index=0, draw "Sirius Software Presents" on line 32.
8bde: a2 08                        ldx     #$08
8be0: a9 00                        lda     #$00
8be2: 85 8c                        sta     ]str_index
8be4: a4 8c        :Loop0          ldy     ]str_index
8be6: b9 35 6e                     lda     text_sirius_pres,y
8be9: 20 95 74                     jsr     PrintCharLine32
8bec: e6 8c                        inc     ]str_index
8bee: e0 20                        cpx     #$20
8bf0: ea                           nop
8bf1: 30 f1                        bmi     :Loop0
8bf3: ea                           nop
8bf4: 4c 2d 8c                     jmp     StartRedraw

8bf7: ad 41 6d     :Not3           lda     title_text_draw_index ;load index again
8bfa: c9 01                        cmp     #$01              ;is it 1?
8bfc: f0 19                        beq     :Not1             ;yes, branch
                   ; Index=1, draw "By  Larry Miller" on line 160.
8bfe: a2 0c                        ldx     #$0c
8c00: a9 00                        lda     #$00
8c02: 85 8c                        sta     ]str_index
8c04: a4 8c        :Loop1          ldy     ]str_index
8c06: b9 5c 6e                     lda     text_larry_spc,y
8c09: 20 03 75                     jsr     PrintCharLine160
8c0c: e6 8c                        inc     ]str_index
8c0e: e0 1c                        cpx     #$1c
8c10: ea                           nop
8c11: 30 f1                        bmi     :Loop1
8c13: ea                           nop
8c14: 4c 2d 8c                     jmp     StartRedraw

                   ; Index = 2, draw "Copyright 1981".
8c17: a2 0d        :Not1           ldx     #$0d
8c19: a9 00                        lda     #$00
8c1b: 85 8c                        sta     ]str_index
8c1d: a4 8c        :Loop2          ldy     ]str_index
8c1f: b9 4e 6e                     lda     text_copyright,y
8c22: 20 71 75                     jsr     PrintCharLine176
8c25: e6 8c                        inc     ]str_index
8c27: e0 1b                        cpx     #$1b
8c29: ea                           nop
8c2a: 30 f1                        bmi     :Loop2
8c2c: ea                           nop
                   ; 
                   ; Starting point for object update and redraw.
                   ; 
                   ; (This could be considered the top of the game loop, since we reset the stack
                   ; pointer.)
                   ; 
8c2d: a9 ee        StartRedraw     lda     #$ee
8c2f: 85 c6                        sta     prev_zpos+1       ;(invalidate? is this actually invalid?)
8c31: a9 00                        lda     #$00
8c33: 85 b2                        sta     engine_sound_ctr?+1 ;reset sound counters
8c35: 85 b3                        sta     engine_sound_ctr?+2
8c37: 85 cc                        sta     engine_sound_enable ;disable "engine noise"?
8c39: a9 df                        lda     #$df
8c3b: 85 74                        sta     prev_obj_index    ;we're at the start, so no previous object
8c3d: a2 c0                        ldx     #$c0
8c3f: 9a                           txs                       ;reset stack pointer
8c40: 20 7f 7f                     jsr     Return7f7f
8c43: a6 6a                        ldx     head_obj_index    ;get index of object at head of list
8c45: 86 62                        stx     cur_obj_index     ;set as current
8c47: 10 0f                        bpl     RedrawObject      ;if valid, start redrawing
8c49: 4c 5c 81                     jmp     PartialRestart    ;otherwise, something is wrong; reset game engine

8c4c: 3d 3d 3d 3d+                 .junk   12

                   ; 
                   ; Erases and draws an object.
                   ; 
                   ; On entry:
                   ;   X-reg: object index (0-39)
                   ; 
8c58: bd 00 9a     RedrawObject    lda     obj_first_elem_index,x ;get index of first element
8c5b: 10 03                        bpl     :ElemOk           ;if valid, branch
8c5d: 4c 5c 81                     jmp     PartialRestart    ;otherwise, reset game engine

8c60: a9 00        :ElemOk         lda     #$00
8c62: 8d 82 8c                     sta     unused_flag_merge
8c65: 20 66 5f                     jsr     UpdateObject      ;update object movement; puts 1st elem into cur_elem
8c68: a6 64                        ldx     cur_elem_index    ;get element index
8c6a: 10 03                        bpl     :Jmp_Redraw       ;is valid, branch
8c6c: 4c 2a 92                     jmp     NextObject        ;not valid, move on to next obj

8c6f: 4c 83 8c     :Jmp_Redraw     jmp     RedrawElement

8c72: 00 00 00 3d+                 .junk   15
8c81: 00           saved_obj_index .dd1    $00               ;temp storage for current object index
                   unused_flag_merge
8c82: 00                           .dd1    $00               ;merged flag values (unused)

                   ; 
                   ; Redraws an element.  Computes the screen coordinates of the new position, then
                   ; jumps to the appropriate erase function, which upon completion jumps to the
                   ; apppropriate draw function.
                   ; 
                   ; Elements that are clipped completely (fully off screen) will have a mod type
                   ; of $82, and won't be drawn.
                   ; 
                   ; (This is not a function that's called.  This is part of a stream of execution
                   ; that loops through here until the set of elements for the current object is
                   ; exhausted.)
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ; 
8c83: bd 00 9f     RedrawElement   lda     elem_obj_index,x  ;get element's object index (this is strictly
8c86: 10 03                        bpl     :IndexOkay        ; a consistency check)
8c88: 4c 5c 81                     jmp     PartialRestart    ;unexpected, reset game

8c8b: 20 55 64     :IndexOkay      jsr     UpdateElement     ;update element position, set mod type and flags
8c8e: a5 c9                        lda     sound_counters+1  ;do sound stuff
8c90: f0 03                        beq     :NoSound
8c92: ad 30 c0                     lda     SPKR              ;click for sfx (player cannon, ship explosion)
8c95: bd 80 9f     :NoSound        lda     elem_mod_types,x  ;check the modified element type
8c98: f0 12                        beq     ErasePoint        ;was $00, erase a point
8c9a: 10 24                        bpl     EraseHorizLine    ;was $01, erase horizontal line
8c9c: 0a                           asl     A
8c9d: f0 07                        beq     :EraseVertLine    ;was $80, erase vertical line
8c9f: 29 04                        and     #$04              ;was it $82 ($04 after shift)?
8ca1: d0 06                        bne     :NoErase          ;yes, element was not drawn, nothing to erase
8ca3: 4c 71 8d                     jmp     EraseRect         ;no, $81 or $83; erase rect

8ca6: 4c 38 8d     :EraseVertLine  jmp     EraseVertLine

8ca9: 4c 52 8e     :NoErase        jmp     DrawElement

                   ; 
                   ; Erases a point.  Pixel bits are set to zero.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ; 
                   • Clear variables
                   ]hptr           .var    $10    {addr/2}

8cac: bd 00 a4     ErasePoint      lda     elem_erase_1,x    ;get high byte of pointer
8caf: 85 11                        sta     ]hptr+1
8cb1: bc c0 a3                     ldy     elem_erase_0,x    ;get index into page
8cb4: bd 40 a5                     lda     elem_erase_6,x    ;get bit mask
8cb7: 49 ff                        eor     #$ff              ;invert it for AND
8cb9: 31 10                        and     (]hptr),y
8cbb: 91 10                        sta     (]hptr),y         ;update hi-res screen
8cbd: 4c 52 8e                     jmp     DrawElement

                   ; 
                   ; Erases a horizontal line, ANDing the color pixel bits to zero.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ; 
                   • Clear variables
                   ]hptr           .var    $18    {addr/2}
                   ]saved_yreg     .var    $86    {addr/1}
                   ]right_col      .var    $87    {addr/1}
                   ]color0         .var    $89    {addr/1}
                   ]odd_even_mask  .var    $90    {addr/1}
                   ]color1         .var    $91    {addr/1}

8cc0: bd c0 a4     EraseHorizLine  lda     elem_erase_4,x    ;get column of right edge
8cc3: 85 87                        sta     ]right_col
8cc5: bd 40 a4                     lda     elem_erase_2,x    ;get hi-res line address, low byte
8cc8: 85 18                        sta     ]hptr
8cca: bd 00 a5                     lda     elem_erase_5,x    ;get hi-res line address, high byte
8ccd: 85 19                        sta     ]hptr+1
8ccf: bd 80 a0                     lda     elem_cur_colors,x ;get current element color
8cd2: 1d c0 a3                     ora     elem_erase_0,x    ;OR with left edge pixel color offset
8cd5: a8                           tay
8cd6: 29 08                        and     #%00001000        ;strip all but bit 3 to get odd/even mask
8cd8: 85 90                        sta     ]odd_even_mask
8cda: b9 63 72                     lda     color_bit_masks_left,y ;get left-edge color bit pattern
8cdd: 49 ff                        eor     #$ff              ;invert bits for AND
8cdf: bc 00 a4                     ldy     elem_erase_1,x    ;get column of left edge
8ce2: 31 18                        and     (]hptr),y         ;mask bits from hi-res screen
8ce4: 91 18                        sta     (]hptr),y         ;update hi-res screen
8ce6: c8                           iny                       ;move to next column
8ce7: c4 87                        cpy     ]right_col        ;compare to right edge
8ce9: f0 38                        beq     :RightCol         ;at right, branch
8ceb: 10 48                        bpl     :DrawDone         ;past right (single-column), we're done
8ced: 84 86                        sty     ]saved_yreg       ;spill Y-reg
8cef: a5 90                        lda     ]odd_even_mask    ;get mask (0 or 8)
8cf1: 1d 80 a0                     ora     elem_cur_colors,x ;combine with current element color
8cf4: a8                           tay
8cf5: b9 63 72                     lda     color_bit_masks_left,y ;get full-byte color
8cf8: 49 ff                        eor     #$ff              ;invert to form AND mask
8cfa: 85 89                        sta     ]color0           ;save as first color
8cfc: a5 90                        lda     ]odd_even_mask
8cfe: 49 08                        eor     #$08              ;flip odd/even
8d00: 1d 80 a0                     ora     elem_cur_colors,x
8d03: a8                           tay
8d04: b9 63 72                     lda     color_bit_masks_left,y ;get full-byte color
8d07: 49 ff                        eor     #$ff              ;invert to form AND mask
8d09: 85 91                        sta     ]color1           ;save as second color
                   ; 
8d0b: a4 86                        ldy     ]saved_yreg       ;restore Y-reg (hi-res column)
8d0d: a5 91        :MiddleLoop     lda     ]color1
8d0f: 31 18                        and     (]hptr),y         ;remove second color from bits in this byte
8d11: 91 18                        sta     (]hptr),y         ;update hi-res screen
8d13: c8                           iny
8d14: c4 87                        cpy     ]right_col        ;at right edge yet?
8d16: 10 0b                        bpl     :RightCol         ;yes, branch
8d18: a5 89                        lda     ]color0
8d1a: 31 18                        and     (]hptr),y         ;remove first color from bits in this byte
8d1c: 91 18                        sta     (]hptr),y         ;update hi-res screen
8d1e: c8                           iny
8d1f: c4 87                        cpy     ]right_col        ;at right edge yet?
8d21: 30 ea                        bmi     :MiddleLoop       ;no, loop
8d23: bd 80 a4     :RightCol       lda     elem_erase_3,x    ;get pixel color offset for right edge
8d26: 1d 80 a0                     ora     elem_cur_colors,x ;combine with element color
8d29: a8                           tay
8d2a: b9 d3 72                     lda     color_bit_masks_right,y ;get pixel color mask
8d2d: 49 ff                        eor     #$ff              ;invert to form AND mask
8d2f: a4 87                        ldy     ]right_col
8d31: 31 18                        and     (]hptr),y
8d33: 91 18                        sta     (]hptr),y         ;update hi-res screen
8d35: 4c 52 8e     :DrawDone       jmp     DrawElement

                   ; 
                   ; Erases a vertical line, ANDing the color pixel bits to zero.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ; 
                   ]instr_ptr      .var    $10    {addr/2}
                   ]mod_offset     .var    $8a    {addr/1}

8d38: bc 00 a5     EraseVertLine   ldy     elem_erase_5,x    ;get bottom coordinate
8d3b: c8                           iny                       ;increment to get start of next entry
8d3c: b9 00 55                     lda     unroll_and_addr_hi,y ;get address of instruction, high byte
8d3f: 85 11                        sta     ]instr_ptr+1      ;set high byte of pointer
8d41: b9 00 b7                     lda     unroll_a_o_addr_lo,y ;get address of instruction, low byte
8d44: a8                           tay
8d45: 85 8a                        sta     ]mod_offset       ;save offset
8d47: a9 60                        lda     #INSTR_RTS
8d49: 91 10                        sta     (]instr_ptr),y    ;replace the TXA with an RTS
8d4b: bc 40 a4                     ldy     elem_erase_2,x    ;get top coordinate
8d4e: b9 00 b7                     lda     unroll_a_o_addr_lo,y ;copy instruction address to JSR instruction
8d51: 8d 64 8d                     sta     _CallAnd0+1
8d54: b9 00 55                     lda     unroll_and_addr_hi,y
8d57: 8d 65 8d                     sta     _CallAnd0+2
8d5a: bc 00 a4                     ldy     elem_erase_1,x    ;get left edge column
8d5d: bd 40 a5                     lda     elem_erase_6,x    ;get pixel bit mask
8d60: 49 ff                        eor     #$ff              ;invert to form AND mask
8d62: aa                           tax                       ;copy to X-reg
8d63: 20 76 a8     _CallAnd0       jsr     AndSeq_90         ;execute unrolled AND sequence
8d66: a4 8a                        ldy     ]mod_offset
8d68: a9 8a                        lda     #INSTR_TXA
8d6a: 91 10                        sta     (]instr_ptr),y    ;replace TXA instruction
8d6c: a6 64                        ldx     cur_elem_index
8d6e: 4c 52 8e                     jmp     DrawElement       ;go draw the element in its new position

                   ; 
                   ; Erases a filled rectangle.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ; 
                   • Clear variables
                   ]restore_ptr    .var    $10    {addr/2}
                   ]left_col       .var    $86    {addr/1}
                   ]right_col      .var    $87    {addr/1}
                   ]restore_index  .var    $8a    {addr/1}
                   ]left_pixel_mask .var   $8c    {addr/1}
                   ]odd_even_mask  .var    $90    {addr/1}
                   ]elem_color     .var    $91    {addr/1}

8d71: bd c0 a4     EraseRect       lda     elem_erase_4,x    ;get hi-res column of right edge
8d74: 85 87                        sta     ]right_col
8d76: bd 00 a4                     lda     elem_erase_1,x    ;get hi-res column of left edge
8d79: 85 86                        sta     ]left_col
8d7b: bd 80 a0                     lda     elem_cur_colors,x ;get current element color
8d7e: 85 91                        sta     ]elem_color
8d80: 1d c0 a3                     ora     elem_erase_0,x    ;merge nibbles with left edge color index
8d83: a8                           tay
8d84: 29 08                        and     #%00001000        ;strip all but bit 3 to form odd/even mask
8d86: 85 90                        sta     ]odd_even_mask
8d88: b9 63 72                     lda     color_bit_masks_left,y ;get pixel bits for left edge
8d8b: 49 ff                        eor     #$ff              ;invert to form AND mask
8d8d: 85 8c                        sta     ]left_pixel_mask
8d8f: 38                           sec
8d90: a5 87                        lda     ]right_col        ;compute (right - left - 3)
8d92: e5 86                        sbc     ]left_col
8d94: e9 03                        sbc     #$03
8d96: 85 b0                        sta     mid_col_count
8d98: 10 35                        bpl     :WideRect         ;erasing 4+ columns, use STA
                   ; Erasing 1-3 columns, use sequence of AND instructions.
8d9a: a9 8a                        lda     #INSTR_TXA        ;replacing TXA
8d9c: 85 af                        sta     orig_opcode
8d9e: bc 00 a5                     ldy     elem_erase_5,x    ;get bottom coord
8da1: c8                           iny                       ;incr to get start of next group
8da2: b9 00 55                     lda     unroll_and_addr_hi,y ;get address of TXA instruction
8da5: 85 11                        sta     ]restore_ptr+1    ;save for later
8da7: b9 00 b7                     lda     unroll_a_o_addr_lo,y
8daa: a8                           tay
8dab: 85 8a                        sta     ]restore_index
8dad: a9 60                        lda     #INSTR_RTS
8daf: 91 10                        sta     (]restore_ptr),y  ;replace with RTS instruction
8db1: bc 40 a4                     ldy     elem_erase_2,x    ;get top coord
8db4: b9 00 b7                     lda     unroll_a_o_addr_lo,y ;get address of instruction group
8db7: 8d 08 8e                     sta     _CallAnd1+1       ;modify the JSR instructions
8dba: 8d 2b 8e                     sta     _CallAnd2+1
8dbd: 8d 48 8e                     sta     _CallAnd3+1
8dc0: b9 00 55                     lda     unroll_and_addr_hi,y
8dc3: 8d 09 8e                     sta     _CallAnd1+2
8dc6: 8d 2c 8e                     sta     _CallAnd2+2
8dc9: 8d 49 8e                     sta     _CallAnd3+2
8dcc: 4c 01 8e                     jmp     :DoErase          ;go erase stuff

                   ; Erasing 4+ columns, use sequence of STA instructions.
8dcf: a9 99        :WideRect       lda     #INSTR_STA_ABS    ;replacing STA
8dd1: 85 af                        sta     orig_opcode
8dd3: bc 00 a5                     ldy     elem_erase_5,x    ;get bottom coord
8dd6: c8                           iny                       ;incr to get start of next group
8dd7: b9 00 57                     lda     unroll_sta_hi,y   ;get address of STA instruction
8dda: 85 11                        sta     ]restore_ptr+1    ;save for later
8ddc: b9 00 56                     lda     unroll_sta_lo,y
8ddf: a8                           tay
8de0: 85 8a                        sta     ]restore_index
8de2: a9 60                        lda     #INSTR_RTS
8de4: 91 10                        sta     (]restore_ptr),y  ;replace with RTS instruction
8de6: bc 40 a4                     ldy     elem_erase_2,x    ;get top coord
8de9: b9 00 56                     lda     unroll_sta_lo,y   ;get address of instruction group
8dec: 8d 08 8e                     sta     _CallAnd1+1       ;modify the JSR instructions
8def: 8d 2b 8e                     sta     _CallAnd2+1
8df2: 8d 48 8e                     sta     _CallAnd3+1
8df5: b9 00 57                     lda     unroll_sta_hi,y
8df8: 8d 09 8e                     sta     _CallAnd1+2
8dfb: 8d 2c 8e                     sta     _CallAnd2+2
8dfe: 8d 49 8e                     sta     _CallAnd3+2
                   ; Erase left edge.
8e01: a9 00        :DoErase        lda     #$00              ;for STA, we write $00
8e03: a6 8c                        ldx     ]left_pixel_mask  ;for AND, we mask
8e05: a4 86                        ldy     ]left_col
8e07: 20 61 a8     _CallAnd1       jsr     AndSeq_87         ;perform unrolled AND or STA sequence
8e0a: e6 86                        inc     ]left_col         ;advance to next column
8e0c: a5 86                        lda     ]left_col
8e0e: c5 87                        cmp     ]right_col        ;have we reached the right column?
8e10: f0 23                        beq     :EraseRectRt      ;yes, erase that
8e12: 30 03                        bmi     :EraseRectMid     ;no, erase middle
8e14: 4c 4a 8e                     jmp     :EraseRectDone    ;past it, erase is done

8e17: a5 90        :EraseRectMid   lda     ]odd_even_mask
8e19: 49 08                        eor     #$08              ;flip odd/even
8e1b: 85 90                        sta     ]odd_even_mask
8e1d: 05 91                        ora     ]elem_color       ;merge nibble with current element color
8e1f: a8                           tay
8e20: b9 63 72                     lda     color_bit_masks_left,y ;get full-byte color pixel mask
8e23: 49 ff                        eor     #$ff              ;invert to form AND mask
8e25: aa                           tax                       ;copy to X-reg for AND sequence
8e26: a4 86                        ldy     ]left_col         ;get column
8e28: a9 00                        lda     #$00              ;set A-reg to $00 for STA
8e2a: 20 61 a8     _CallAnd2       jsr     AndSeq_87         ;perform unrolled AND or STA sequence
8e2d: e6 86                        inc     ]left_col         ;advance to next column
8e2f: a5 86                        lda     ]left_col
8e31: c5 87                        cmp     ]right_col        ;have we reached the right column?
8e33: 30 e2                        bmi     :EraseRectMid     ;not yet, loop
8e35: a6 64        :EraseRectRt    ldx     cur_elem_index
8e37: bd 80 a4                     lda     elem_erase_3,x    ;get right edge pixel color offset
8e3a: 05 91                        ora     ]elem_color       ;merge nibble with current element color
8e3c: a8                           tay
8e3d: b9 d3 72                     lda     color_bit_masks_right,y ;get full-byte color pixel mask
8e40: 49 ff                        eor     #$ff              ;invert to form AND mask
8e42: aa                           tax                       ;copy to X-reg for AND sequence
8e43: a4 87                        ldy     ]right_col        ;get column
8e45: a9 00                        lda     #$00              ;set A-reg to $00 for STA
8e47: 20 61 a8     _CallAnd3       jsr     AndSeq_87         ;perform unrolled AND or STA sequence
8e4a: 4c 70 5a     :EraseRectDone  jmp     AfterEraseRect    ;draw crosshairs, then restore instruction

8e4d: 8a                           .junk   1

                   ; 
                   ; Finishes the erase-rect operation by restoring the opcode in the unrolled op
                   ; sequence, then falling into the draw routine.
                   ; 
8e4e: a5 af        AfterEraseRect1 lda     orig_opcode
8e50: 91 10                        sta     (]restore_ptr),y  ;restore opcode
                   ; 
                   ; Draws an element.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ; 
8e52: a5 c8        DrawElement     lda     sound_counters    ;do sound stuff
8e54: f0 03                        beq     :NoSound
8e56: ad 30 c0                     lda     SPKR
8e59: a5 72        :NoSound        lda     no_draw_obj_flag
8e5b: 05 7c                        ora     no_draw_elem_flag?
8e5d: f0 13                        beq     :UpdateColor
8e5f: a9 82        :NoDraw         lda     #$82
8e61: 9d 80 9f                     sta     elem_mod_types,x  ;set mod type to "do not draw"
8e64: 20 7f 7f                     jsr     Return7f7f
8e67: ad 82 8c                     lda     unused_flag_merge ;update this location; results never used
8e6a: 05 7a                        ora     elem_bad_z_flag?
8e6c: 8d 82 8c                     sta     unused_flag_merge
8e6f: 4c 16 92                     jmp     ElemDrawDone

8e72: e6 a1        :UpdateColor    inc     drawn_elem_count
8e74: bd c0 a0                     lda     elem_colorchanges,x ;get the color change counter
8e77: f0 27                        beq     :NoChanges        ;zero, no changes for this one
8e79: de 00 a1                     dec     elem_colorchange_ctrs,x ;decrement the counter
8e7c: 10 1d                        bpl     :NotYet           ;not time to change yet, branch
8e7e: bd c0 a0                     lda     elem_colorchanges,x
8e81: 9d 00 a1                     sta     elem_colorchange_ctrs,x ;reset the counter
8e84: bd 00 a0                     lda     elem_colorsA,x
8e87: dd 80 a0                     cmp     elem_cur_colors,x ;is it currently colorA?
8e8a: 20 7f 7f                     jsr     Return7f7f
8e8d: f0 06                        beq     :UseB             ;yes, use B
8e8f: 9d 80 a0                     sta     elem_cur_colors,x ;no, use A
8e92: 4c 9b 8e                     jmp     :NotYet

8e95: bd 40 a0     :UseB           lda     elem_colorsB,x
8e98: 9d 80 a0                     sta     elem_cur_colors,x
8e9b: bd 80 a0     :NotYet         lda     elem_cur_colors,x ;get the color
8e9e: 30 bf                        bmi     :NoDraw           ;>= $80, don't draw the element
8ea0: a5 70        :NoChanges      lda     mod_elem_type     ;get mod type set by update-element code
8ea2: 9d 80 9f                     sta     elem_mod_types,x  ;set as type in table
8ea5: f0 15                        beq     DrawPoint         ;$00, draw point
8ea7: 10 10                        bpl     :JmpDrawHoriz     ;$01, draw horizontal line
8ea9: 0a                           asl     A
8eaa: f0 0a                        beq     :JmpDrawVert      ;$80, draw vertical line
8eac: a9 81                        lda     #$81              ;rect
8eae: 9d 80 9f                     sta     elem_mod_types,x  ;set mod type (should already be $81?)
8eb1: 85 70                        sta     mod_elem_type     ;set in ZP as well (should already be $81?)
8eb3: 4c a6 90                     jmp     DrawRect

8eb6: 4c 07 90     :JmpDrawVert    jmp     DrawVertLine

8eb9: 4c 1f 8f     :JmpDrawHoriz   jmp     DrawHorizLine

                   ; 
                   ; Draws a point.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ;   $7e: top screen coordinate (0-191)
                   ;   $82: abs val of left screen coordinate (0-139)
                   ; 
                   ; On exit:
                   ;   X-reg: preserved
                   ; 
                   • Clear variables
                   ]hpage_ptr      .var    $10    {addr/2}
                   ]top_coord      .var    $7e    {addr/1}
                   ]left_coord_abs .var    $82    {addr/1}
                   ]hires_col      .var    $86    {addr/1}

8ebc: 18           DrawPoint       clc                       ;do sound stuff
8ebd: a5 b2                        lda     engine_sound_ctr?+1
8ebf: 69 09                        adc     #$09
8ec1: 85 b2                        sta     engine_sound_ctr?+1
8ec3: 90 0f                        bcc     :NoSound
8ec5: e6 b3                        inc     engine_sound_ctr?+2
8ec7: a5 cc                        lda     engine_sound_enable
8ec9: f0 09                        beq     :NoSound
8ecb: a5 b3                        lda     engine_sound_ctr?+2
8ecd: 25 b1                        and     engine_sound_ctr?
8ecf: d0 03                        bne     :NoSound
8ed1: ad 30 c0                     lda     SPKR
8ed4: a4 82        :NoSound        ldy     ]left_coord_abs   ;get absolute value of left coord
8ed6: bd 00 a2                     lda     elem_left_hi,x    ;get left coord high byte
8ed9: 30 0b                        bmi     :NegLeft          ;negative, branch
8edb: b9 00 bc                     lda     pos_xc_to_col,y   ;convert coordinate to column (20-39)
8ede: 85 86                        sta     ]hires_col
8ee0: b9 00 be                     lda     pos_xc_to_color_idx,y ;get pixel color index
8ee3: 4c ee 8e                     jmp     :Cont

8ee6: b9 00 bd     :NegLeft        lda     neg_xc_to_col,y   ;convert coordinate to column (0-19)
8ee9: 85 86                        sta     ]hires_col
8eeb: b9 00 bf                     lda     neg_xc_to_color_idx,y ;get pixel color index
8eee: 1d 80 a0     :Cont           ora     elem_cur_colors,x ;get high nibble of current color
8ef1: a8                           tay
8ef2: b9 c3 71                     lda     color_bit_masks_thin,y ;get the bit pattern for the color
8ef5: 9d 40 a5                     sta     elem_erase_6,x
8ef8: a4 7e                        ldy     ]top_coord        ;get top coord
8efa: 18                           clc
8efb: a5 86                        lda     ]hires_col        ;get the column (byte offset)
8efd: 79 00 ba                     adc     hires_addr_lo,y   ;add the low byte of the hi-res line address
8f00: 9d c0 a3                     sta     elem_erase_0,x    ;save that for erase time
8f03: b9 00 bb                     lda     hires_addr_hi,y   ;get the high byte of the hi-res line address
8f06: 69 00                        adc     #$00
8f08: 9d 00 a4                     sta     elem_erase_1,x    ;save that as well
8f0b: 85 11                        sta     ]hpage_ptr+1
8f0d: bd 80 a0                     lda     elem_cur_colors,x ;get color
8f10: f0 0a                        beq     :IsBlack          ;black, ORA will do nothing
8f12: bc c0 a3                     ldy     elem_erase_0,x
8f15: b1 10                        lda     (]hpage_ptr),y
8f17: 1d 40 a5                     ora     elem_erase_6,x
8f1a: 91 10                        sta     (]hpage_ptr),y
8f1c: 4c 16 92     :IsBlack        jmp     ElemDrawDone

                   ; 
                   ; Draws a horizontal line.
                   ; 
                   ; The pixels are ORed onto the screen, blending the current contents.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ;   $7e: screen Y coordinate (0-191)
                   ;   $82: screen left X coordinate magnitude (0-139)
                   ;   $84: screen right X coordinate magnitude (0-139)
                   ; 
                   • Clear variables
                   ]hptr           .var    $18    {addr/2}
                   ]ycoord         .var    $7e    {addr/1}
                   ]left_mag       .var    $82    {addr/1}
                   ]right_mag      .var    $84    {addr/1}
                   ]index_tmp      .var    $86    {addr/1}
                   ]right_col      .var    $87    {addr/1}
                   ]color0         .var    $89    {addr/1}
                   ]odd_even_mask  .var    $90    {addr/1}
                   ]color1         .var    $91    {addr/1}

8f1f: 18           DrawHorizLine   clc                       ;do sound stuff
8f20: a5 b2                        lda     engine_sound_ctr?+1
8f22: 69 23                        adc     #$23
8f24: 85 b2                        sta     engine_sound_ctr?+1
8f26: 90 0f                        bcc     :NoSound
8f28: e6 b3                        inc     engine_sound_ctr?+2
8f2a: a5 cc                        lda     engine_sound_enable
8f2c: f0 09                        beq     :NoSound
8f2e: a5 b3                        lda     engine_sound_ctr?+2
8f30: 25 b1                        and     engine_sound_ctr?
8f32: d0 03                        bne     :NoSound
8f34: ad 30 c0                     lda     SPKR
8f37: a4 82        :NoSound        ldy     ]left_mag         ;get magnitude of X coord for left end
8f39: bd 00 a2                     lda     elem_left_hi,x    ;check sign
8f3c: 30 0c                        bmi     :IsNegL
8f3e: b9 00 bc                     lda     pos_xc_to_col,y   ;get column from positive table
8f41: 9d 00 a4                     sta     elem_erase_1,x
8f44: b9 00 be                     lda     pos_xc_to_color_idx,y ;get coord color index
8f47: 4c 53 8f                     jmp     :ContL

8f4a: b9 00 bd     :IsNegL         lda     neg_xc_to_col,y   ;get column from negative table
8f4d: 9d 00 a4                     sta     elem_erase_1,x
8f50: b9 00 bf                     lda     neg_xc_to_color_idx,y ;get coord color index
8f53: 9d c0 a3     :ContL          sta     elem_erase_0,x
8f56: a4 84                        ldy     ]right_mag        ;get magnitude of X coord for right end
8f58: bd 00 a3                     lda     elem_right_hi,x   ;check sign
8f5b: 30 0e                        bmi     :IsNegR
8f5d: b9 00 bc                     lda     pos_xc_to_col,y   ;get column from positive table
8f60: 9d c0 a4                     sta     elem_erase_4,x
8f63: 85 87                        sta     ]right_col
8f65: b9 00 be                     lda     pos_xc_to_color_idx,y ;get coord color index
8f68: 4c 76 8f                     jmp     :ContR

8f6b: b9 00 bd     :IsNegR         lda     neg_xc_to_col,y   ;get column from negative table
8f6e: 9d c0 a4                     sta     elem_erase_4,x
8f71: 85 87                        sta     ]right_col
8f73: b9 00 bf                     lda     neg_xc_to_color_idx,y ;get coord color index
8f76: 9d 80 a4     :ContR          sta     elem_erase_3,x
                   ; 
8f79: a4 7e                        ldy     ]ycoord           ;get Y coordinate for line
8f7b: b9 00 bb                     lda     hires_addr_hi,y   ;get hi-res line base address
8f7e: 9d 00 a5                     sta     elem_erase_5,x
8f81: 85 19                        sta     ]hptr+1           ;set up the pointer
8f83: b9 00 ba                     lda     hires_addr_lo,y
8f86: 9d 40 a4                     sta     elem_erase_2,x
8f89: 85 18                        sta     ]hptr
                   ; Draw partial byte for left end of line.
8f8b: bd 80 a0                     lda     elem_cur_colors,x ;get current element color (high nibble)
8f8e: f0 74                        beq     :DrawDone         ;black, do nothing
8f90: 1d c0 a3                     ora     elem_erase_0,x    ;get element color (low nibble)
8f93: a8                           tay
8f94: 29 08                        and     #%00001000        ;mask bit 3 so it's 0/8 for odd/even
8f96: 85 90                        sta     ]odd_even_mask
8f98: b9 63 72                     lda     color_bit_masks_left,y ;get pixel bit mask for left-side byte
8f9b: bc 00 a4                     ldy     elem_erase_1,x    ;get column of left edge
8f9e: 11 18                        ora     (]hptr),y
8fa0: 91 18                        sta     (]hptr),y         ;set pixels on hi-res screen
8fa2: c8                           iny                       ;advance to next column
8fa3: c4 87                        cpy     ]right_col        ;is right pixel in next column?
8fa5: f0 4d                        beq     :RightSide        ;yes, branch
8fa7: 10 5b                        bpl     :DrawDone         ;right/left pixels are in same byte, bail
                   ; Draw middle.  We set up odd vs. even and draw alternately.
8fa9: 84 86                        sty     ]index_tmp        ;spill Y-reg
8fab: a5 90                        lda     ]odd_even_mask    ;get color index (0 or 8)
8fad: 1d 80 a0                     ora     elem_cur_colors,x ;combine with current element color
8fb0: a8                           tay
8fb1: b9 63 72                     lda     color_bit_masks_left,y ;get full-byte color bit mask
8fb4: 85 89                        sta     ]color0           ;save as first color
8fb6: a5 90                        lda     ]odd_even_mask
8fb8: 49 08                        eor     #$08              ;flip odd/even
8fba: 1d 80 a0                     ora     elem_cur_colors,x ;combine with current element color
8fbd: a8                           tay
8fbe: b9 63 72                     lda     color_bit_masks_left,y ;get full-byte color bit mask
8fc1: 85 91                        sta     ]color1           ;save as second color
8fc3: a4 86                        ldy     ]index_tmp        ;restore Y-reg (hi-res col)
8fc5: 18                           clc
8fc6: a5 91        :MiddleLoop     lda     ]color1           ;get second color
8fc8: 11 18                        ora     (]hptr),y         ;blend with hi-res screen
8fca: 91 18                        sta     (]hptr),y         ;update screen
8fcc: c8                           iny
8fcd: c4 87                        cpy     ]right_col        ;have we reached right edge?
8fcf: 10 23                        bpl     :RightSide        ;yes, go handle that
8fd1: 18                           clc                       ;do sound stuff
8fd2: a5 b2                        lda     engine_sound_ctr?+1
8fd4: 69 07                        adc     #$07
8fd6: 85 b2                        sta     engine_sound_ctr?+1
8fd8: 90 0f                        bcc     :NoSound
8fda: e6 b3                        inc     engine_sound_ctr?+2
8fdc: a5 cc                        lda     engine_sound_enable
8fde: f0 09                        beq     :NoSound
8fe0: a5 b3                        lda     engine_sound_ctr?+2
8fe2: 25 b1                        and     engine_sound_ctr?
8fe4: d0 03                        bne     :NoSound
8fe6: ad 30 c0                     lda     SPKR
8fe9: a5 89        :NoSound        lda     ]color0           ;get first color
8feb: 11 18                        ora     (]hptr),y         ;blend with hi-res screen
8fed: 91 18                        sta     (]hptr),y         ;update screen
8fef: c8                           iny
8ff0: c4 87                        cpy     ]right_col        ;have we reached right edge?
8ff2: 30 d2                        bmi     :MiddleLoop       ;no, keep going
                   ; Draw partial byte for right end of line.
8ff4: bd 80 a4     :RightSide      lda     elem_erase_3,x    ;get pixel color offset
8ff7: 1d 80 a0                     ora     elem_cur_colors,x ;combine with current element color
8ffa: a8                           tay
8ffb: b9 d3 72                     lda     color_bit_masks_right,y ;get pixel bit mask
8ffe: a4 87                        ldy     ]right_col        ;get index of right column
9000: 11 18                        ora     (]hptr),y         ;blend with hi-res screen
9002: 91 18                        sta     (]hptr),y         ;update screen
9004: 4c 16 92     :DrawDone       jmp     ElemDrawDone

                   ; 
                   ; Draws a vertical line.
                   ; 
                   ; The pixels are ORed onto the screen, blending the current contents.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ;   $7e: top (0-191)
                   ;   $80: bottom (0-191)
                   ;   $82: abs value of left (0-139)
                   ;   $84: abs value of right (0-139)
                   ; 
                   • Clear variables
                   ]restore_ptr    .var    $10    {addr/2}
                   ]yc_top         .var    $7e    {addr/1}
                   ]yc_bottom      .var    $80    {addr/1}
                   ]xc_left_abs    .var    $82    {addr/1}
                   ]restore_index  .var    $8a    {addr/1}
                   ]color_mask     .var    $92    {addr/1}

9007: 18           DrawVertLine    clc                       ;do sound stuff
9008: a5 b2                        lda     engine_sound_ctr?+1
900a: 69 20                        adc     #$20
900c: 85 b2                        sta     engine_sound_ctr?+1
900e: 90 0f                        bcc     :NoSound
9010: e6 b3                        inc     engine_sound_ctr?+2
9012: a5 cc                        lda     engine_sound_enable
9014: f0 09                        beq     :NoSound
9016: a5 b3                        lda     engine_sound_ctr?+2
9018: 25 b1                        and     engine_sound_ctr?
901a: d0 03                        bne     :NoSound
901c: ad 30 c0                     lda     SPKR
901f: a5 80        :NoSound        lda     ]yc_bottom
9021: 9d 00 a5                     sta     elem_erase_5,x    ;save bottom coord
9024: e5 7e                        sbc     ]yc_top           ;do more sound stuff
9026: 0a                           asl     A
9027: 65 b2                        adc     engine_sound_ctr?+1
9029: 85 b2                        sta     engine_sound_ctr?+1
902b: 90 0f                        bcc     :NoSound
902d: e6 b3                        inc     engine_sound_ctr?+2
902f: a5 cc                        lda     engine_sound_enable
9031: f0 09                        beq     :NoSound
9033: a5 b3                        lda     engine_sound_ctr?+2
9035: 25 b1                        and     engine_sound_ctr?
9037: d0 03                        bne     :NoSound
9039: ad 30 c0                     lda     SPKR
903c: a5 7e        :NoSound        lda     ]yc_top
903e: 9d 40 a4                     sta     elem_erase_2,x    ;save top coordinate
9041: bc 00 a5                     ldy     elem_erase_5,x    ;get bottom coordinate
9044: c8                           iny                       ;increment to get following instruction group
9045: b9 00 b8                     lda     unroll_ora_addr_hi,y ;get address of TXA instruction, high byte
9048: 85 11                        sta     ]restore_ptr+1    ;set pointer
904a: b9 00 b7                     lda     unroll_a_o_addr_lo,y ;get address of instruction, low byte
904d: a8                           tay
904e: 85 8a                        sta     ]restore_index
9050: a9 60                        lda     #INSTR_RTS
9052: 91 10                        sta     (]restore_ptr),y  ;replace TXA with RTS
9054: bc 40 a4                     ldy     elem_erase_2,x    ;get top coordinate
9057: b9 00 b7                     lda     unroll_a_o_addr_lo,y ;get address of corresponding ORA sequence
905a: 8d 99 90                     sta     _CallOra0+1       ;modify JSR call
905d: b9 00 b8                     lda     unroll_ora_addr_hi,y
9060: 8d 9a 90                     sta     _CallOra0+2
                   ; 
9063: a4 82                        ldy     ]xc_left_abs      ;get absolute value of left X coord
9065: bd 00 a2                     lda     elem_left_hi,x    ;get sign
9068: 30 0c                        bmi     :IsNeg            ;negative, branch
906a: b9 00 bc                     lda     pos_xc_to_col,y   ;get hi-res column of line
906d: 9d 00 a4                     sta     elem_erase_1,x    ;save it
9070: b9 00 be                     lda     pos_xc_to_color_idx,y ;get color index
9073: 4c 7f 90                     jmp     :Cont

9076: b9 00 bd     :IsNeg          lda     neg_xc_to_col,y   ;get hi-res column of line
9079: 9d 00 a4                     sta     elem_erase_1,x    ;save it
907c: b9 00 bf                     lda     neg_xc_to_color_idx,y ;get color index
907f: 9d c0 a3     :Cont           sta     elem_erase_0,x
9082: 1d 80 a0                     ora     elem_cur_colors,x ;OR with current element color nibble
9085: a8                           tay
9086: b9 c3 71                     lda     color_bit_masks_thin,y ;get pixel mask for a single color pixel
9089: 9d 40 a5                     sta     elem_erase_6,x    ;save it
908c: 85 92                        sta     ]color_mask
908e: bd 80 a0                     lda     elem_cur_colors,x ;get current color
9091: f0 08                        beq     :NoDraw           ;it's black, skip drawing
9093: bc 00 a4                     ldy     elem_erase_1,x    ;get hi-res column
9096: a6 92                        ldx     ]color_mask       ;get pixel mask
9098: 20 6f 1a     _CallOra0       jsr     OraSeq_89         ;perform unrolled ORA sequence
909b: a4 8a        :NoDraw         ldy     ]restore_index
909d: a9 8a                        lda     #INSTR_TXA
909f: 91 10                        sta     (]restore_ptr),y  ;change the RTS back to TXA
90a1: a6 64                        ldx     cur_elem_index
90a3: 4c 16 92                     jmp     ElemDrawDone      ;done

                   ; 
                   ; Draws a filled rectangle.
                   ; 
                   ; On entry:
                   ;   X-reg: element index
                   ;   $7e: top (0-191)
                   ;   $80: bottom (0-191)
                   ;   $82: abs value of left (0-139)
                   ;   $84: abs value of right (0-139)
                   ; 
                   • Clear variables
                   ]restore_ptr    .var    $10    {addr/2}
                   ]yc_top         .var    $7e    {addr/1}
                   ]yc_bottom      .var    $80    {addr/1}
                   ]xc_left_abs    .var    $82    {addr/1}
                   ]xc_right_abs   .var    $84    {addr/1}
                   ]left_col       .var    $88    {addr/1}
                   ]right_col      .var    $89    {addr/1}
                   ]restore_index  .var    $8a    {addr/1}
                   ]height_approx  .var    $8c    {addr/1}
                   ]pix_clr_idx_rt .var    $8f    {addr/1}
                   ]odd_even_mask  .var    $90    {addr/1}
                   ]cur_color      .var    $91    {addr/1}
                   ]left_color_mask .var   $92    {addr/1}

90a6: 18           DrawRect        clc                       ;do sound stuff
90a7: a5 b2                        lda     engine_sound_ctr?+1
90a9: 69 2a                        adc     #$2a
90ab: 85 b2                        sta     engine_sound_ctr?+1
90ad: 90 0f                        bcc     :NoSound
90af: e6 b3                        inc     engine_sound_ctr?+2
90b1: a5 cc                        lda     engine_sound_enable
90b3: f0 09                        beq     :NoSound
90b5: a5 b3                        lda     engine_sound_ctr?+2
90b7: 25 b1                        and     engine_sound_ctr?
90b9: d0 03                        bne     :NoSound
90bb: ad 30 c0                     lda     SPKR
90be: bd 80 a0     :NoSound        lda     elem_cur_colors,x ;get current color
90c1: 85 91                        sta     ]cur_color
90c3: a5 80                        lda     ]yc_bottom
90c5: 9d 00 a5                     sta     elem_erase_5,x    ;save bottom coord
90c8: e5 7e                        sbc     ]yc_top           ;compute (bottom - top); carry undefined (bug?)
90ca: 85 8c                        sta     ]height_approx
90cc: a5 7e                        lda     ]yc_top
90ce: 9d 40 a4                     sta     elem_erase_2,x    ;save top coord
                   ; Set up right edge.
90d1: a4 84                        ldy     ]xc_right_abs     ;get absolute value of X coord
90d3: bd 00 a3                     lda     elem_right_hi,x   ;get sign (from eye coords)
90d6: 30 0e                        bmi     :IsNegR
90d8: b9 00 bc                     lda     pos_xc_to_col,y   ;get hi-res column for right edge
90db: 9d c0 a4                     sta     elem_erase_4,x    ;save it
90de: 85 89                        sta     ]right_col
90e0: b9 00 be                     lda     pos_xc_to_color_idx,y ;get pixel color index
90e3: 4c f1 90                     jmp     :ContR

90e6: b9 00 bd     :IsNegR         lda     neg_xc_to_col,y   ;get hi-res colum for right edge
90e9: 9d c0 a4                     sta     elem_erase_4,x    ;save it
90ec: 85 89                        sta     ]right_col
90ee: b9 00 bf                     lda     neg_xc_to_color_idx,y ;get pixel color index
90f1: 9d 80 a4     :ContR          sta     elem_erase_3,x    ;save it
90f4: 85 8f                        sta     ]pix_clr_idx_rt
                   ; Set up left edge.
90f6: a4 82                        ldy     ]xc_left_abs      ;get absolute value of X coord
90f8: bd 00 a2                     lda     elem_left_hi,x    ;get sign
90fb: 30 0c                        bmi     :IsNegL
90fd: b9 00 bc                     lda     pos_xc_to_col,y   ;get hi-res column for left edge
9100: 9d 00 a4                     sta     elem_erase_1,x    ;save it
9103: b9 00 be                     lda     pos_xc_to_color_idx,y ;get pixel color index
9106: 4c 12 91                     jmp     :ContL

9109: b9 00 bd     :IsNegL         lda     neg_xc_to_col,y   ;get hi-res column for right edge
910c: 9d 00 a4                     sta     elem_erase_1,x    ;save it
910f: b9 00 bf                     lda     neg_xc_to_color_idx,y ;get pixel color index
9112: 9d c0 a3     :ContL          sta     elem_erase_0,x
9115: 05 91                        ora     ]cur_color        ;combine nibbles with element color
9117: a8                           tay
9118: 29 08                        and     #%00001000        ;strip all but bit 3 to get odd/even mask
911a: 85 90                        sta     ]odd_even_mask
911c: a5 91                        lda     ]cur_color        ;check color
911e: d0 03                        bne     :NotBlack         ;not black, keep going
9120: 4c 16 92                     jmp     ElemDrawDone

9123: b9 63 72     :NotBlack       lda     color_bit_masks_left,y
9126: 85 92                        sta     ]left_color_mask
9128: bc 00 a4                     ldy     elem_erase_1,x    ;get hi-res column of left edge
912b: 84 88                        sty     ]left_col
912d: 38                           sec
912e: a5 89                        lda     ]right_col        ;compute (right - left - 3)
9130: e5 88                        sbc     ]left_col
9132: e9 03                        sbc     #$03
9134: 85 b0                        sta     mid_col_count
9136: 10 35                        bpl     :WideRect         ;touch 4+ columns, use STA
                   ; We touch 1-3 columns, use ORA for all parts.
9138: a9 8a                        lda     #INSTR_TXA        ;replacing a TXA instruction
913a: 85 af                        sta     orig_opcode
913c: bc 00 a5                     ldy     elem_erase_5,x    ;get bottom coordinate
913f: c8                           iny                       ;increment so we're at start of next group
9140: b9 00 b8                     lda     unroll_ora_addr_hi,y ;get address of instruction, high byte
9143: 85 11                        sta     ]restore_ptr+1
9145: b9 00 b7                     lda     unroll_a_o_addr_lo,y ;get address of instruction, low byte
9148: a8                           tay
9149: 85 8a                        sta     ]restore_index
914b: a9 60                        lda     #INSTR_RTS
914d: 91 10                        sta     (]restore_ptr),y  ;replace TXA with RTS
914f: bc 40 a4                     ldy     elem_erase_2,x    ;get top coordinate
9152: b9 00 b7                     lda     unroll_a_o_addr_lo,y ;copy address of instruction group to JSRs
9155: 8d a5 91                     sta     _CallOraSta1+1
9158: 8d c4 91                     sta     _CallOraSta2+1
915b: 8d f2 91                     sta     _CallOraSta3+1
915e: b9 00 b8                     lda     unroll_ora_addr_hi,y
9161: 8d a6 91                     sta     _CallOraSta1+2
9164: 8d c5 91                     sta     _CallOraSta2+2
9167: 8d f3 91                     sta     _CallOraSta3+2
916a: 4c 9f 91                     jmp     :DoDraw           ;go draw

                   ; We touch 4+ columns, use STA for middle and edges.
916d: a9 99        :WideRect       lda     #INSTR_STA_ABS    ;replacing a STA instruction
916f: 85 af                        sta     orig_opcode
9171: bc 00 a5                     ldy     elem_erase_5,x    ;get bottom coord
9174: c8                           iny                       ;increment so we're at start of next group
9175: b9 00 57                     lda     unroll_sta_hi,y   ;get address of instruction, high byte
9178: 85 11                        sta     ]restore_ptr+1
917a: b9 00 56                     lda     unroll_sta_lo,y   ;get address of instruction, low byte
917d: a8                           tay
917e: 85 8a                        sta     ]restore_index
9180: a9 60                        lda     #INSTR_RTS
9182: 91 10                        sta     (]restore_ptr),y  ;replace STA with RTS
9184: bc 40 a4                     ldy     elem_erase_2,x    ;get top coord
9187: b9 00 56                     lda     unroll_sta_lo,y   ;copy address of instruction group to JSRs
918a: 8d a5 91                     sta     _CallOraSta1+1
918d: 8d c4 91                     sta     _CallOraSta2+1
9190: 8d f2 91                     sta     _CallOraSta3+1
9193: b9 00 57                     lda     unroll_sta_hi,y
9196: 8d a6 91                     sta     _CallOraSta1+2
9199: 8d c5 91                     sta     _CallOraSta2+2
919c: 8d f3 91                     sta     _CallOraSta3+2
                   ; Draw left edge.
919f: a6 92        :DoDraw         ldx     ]left_color_mask  ;get color bits for left edge
91a1: 8a                           txa                       ;need in A-reg for STA, X-reg for ORA
91a2: a4 88                        ldy     ]left_col         ;get column
91a4: 20 5a 1a     _CallOraSta1    jsr     OraSeq_86         ;perform unrolled STA or ORA sequence
91a7: e6 88                        inc     ]left_col         ;advance to next column
91a9: a5 88                        lda     ]left_col
91ab: c5 89                        cmp     ]right_col        ;are we at right column?
91ad: f0 37                        beq     :DrawRight        ;yes, draw that
91af: 30 03                        bmi     :DrawMiddle       ;not yet, draw middle
91b1: 4c f6 91                     jmp     :RectDone         ;past it, must be single column; we're done

91b4: a5 90        :DrawMiddle     lda     ]odd_even_mask
91b6: 49 08                        eor     #$08              ;flip odd/even
91b8: 85 90                        sta     ]odd_even_mask
91ba: 05 91                        ora     ]cur_color        ;merge nibbles with current element color
91bc: a8                           tay                       ; to form index for whole-byte color
91bd: b9 63 72                     lda     color_bit_masks_left,y ;get pixel bit mask
91c0: aa                           tax                       ;need in A-reg for STA, X-reg for ORA
91c1: a4 88                        ldy     ]left_col         ;get column
91c3: 20 5a 1a     _CallOraSta2    jsr     OraSeq_86         ;perform unrolled STA or ORA sequence
                   ; 
91c6: 18                           clc                       ;do sound stuff
91c7: a5 b2                        lda     engine_sound_ctr?+1
91c9: 65 8c                        adc     ]height_approx
91cb: 85 b2                        sta     engine_sound_ctr?+1
91cd: 90 0f                        bcc     :NoSound
91cf: e6 b3                        inc     engine_sound_ctr?+2
91d1: a5 cc                        lda     engine_sound_enable
91d3: f0 09                        beq     :NoSound
91d5: a5 b3                        lda     engine_sound_ctr?+2
91d7: 25 b1                        and     engine_sound_ctr?
91d9: d0 03                        bne     :NoSound
91db: ad 30 c0                     lda     SPKR
91de: e6 88        :NoSound        inc     ]left_col         ;advance to next column
91e0: a5 88                        lda     ]left_col
91e2: c5 89                        cmp     ]right_col        ;are we at right column?
91e4: 30 ce                        bmi     :DrawMiddle       ;not yet, loop
91e6: a5 8f        :DrawRight      lda     ]pix_clr_idx_rt   ;get pixel color index for right edge
91e8: 05 91                        ora     ]cur_color        ;merge nibbles with current element color
91ea: a8                           tay
91eb: b9 d3 72                     lda     color_bit_masks_right,y ;get pixel bit mask
91ee: a4 89                        ldy     ]right_col        ;get column
91f0: aa                           tax                       ;need in A-reg for STA, X-reg for ORA
91f1: 20 5a 1a     _CallOraSta3    jsr     OraSeq_86         ;perform unrolled STA or ORA sequence
                   ; 
91f4: 06 8c                        asl     ]height_approx    ;do sound stuff
91f6: 18           :RectDone       clc
91f7: a5 b2                        lda     engine_sound_ctr?+1
91f9: 65 8c                        adc     ]height_approx
91fb: 85 b2                        sta     engine_sound_ctr?+1
91fd: 90 0f                        bcc     :NoSound
91ff: e6 b3                        inc     engine_sound_ctr?+2
9201: a5 cc                        lda     engine_sound_enable
9203: f0 09                        beq     :NoSound
9205: a5 b3                        lda     engine_sound_ctr?+2
9207: 25 b1                        and     engine_sound_ctr?
9209: d0 03                        bne     :NoSound
920b: ad 30 c0                     lda     SPKR
920e: a6 64        :NoSound        ldx     cur_elem_index    ;get element index in X-reg
9210: a4 8a                        ldy     ]restore_index    ;get index of byte we need to restore
9212: a5 af                        lda     orig_opcode       ;get original opcode
9214: 91 10                        sta     (]restore_ptr),y  ;restore the opcode we overwrote
                   ; 
                   ; Done drawing an element.  Move to the next one.
                   ; 
9216: a5 c8        ElemDrawDone    lda     sound_counters    ;do sound stuff
9218: f0 03                        beq     :NoSound
921a: ad 30 c0                     lda     SPKR
921d: bd 40 9f     :NoSound        lda     elem_next_elem,x  ;get index of next element
9220: 30 08                        bmi     NextObject        ;found end of list for this object; branch
9222: aa                           tax                       ;copy to X-reg
9223: 86 64                        stx     cur_elem_index    ;save a copy here
9225: e6 a5                        inc     wronly_a5?
9227: 4c 83 8c                     jmp     RedrawElement     ;erase and redraw it

                   ; 
                   ; Done drawing object.  Move to the next one.
                   ; 
                   • Clear variables
                   ]tmp_obj_index  .var    $8c    {addr/1}

922a: a5 ca        NextObject      lda     sound_counters+2  ;do sound stuff
922c: f0 03                        beq     :NoSound
922e: ad 30 c0                     lda     SPKR              ;click for sfx (player cannon, ship explosion)
9231: a6 62        :NoSound        ldx     cur_obj_index
9233: 20 7f 7f                     jsr     Return7f7f
9236: bd 50 9a                     lda     obj_next_obj,x    ;get index of next object
9239: 85 8c                        sta     ]tmp_obj_index
923b: a5 a1                        lda     drawn_elem_count  ;check drawn element count
923d: d0 0c                        bne     :Jmp_NextObject1  ;we drew at least one, keep it around
923f: bd a0 9a                     lda     obj_shape_uid,x   ;get the shape ID
9242: 29 f0                        and     #$f0
9244: c9 f0                        cmp     #$f0              ;is it $Fn?
9246: f0 06                        beq     UnusedThing?      ;yes, do special thing
                   :Jmp_ObjOffScreen
9248: 4c 24 93                     jmp     ObjectOffScreen   ;no, kill the object, possibly with special behavior

                   :Jmp_NextObject1
924b: 4c 18 93                     jmp     NextObject1

                   ; 
                   ; Draws a direction in place of the ammunition count.  This doesn't appear to be
                   ; used.
                   ; 
                   ; (If you change the code above with 9245:50, you can see it trying to show
                   ; which way you need to move while flying through a time portal.  However, it
                   ; flashes conflicting messages and fights with the rendering of the ammunition
                   ; count, so it's possible this feature was abandoned before completion.)
                   ; 
                   • Clear variables
                   ]screen_left    .var    $86    {addr/2}
                   ]screen_top     .var    $88    {addr/2}
                   ]screen_left_abs .var   $8c    {addr/2}

924e: bd 18 9b     UnusedThing?    lda     obj_activity_state,x
9251: 30 f5                        bmi     :Jmp_ObjOffScreen
9253: ad 3b 6d                     lda     game_active_flag  ;are we in demo mode?
9256: f0 f0                        beq     :Jmp_ObjOffScreen ;yes, branch
9258: bc 00 9a                     ldy     obj_first_elem_index,x
925b: a9 02                        lda     #$02
925d: 85 a9                        sta     wronly_a9?
925f: b9 40 a2                     lda     elem_top_lo,y
9262: 85 88                        sta     ]screen_top
9264: b9 80 a2                     lda     elem_top_hi,y
9267: 85 89                        sta     ]screen_top+1
9269: b9 c0 a1                     lda     elem_left_lo,y
926c: 85 86                        sta     ]screen_left
926e: b9 00 a2                     lda     elem_left_hi,y
9271: 85 87                        sta     ]screen_left+1
9273: a5 87                        lda     ]screen_left+1    ;(?)
9275: 10 0d                        bpl     :PosLeft1
9277: 49 ff                        eor     #$ff              ;negate (without +1)
9279: 85 8d                        sta     ]screen_left_abs+1
927b: a5 86                        lda     ]screen_left
927d: 49 ff                        eor     #$ff
927f: 85 8c                        sta     ]screen_left_abs
9281: 4c 8a 92                     jmp     :GotAbs

9284: 85 8d        :PosLeft1       sta     ]screen_left_abs+1
9286: a5 86                        lda     ]screen_left
9288: 85 8c                        sta     ]screen_left_abs
928a: a5 89        :GotAbs         lda     ]screen_top+1
928c: 10 02                        bpl     :PosLeft2
928e: 49 ff                        eor     #$ff
9290: c5 8d        :PosLeft2       cmp     ]screen_left_abs+1
9292: f0 06                        beq     :CheckTop
9294: 10 13                        bpl     L92A9
9296: 18                           clc
9297: 4c b6 92                     jmp     L92B6

929a: a5 88        :CheckTop       lda     ]screen_top
929c: a4 89                        ldy     ]screen_top+1
929e: 10 02                        bpl     L92A2
92a0: 49 ff                        eor     #$ff
92a2: c5 8c        L92A2           cmp     ]screen_left_abs
92a4: 90 10                        bcc     L92B6
92a6: 4c b3 92                     jmp     L92B3

92a9: 85 8d        L92A9           sta     ]screen_left_abs+1
92ab: a5 88                        lda     ]screen_top
92ad: a4 89                        ldy     ]screen_top+1
92af: 10 02                        bpl     L92B3
92b1: 49 ff                        eor     #$ff
92b3: 85 8c        L92B3           sta     ]screen_left_abs
92b5: 38                           sec
92b6: 90 52        L92B6           bcc     :RightOrLeft
92b8: a5 89                        lda     ]screen_top+1
92ba: 10 49                        bpl     :Below
                   ; This appears to flash a direction (ABOVE, BELOW, LEFT, RIGHT) in place of the
                   ; ammunition count.
92bc: a9 00                        lda     #$00
92be: 85 8c        :SetDir         sta     ]screen_left_abs  ;save string index
92c0: ad cd 6d                     lda     frame_counter
92c3: 29 02                        and     #$02
92c5: f0 1b                        beq     :EraseAmunCount   ;erase instead of draw this frame
92c7: a2 1b                        ldx     #27               ;first column under "AMUN"
92c9: a5 8c                        lda     ]screen_left_abs  ;(?)
92cb: 85 8c                        sta     ]screen_left_abs  ;(?)
92cd: a4 8c        :CharLoop       ldy     ]screen_left_abs  ;get char index
92cf: b9 ad 6e                     lda     text_position,y   ;get char
92d2: 20 27 74                     jsr     PrintCharLine9    ;print char
92d5: e6 8c                        inc     ]screen_left_abs  ;advance char index
92d7: e0 20                        cpx     #32               ;printed 5 chars?
92d9: ea                           nop
92da: 30 f1                        bmi     :CharLoop         ;not yet, branch
92dc: ea                           nop
92dd: a6 62                        ldx     cur_obj_index     ;put object index in X-reg
92df: 4c 18 93                     jmp     NextObject1       ;back to work

                   ; Erases 5 characters under "AMUN ".  Probably used to make the direction flash.
92e2: a2 1b        :EraseAmunCount ldx     #27
92e4: a9 00        :Loop           lda     #$00
92e6: 9d 80 24                     sta     HIRES_P1+$480,x   ;line 9
92e9: 9d 80 28                     sta     HIRES_P1+$880,x   ; ...
92ec: 9d 80 2c                     sta     HIRES_P1+$c80,x
92ef: 9d 80 30                     sta     HIRES_P1+$1080,x
92f2: 9d 80 38                     sta     HIRES_P1+$1880,x
92f5: 9d 80 34                     sta     HIRES_P1+$1480,x
92f8: 9d 80 3c                     sta     HIRES_P1+$1c80,x  ;line 15
92fb: e8                           inx
92fc: e0 20                        cpx     #32               ;erased 5 bytes?
92fe: 30 e4                        bmi     :Loop
9300: a6 62                        ldx     cur_obj_index     ;put object index in X-reg
9302: 4c 18 93                     jmp     NextObject1       ;back to work

9305: a9 05        :Below          lda     #5
9307: 4c be 92                     jmp     :SetDir

930a: a5 87        :RightOrLeft    lda     ]screen_left+1
930c: 30 05                        bmi     :Left
930e: a9 0a                        lda     #10
9310: 4c be 92                     jmp     :SetDir

9313: a9 0f        :Left           lda     #15
9315: 4c be 92                     jmp     :SetDir

                   ; Check for some special conditions.
9318: a5 72        NextObject1     lda     no_draw_obj_flag  ;is the "no draw" flag set?
931a: d0 08                        bne     ObjectOffScreen   ;yes, branch
931c: bd 18 9b                     lda     obj_activity_state,x ;is the object going away?
931f: 30 03                        bmi     ObjectOffScreen   ;yes, branch
9321: 4c 9f 94                     jmp     CheckPlyrHit      ;alive and well, go check for collisions

                   ; 
                   ; Handles an object that is no longer on-screen.  If it's a friendly base or
                   ; time portal, and we "collided" with the center, do the special behavior.
                   ; 
                   ; If we're done with the object, we want to free up the object and element
                   ; slots.
                   ; 
                   ; On entry:
                   ;   X-reg: object index
                   ; 
                   • Clear variables
                   ]abs_coord_diff .var    $86    {addr/2}
                   ]shape_class_nib .var   $88    {addr/1}

9324: e6 72        ObjectOffScreen inc     no_draw_obj_flag
9326: bd a0 9a                     lda     obj_shape_uid,x   ;get shape ID
9329: 29 f0                        and     #$f0
932b: 85 88                        sta     ]shape_class_nib
932d: c9 60                        cmp     #$60              ;friendly base ($61) or time portal ($6f)?
932f: f0 07                        beq     :IsFriendly
9331: c9 50                        cmp     #$50              ;time portal boundary ($5x)?
9333: f0 03                        beq     :IsFriendly
9335: 4c f7 93                     jmp     :FriendlyCollDone

9338: a9 00        :IsFriendly     lda     #$00
933a: 85 f8                        sta     elem_collision_flag
933c: bd 18 9b                     lda     obj_activity_state,x
933f: 10 03                        bpl     :CheckCenterColl
9341: 4c f7 93                     jmp     :FriendlyCollDone

                   ; Check for collision with first element, which is a point in the middle of the
                   ; gap.
                   :CheckCenterColl
9344: bc 00 9a                     ldy     obj_first_elem_index,x ;get index of first element
9347: b9 c0 a1                     lda     elem_left_lo,y    ;copy left coordinate to ZP
934a: 85 86                        sta     ]abs_coord_diff
934c: b9 00 a2                     lda     elem_left_hi,y
934f: 85 87                        sta     ]abs_coord_diff+1
9351: 10 0a                        bpl     :LeftPos
9353: 49 ff                        eor     #$ff              ;negate to get abs val
9355: 85 87                        sta     ]abs_coord_diff+1
9357: a5 86                        lda     ]abs_coord_diff
9359: 49 ff                        eor     #$ff
935b: 85 86                        sta     ]abs_coord_diff
935d: bd b8 9b     :LeftPos        lda     hitbox_size_lo,x  ;get object hitbox size
9360: c5 86                        cmp     ]abs_coord_diff   ;compare to coordinate difference
9362: bd e0 9b                     lda     hitbox_size_hi,x
9365: e5 87                        sbc     ]abs_coord_diff+1
9367: 30 30                        bmi     :Missed           ;missed, branch
9369: b9 40 a2                     lda     elem_top_lo,y     ;copy top coordinate to ZP
936c: 85 86                        sta     ]abs_coord_diff
936e: b9 80 a2                     lda     elem_top_hi,y
9371: 85 87                        sta     ]abs_coord_diff+1
9373: 10 0a                        bpl     :TopPos
9375: 49 ff                        eor     #$ff              ;negate to get abs val
9377: 85 87                        sta     ]abs_coord_diff+1
9379: a5 86                        lda     ]abs_coord_diff
937b: 49 ff                        eor     #$ff
937d: 85 86                        sta     ]abs_coord_diff
937f: bd b8 9b     :TopPos         lda     hitbox_size_lo,x  ;get object hitbox size
9382: c5 86                        cmp     ]abs_coord_diff   ;compare to coordinate difference
9384: bd e0 9b                     lda     hitbox_size_hi,x
9387: e5 87                        sbc     ]abs_coord_diff+1
9389: 30 0e                        bmi     :Missed           ;missed, branch
                   ; We flew into something.  See what it was.
938b: a5 88                        lda     ]shape_class_nib
938d: c9 50                        cmp     #$50              ;was it a time portal boundary?
938f: d0 3c                        bne     :HitNonBound      ;no, branch
9391: a9 00                        lda     #$00              ;yes, we passed through center of portal bound obj
9393: 8d 98 6d                     sta     time_portal_fail_ctr ;reset counter
9396: 4c f7 93                     jmp     :FriendlyCollDone

9399: a5 88        :Missed         lda     ]shape_class_nib
939b: c9 50                        cmp     #$50              ;was it a time portal boundary?
939d: d0 29                        bne     :MissedNonBound   ;no, branch
                   ; Flew outside a portal boundary.
939f: ee 98 6d                     inc     time_portal_fail_ctr ;increment fail counter
93a2: 38                           sec
93a3: ad 61 6d                     lda     region_progress_ctr ;advance progress tracker
93a6: e9 00                        sbc     #$00
93a8: 8d 61 6d                     sta     region_progress_ctr
93ab: ad 62 6d                     lda     region_progress_ctr+1
93ae: e9 04                        sbc     #$04
93b0: 8d 62 6d                     sta     region_progress_ctr+1
93b3: a9 01                        lda     #$01
93b5: 85 a0                        sta     impact_flash_ctr  ;flash once
93b7: ad 48 6d                     lda     sound_disab_flag  ;do sound stuff
93ba: d0 3b                        bne     :FriendlyCollDone
93bc: a9 01                        lda     #$01
93be: 85 fa                        sta     impact_sound_flag
93c0: a9 fe                        lda     #$fe              ;(?)
93c2: 20 f0 0f                     jsr     Return0ff0
93c5: 4c f7 93                     jmp     :FriendlyCollDone

                   ; Flew outside center of a non-portal-boundary object.
93c8: ea           :MissedNonBound nop
93c9: ea                           nop
93ca: 4c f7 93                     jmp     :FriendlyCollDone

                   ; Flew through middle of something other than portal boundary.
93cd: bd a0 9a     :HitNonBound    lda     obj_shape_uid,x   ;get shape identifier
93d0: c9 6f                        cmp     #$6f              ;is it a time warp?
93d2: d0 06                        bne     :GiveRsrc         ;no, must be base; branch
93d4: 8d 99 6d                     sta     entered_portal_flag ;yes, set "in time warp" flag to non-zero
93d7: 4c f7 93                     jmp     :FriendlyCollDone

                   ; Flew threw base, give max fuel and ammo.
93da: a9 00        :GiveRsrc       lda     #$00
93dc: 8d c4 6d                     sta     time_left+2
93df: 8d c5 6d                     sta     fuel_left
93e2: 8d c7 6d                     sta     fuel_left+2
93e5: 8d c8 6d                     sta     amun_left
93e8: a9 90                        lda     #$90              ;set fuel to 9000
93ea: 8d c6 6d                     sta     fuel_left+1
93ed: a9 01                        lda     #$01              ;set ammo to 100
93ef: 8d c9 6d                     sta     amun_left+1
93f2: a9 04                        lda     #$04
93f4: 20 c2 7f                     jsr     PlayMusicSeq      ;play "fly through base" music
                   ; Done with tests for player colliding with friendly object.
                   :FriendlyCollDone
93f7: a6 62                        ldx     cur_obj_index     ;get object index
93f9: bd 18 9b                     lda     obj_activity_state,x ;check object state
93fc: 30 03                        bmi     DeleteObject      ;was negative, go ahead and delete
93fe: 4c 9a 94                     jmp     :NoDeleteYet      ;was positive, still need to erase

                   ; 
                   ; Deletes an object, marking its slot as unused.  All associated elements are
                   ; also deleted.
                   ; 
                   ; -----
                   ; 
                   ; The first chunk of code is a copy protection booby-trap.  It essentially
                   ; checks the value in the keyboard input buffer at $0200 to see if it's $90. 
                   ; The pointer at $12-13 has its low byte initialized to zero infrequently, so
                   ; storing a nonzero value there causes annoying graphical glitches.
                   ; 
                   • Clear variables
                   ]prot_ptr       .var    $10    {addr/2}

9401: ad c4 71     DeleteObject    lda     color_bit_masks_thin+1 ;#$02
9404: 85 11                        sta     ]prot_ptr+1       ;create pointer to $0200
9406: a0 00                        ldy     #$00
9408: ad c6 71                     lda     color_bit_masks_thin+3 ;#$08
940b: 18                           clc
940c: 69 88                        adc     #$88              ;now A-reg=$90
940e: 51 10                        eor     (]prot_ptr),y     ;XOR value at $0200 (#$93), A-reg=$03
9410: 84 11                        sty     ]prot_ptr+1       ;Y-reg=0, so now ($10) points at $0000
9412: a0 11                        ldy     #$11
9414: 49 03                        eor     #$03              ;A-reg=$00
9416: c8                           iny                       ;Y=reg=$12
9417: 91 10                        sta     (]prot_ptr),y     ;set $12 to $00
9419: c6 11                        dec     ]prot_ptr+1
                   ; 
                   ]elem_tmp       .var    $88    {addr/1}
                   ]index_tmp      .var    $8a    {addr/1}

941b: bc 00 9a                     ldy     obj_first_elem_index,x ;get element index
941e: b9 40 9f     :DelElemLoop    lda     elem_next_elem,y  ;get index of following element
9421: 85 88                        sta     ]elem_tmp         ;save that
9423: a5 68                        lda     avail_elem_index  ;get "next available element" index
9425: 84 68                        sty     avail_elem_index  ;replace with index of following element
9427: 99 40 9f                     sta     elem_next_elem,y  ;replace following-element index with next element
942a: 20 7f 7f                     jsr     Return7f7f
942d: a9 fd                        lda     #$fd
942f: 99 00 9f                     sta     elem_obj_index,y  ;invalidate reference back to object
9432: e6 6e                        inc     free_elem_count   ;increment number of available elements
9434: a4 88                        ldy     ]elem_tmp         ;get index of following element
9436: 10 e6                        bpl     :DelElemLoop      ;if it's not an end-of-list marker, loop
9438: a9 dd                        lda     #$dd
943a: 9d 00 9a                     sta     obj_first_elem_index,x ;invalidate reference from object to first element
943d: bd 78 9a                     lda     obj_score_class,x ;get the score class
9440: f0 22                        beq     :NoPoints         ;not enemy ship or base, branch
9442: 20 7f 7f                     jsr     Return7f7f
9445: bc f0 9a                     ldy     obj_next_enemy_index,x ;get next-enemy index
9448: 10 0a                        bpl     :HaveNext         ;found a valid value, branch
944a: a0 fc                        ldy     #$fc
944c: bd c8 9a                     lda     obj_prev_enemy_index,x ;invalidate prev-enemy index
944f: 85 6c                        sta     head_enemy_obj_index ;update ZP
9451: 4c 5a 94                     jmp     :SetNext

9454: bd c8 9a     :HaveNext       lda     obj_prev_enemy_index,x ;get prev-enemy index
9457: 99 c8 9a                     sta     obj_prev_enemy_index,y ;set as next enemy's prev-enemy index
945a: 30 08        :SetNext        bmi     :NoPoints
945c: 84 8a                        sty     ]index_tmp        ;swap A-reg/Y-reg
945e: a8                           tay
945f: a5 8a                        lda     ]index_tmp
9461: 99 f0 9a                     sta     obj_next_enemy_index,y ;set prev enemy's next-enemy index
9464: bd 50 9a     :NoPoints       lda     obj_next_obj,x    ;get next-object index
9467: 85 62                        sta     cur_obj_index     ;make that object current
9469: a4 74                        ldy     prev_obj_index    ;get index of object from previous loop
946b: 20 7f 7f                     jsr     Return7f7f
946e: 10 05                        bpl     :PrevValid
9470: 85 6a                        sta     head_obj_index    ;copy current object index here
9472: 4c 78 94                     jmp     :Cont

9475: 99 50 9a     :PrevValid      sta     obj_next_obj,y    ;set previous object's next-object index
9478: a5 66        :Cont           lda     avail_obj_index   ;get the next-object index
947a: 9d 50 9a                     sta     obj_next_obj,x    ;store that in the table
947d: 86 66                        stx     avail_obj_index   ;set deleted object index as ZP next-obj value
947f: e6 6d                        inc     free_obj_count    ;increment the number of free objects
9481: bc 08 9c                     ldy     obj_shape_cl_index,x ;get shape class of deleted object
9484: b9 69 6d                     lda     active_class_ctrs,y ;update the appropriate active-class counter
9487: 38                           sec
9488: e9 01                        sbc     #$01              ;reduce by 1
948a: 99 69 6d                     sta     active_class_ctrs,y
948d: 20 7f 7f                     jsr     Return7f7f
9490: a6 62                        ldx     cur_obj_index     ;put the next object in X-reg
9492: 10 03                        bpl     :DrawNext         ;if it's valid, branch to redraw it
9494: 4c 60 96                     jmp     :DoneWithObjs     ;not valid, done with objects

9497: 4c 58 8c     :DrawNext       jmp     RedrawObject

949a: a9 fe        :NoDeleteYet    lda     #$fe
949c: 9d 18 9b                     sta     obj_activity_state,x ;mark as pending deletion
                   ; 
                   ; Check if the collision flag is set.  The flag is not set for time portals or
                   ; friendly bases, so this only handles collisions with enemy ships, bases, and
                   ; projectiles.
                   ; 
949f: 86 74        CheckPlyrHit    stx     prev_obj_index    ;save current object index as prev object
94a1: a9 ad                        lda     #INSTR_LDA_ABS
94a3: 20 4c 7b                     jsr     ModDrwEraVrtRct   ;disable rect draw/erase
94a6: a5 f8                        lda     elem_collision_flag ;did we collide with hostile object?
94a8: d0 03                        bne     :DidCollide       ;yes, branch
94aa: 4c eb 94                     jmp     CheckPlyrProj     ;no, go check our projectiles

94ad: 10 07        :DidCollide     bpl     :DidCollide1      ;always?
94af: a9 02                        lda     #$02              ;(not sure what this is; flashes twice and then jumps
94b1: 85 a0                        sta     impact_flash_ctr  ; to player projectile handling.  A breakpoint here
94b3: 4c eb 94                     jmp     CheckPlyrProj     ; never fired.)

94b6: ad 3b 6d     :DidCollide1    lda     game_active_flag  ;are we in demo mode?
94b9: d0 03                        bne     :PlayerHit        ;no, take your lumps
94bb: 4c eb 94                     jmp     CheckPlyrProj     ;yes, skip next bit

                   ; Player collided with something other than a friendly base, time portal, or
                   ; time portal boundary.  Flash the screen and deduct fuel.
                   • Clear variables
                   ]num_digit_bytes .var   $8a    {addr/1}

94be: a9 ef        :PlayerHit      lda     #$ef
94c0: ea                           nop
94c1: 9d 18 9b                     sta     obj_activity_state,x ;mark thing player hit for deletion
94c4: a9 03                        lda     #$03
94c6: 85 a0                        sta     impact_flash_ctr  ;flash 3x
94c8: ad 48 6d                     lda     sound_disab_flag  ;do sound stuff
94cb: d0 09                        bne     :NoSound
94cd: a9 01                        lda     #$01
94cf: 85 fa                        sta     impact_sound_flag ;set this flag
94d1: a9 ff                        lda     #$ff
94d3: 20 f0 0f                     jsr     Return0ff0
94d6: a9 02        :NoSound        lda     #$02
94d8: 85 8a                        sta     ]num_digit_bytes  ;2-byte value
94da: a2 08                        ldx     #$08              ;select fuel, reduce by impact amount
94dc: a0 37                        ldy     #$37
94de: 20 68 7c                     jsr     ReduceResource    ;reduce fuel by 300
94e1: ea                           nop
94e2: a6 62                        ldx     cur_obj_index
94e4: 86 a2                        stx     linked_obj_index
94e6: a9 03                        lda     #$03
94e8: 85 a0                        sta     impact_flash_ctr  ;(again?)
94ea: ea                           nop
                   ; 
                   ; If this object is a player projectile, see if it hit something.
                   ; 
                   ]proj_move_zc   .var    $88    {addr/2}
                   ]coord_diff     .var    $8e    {addr/2}
                   ]hitbox_size    .var    $90    {addr/2}

94eb: bd 40 9b     CheckPlyrProj   lda     obj_plyr_proj_flag,x ;is this a player projectile?
94ee: 20 7f 7f                     jsr     Return7f7f
94f1: f0 2f                        beq     :Jmp_Bottom       ;no, branch
94f3: ad 3b 6d                     lda     game_active_flag  ;are we in demo mode?
94f6: f0 2a                        beq     :Jmp_Bottom       ;yes, branch
94f8: bd 18 9b                     lda     obj_activity_state,x ;is object active?
94fb: 30 25                        bmi     :Jmp_Bottom       ;no, branch
                   ; Set up 3D hit box.
94fd: bd 10 9e                     lda     obj_move_zc_lo,x  ;get player projectile Z movement
9500: 85 88                        sta     ]proj_move_zc     ;copy to DP
9502: bd 38 9e                     lda     obj_move_zc_hi,x
9505: 18                           clc
9506: 69 02                        adc     #$02              ;add $0200 so enemy can't move forward and
9508: 85 89                        sta     ]proj_move_zc+1   ; jump across seam from one frame to next
950a: bd b8 9b                     lda     hitbox_size_lo,x  ;get size of projectile hitbox ($0030)
950d: 85 90                        sta     ]hitbox_size
950f: bd e0 9b                     lda     hitbox_size_hi,x
9512: 85 91                        sta     ]hitbox_size+1
9514: 06 90                        asl     ]hitbox_size      ;double it
9516: 26 91                        rol     ]hitbox_size+1
9518: bd 00 9a                     lda     obj_first_elem_index,x ;get index of player projectile rect
951b: aa                           tax                       ;put that in X-reg
951c: 85 64                        sta     cur_elem_index    ;save in ZP
951e: a4 6a                        ldy     head_obj_index    ;get index of first object in list
9520: 10 03                        bpl     :IsValidObj       ;is valid, branch
9522: 4c 55 96     :Jmp_Bottom     jmp     ObjLoopBottom     ;done with objects

9525: b9 78 9a     :IsValidObj     lda     obj_score_class,y ;get score class
9528: d0 09                        bne     :IsTarget         ;is enemy ship or base, branch
952a: b9 50 9a     :NextObj        lda     obj_next_obj,y    ;get next object index
952d: a8                           tay
952e: 10 f5                        bpl     :IsValidObj       ;is valid, loop
9530: 4c 55 96                     jmp     ObjLoopBottom     ;done with objects

9533: 84 a8        :IsTarget       sty     test_obj_index    ;save index of object we're testing
9535: b9 00 9a                     lda     obj_first_elem_index,y ;get index of first element in object
9538: 10 05                        bpl     :IsValidElem      ;is valid, branch
953a: a6 62                        ldx     cur_obj_index     ;not valid (does this happen?)
953c: 4c 55 96                     jmp     ObjLoopBottom     ;done with objects

                   ; Check for collision by comparing the left, top, and Z coordinates of the first
                   ; element of the objects.  The hitbox extends over and down by an amount
                   ; specified by the projectile shape definition.  Note this does NOT take into
                   ; account the hitbox of the enemy ship or base, which is why you should aim for
                   ; the top-left corner of the main body rect for the 30/40/60-pt aliens.
                   ]targ_elem_index .var   $86    {addr/1}

953f: a8           :IsValidElem    tay                       ;copy target obj's first element index to Y-reg
9540: 85 86                        sta     ]targ_elem_index  ;save in ZP (not used?)
9542: 38                           sec
9543: bd c0 a1                     lda     elem_left_lo,x    ;compute difference of left coordinates
9546: f9 c0 a1                     sbc     elem_left_lo,y
9549: 85 8e                        sta     ]coord_diff
954b: bd 00 a2                     lda     elem_left_hi,x
954e: f9 00 a2                     sbc     elem_left_hi,y
9551: 70 18                        bvs     :MissX            ;signed overflow, that's a big miss; branch
9553: 85 8f                        sta     ]coord_diff+1
9555: 10 0a                        bpl     :PosX
9557: 49 ff                        eor     #$ff              ;negate (without +1?) to get absolute value
9559: 85 8f                        sta     ]coord_diff+1
955b: a5 8e                        lda     ]coord_diff
955d: 49 ff                        eor     #$ff
955f: 85 8e                        sta     ]coord_diff
9561: a5 8e        :PosX           lda     ]coord_diff       ;compare diff to hitbox size
9563: c5 90                        cmp     ]hitbox_size
9565: a5 8f                        lda     ]coord_diff+1
9567: e5 91                        sbc     ]hitbox_size+1
9569: 30 03                        bmi     :InsideX          ;diff < hitbox size, keep going
956b: 4c 38 96     :MissX          jmp     :LoopBottom       ;missed, bail

956e: 38           :InsideX        sec
956f: bd 40 a2                     lda     elem_top_lo,x     ;compute difference of top coordinates
9572: f9 40 a2                     sbc     elem_top_lo,y
9575: 85 8e                        sta     ]coord_diff
9577: bd 80 a2                     lda     elem_top_hi,x
957a: f9 80 a2                     sbc     elem_top_hi,y
957d: 70 ec                        bvs     :MissX            ;signed overflow, missed; branch
957f: 85 8f                        sta     ]coord_diff+1
9581: 10 0a                        bpl     :PosY
9583: 49 ff                        eor     #$ff              ;negate (without +1?) to get absolute value
9585: 85 8f                        sta     ]coord_diff+1
9587: a5 8e                        lda     ]coord_diff
9589: 49 ff                        eor     #$ff
958b: 85 8e                        sta     ]coord_diff
958d: a5 8e        :PosY           lda     ]coord_diff       ;compare diff to hitbox size
958f: c5 90                        cmp     ]hitbox_size
9591: a5 8f                        lda     ]coord_diff+1
9593: e5 91                        sbc     ]hitbox_size+1
9595: 10 29                        bpl     :MissZ            ;diff >= hitbox size, bail
9597: 38                           sec
9598: bd 40 a1                     lda     elem_zpos_lo,x    ;compute difference of Z coordinates
959b: f9 40 a1                     sbc     elem_zpos_lo,y
959e: 85 8e                        sta     ]coord_diff
95a0: bd 80 a1                     lda     elem_zpos_hi,x
95a3: f9 80 a1                     sbc     elem_zpos_hi,y
95a6: 70 18                        bvs     :MissZ            ;signed overflow, missed; branch
95a8: 85 8f                        sta     ]coord_diff+1
95aa: 10 0a                        bpl     :PosZ
95ac: 49 ff                        eor     #$ff              ;negate (without +1?) to get absolute value
95ae: 85 8f                        sta     ]coord_diff+1
95b0: a5 8e                        lda     ]coord_diff
95b2: 49 ff                        eor     #$ff
95b4: 85 8e                        sta     ]coord_diff
95b6: a5 8e        :PosZ           lda     ]coord_diff       ;compare difference in coordinates to projectile's Z
95b8: c5 88                        cmp     ]proj_move_zc     ; speed, so we collide if we're about to move through
95ba: a5 8f                        lda     ]coord_diff+1     ; the target or already moved through it
95bc: e5 89                        sbc     ]proj_move_zc+1
95be: 30 03                        bmi     EnemyDestroyed
95c0: 4c 38 96     :MissZ          jmp     :LoopBottom

                   ; 
                   ; Handles an enemy ship or base that has been struck by a player projectile. 
                   ; Flashes the screen and updates the score.
                   ; 
95c3: 20 7f 7f     EnemyDestroyed  jsr     Return7f7f
95c6: a4 a8                        ldy     test_obj_index    ;get index of object we're testing
95c8: 84 a2                        sty     linked_obj_index  ;set as "linked object" for chunks/flare
95ca: b9 78 9a                     lda     obj_score_class,y ;get index into score table
95cd: 85 a0                        sta     impact_flash_ctr  ;flash that many times (more for bases)
95cf: a2 00                        ldx     #$00              ;index of score bytes
95d1: 0a                           asl     A                 ;multiply score class by 4
95d2: 0a                           asl     A
95d3: 18                           clc
95d4: 69 17                        adc     #$17              ;add offset to enemy point value table
95d6: a8                           tay
95d7: a9 04                        lda     #$04              ;4-byte value
95d9: 85 8a                        sta     ]num_digit_bytes
95db: 20 a0 7c                     jsr     IncreaseResource  ;increase score
95de: a5 a0                        lda     impact_flash_ctr  ;get score class
95e0: c9 06                        cmp     #$06              ;was it a base?
95e2: 30 08                        bmi     :NotBase
95e4: a9 03                        lda     #$03
95e6: 20 c2 7f                     jsr     PlayMusicSeq      ;enemy base destroyed, play chirp sound
95e9: 4c f6 95                     jmp     :SoundDone

95ec: a0 02        :NotBase        ldy     #$02
95ee: 20 da 7c                     jsr     InitiateSfx       ;play enemy destroyed sound
95f1: a5 a0                        lda     impact_flash_ctr  ;(?)
95f3: 20 f0 0f                     jsr     Return0ff0
                   ; Create flare and chunks.
95f6: a5 a0        :SoundDone      lda     impact_flash_ctr  ;(?)
95f8: a0 0a                        ldy     #$0a              ;class = ship explosion flare
95fa: a6 62                        ldx     cur_obj_index     ;preserve current object index
95fc: 8e 81 8c                     stx     saved_obj_index
95ff: 20 0f 76                     jsr     CreateObject      ;create explosion object
9602: ea                           nop
9603: ae 81 8c                     ldx     saved_obj_index   ;restore object index
9606: 86 62                        stx     cur_obj_index
9608: 18                           clc
9609: a5 a0                        lda     impact_flash_ctr  ;get score class
960b: 69 02                        adc     #$02              ;add two
960d: 8d 37 96                     sta     :chunk_ctr        ;create this many chunks
9610: ce 37 96     :ChunkLoop      dec     :chunk_ctr        ;done yet?
9613: 30 16                        bmi     :ChunksDone       ;yes, branch
9615: a0 09                        ldy     #$09              ;class = explosion chunks
9617: a5 a8                        lda     test_obj_index
9619: 85 a2                        sta     linked_obj_index
961b: a6 62                        ldx     cur_obj_index
961d: 8e 81 8c                     stx     saved_obj_index   ;save current object index
9620: 20 0f 76                     jsr     CreateObject      ;create chunk
9623: ae 81 8c                     ldx     saved_obj_index
9626: 86 62                        stx     cur_obj_index     ;restore object index
9628: 4c 10 96                     jmp     :ChunkLoop

962b: a9 fa        :ChunksDone     lda     #$fa
962d: a4 a8                        ldy     test_obj_index
962f: 99 18 9b                     sta     obj_activity_state,y
9632: a6 62                        ldx     cur_obj_index
9634: 4c 55 96                     jmp     ObjLoopBottom

9637: 00           :chunk_ctr      .dd1    $00               ;explosion chunk counter

9638: 18           :LoopBottom     clc                       ;do sound stuff
9639: a5 b2                        lda     engine_sound_ctr?+1
963b: 69 06                        adc     #$06
963d: 85 b2                        sta     engine_sound_ctr?+1
963f: 90 0f                        bcc     :NoSound
9641: e6 b3                        inc     engine_sound_ctr?+2
9643: a5 cc                        lda     engine_sound_enable
9645: f0 09                        beq     :NoSound
9647: a5 b3                        lda     engine_sound_ctr?+2
9649: 25 b1                        and     engine_sound_ctr?
964b: d0 03                        bne     :NoSound
964d: ad 30 c0                     lda     SPKR
9650: a4 a8        :NoSound        ldy     test_obj_index
9652: 4c 2a 95                     jmp     :NextObj          ;check next object

9655: 20 7f 7f     ObjLoopBottom   jsr     Return7f7f
9658: a6 62                        ldx     cur_obj_index     ;get object index
965a: bd 50 9a                     lda     obj_next_obj,x    ;see if there's another object
965d: aa                           tax
965e: 10 54                        bpl     :MoreObjs         ;there is, go handle it
                   ; Done walking objects.  If we're showing an impact flash, do it now, otherwise
                   ; just restart the main loop.
9660: a5 a0        :DoneWithObjs   lda     impact_flash_ctr  ;are we flashing the lo-res screen?
9662: d0 07                        bne     :ShowImpactFlash  ;yes, go do that
9664: 4c fc 81                     jmp     MainLoop

9667: a9 ff 85 88                  .junk   4

                   ; Flash the screen when something gets hit.  Set the lo-res screen to a random
                   ; color and display it briefly.
                   ]rng_result     .var    $8a    {addr/2}

                   :ShowImpactFlash
966b: c6 a0                        dec     impact_flash_ctr
966d: 20 b0 7b                     jsr     GenRandom         ;get random value (is limit set?)
9670: a5 8b                        lda     ]rng_result+1     ;get high byte
9672: 29 07                        and     #$07              ;reduce to 0-7
9674: a8                           tay
9675: b9 ce 70                     lda     lo_res_color,y    ;get color value from table
9678: 20 4e 7c                     jsr     SetLoRes2         ;fill lo-res screen with it
967b: ad 56 c0                     lda     LORES             ;switch to lo-res screen
967e: ad 55 c0                     lda     TXTPAGE2          ;page 2
                   ; Play a brief sound effect (about 144 Hz).
9681: a2 07                        ldx     #$07
9683: a0 f6        :DelayLoop      ldy     #$f6              ;2
9685: 88           :Delay1         dey                       ;2
9686: d0 fd                        bne     :Delay1           ;3  (7 * 246) - 1 = 1721 cycles
9688: a0 f6                        ldy     #$f6
968a: 88           :Delay2         dey
968b: d0 fd                        bne     :Delay2
968d: a0 f6                        ldy     #$f6
968f: 88           :Delay3         dey
9690: d0 fd                        bne     :Delay3
9692: a0 f6                        ldy     #$f6
9694: 88           :Delay4         dey
9695: d0 fd                        bne     :Delay4           ;1721 * 4 = 6884 cycles
9697: a5 fa                        lda     impact_sound_flag ;play sound?
9699: f0 0d                        beq     :NoSound          ;no, done with sound (even if not done with flash)
969b: ad 3b 6d                     lda     game_active_flag  ;showing the demo?
969e: f0 08                        beq     :NoSound          ;yes, no sound
96a0: ad 48 6d                     lda     sound_disab_flag  ;sound disabled?
96a3: d0 03                        bne     :NoSound          ;yes, no sound
96a5: ad 30 c0                     lda     SPKR              ;click
96a8: ca           :NoSound        dex
96a9: d0 d8                        bne     :DelayLoop
96ab: ad 54 c0                     lda     TXTPAGE1          ;switch back to page 1
96ae: ad 57 c0                     lda     HIRES             ;hi-res graphics
96b1: 4c fc 81                     jmp     MainLoop

96b4: 86 62        :MoreObjs       stx     cur_obj_index
96b6: 20 7f 7f                     jsr     Return7f7f
96b9: 4c 58 8c                     jmp     RedrawObject      ;jump to top of object redraw loop

96bc: 3d 3d 3d 3d+                 .align  $0100 (68 bytes)

                                   .org    $9a00
                   ; 
                   ; Active object state, for up to 40 objects.
                   ; 
                   ; -----
                   ; 
                   ; Index of first element in object.  Unused entries are set to $f7.  The last
                   ; entry is set to $ed as an end-of-list marker.
                   ; 
                   ; Set to $dd when object is being deleted.
                   obj_first_elem_index
9a00: 00 01 14 15+                 .junk   40
                   ; 
                   ; Lifespan counter.  If initially $00, object can live forever.  If nonzero,
                   ; object expires after that many ticks.
                   ; 
                   ; From shape header +$01.
                   obj_lifetime_ctr
9a28: 00 00 00 00+                 .junk   40
                   ; 
                   ; Index of next active object.  Initialized to $01-27 (1-39).  The last entry is
                   ; set to $ed as an end-of-list marker.
9a50: ef 00 01 02+ obj_next_obj    .junk   40
                   ; 
                   ; "Score class" for enemy ships and bases (1-7), or 0 for other entities.  See
                   ; table at $70fd for score values.
                   ; 
                   ; From shape header +$02.
9a78: 00 00 00 00+ obj_score_class .junk   40
                   ; 
                   ; Shape unique identifier.  Code checks for $6f (time warp), $5x (time portal
                   ; boundaries), and $fx (which never happens).
                   ; 
                   ; From shape header +$03.
9aa0: 72 01 75 75+ obj_shape_uid   .junk   40
                   ; 
                   ; Link to previous object slot with an enemy ship or base.
                   obj_prev_enemy_index
9ac8: 00 00 00 00+                 .junk   40
                   ; 
                   ; Link to next object slot with an enemy ship or base.
                   obj_next_enemy_index
9af0: 00 00 00 00+                 .junk   40
                   ; 
                   ; Initially set to value (0-3) from shape header at +$04:
                   ;  $00: friendly/enemy bases, time portals, stars
                   ;  $01: player projectiles, explosion flares
                   ;  $02: explosion chunks
                   ;  $03: enemy ships
                   ; 
                   ; Value $02 will be replaced with $01 after initial velocity is set, and the
                   ; state may be replaced with other values at the end of the object's life.  So
                   ; the meaning becomes:
                   ; 
                   ;  $00: no movement: friendly/enemy bases, stars
                   ;  $01: movement doesn't change: player projectile, enemy projectile, explosion
                   ; chunks, explosion flare
                   ;  $02: (unused)
                   ;  $03: movement updated periodically: enemy ships
                   ;  $ef: player collided with this
                   ;  $fe: object is being / has been deleted
                   ;  $ff: object lifetime has expired (e.g. explosion flares)
                   obj_activity_state
9b18: 00 00 00 00+                 .junk   40
                   ; 
                   ; Set to 4 for player projectiles, 0 for everything else.  Used as an "is it a
                   ; friendly projectile" flag.
                   ; 
                   ; From shape header +$05.
                   obj_plyr_proj_flag
9b40: 00 00 00 00+                 .junk   40
                   ; 
                   ; Max interval between velocity re-evaluation.
                   ; 
                   ; From shape header +$06.
                   vel_change_intvl_max
9b68: 00 00 00 00+                 .junk   40
                   ; 
                   ; Velocity change counter, only used for enemy ships.  When this reaches zero,
                   ; we recompute the ship's velocity, and reset the counter to a random value.
                   ; 
                   ; Random value is limited by shape header value +$06.  Initialized to $01 for
                   ; new slot.
9b90: 01 01 01 01+ vel_change_ctr  .junk   40
                   ; 
                   ; Size of hitbox, in eye coordinates.  The top-left corner is specified by the
                   ; first element in the shape defintion.
                   ; 
                   ; From shape header $0f/$10.
9bb8: 01 c0 01 01+ hitbox_size_lo  .junk   40
9be0: 00 01 00 00+ hitbox_size_hi  .junk   40
                   ; 
                   ; Shape class for this object (0-11).
                   obj_shape_cl_index
9c08: 07 00 07 07+                 .junk   40
                   ; 
                   ; Base movement, to which random values may be added.
                   ; 
                   ; These are updated in specific situations.
9c30: 00 00 00 00+ obj_move_zc2_lo .junk   40
9c58: 00 00 00 00+ obj_move_zc2_hi .junk   40
9c80: 00 00 00 00+ obj_move_xc2_lo .junk   40
9ca8: 00 00 00 00+ obj_move_xc2_hi .junk   40
9cd0: 00 00 00 00+ obj_move_yc2_lo .junk   40
9cf8: 00 00 00 00+ obj_move_yc2_hi .junk   7
                   ; 
                   ; NOTE: some additional per-object tables follow.  There's no data in the file
                   ; at this point, so they're defined as equates.
                   ; 
                   ; obj_spdlim_z_lo .eq   $9d20  {addr/40} ;Z speed limit, low (hdr +$11)
                   ; obj_spdlim_z_hi .eq   $9d48  {addr/40} ;Z speed limit, high (hdr +$12)
                   ; obj_spdlim_x_lo .eq   $9d70  {addr/40} ;X speed limit, low (hdr +$13)
                   ; obj_spdlim_x_hi .eq   $9d98  {addr/40} ;X speed limit, high (hdr +$14)
                   ; obj_spdlim_y_lo .eq   $9dc0  {addr/40} ;Y speed limit, low (hdr +$15)
                   ; obj_spdlim_y_hi .eq   $9de8  {addr/40} ;Y speed limit, high (hdr +$16)
                   ; obj_move_zc_lo  .eq   $9e10  {addr/40} ;object movement vector, Z low
                   ; obj_move_zc_hi  .eq   $9e38  {addr/40} ;object movement vector, Z high
                   ; obj_move_xc_lo  .eq   $9e60  {addr/40} ;object movement vector, X low
                   ; obj_move_xc_hi  .eq   $9e88  {addr/40} ;object movement vector, X high
                   ; obj_move_yc_lo  .eq   $9eb0  {addr/40} ;object movement vector, Y low
                   ; obj_move_yc_hi  .eq   $9ed8  {addr/40} ;object movement vector, Y high
                   ; 
9cff: 00                           .junk   1

                                   .org    $9f00
                   ; 
                   ; Active element state, for up to 64 elements.
                   ; 
                   ; -----
                   ; 
                   ; Index of object that the element is a part of (0-39).  It may also hold $f6
                   ; when first initialized, $ec as an end-of-list marker ($9f3f only), or
                   ; $ec/f6/fd after various events.
9f00: 00 01 01 01+ elem_obj_index  .junk   64
                   ; 
                   ; Index of next element in this object.  This is initialized to N+1, i.e.
                   ; entries 0,1,2 have values 1,2,3.  When an object is created, the entry for the
                   ; last element is changed to #$fc to mark the end of the list.
9f40: fc 02 03 04+ elem_next_elem  .junk   64
                   ; 
                   ; Modified element type.  Value is based on the element type and state:
                   ;   $00=point
                   ;   $01=horizontal line
                   ;   $80=vertical line ($ff in element def)
                   ;   $81=rect ($80 in elementdef)
                   ;   $82=do not draw
                   ;   $83=created, not yet draw
                   ; 
                   ; These may not match the original type, e.g. a rect may be "demoted" to a
                   ; vertical line if the left and right coordinates are equal.
9f80: 00 00 81 81+ elem_mod_types  .junk   64
                   ; 
                   ; Unmodified element type: $00=point, $01=hline, $80=rect, $ff=vline.
9fc0: 00 00 80 80+ elem_types      .junk   64
                   ; 
                   ; Colors and color-change tracking.
a000: 50 00 40 40+ elem_colorsA    .junk   64                ;first color
a040: 00 00 00 00+ elem_colorsB    .junk   64                ;second color (optional)
a080: 50 00 40 40+ elem_cur_colors .junk   64                ;holds colorA or colorB
                   elem_colorchanges
a0c0: 00 00 00 00+                 .junk   64                ;change frequency, from shape definition
                   elem_colorchange_ctrs
a100: 00 00 00 00+                 .junk   64                ;current value of counter
                   ; 
                   ; Current element position (eye coordinates), updated as things move.  Negative
                   ; values indicate positions to the left and above the crosshairs.
                   ; 
                   ; For points and lines, only the relevant coordinates are used (e.g.
                   ; right/bottom don't matter for points).
a140: 40 ba ba ba+ elem_zpos_lo    .junk   64
a180: 3a 09 09 09+ elem_zpos_hi    .junk   64
a1c0: 95 00 80 c0+ elem_left_lo    .junk   64
a200: f5 00 fc fc+ elem_left_hi    .junk   64
a240: 95 00 00 00+ elem_top_lo     .junk   64
a280: fc 00 ff ff+ elem_top_hi     .junk   64
a2c0: 95 00 c0 80+ elem_right_lo   .junk   64
a300: f5 00 fc fd+ elem_right_hi   .junk   64
a340: 95 00 00 40+ elem_bottom_lo  .junk   64
a380: fc 00 01 ff+ elem_bottom_hi  .junk   64
                   ; 
                   ; These values are recorded while drawing, so that we can erase the element
                   ; before drawing the next.  Some of these have different meanings for different
                   ; element types.
                   ; 
                   ; Points:
                   ;   a3c0: offset into hi-res page (addr low byte + col)
                   ;   a400: high byte of hi-res page
                   ;   a540: pixel bit mask
                   ; 
                   ; Horizontal lines:
                   ;   a3c0: left edge pixel color offset (0-6,8-14)
                   ;   a400: hi-res column of left edge (0-39)
                   ;   a440: hi-res line address, low byte
                   ;   a480: right edge pixel color offset (0-6,8-14)
                   ;   a4c0: hi-res column of right edge (0-39)
                   ;   a500: hi-res line address, high byte
                   ; 
                   ; Vertical lines and rects:
                   ;   $a3c0: left edge pixel color offset (0-6,8-14)
                   ;   $a400: hi-res column of left edge (0-39)
                   ;   $a440: top coord (0-191)
                   ;   $a480: right edge pixel color offset (0-6,8-14)
                   ;   $a4c0: hi-res column of right edge (0-39)
                   ;   $a500: bottom coord (0-191)
                   ;   $a540: pixel bit mask (vertical line only)
a3c0: b8 3c 06 0b+ elem_erase_0    .junk   64
a400: 2d 22 0c 0d+ elem_erase_1    .junk   64
a440: 00 00 56 56+ elem_erase_2    .junk   64
a480: 00 00 0b 06+ elem_erase_3    .junk   64
a4c0: 00 00 0d 0e+ elem_erase_4    .junk   64
a500: 00 00 6a 59+ elem_erase_5    .junk   64
a540: 90 01 00 00+ elem_erase_6    .junk   64
a580: 00 00 00 00+                 .junk   64
a5c0: 00 00 00 00+                 .junk   64

                   ; 
                   ; Erases a vertical stripe.
                   ; 
                   ; This is generally not called directly.  A lookup table ($5500/b800) converts
                   ; line numbers to addresses, which are then used as an indirect jump (for the
                   ; top) or as a location to store an RTS (for the bottom).
                   ; 
                   ; On entry:
                   ;   X-reg: pixel byte value (adjusted for odd/even)
                   ;   Y-reg: horizontal offset (0-39)
                   ; 
a600: 8a           UnrolledAND     txa
a601: 39 00 20                     and     HIRES_P1,y
a604: 99 00 20                     sta     HIRES_P1,y
a607: 8a                           txa
a608: 39 00 24                     and     HIRES_P1+$400,y
a60b: 99 00 24                     sta     HIRES_P1+$400,y
a60e: 8a                           txa
a60f: 39 00 28                     and     HIRES_P1+$800,y
a612: 99 00 28                     sta     HIRES_P1+$800,y
a615: 8a                           txa
a616: 39 00 2c                     and     HIRES_P1+$c00,y
a619: 99 00 2c                     sta     HIRES_P1+$c00,y
a61c: 8a                           txa
a61d: 39 00 30                     and     HIRES_P1+$1000,y
a620: 99 00 30                     sta     HIRES_P1+$1000,y
a623: 8a                           txa
a624: 39 00 34                     and     HIRES_P1+$1400,y
a627: 99 00 34                     sta     HIRES_P1+$1400,y
a62a: 8a                           txa
a62b: 39 00 38                     and     HIRES_P1+$1800,y
a62e: 99 00 38                     sta     HIRES_P1+$1800,y
a631: 8a                           txa
a632: 39 00 3c                     and     HIRES_P1+$1c00,y
a635: 99 00 3c                     sta     HIRES_P1+$1c00,y
a638: 8a                           txa
a639: 39 80 20                     and     HIRES_P1+128,y
a63c: 99 80 20                     sta     HIRES_P1+128,y
a63f: 8a                           txa
a640: 39 80 24                     and     HIRES_P1+$480,y
a643: 99 80 24                     sta     HIRES_P1+$480,y
a646: 8a                           txa
a647: 39 80 28                     and     HIRES_P1+$880,y
a64a: 99 80 28                     sta     HIRES_P1+$880,y
a64d: 8a                           txa
a64e: 39 80 2c                     and     HIRES_P1+$c80,y
a651: 99 80 2c                     sta     HIRES_P1+$c80,y
a654: 8a                           txa
a655: 39 80 30                     and     HIRES_P1+$1080,y
a658: 99 80 30                     sta     HIRES_P1+$1080,y
a65b: 8a                           txa
a65c: 39 80 34                     and     HIRES_P1+$1480,y
a65f: 99 80 34                     sta     HIRES_P1+$1480,y
a662: 8a                           txa
a663: 39 80 38                     and     HIRES_P1+$1880,y
a666: 99 80 38                     sta     HIRES_P1+$1880,y
a669: 8a                           txa
a66a: 39 80 3c                     and     HIRES_P1+$1c80,y
a66d: 99 80 3c                     sta     HIRES_P1+$1c80,y
a670: 8a                           txa
a671: 39 00 21                     and     HIRES_P1+$100,y
a674: 99 00 21                     sta     HIRES_P1+$100,y
a677: 8a                           txa
a678: 39 00 25                     and     HIRES_P1+$500,y
a67b: 99 00 25                     sta     HIRES_P1+$500,y
a67e: 8a                           txa
a67f: 39 00 29                     and     HIRES_P1+$900,y
a682: 99 00 29                     sta     HIRES_P1+$900,y
a685: 8a                           txa
a686: 39 00 2d                     and     HIRES_P1+$d00,y
a689: 99 00 2d                     sta     HIRES_P1+$d00,y
a68c: 8a                           txa
a68d: 39 00 31                     and     HIRES_P1+$1100,y
a690: 99 00 31                     sta     HIRES_P1+$1100,y
a693: 8a                           txa
a694: 39 00 35                     and     HIRES_P1+$1500,y
a697: 99 00 35                     sta     HIRES_P1+$1500,y
a69a: 8a                           txa
a69b: 39 00 39                     and     HIRES_P1+$1900,y
a69e: 99 00 39                     sta     HIRES_P1+$1900,y
a6a1: 8a                           txa
a6a2: 39 00 3d                     and     HIRES_P1+$1d00,y
a6a5: 99 00 3d                     sta     HIRES_P1+$1d00,y
a6a8: 8a                           txa
a6a9: 39 80 21                     and     HIRES_P1+$180,y
a6ac: 99 80 21                     sta     HIRES_P1+$180,y
a6af: 8a                           txa
a6b0: 39 80 25                     and     HIRES_P1+$580,y
a6b3: 99 80 25                     sta     HIRES_P1+$580,y
a6b6: 8a                           txa
a6b7: 39 80 29                     and     HIRES_P1+$980,y
a6ba: 99 80 29                     sta     HIRES_P1+$980,y
a6bd: 8a                           txa
a6be: 39 80 2d                     and     HIRES_P1+$d80,y
a6c1: 99 80 2d                     sta     HIRES_P1+$d80,y
a6c4: 8a                           txa
a6c5: 39 80 31                     and     HIRES_P1+$1180,y
a6c8: 99 80 31                     sta     HIRES_P1+$1180,y
a6cb: 8a                           txa
a6cc: 39 80 35                     and     HIRES_P1+$1580,y
a6cf: 99 80 35                     sta     HIRES_P1+$1580,y
a6d2: 8a                           txa
a6d3: 39 80 39                     and     HIRES_P1+$1980,y
a6d6: 99 80 39                     sta     HIRES_P1+$1980,y
a6d9: 8a                           txa
a6da: 39 80 3d                     and     HIRES_P1+$1d80,y
a6dd: 99 80 3d                     sta     HIRES_P1+$1d80,y
a6e0: 8a                           txa
a6e1: 39 00 22                     and     HIRES_P1+$200,y
a6e4: 99 00 22                     sta     HIRES_P1+$200,y
a6e7: 8a                           txa
a6e8: 39 00 26                     and     HIRES_P1+$600,y
a6eb: 99 00 26                     sta     HIRES_P1+$600,y
a6ee: 8a                           txa
a6ef: 39 00 2a                     and     HIRES_P1+$a00,y
a6f2: 99 00 2a                     sta     HIRES_P1+$a00,y
a6f5: 8a                           txa
a6f6: 39 00 2e                     and     HIRES_P1+$e00,y
a6f9: 99 00 2e                     sta     HIRES_P1+$e00,y
a6fc: 8a                           txa
a6fd: 39 00 32                     and     HIRES_P1+$1200,y
a700: 99 00 32                     sta     HIRES_P1+$1200,y
a703: 8a                           txa
a704: 39 00 36                     and     HIRES_P1+$1600,y
a707: 99 00 36                     sta     HIRES_P1+$1600,y
a70a: 8a                           txa
a70b: 39 00 3a                     and     HIRES_P1+$1a00,y
a70e: 99 00 3a                     sta     HIRES_P1+$1a00,y
a711: 8a                           txa
a712: 39 00 3e                     and     HIRES_P1+$1e00,y
a715: 99 00 3e                     sta     HIRES_P1+$1e00,y
a718: 8a                           txa
a719: 39 80 22                     and     HIRES_P1+$280,y
a71c: 99 80 22                     sta     HIRES_P1+$280,y
a71f: 8a                           txa
a720: 39 80 26                     and     HIRES_P1+$680,y
a723: 99 80 26                     sta     HIRES_P1+$680,y
a726: 8a                           txa
a727: 39 80 2a                     and     HIRES_P1+$a80,y
a72a: 99 80 2a                     sta     HIRES_P1+$a80,y
a72d: 8a                           txa
a72e: 39 80 2e                     and     HIRES_P1+$e80,y
a731: 99 80 2e                     sta     HIRES_P1+$e80,y
a734: 8a                           txa
a735: 39 80 32                     and     HIRES_P1+$1280,y
a738: 99 80 32                     sta     HIRES_P1+$1280,y
a73b: 8a                           txa
a73c: 39 80 36                     and     HIRES_P1+$1680,y
a73f: 99 80 36                     sta     HIRES_P1+$1680,y
a742: 8a                           txa
a743: 39 80 3a                     and     HIRES_P1+$1a80,y
a746: 99 80 3a                     sta     HIRES_P1+$1a80,y
a749: 8a                           txa
a74a: 39 80 3e                     and     HIRES_P1+$1e80,y
a74d: 99 80 3e                     sta     HIRES_P1+$1e80,y
a750: 8a                           txa
a751: 39 00 23                     and     HIRES_P1+$300,y
a754: 99 00 23                     sta     HIRES_P1+$300,y
a757: 8a                           txa
a758: 39 00 27                     and     HIRES_P1+$700,y
a75b: 99 00 27                     sta     HIRES_P1+$700,y
a75e: 8a                           txa
a75f: 39 00 2b                     and     HIRES_P1+$b00,y
a762: 99 00 2b                     sta     HIRES_P1+$b00,y
a765: 8a                           txa
a766: 39 00 2f                     and     HIRES_P1+$f00,y
a769: 99 00 2f                     sta     HIRES_P1+$f00,y
a76c: 8a                           txa
a76d: 39 00 33                     and     HIRES_P1+$1300,y
a770: 99 00 33                     sta     HIRES_P1+$1300,y
a773: 8a                           txa
a774: 39 00 37                     and     HIRES_P1+$1700,y
a777: 99 00 37                     sta     HIRES_P1+$1700,y
a77a: 8a                           txa
a77b: 39 00 3b                     and     HIRES_P1+$1b00,y
a77e: 99 00 3b                     sta     HIRES_P1+$1b00,y
a781: 8a                           txa
a782: 39 00 3f                     and     HIRES_P1+$1f00,y
a785: 99 00 3f                     sta     HIRES_P1+$1f00,y
a788: 8a                           txa
a789: 39 80 23                     and     HIRES_P1+$380,y
a78c: 99 80 23                     sta     HIRES_P1+$380,y
a78f: 8a                           txa
a790: 39 80 27                     and     HIRES_P1+$780,y
a793: 99 80 27                     sta     HIRES_P1+$780,y
a796: 8a                           txa
a797: 39 80 2b                     and     HIRES_P1+$b80,y
a79a: 99 80 2b                     sta     HIRES_P1+$b80,y
a79d: 8a                           txa
a79e: 39 80 2f                     and     HIRES_P1+$f80,y
a7a1: 99 80 2f                     sta     HIRES_P1+$f80,y
a7a4: 8a                           txa
a7a5: 39 80 33                     and     HIRES_P1+$1380,y
a7a8: 99 80 33                     sta     HIRES_P1+$1380,y
a7ab: 8a                           txa
a7ac: 39 80 37                     and     HIRES_P1+$1780,y
a7af: 99 80 37                     sta     HIRES_P1+$1780,y
a7b2: 8a                           txa
a7b3: 39 80 3b                     and     HIRES_P1+$1b80,y
a7b6: 99 80 3b                     sta     HIRES_P1+$1b80,y
a7b9: 8a                           txa
a7ba: 39 80 3f                     and     HIRES_P1+$1f80,y
a7bd: 99 80 3f                     sta     HIRES_P1+$1f80,y
a7c0: 8a                           txa
a7c1: 39 28 20                     and     HIRES_P1+40,y
a7c4: 99 28 20                     sta     HIRES_P1+40,y
a7c7: 8a                           txa
a7c8: 39 28 24                     and     HIRES_P1+$428,y
a7cb: 99 28 24                     sta     HIRES_P1+$428,y
a7ce: 8a                           txa
a7cf: 39 28 28                     and     HIRES_P1+$828,y
a7d2: 99 28 28                     sta     HIRES_P1+$828,y
a7d5: 8a                           txa
a7d6: 39 28 2c                     and     HIRES_P1+$c28,y
a7d9: 99 28 2c                     sta     HIRES_P1+$c28,y
a7dc: 8a                           txa
a7dd: 39 28 30                     and     HIRES_P1+$1028,y
a7e0: 99 28 30                     sta     HIRES_P1+$1028,y
a7e3: 8a                           txa
a7e4: 39 28 34                     and     HIRES_P1+$1428,y
a7e7: 99 28 34                     sta     HIRES_P1+$1428,y
a7ea: 8a                           txa
a7eb: 39 28 38                     and     HIRES_P1+$1828,y
a7ee: 99 28 38                     sta     HIRES_P1+$1828,y
a7f1: 8a                           txa
a7f2: 39 28 3c                     and     HIRES_P1+$1c28,y
a7f5: 99 28 3c                     sta     HIRES_P1+$1c28,y
a7f8: 8a                           txa
a7f9: 39 a8 20                     and     HIRES_P1+168,y
a7fc: 99 a8 20                     sta     HIRES_P1+168,y
a7ff: 8a                           txa
a800: 39 a8 24                     and     HIRES_P1+$4a8,y
a803: 99 a8 24                     sta     HIRES_P1+$4a8,y
a806: 8a                           txa
a807: 39 a8 28                     and     HIRES_P1+$8a8,y
a80a: 99 a8 28                     sta     HIRES_P1+$8a8,y
a80d: 8a                           txa
a80e: 39 a8 2c                     and     HIRES_P1+$ca8,y
a811: 99 a8 2c                     sta     HIRES_P1+$ca8,y
a814: 8a                           txa
a815: 39 a8 30                     and     HIRES_P1+$10a8,y
a818: 99 a8 30                     sta     HIRES_P1+$10a8,y
a81b: 8a                           txa
a81c: 39 a8 34                     and     HIRES_P1+$14a8,y
a81f: 99 a8 34                     sta     HIRES_P1+$14a8,y
a822: 8a                           txa
a823: 39 a8 38                     and     HIRES_P1+$18a8,y
a826: 99 a8 38                     sta     HIRES_P1+$18a8,y
a829: 8a                           txa
a82a: 39 a8 3c                     and     HIRES_P1+$1ca8,y
a82d: 99 a8 3c                     sta     HIRES_P1+$1ca8,y
a830: 8a                           txa
a831: 39 28 21                     and     HIRES_P1+$128,y
a834: 99 28 21                     sta     HIRES_P1+$128,y
a837: 8a                           txa
a838: 39 28 25                     and     HIRES_P1+$528,y
a83b: 99 28 25                     sta     HIRES_P1+$528,y
a83e: 8a                           txa
a83f: 39 28 29                     and     HIRES_P1+$928,y
a842: 99 28 29                     sta     HIRES_P1+$928,y
a845: 8a                           txa
a846: 39 28 2d                     and     HIRES_P1+$d28,y
a849: 99 28 2d                     sta     HIRES_P1+$d28,y
a84c: 8a                           txa
a84d: 39 28 31                     and     HIRES_P1+$1128,y
a850: 99 28 31                     sta     HIRES_P1+$1128,y
a853: 8a                           txa
a854: 39 28 35                     and     HIRES_P1+$1528,y
a857: 99 28 35                     sta     HIRES_P1+$1528,y
a85a: 8a                           txa
a85b: 39 28 39                     and     HIRES_P1+$1928,y
a85e: 99 28 39                     sta     HIRES_P1+$1928,y
a861: 8a           AndSeq_87       txa
a862: 39 28 3d                     and     HIRES_P1+$1d28,y  ;line 87
a865: 99 28 3d                     sta     HIRES_P1+$1d28,y
a868: 8a                           txa
a869: 39 a8 21                     and     HIRES_P1+$1a8,y
a86c: 99 a8 21                     sta     HIRES_P1+$1a8,y
a86f: 8a                           txa
a870: 39 a8 25                     and     HIRES_P1+$5a8,y
a873: 99 a8 25                     sta     HIRES_P1+$5a8,y
a876: 8a           AndSeq_90       txa
a877: 39 a8 29                     and     HIRES_P1+$9a8,y   ;line 90
a87a: 99 a8 29                     sta     HIRES_P1+$9a8,y
a87d: 8a                           txa
a87e: 39 a8 2d                     and     HIRES_P1+$da8,y
a881: 99 a8 2d                     sta     HIRES_P1+$da8,y
a884: 8a                           txa
a885: 39 a8 31                     and     HIRES_P1+$11a8,y
a888: 99 a8 31                     sta     HIRES_P1+$11a8,y
a88b: 8a                           txa
a88c: 39 a8 35                     and     HIRES_P1+$15a8,y
a88f: 99 a8 35                     sta     HIRES_P1+$15a8,y
a892: 8a                           txa
a893: 39 a8 39                     and     HIRES_P1+$19a8,y
a896: 99 a8 39                     sta     HIRES_P1+$19a8,y
a899: 8a                           txa
a89a: 39 a8 3d                     and     HIRES_P1+$1da8,y
a89d: 99 a8 3d                     sta     HIRES_P1+$1da8,y
a8a0: 8a                           txa
a8a1: 39 28 22                     and     HIRES_P1+$228,y
a8a4: 99 28 22                     sta     HIRES_P1+$228,y
a8a7: 8a                           txa
a8a8: 39 28 26                     and     HIRES_P1+$628,y
a8ab: 99 28 26                     sta     HIRES_P1+$628,y
a8ae: 8a                           txa
a8af: 39 28 2a                     and     HIRES_P1+$a28,y
a8b2: 99 28 2a                     sta     HIRES_P1+$a28,y
a8b5: 8a                           txa
a8b6: 39 28 2e                     and     HIRES_P1+$e28,y
a8b9: 99 28 2e                     sta     HIRES_P1+$e28,y
a8bc: 8a                           txa
a8bd: 39 28 32                     and     HIRES_P1+$1228,y
a8c0: 99 28 32                     sta     HIRES_P1+$1228,y
a8c3: 8a                           txa
a8c4: 39 28 36                     and     HIRES_P1+$1628,y
a8c7: 99 28 36                     sta     HIRES_P1+$1628,y
a8ca: 8a                           txa
a8cb: 39 28 3a                     and     HIRES_P1+$1a28,y
a8ce: 99 28 3a                     sta     HIRES_P1+$1a28,y
a8d1: 8a                           txa
a8d2: 39 28 3e                     and     HIRES_P1+$1e28,y
a8d5: 99 28 3e                     sta     HIRES_P1+$1e28,y
a8d8: 8a                           txa
a8d9: 39 a8 22                     and     HIRES_P1+$2a8,y
a8dc: 99 a8 22                     sta     HIRES_P1+$2a8,y
a8df: 8a                           txa
a8e0: 39 a8 26                     and     HIRES_P1+$6a8,y
a8e3: 99 a8 26                     sta     HIRES_P1+$6a8,y
a8e6: 8a                           txa
a8e7: 39 a8 2a                     and     HIRES_P1+$aa8,y
a8ea: 99 a8 2a                     sta     HIRES_P1+$aa8,y
a8ed: 8a                           txa
a8ee: 39 a8 2e                     and     HIRES_P1+$ea8,y
a8f1: 99 a8 2e                     sta     HIRES_P1+$ea8,y
a8f4: 8a                           txa
a8f5: 39 a8 32                     and     HIRES_P1+$12a8,y
a8f8: 99 a8 32                     sta     HIRES_P1+$12a8,y
a8fb: 8a                           txa
a8fc: 39 a8 36                     and     HIRES_P1+$16a8,y
a8ff: 99 a8 36                     sta     HIRES_P1+$16a8,y
a902: 8a                           txa
a903: 39 a8 3a                     and     HIRES_P1+$1aa8,y
a906: 99 a8 3a                     sta     HIRES_P1+$1aa8,y
a909: 8a                           txa
a90a: 39 a8 3e                     and     HIRES_P1+$1ea8,y
a90d: 99 a8 3e                     sta     HIRES_P1+$1ea8,y
a910: 8a                           txa
a911: 39 28 23                     and     HIRES_P1+$328,y
a914: 99 28 23                     sta     HIRES_P1+$328,y
a917: 8a                           txa
a918: 39 28 27                     and     HIRES_P1+$728,y
a91b: 99 28 27                     sta     HIRES_P1+$728,y
a91e: 8a                           txa
a91f: 39 28 2b                     and     HIRES_P1+$b28,y
a922: 99 28 2b                     sta     HIRES_P1+$b28,y
a925: 8a                           txa
a926: 39 28 2f                     and     HIRES_P1+$f28,y
a929: 99 28 2f                     sta     HIRES_P1+$f28,y
a92c: 8a                           txa
a92d: 39 28 33                     and     HIRES_P1+$1328,y
a930: 99 28 33                     sta     HIRES_P1+$1328,y
a933: 8a                           txa
a934: 39 28 37                     and     HIRES_P1+$1728,y
a937: 99 28 37                     sta     HIRES_P1+$1728,y
a93a: 8a                           txa
a93b: 39 28 3b                     and     HIRES_P1+$1b28,y
a93e: 99 28 3b                     sta     HIRES_P1+$1b28,y
a941: 8a                           txa
a942: 39 28 3f                     and     HIRES_P1+$1f28,y
a945: 99 28 3f                     sta     HIRES_P1+$1f28,y
a948: 8a                           txa
a949: 39 a8 23                     and     HIRES_P1+$3a8,y
a94c: 99 a8 23                     sta     HIRES_P1+$3a8,y
a94f: 8a                           txa
a950: 39 a8 27                     and     HIRES_P1+$7a8,y
a953: 99 a8 27                     sta     HIRES_P1+$7a8,y
a956: 8a                           txa
a957: 39 a8 2b                     and     HIRES_P1+$ba8,y
a95a: 99 a8 2b                     sta     HIRES_P1+$ba8,y
a95d: 8a                           txa
a95e: 39 a8 2f                     and     HIRES_P1+$fa8,y
a961: 99 a8 2f                     sta     HIRES_P1+$fa8,y   ;line 123
a964: 8a                           txa
a965: 39 a8 33                     and     HIRES_P1+$13a8,y
a968: 99 a8 33                     sta     HIRES_P1+$13a8,y
a96b: 8a                           txa
a96c: 39 a8 37                     and     HIRES_P1+$17a8,y
a96f: 99 a8 37                     sta     HIRES_P1+$17a8,y
a972: 8a                           txa
a973: 39 a8 3b                     and     HIRES_P1+$1ba8,y
a976: 99 a8 3b                     sta     HIRES_P1+$1ba8,y
a979: 8a                           txa
a97a: 39 a8 3f                     and     HIRES_P1+$1fa8,y
a97d: 99 a8 3f                     sta     HIRES_P1+$1fa8,y
a980: 8a                           txa
a981: 39 50 20                     and     HIRES_P1+80,y
a984: 99 50 20                     sta     HIRES_P1+80,y
a987: 8a                           txa
a988: 39 50 24                     and     HIRES_P1+$450,y
a98b: 99 50 24                     sta     HIRES_P1+$450,y
a98e: 8a                           txa
a98f: 39 50 28                     and     HIRES_P1+$850,y
a992: 99 50 28                     sta     HIRES_P1+$850,y
a995: 8a                           txa
a996: 39 50 2c                     and     HIRES_P1+$c50,y
a999: 99 50 2c                     sta     HIRES_P1+$c50,y
a99c: 8a                           txa
a99d: 39 50 30                     and     HIRES_P1+$1050,y
a9a0: 99 50 30                     sta     HIRES_P1+$1050,y
a9a3: 8a                           txa
a9a4: 39 50 34                     and     HIRES_P1+$1450,y
a9a7: 99 50 34                     sta     HIRES_P1+$1450,y
a9aa: 8a                           txa
a9ab: 39 50 38                     and     HIRES_P1+$1850,y
a9ae: 99 50 38                     sta     HIRES_P1+$1850,y
a9b1: 8a                           txa
a9b2: 39 50 3c                     and     HIRES_P1+$1c50,y
a9b5: 99 50 3c                     sta     HIRES_P1+$1c50,y
a9b8: 8a                           txa
a9b9: 39 d0 20                     and     HIRES_P1+208,y
a9bc: 99 d0 20                     sta     HIRES_P1+208,y
a9bf: 8a                           txa
a9c0: 39 d0 24                     and     HIRES_P1+$4d0,y
a9c3: 99 d0 24                     sta     HIRES_P1+$4d0,y
a9c6: 8a                           txa
a9c7: 39 d0 28                     and     HIRES_P1+$8d0,y
a9ca: 99 d0 28                     sta     HIRES_P1+$8d0,y
a9cd: 8a                           txa
a9ce: 39 d0 2c                     and     HIRES_P1+$cd0,y
a9d1: 99 d0 2c                     sta     HIRES_P1+$cd0,y
a9d4: 8a                           txa
a9d5: 39 d0 30                     and     HIRES_P1+$10d0,y
a9d8: 99 d0 30                     sta     HIRES_P1+$10d0,y
a9db: 8a                           txa
a9dc: 39 d0 34                     and     HIRES_P1+$14d0,y
a9df: 99 d0 34                     sta     HIRES_P1+$14d0,y
a9e2: 8a                           txa
a9e3: 39 d0 38                     and     HIRES_P1+$18d0,y
a9e6: 99 d0 38                     sta     HIRES_P1+$18d0,y
a9e9: 8a                           txa
a9ea: 39 d0 3c                     and     HIRES_P1+$1cd0,y
a9ed: 99 d0 3c                     sta     HIRES_P1+$1cd0,y
a9f0: 8a                           txa
a9f1: 39 50 21                     and     HIRES_P1+$150,y
a9f4: 99 50 21                     sta     HIRES_P1+$150,y
a9f7: 8a                           txa
a9f8: 39 50 25                     and     HIRES_P1+$550,y
a9fb: 99 50 25                     sta     HIRES_P1+$550,y
a9fe: 8a                           txa
a9ff: 39 50 29                     and     HIRES_P1+$950,y
aa02: 99 50 29                     sta     HIRES_P1+$950,y
aa05: 8a                           txa
aa06: 39 50 2d                     and     HIRES_P1+$d50,y
aa09: 99 50 2d                     sta     HIRES_P1+$d50,y
aa0c: 8a                           txa
aa0d: 39 50 31                     and     HIRES_P1+$1150,y
aa10: 99 50 31                     sta     HIRES_P1+$1150,y
aa13: 8a                           txa
aa14: 39 50 35                     and     HIRES_P1+$1550,y
aa17: 99 50 35                     sta     HIRES_P1+$1550,y
aa1a: 8a                           txa
aa1b: 39 50 39                     and     HIRES_P1+$1950,y
aa1e: 99 50 39                     sta     HIRES_P1+$1950,y
aa21: 8a                           txa
aa22: 39 50 3d                     and     HIRES_P1+$1d50,y
aa25: 99 50 3d                     sta     HIRES_P1+$1d50,y
aa28: 8a                           txa
aa29: 39 d0 21                     and     HIRES_P1+$1d0,y
aa2c: 99 d0 21                     sta     HIRES_P1+$1d0,y
aa2f: 8a                           txa
aa30: 39 d0 25                     and     HIRES_P1+$5d0,y
aa33: 99 d0 25                     sta     HIRES_P1+$5d0,y
aa36: 8a                           txa
aa37: 39 d0 29                     and     HIRES_P1+$9d0,y
aa3a: 99 d0 29                     sta     HIRES_P1+$9d0,y
aa3d: 8a                           txa
aa3e: 39 d0 2d                     and     HIRES_P1+$dd0,y
aa41: 99 d0 2d                     sta     HIRES_P1+$dd0,y
aa44: 8a                           txa
aa45: 39 d0 31                     and     HIRES_P1+$11d0,y
aa48: 99 d0 31                     sta     HIRES_P1+$11d0,y
aa4b: 8a                           txa
aa4c: 39 d0 35                     and     HIRES_P1+$15d0,y
aa4f: 99 d0 35                     sta     HIRES_P1+$15d0,y
aa52: 8a                           txa
aa53: 39 d0 39                     and     HIRES_P1+$19d0,y
aa56: 99 d0 39                     sta     HIRES_P1+$19d0,y
aa59: 8a                           txa
aa5a: 39 d0 3d                     and     HIRES_P1+$1dd0,y
aa5d: 99 d0 3d                     sta     HIRES_P1+$1dd0,y
aa60: 8a                           txa
aa61: 39 50 22                     and     HIRES_P1+$250,y
aa64: 99 50 22                     sta     HIRES_P1+$250,y
aa67: 8a                           txa
aa68: 39 50 26                     and     HIRES_P1+$650,y
aa6b: 99 50 26                     sta     HIRES_P1+$650,y
aa6e: 8a                           txa
aa6f: 39 50 2a                     and     HIRES_P1+$a50,y
aa72: 99 50 2a                     sta     HIRES_P1+$a50,y
aa75: 8a                           txa
aa76: 39 50 2e                     and     HIRES_P1+$e50,y
aa79: 99 50 2e                     sta     HIRES_P1+$e50,y
aa7c: 8a                           txa
aa7d: 39 50 32                     and     HIRES_P1+$1250,y
aa80: 99 50 32                     sta     HIRES_P1+$1250,y
aa83: 8a                           txa
aa84: 39 50 36                     and     HIRES_P1+$1650,y
aa87: 99 50 36                     sta     HIRES_P1+$1650,y
aa8a: 8a                           txa
aa8b: 39 50 3a                     and     HIRES_P1+$1a50,y
aa8e: 99 50 3a                     sta     HIRES_P1+$1a50,y
aa91: 8a                           txa
aa92: 39 50 3e                     and     HIRES_P1+$1e50,y
aa95: 99 50 3e                     sta     HIRES_P1+$1e50,y
aa98: 8a                           txa
aa99: 39 d0 22                     and     HIRES_P1+$2d0,y
aa9c: 99 d0 22                     sta     HIRES_P1+$2d0,y
aa9f: 8a                           txa
aaa0: 39 d0 26                     and     HIRES_P1+$6d0,y
aaa3: 99 d0 26                     sta     HIRES_P1+$6d0,y
aaa6: 8a                           txa
aaa7: 39 d0 2a                     and     HIRES_P1+$ad0,y
aaaa: 99 d0 2a                     sta     HIRES_P1+$ad0,y
aaad: 8a                           txa
aaae: 39 d0 2e                     and     HIRES_P1+$ed0,y
aab1: 99 d0 2e                     sta     HIRES_P1+$ed0,y
aab4: 8a                           txa
aab5: 39 d0 32                     and     HIRES_P1+$12d0,y
aab8: 99 d0 32                     sta     HIRES_P1+$12d0,y
aabb: 8a                           txa
aabc: 39 d0 36                     and     HIRES_P1+$16d0,y
aabf: 99 d0 36                     sta     HIRES_P1+$16d0,y
aac2: 8a                           txa
aac3: 39 d0 3a                     and     HIRES_P1+$1ad0,y
aac6: 99 d0 3a                     sta     HIRES_P1+$1ad0,y
aac9: 8a                           txa
aaca: 39 d0 3e                     and     HIRES_P1+$1ed0,y
aacd: 99 d0 3e                     sta     HIRES_P1+$1ed0,y
aad0: 8a                           txa
aad1: 39 50 23                     and     HIRES_P1+$350,y
aad4: 99 50 23                     sta     HIRES_P1+$350,y
aad7: 8a                           txa
aad8: 39 50 27                     and     HIRES_P1+$750,y
aadb: 99 50 27                     sta     HIRES_P1+$750,y
aade: 8a                           txa
aadf: 39 50 2b                     and     HIRES_P1+$b50,y
aae2: 99 50 2b                     sta     HIRES_P1+$b50,y
aae5: 8a                           txa
aae6: 39 50 2f                     and     HIRES_P1+$f50,y
aae9: 99 50 2f                     sta     HIRES_P1+$f50,y
aaec: 8a                           txa
aaed: 39 50 33                     and     HIRES_P1+$1350,y
aaf0: 99 50 33                     sta     HIRES_P1+$1350,y
aaf3: 8a                           txa
aaf4: 39 50 37                     and     HIRES_P1+$1750,y
aaf7: 99 50 37                     sta     HIRES_P1+$1750,y
aafa: 8a                           txa
aafb: 39 50 3b                     and     HIRES_P1+$1b50,y
aafe: 99 50 3b                     sta     HIRES_P1+$1b50,y
ab01: 8a                           txa
ab02: 39 50 3f                     and     HIRES_P1+$1f50,y
ab05: 99 50 3f                     sta     HIRES_P1+$1f50,y
ab08: 8a                           txa
ab09: 39 d0 23                     and     HIRES_P1+$3d0,y
ab0c: 99 d0 23                     sta     HIRES_P1+$3d0,y
ab0f: 8a                           txa
ab10: 39 d0 27                     and     HIRES_P1+$7d0,y
ab13: 99 d0 27                     sta     HIRES_P1+$7d0,y
ab16: 8a                           txa
ab17: 39 d0 2b                     and     HIRES_P1+$bd0,y
ab1a: 99 d0 2b                     sta     HIRES_P1+$bd0,y
ab1d: 8a                           txa
ab1e: 39 d0 2f                     and     HIRES_P1+$fd0,y
ab21: 99 d0 2f                     sta     HIRES_P1+$fd0,y
ab24: 8a                           txa
ab25: 39 d0 33                     and     HIRES_P1+$13d0,y
ab28: 99 d0 33                     sta     HIRES_P1+$13d0,y
ab2b: 8a                           txa
ab2c: 39 d0 37                     and     HIRES_P1+$17d0,y
ab2f: 99 d0 37                     sta     HIRES_P1+$17d0,y
ab32: 8a                           txa
ab33: 39 d0 3b                     and     HIRES_P1+$1bd0,y
ab36: 99 d0 3b                     sta     HIRES_P1+$1bd0,y
ab39: 8a                           txa
ab3a: 39 d0 3f                     and     HIRES_P1+$1fd0,y
ab3d: 99 d0 3f                     sta     HIRES_P1+$1fd0,y
ab40: 60                           rts

ab41: 60 a0 20 99+                 .align  $0100 (191 bytes)
                   ; 
                   ; Math table #2, maps ? to ?.  The result is generally used as an index into
                   ; math table #1 (at $1000).
                   ; 
                   ; This is indexed with a 16-bit value that is effectively reduced to 11 bits. 
                   ; For example, if we want to retrieve a value for %00001ABC DEFGHIJKL, we count
                   ; the leading zeroes (4), use that to create an AND mask (%11110000) that is
                   ; applied to the low byte, and then we OR the bytes together (DEFG1ABC).  The
                   ; count of leading zeroes (0-8) is used as an index into the 9 256-byte pages
                   ; that follow.
                   ; 
                   ; The situation where the high byte is zero is special-cased in the code.
                   ; 
                   ; The general effect is of decreasing precision as the values get larger.
                   ; 
                   ; It might seem that parts of the table will go unused, e.g. the page for lz=6
                   ; handles $02xx and $03xx, so only entries whose indices end with %10 or %11
                   ; will be accessed.  In practice, the leading-zero count may be established for
                   ; the Z coordinate, and then lookups performed for the X/Y coordinates, so the
                   ; full range of values is possible.
ac00: 00 01 02 03+ math_tab2_base? .bulk   $00,$01,$02,$03,$04,$05,$06,$07,$08,$09,$0a,$0b,$0c,$0d,$0e,$0f
                                    +      $10,$11,$12,$13,$14,$15,$16,$17,$18,$19,$1a,$1b,$1c,$1d,$1e,$1f
                                    +      $20,$21,$22,$23,$24,$25,$26,$27,$28,$29,$2a,$2b,$2c,$2d,$2e,$2f
                                    +      $30,$31,$32,$33,$34,$35,$36,$37,$38,$39,$3a,$3b,$3c,$3d,$3e,$3f
                                    +      $40,$41,$42,$43,$44,$45,$46,$47,$48,$49,$4a,$4b,$4c,$4d,$4e,$4f
                                    +      $50,$51,$52,$53,$54,$55,$56,$57,$58,$59,$5a,$5b,$5c,$5d,$5e,$5f
                                    +      $60,$61,$62,$63,$64,$65,$66,$67,$68,$69,$6a,$6b,$6c,$6d,$6e,$6f
                                    +      $70,$71,$72,$73,$74,$75,$76,$77,$78,$79,$7a,$7b,$7c,$7d,$7e,$7f
                                    +      $80,$81,$82,$83,$84,$85,$86,$87,$88,$89,$8a,$8b,$8c,$8d,$8e,$8f
                                    +      $90,$91,$92,$93,$94,$95,$96,$97,$98,$99,$9a,$9b,$9c,$9d,$9e,$9f
                                    +      $a0,$a1,$a2,$a3,$a4,$a5,$a6,$a7,$a8,$a9,$aa,$ab,$ac,$ad,$ae,$af
                                    +      $b0,$b1,$b2,$b3,$b4,$b5,$b6,$b7,$b8,$b9,$ba,$bb,$bc,$bd,$be,$bf
                                    +      $c0,$c1,$c2,$c3,$c4,$c5,$c6,$c7,$c8,$c9,$ca,$cb,$cc,$cd,$ce,$cf
                                    +      $d0,$d1,$d2,$d3,$d4,$d5,$d6,$d7,$d8,$d9,$da,$db,$dc,$dd,$de,$df
                                    +      $e0,$e1,$e2,$e3,$e4,$e5,$e6,$e7,$e8,$e9,$ea,$eb,$ec,$ed,$ee,$ef
                                    +      $f0,$f1,$f2,$f3,$f4,$f5,$f6,$f7,$f8,$f9,$fa,$fb,$fc,$fd,$fe,$ff
ad00: 00 02 04 06+                 .bulk   $00,$02,$04,$06,$08,$0a,$0c,$0e,$10,$12,$14,$16,$18,$1a,$1c,$1e
                                    +      $20,$22,$24,$26,$28,$2a,$2c,$2e,$30,$32,$34,$36,$38,$3a,$3c,$3e
                                    +      $40,$42,$44,$46,$48,$4a,$4c,$4e,$50,$52,$54,$56,$58,$5a,$5c,$5e
                                    +      $60,$62,$64,$66,$68,$6a,$6c,$6e,$70,$72,$74,$76,$78,$7a,$7c,$7e
                                    +      $80,$82,$84,$86,$88,$8a,$8c,$8e,$90,$92,$94,$96,$98,$9a,$9c,$9e
                                    +      $a0,$a2,$a4,$a6,$a8,$aa,$ac,$ae,$b0,$b2,$b4,$b6,$b8,$ba,$bc,$be
                                    +      $c0,$c2,$c4,$c6,$c8,$ca,$cc,$ce,$d0,$d2,$d4,$d6,$d8,$da,$dc,$de
                                    +      $e0,$e2,$e4,$e6,$e8,$ea,$ec,$ee,$f0,$f2,$f4,$f6,$f8,$fa,$fc,$fe
                                    +      $01,$03,$05,$07,$09,$0b,$0d,$0f,$11,$13,$15,$17,$19,$1b,$1d,$1f
                                    +      $21,$23,$25,$27,$29,$2b,$2d,$2f,$31,$33,$35,$37,$39,$3b,$3d,$3f
                                    +      $41,$43,$45,$47,$49,$4b,$4d,$4f,$51,$53,$55,$57,$59,$5b,$5d,$5f
                                    +      $61,$63,$65,$67,$69,$6b,$6d,$6f,$71,$73,$75,$77,$79,$7b,$7d,$7f
                                    +      $81,$83,$85,$87,$89,$8b,$8d,$8f,$91,$93,$95,$97,$99,$9b,$9d,$9f
                                    +      $a1,$a3,$a5,$a7,$a9,$ab,$ad,$af,$b1,$b3,$b5,$b7,$b9,$bb,$bd,$bf
                                    +      $c1,$c3,$c5,$c7,$c9,$cb,$cd,$cf,$d1,$d3,$d5,$d7,$d9,$db,$dd,$df
                                    +      $e1,$e3,$e5,$e7,$e9,$eb,$ed,$ef,$f1,$f3,$f5,$f7,$f9,$fb,$fd,$ff
ae00: 00 04 08 0c+                 .bulk   $00,$04,$08,$0c,$10,$14,$18,$1c,$20,$24,$28,$2c,$30,$34,$38,$3c
                                    +      $40,$44,$48,$4c,$50,$54,$58,$5c,$60,$64,$68,$6c,$70,$74,$78,$7c
                                    +      $80,$84,$88,$8c,$90,$94,$98,$9c,$a0,$a4,$a8,$ac,$b0,$b4,$b8,$bc
                                    +      $c0,$c4,$c8,$cc,$d0,$d4,$d8,$dc,$e0,$e4,$e8,$ec,$f0,$f4,$f8,$fc
                                    +      $01,$05,$09,$0d,$11,$15,$19,$1d,$21,$25,$29,$2d,$31,$35,$39,$3d
                                    +      $41,$45,$49,$4d,$51,$55,$59,$5d,$61,$65,$69,$6d,$71,$75,$79,$7d
                                    +      $81,$85,$89,$8d,$91,$95,$99,$9d,$a1,$a5,$a9,$ad,$b1,$b5,$b9,$bd
                                    +      $c1,$c5,$c9,$cd,$d1,$d5,$d9,$dd,$e1,$e5,$e9,$ed,$f1,$f5,$f9,$fd
                                    +      $02,$06,$0a,$0e,$12,$16,$1a,$1e,$22,$26,$2a,$2e,$32,$36,$3a,$3e
                                    +      $42,$46,$4a,$4e,$52,$56,$5a,$5e,$62,$66,$6a,$6e,$72,$76,$7a,$7e
                                    +      $82,$86,$8a,$8e,$92,$96,$9a,$9e,$a2,$a6,$aa,$ae,$b2,$b6,$ba,$be
                                    +      $c2,$c6,$ca,$ce,$d2,$d6,$da,$de,$e2,$e6,$ea,$ee,$f2,$f6,$fa,$fe
                                    +      $03,$07,$0b,$0f,$13,$17,$1b,$1f,$23,$27,$2b,$2f,$33,$37,$3b,$3f
                                    +      $43,$47,$4b,$4f,$53,$57,$5b,$5f,$63,$67,$6b,$6f,$73,$77,$7b,$7f
                                    +      $83,$87,$8b,$8f,$93,$97,$9b,$9f,$a3,$a7,$ab,$af,$b3,$b7,$bb,$bf
                                    +      $c3,$c7,$cb,$cf,$d3,$d7,$db,$df,$e3,$e7,$eb,$ef,$f3,$f7,$fb,$ff
af00: 00 08 10 18+                 .bulk   $00,$08,$10,$18,$20,$28,$30,$38,$40,$48,$50,$58,$60,$68,$70,$78
                                    +      $80,$88,$90,$98,$a0,$a8,$b0,$b8,$c0,$c8,$d0,$d8,$e0,$e8,$f0,$f8
                                    +      $01,$09,$11,$19,$21,$29,$31,$39,$41,$49,$51,$59,$61,$69,$71,$79
                                    +      $81,$89,$91,$99,$a1,$a9,$b1,$b9,$c1,$c9,$d1,$d9,$e1,$e9,$f1,$f9
                                    +      $02,$0a,$12,$1a,$22,$2a,$32,$3a,$42,$4a,$52,$5a,$62,$6a,$72,$7a
                                    +      $82,$8a,$92,$9a,$a2,$aa,$b2,$ba,$c2,$ca,$d2,$da,$e2,$ea,$f2,$fa
                                    +      $03,$0b,$13,$1b,$23,$2b,$33,$3b,$43,$4b,$53,$5b,$63,$6b,$73,$7b
                                    +      $83,$8b,$93,$9b,$a3,$ab,$b3,$bb,$c3,$cb,$d3,$db,$e3,$eb,$f3,$fb
                                    +      $04,$0c,$14,$1c,$24,$2c,$34,$3c,$44,$4c,$54,$5c,$64,$6c,$74,$7c
                                    +      $84,$8c,$94,$9c,$a4,$ac,$b4,$bc,$c4,$cc,$d4,$dc,$e4,$ec,$f4,$fc
                                    +      $05,$0d,$15,$1d,$25,$2d,$35,$3d,$45,$4d,$55,$5d,$65,$6d,$75,$7d
                                    +      $85,$8d,$95,$9d,$a5,$ad,$b5,$bd,$c5,$cd,$d5,$dd,$e5,$ed,$f5,$fd
                                    +      $06,$0e,$16,$1e,$26,$2e,$36,$3e,$46,$4e,$56,$5e,$66,$6e,$76,$7e
                                    +      $86,$8e,$96,$9e,$a6,$ae,$b6,$be,$c6,$ce,$d6,$de,$e6,$ee,$f6,$fe
                                    +      $07,$0f,$17,$1f,$27,$2f,$37,$3f,$47,$4f,$57,$5f,$67,$6f,$77,$7f
                                    +      $87,$8f,$97,$9f,$a7,$af,$b7,$bf,$c7,$cf,$d7,$df,$e7,$ef,$f7,$ff
b000: 00 10 20 30+ speed_table?    .bulk   $00,$10,$20,$30,$40,$50,$60,$70,$80,$90,$a0,$b0,$c0,$d0,$e0,$f0
                                    +      $01,$11,$21,$31,$41,$51,$61,$71,$81,$91,$a1,$b1,$c1,$d1,$e1,$f1
                                    +      $02,$12,$22,$32,$42,$52,$62,$72,$82,$92,$a2,$b2,$c2,$d2,$e2,$f2
                                    +      $03,$13,$23,$33,$43,$53,$63,$73,$83,$93,$a3,$b3,$c3,$d3,$e3,$f3
                                    +      $04,$14,$24,$34,$44,$54,$64,$74,$84,$94,$a4,$b4,$c4,$d4,$e4,$f4
                                    +      $05,$15,$25,$35,$45,$55,$65,$75,$85,$95,$a5,$b5,$c5,$d5,$e5,$f5
                                    +      $06,$16,$26,$36,$46,$56,$66,$76,$86,$96,$a6,$b6,$c6,$d6,$e6,$f6
                                    +      $07,$17,$27,$37,$47,$57,$67,$77,$87,$97,$a7,$b7,$c7,$d7,$e7,$f7
                                    +      $08,$18,$28,$38,$48,$58,$68,$78,$88,$98,$a8,$b8,$c8,$d8,$e8,$f8
                                    +      $09,$19,$29,$39,$49,$59,$69,$79,$89,$99,$a9,$b9,$c9,$d9,$e9,$f9
                                    +      $0a,$1a,$2a,$3a,$4a,$5a,$6a,$7a,$8a,$9a,$aa,$ba,$ca,$da,$ea,$fa
                                    +      $0b,$1b,$2b,$3b,$4b,$5b,$6b,$7b,$8b,$9b,$ab,$bb,$cb,$db,$eb,$fb
                                    +      $0c,$1c,$2c,$3c,$4c,$5c,$6c,$7c,$8c,$9c,$ac,$bc,$cc,$dc,$ec,$fc
                                    +      $0d,$1d,$2d,$3d,$4d,$5d,$6d,$7d,$8d,$9d,$ad,$bd,$cd,$dd,$ed,$fd
                                    +      $0e,$1e,$2e,$3e,$4e,$5e,$6e,$7e,$8e,$9e,$ae,$be,$ce,$de,$ee,$fe
                                    +      $0f,$1f,$2f,$3f,$4f,$5f,$6f,$7f,$8f,$9f,$af,$bf,$cf,$df,$ef,$ff
b100: 00 20 40 60+                 .bulk   $00,$20,$40,$60,$80,$a0,$c0,$e0,$01,$21,$41,$61,$81,$a1,$c1,$e1
                                    +      $02,$22,$42,$62,$82,$a2,$c2,$e2,$03,$23,$43,$63,$83,$a3,$c3,$e3
                                    +      $04,$24,$44,$64,$84,$a4,$c4,$e4,$05,$25,$45,$65,$85,$a5,$c5,$e5
                                    +      $06,$26,$46,$66,$86,$a6,$c6,$e6,$07,$27,$47,$67,$87,$a7,$c7,$e7
                                    +      $08,$28,$48,$68,$88,$a8,$c8,$e8,$09,$29,$49,$69,$89,$a9,$c9,$e9
                                    +      $0a,$2a,$4a,$6a,$8a,$aa,$ca,$ea,$0b,$2b,$4b,$6b,$8b,$ab,$cb,$eb
                                    +      $0c,$2c,$4c,$6c,$8c,$ac,$cc,$ec,$0d,$2d,$4d,$6d,$8d,$ad,$cd,$ed
                                    +      $0e,$2e,$4e,$6e,$8e,$ae,$ce,$ee,$0f,$2f,$4f,$6f,$8f,$af,$cf,$ef
                                    +      $10,$30,$50,$70,$90,$b0,$d0,$f0,$11,$31,$51,$71,$91,$b1,$d1,$f1
                                    +      $12,$32,$52,$72,$92,$b2,$d2,$f2,$13,$33,$53,$73,$93,$b3,$d3,$f3
                                    +      $14,$34,$54,$74,$94,$b4,$d4,$f4,$15,$35,$55,$75,$95,$b5,$d5,$f5
                                    +      $16,$36,$56,$76,$96,$b6,$d6,$f6,$17,$37,$57,$77,$97,$b7,$d7,$f7
                                    +      $18,$38,$58,$78,$98,$b8,$d8,$f8,$19,$39,$59,$79,$99,$b9,$d9,$f9
                                    +      $1a,$3a,$5a,$7a,$9a,$ba,$da,$fa,$1b,$3b,$5b,$7b,$9b,$bb,$db,$fb
                                    +      $1c,$3c,$5c,$7c,$9c,$bc,$dc,$fc,$1d,$3d,$5d,$7d,$9d,$bd,$dd,$fd
                                    +      $1e,$3e,$5e,$7e,$9e,$be,$de,$fe,$1f,$3f,$5f,$7f,$9f,$bf,$df,$ff
b200: 00 40 80 c0+                 .bulk   $00,$40,$80,$c0,$01,$41,$81,$c1,$02,$42,$82,$c2,$03,$43,$83,$c3
                                    +      $04,$44,$84,$c4,$05,$45,$85,$c5,$06,$46,$86,$c6,$07,$47,$87,$c7
                                    +      $08,$48,$88,$c8,$09,$49,$89,$c9,$0a,$4a,$8a,$ca,$0b,$4b,$8b,$cb
                                    +      $0c,$4c,$8c,$cc,$0d,$4d,$8d,$cd,$0e,$4e,$8e,$ce,$0f,$4f,$8f,$cf
                                    +      $10,$50,$90,$d0,$11,$51,$91,$d1,$12,$52,$92,$d2,$13,$53,$93,$d3
                                    +      $14,$54,$94,$d4,$15,$55,$95,$d5,$16,$56,$96,$d6,$17,$57,$97,$d7
                                    +      $18,$58,$98,$d8,$19,$59,$99,$d9,$1a,$5a,$9a,$da,$1b,$5b,$9b,$db
                                    +      $1c,$5c,$9c,$dc,$1d,$5d,$9d,$dd,$1e,$5e,$9e,$de,$1f,$5f,$9f,$df
                                    +      $20,$60,$a0,$e0,$21,$61,$a1,$e1,$22,$62,$a2,$e2,$23,$63,$a3,$e3
                                    +      $24,$64,$a4,$e4,$25,$65,$a5,$e5,$26,$66,$a6,$e6,$27,$67,$a7,$e7
                                    +      $28,$68,$a8,$e8,$29,$69,$a9,$e9,$2a,$6a,$aa,$ea,$2b,$6b,$ab,$eb
                                    +      $2c,$6c,$ac,$ec,$2d,$6d,$ad,$ed,$2e,$6e,$ae,$ee,$2f,$6f,$af,$ef
                                    +      $30,$70,$b0,$f0,$31,$71,$b1,$f1,$32,$72,$b2,$f2,$33,$73,$b3,$f3
                                    +      $34,$74,$b4,$f4,$35,$75,$b5,$f5,$36,$76,$b6,$f6,$37,$77,$b7,$f7
                                    +      $38,$78,$b8,$f8,$39,$79,$b9,$f9,$3a,$7a,$ba,$fa,$3b,$7b,$bb,$fb
                                    +      $3c,$7c,$bc,$fc,$3d,$7d,$bd,$fd,$3e,$7e,$be,$fe,$3f,$7f,$bf,$ff
b300: 00 80 01 81+                 .bulk   $00,$80,$01,$81,$02,$82,$03,$83,$04,$84,$05,$85,$06,$86,$07,$87 ;lz=7; even bytes unused
                                    +      $08,$88,$09,$89,$0a,$8a,$0b,$8b,$0c,$8c,$0d,$8d,$0e,$8e,$0f,$8f
                                    +      $10,$90,$11,$91,$12,$92,$13,$93,$14,$94,$15,$95,$16,$96,$17,$97
                                    +      $18,$98,$19,$99,$1a,$9a,$1b,$9b,$1c,$9c,$1d,$9d,$1e,$9e,$1f,$9f
                                    +      $20,$a0,$21,$a1,$22,$a2,$23,$a3,$24,$a4,$25,$a5,$26,$a6,$27,$a7
                                    +      $28,$a8,$29,$a9,$2a,$aa,$2b,$ab,$2c,$ac,$2d,$ad,$2e,$ae,$2f,$af
                                    +      $30,$b0,$31,$b1,$32,$b2,$33,$b3,$34,$b4,$35,$b5,$36,$b6,$37,$b7
                                    +      $38,$b8,$39,$b9,$3a,$ba,$3b,$bb,$3c,$bc,$3d,$bd,$3e,$be,$3f,$bf
                                    +      $40,$c0,$41,$c1,$42,$c2,$43,$c3,$44,$c4,$45,$c5,$46,$c6,$47,$c7
                                    +      $48,$c8,$49,$c9,$4a,$ca,$4b,$cb,$4c,$cc,$4d,$cd,$4e,$ce,$4f,$cf
                                    +      $50,$d0,$51,$d1,$52,$d2,$53,$d3,$54,$d4,$55,$d5,$56,$d6,$57,$d7
                                    +      $58,$d8,$59,$d9,$5a,$da,$5b,$db,$5c,$dc,$5d,$dd,$5e,$de,$5f,$df
                                    +      $60,$e0,$61,$e1,$62,$e2,$63,$e3,$64,$e4,$65,$e5,$66,$e6,$67,$e7
                                    +      $68,$e8,$69,$e9,$6a,$ea,$6b,$eb,$6c,$ec,$6d,$ed,$6e,$ee,$6f,$ef
                                    +      $70,$f0,$71,$f1,$72,$f2,$73,$f3,$74,$f4,$75,$f5,$76,$f6,$77,$f7
                                    +      $78,$f8,$79,$f9,$7a,$fa,$7b,$fb,$7c,$fc,$7d,$fd,$7e,$fe,$7f,$ff
b400: 00 01 02 03+                 .bulk   $00,$01,$02,$03,$04,$05,$06,$07,$08,$09,$0a,$0b,$0c,$0d,$0e,$0f ;for high byte == 0
                                    +      $10,$11,$12,$13,$14,$15,$16,$17,$18,$19,$1a,$1b,$1c,$1d,$1e,$1f
                                    +      $20,$21,$22,$23,$24,$25,$26,$27,$28,$29,$2a,$2b,$2c,$2d,$2e,$2f
                                    +      $30,$31,$32,$33,$34,$35,$36,$37,$38,$39,$3a,$3b,$3c,$3d,$3e,$3f
                                    +      $40,$41,$42,$43,$44,$45,$46,$47,$48,$49,$4a,$4b,$4c,$4d,$4e,$4f
                                    +      $50,$51,$52,$53,$54,$55,$56,$57,$58,$59,$5a,$5b,$5c,$5d,$5e,$5f
                                    +      $60,$61,$62,$63,$64,$65,$66,$67,$68,$69,$6a,$6b,$6c,$6d,$6e,$6f
                                    +      $70,$71,$72,$73,$74,$75,$76,$77,$78,$79,$7a,$7b,$7c,$7d,$7e,$7f
                                    +      $80,$81,$82,$83,$84,$85,$86,$87,$88,$89,$8a,$8b,$8c,$8d,$8e,$8f
                                    +      $90,$91,$92,$93,$94,$95,$96,$97,$98,$99,$9a,$9b,$9c,$9d,$9e,$9f
                                    +      $a0,$a1,$a2,$a3,$a4,$a5,$a6,$a7,$a8,$a9,$aa,$ab,$ac,$ad,$ae,$af
                                    +      $b0,$b1,$b2,$b3,$b4,$b5,$b6,$b7,$b8,$b9,$ba,$bb,$bc,$bd,$be,$bf
                                    +      $c0,$c1,$c2,$c3,$c4,$c5,$c6,$c7,$c8,$c9,$ca,$cb,$cc,$cd,$ce,$cf
                                    +      $d0,$d1,$d2,$d3,$d4,$d5,$d6,$d7,$d8,$d9,$da,$db,$dc,$dd,$de,$df
                                    +      $e0,$e1,$e2,$e3,$e4,$e5,$e6,$e7,$e8,$e9,$ea,$eb,$ec,$ed,$ee,$ef
                                    +      $f0,$f1,$f2,$f3,$f4,$f5,$f6,$f7,$f8,$f9,$fa,$fb,$fc,$fd,$fe,$ff
                   ; 
                   ; Math table #3, maps ? to ?.
                   ; 
                   ; Appears to be lo/hi 16-bit value in the range [$0000,$07ff].
                   ; 
                   ; Used to map joystick deflection to horizontal and vertical turn rate;
                   ; AppleWin's joystick emulation generates indexes 0-101.
b500: 00 00 00 96+ turn_map_lo?    .bulk   $00,$00,$00,$96,$00,$52,$96,$cf,$00,$2b,$52,$76,$96,$b3,$cf,$e8
                                    +      $00,$16,$2c,$3f,$52,$64,$76,$86,$96,$a5,$b3,$c1,$cf,$dc,$e8,$f4
                                    +      $00,$0b,$16,$21,$2b,$36,$3f,$49,$52,$5c,$64,$6d,$76,$7e,$86,$8e
                                    +      $96,$9d,$a5,$ac,$b3,$ba,$c1,$c8,$cf,$d5,$dc,$e2,$e8,$ee,$f4,$fa
                                    +      $00,$06,$0b,$11,$16,$1c,$21,$26,$2b,$31,$36,$3b,$3f,$44,$49,$4e
                                    +      $52,$57,$5c,$60,$64,$69,$6d,$71,$76,$7a,$7e,$82,$86,$8a,$8e,$92
                                    +      $96,$9a,$9d,$a1,$a5,$a8,$ac,$b0,$b3,$b7,$ba,$be,$c1,$c5,$c8,$cb
                                    +      $cf,$d2,$d5,$d8,$dc,$df,$e2,$e5,$e8,$eb,$ee,$f1,$f4,$f7,$fa,$fd
                                    +      $00,$03,$06,$08,$0b,$0e,$11,$14,$16,$19,$1c,$1e,$21,$24,$26,$29
                                    +      $2b,$2e,$31,$33,$36,$38,$3b,$3d,$3f,$42,$44,$47,$49,$4b,$4e,$50
                                    +      $52,$55,$57,$59,$5b,$5e,$60,$62,$64,$67,$69,$6b,$6d,$6f,$71,$73
                                    +      $76,$78,$7a,$7c,$7e,$80,$82,$84,$86,$88,$8a,$8c,$8e,$90,$92,$94
                                    +      $96,$98,$99,$9b,$9d,$9f,$a1,$a3,$a5,$a7,$a8,$aa,$ac,$ae,$b0,$b1
                                    +      $b3,$b5,$b7,$b9,$ba,$bc,$be,$bf,$c1,$c3,$c5,$c6,$c8,$ca,$cb,$cd
                                    +      $cf,$d0,$d2,$d4,$d5,$d7,$d8,$da,$dc,$dd,$df,$e0,$e2,$e3,$e5,$e7
                                    +      $e8,$ea,$eb,$ed,$ee,$f0,$f1,$f3,$f4,$f6,$f7,$f9,$fa,$fc,$fd,$fe
b600: 00 00 01 01+ turn_map_hi?    .bulk   $00,$00,$01,$01,$02,$02,$02,$02,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04,$04
                                    +      $05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05
                                    +      $05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05,$05
                                    +      $06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06
                                    +      $06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06
                                    +      $06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06
                                    +      $06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06,$06
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                                    +      $07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07,$07
                   ; 
                   ; Points of interest in the unrolled hi-res AND/OR stores, indexed by hi-res
                   ; line number.  Lines from 192-255 go to a no-op RTS.
                   ; 
                   ; There's a series of ORA/STA commands from $1800-1dff, and a series of AND/STA
                   ; commands from $a600-abff.
                   ; 
                   ; Both sets of tables use the same low byte.  The high byte comes from tables at
                   ; $5500 and $b800.
                   ; 
                   unroll_a_o_addr_lo
b700: 00 07 0e 15+                 .bulk   $00,$07,$0e,$15,$1c,$23,$2a,$31,$38,$3f,$46,$4d,$54,$5b,$62,$69
                                    +      $70,$77,$7e,$85,$8c,$93,$9a,$a1,$a8,$af,$b6,$bd,$c4,$cb,$d2,$d9
                                    +      $e0,$e7,$ee,$f5,$fc,$03,$0a,$11,$18,$1f,$26,$2d,$34,$3b,$42,$49
                                    +      $50,$57,$5e,$65,$6c,$73,$7a,$81,$88,$8f,$96,$9d,$a4,$ab,$b2,$b9
                                    +      $c0,$c7,$ce,$d5,$dc,$e3,$ea,$f1,$f8,$ff,$06,$0d,$14,$1b,$22,$29
                                    +      $30,$37,$3e,$45,$4c,$53,$5a,$61,$68,$6f,$76,$7d,$84,$8b,$92,$99
                                    +      $a0,$a7,$ae,$b5,$bc,$c3,$ca,$d1,$d8,$df,$e6,$ed,$f4,$fb,$02,$09
                                    +      $10,$17,$1e,$25,$2c,$33,$3a,$41,$48,$4f,$56,$5d,$64,$6b,$72,$79
                                    +      $80,$87,$8e,$95,$9c,$a3,$aa,$b1,$b8,$bf,$c6,$cd,$d4,$db,$e2,$e9
                                    +      $f0,$f7,$fe,$05,$0c,$13,$1a,$21,$28,$2f,$36,$3d,$44,$4b,$52,$59
                                    +      $60,$67,$6e,$75,$7c,$83,$8a,$91,$98,$9f,$a6,$ad,$b4,$bb,$c2,$c9
                                    +      $d0,$d7,$de,$e5,$ec,$f3,$fa,$01,$08,$0f,$16,$1d,$24,$2b,$32,$39
                                    +      $40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40
                                    +      $40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40
                                    +      $40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40
                                    +      $40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40,$40
                   ; 
                   ; High byte of address of unrolled ORA instructions.
                   unroll_ora_addr_hi
b800: 18 18 18 18+                 .bulk   $18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18
                                    +      $18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18,$18
                                    +      $18,$18,$18,$18,$18,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19
                                    +      $19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$19
                                    +      $19,$19,$19,$19,$19,$19,$19,$19,$19,$19,$1a,$1a,$1a,$1a,$1a,$1a
                                    +      $1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a
                                    +      $1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1a,$1b,$1b
                                    +      $1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b
                                    +      $1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1b
                                    +      $1b,$1b,$1b,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c
                                    +      $1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1c
                                    +      $1c,$1c,$1c,$1c,$1c,$1c,$1c,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d
                                    +      $1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d
                                    +      $1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d
                                    +      $1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d
                                    +      $1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d,$1d
                   ; 
                   ; This provides the number of leading zero bits in an 8-bit value ("count
                   ; leading zeroes").  On a modern system you'd do this with something like gcc's
                   ; __builtin_clz().
                   ; 
                   ; Mathematically, it's 8 minus the binary order of N:
                   ;   8 - ceiling(log2(N))
                   ; 
                   ;  0: %00000000 = 8
                   ;  1: %00000001 = 7
                   ;  2: %00000010 = 6
                   ;  3: %00000011 = 6
                   ;  4: %00000100 = 5
                   ;  5: %00000101 = 5
                   ;  ...
                   ;  255: %11111111 = 0
b900: 08 07 06 06+ clz_table       .bulk   $08,$07,$06,$06,$05,$05,$05,$05,$04,$04,$04,$04,$04,$04,$04,$04
                                    +      $03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03,$03
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02,$02
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01,$01
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00,$00
                   ; 
                   ; Hi-res line start address, low byte.
ba00: 00 00 00 00+ hires_addr_lo   .bulk   $00,$00,$00,$00,$00,$00,$00,$00,$80,$80,$80,$80,$80,$80,$80,$80
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$80,$80,$80,$80,$80,$80,$80,$80
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$80,$80,$80,$80,$80,$80,$80,$80
                                    +      $00,$00,$00,$00,$00,$00,$00,$00,$80,$80,$80,$80,$80,$80,$80,$80
                                    +      $28,$28,$28,$28,$28,$28,$28,$28,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8
                                    +      $28,$28,$28,$28,$28,$28,$28,$28,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8
                                    +      $28,$28,$28,$28,$28,$28,$28,$28,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8
                                    +      $28,$28,$28,$28,$28,$28,$28,$28,$a8,$a8,$a8,$a8,$a8,$a8,$a8,$a8
                                    +      $50,$50,$50,$50,$50,$50,$50,$50,$d0,$d0,$d0,$d0,$d0,$d0,$d0,$d0
                                    +      $50,$50,$50,$50,$50,$50,$50,$50,$d0,$d0,$d0,$d0,$d0,$d0,$d0,$d0
                                    +      $50,$50,$50,$50,$50,$50,$50,$50,$d0,$d0,$d0,$d0,$d0,$d0,$d0,$d0
                                    +      $50,$50,$50,$50,$50,$50,$50,$50,$d0,$d0,$d0,$d0,$d0,$d0,$d0,$d0
bac0: d0                           .dd1    $d0
bac1: 00 00 00 00+                 .align  $0100 (63 bytes)
                   ; 
                   ; Hi-res line start address, high byte.
bb00: 20 24 28 2c+ hires_addr_hi   .bulk   $20,$24,$28,$2c,$30,$34,$38,$3c,$20,$24,$28,$2c,$30,$34,$38,$3c
                                    +      $21,$25,$29,$2d,$31,$35,$39,$3d,$21,$25,$29,$2d,$31,$35,$39,$3d
                                    +      $22,$26,$2a,$2e,$32,$36,$3a,$3e,$22,$26,$2a,$2e,$32,$36,$3a,$3e
                                    +      $23,$27,$2b,$2f,$33,$37,$3b,$3f,$23,$27,$2b,$2f,$33,$37,$3b,$3f
                                    +      $20,$24,$28,$2c,$30,$34,$38,$3c,$20,$24,$28,$2c,$30,$34,$38,$3c
                                    +      $21,$25,$29,$2d,$31,$35,$39,$3d,$21,$25,$29,$2d,$31,$35,$39,$3d
                                    +      $22,$26,$2a,$2e,$32,$36,$3a,$3e,$22,$26,$2a,$2e,$32,$36,$3a,$3e
                                    +      $23,$27,$2b,$2f,$33,$37,$3b,$3f,$23,$27,$2b,$2f,$33,$37,$3b,$3f
                                    +      $20,$24,$28,$2c,$30,$34,$38,$3c,$20,$24,$28,$2c,$30,$34,$38,$3c
                                    +      $21,$25,$29,$2d,$31,$35,$39,$3d,$21,$25,$29,$2d,$31,$35,$39,$3d
                                    +      $22,$26,$2a,$2e,$32,$36,$3a,$3e,$22,$26,$2a,$2e,$32,$36,$3a,$3e
                                    +      $23,$27,$2b,$2f,$33,$37,$3b,$3f,$23,$27,$2b,$2f,$33,$37,$3b,$3f
bbc0: 3f                           .dd1    $3f
bbc1: 0e 0e 0e 0e+                 .align  $0100 (63 bytes)
                   ; 
                   ; Converts a positive screen X coordinate (0-139) to a horizontal column (20-
                   ; 39).
bc00: 14 14 14 14+ pos_xc_to_col   .bulk   $14,$14,$14,$14,$14,$14,$14,$15,$15,$15,$15,$15,$15,$15,$16,$16
                                    +      $16,$16,$16,$16,$16,$17,$17,$17,$17,$17,$17,$17,$18,$18,$18,$18
                                    +      $18,$18,$18,$19,$19,$19,$19,$19,$19,$19,$1a,$1a,$1a,$1a,$1a,$1a
                                    +      $1a,$1b,$1b,$1b,$1b,$1b,$1b,$1b,$1c,$1c,$1c,$1c,$1c,$1c,$1c,$1d
                                    +      $1d,$1d,$1d,$1d,$1d,$1d,$1e,$1e,$1e,$1e,$1e,$1e,$1e,$1f,$1f,$1f
                                    +      $1f,$1f,$1f,$1f,$20,$20,$20,$20,$20,$20,$20,$21,$21,$21,$21,$21
                                    +      $21,$21,$22,$22,$22,$22,$22,$22,$22,$23,$23,$23,$23,$23,$23,$23
                                    +      $24,$24,$24,$24,$24,$24,$24,$25,$25,$25,$25,$25,$25,$25,$26,$26
                                    +      $26,$26,$26,$26,$26,$27,$27,$27,$27,$27,$27,$27
bc8c: 00 00 00 00+                 .align  $0100 (116 bytes)
                   ; 
                   ; Converts the absolute value of a negative screen X coordinate (1-139) to a
                   ; horizontal hi-res column (0-19).
bd00: 14 13 13 13+ neg_xc_to_col   .bulk   $14,$13,$13,$13,$13,$13,$13,$13,$12,$12,$12,$12,$12,$12,$12,$11
                                    +      $11,$11,$11,$11,$11,$11,$10,$10,$10,$10,$10,$10,$10,$0f,$0f,$0f
                                    +      $0f,$0f,$0f,$0f,$0e,$0e,$0e,$0e,$0e,$0e,$0e,$0d,$0d,$0d,$0d,$0d
                                    +      $0d,$0d,$0c,$0c,$0c,$0c,$0c,$0c,$0c,$0b,$0b,$0b,$0b,$0b,$0b,$0b
                                    +      $0a,$0a,$0a,$0a,$0a,$0a,$0a,$09,$09,$09,$09,$09,$09,$09,$08,$08
                                    +      $08,$08,$08,$08,$08,$07,$07,$07,$07,$07,$07,$07,$06,$06,$06,$06
                                    +      $06,$06,$06,$05,$05,$05,$05,$05,$05,$05,$04,$04,$04,$04,$04,$04
                                    +      $04,$03,$03,$03,$03,$03,$03,$03,$02,$02,$02,$02,$02,$02,$02,$01
                                    +      $01,$01,$01,$01,$01,$01,$00,$00,$00,$00,$00,$00
bd8c: 00 00 00 00+                 .align  $0100 (116 bytes)
                   ; 
                   ; Converts a positive screen X coordinate (0-139) to a pixel color offset (0-
                   ; 6,8-14).  This can't simply be 0-7 because of the odd/even color scheme.
                   ; 
                   ; Note you can identify whether this color is for an odd or even byte by ANDing
                   ; the value with #$08 (bit is set for even columns).
                   pos_xc_to_color_idx
be00: 00 01 02 03+                 .bulk   $00,$01,$02,$03,$04,$05,$06,$08,$09,$0a,$0b,$0c,$0d,$0e,$00,$01
                                    +      $02,$03,$04,$05,$06,$08,$09,$0a,$0b,$0c,$0d,$0e,$00,$01,$02,$03
                                    +      $04,$05,$06,$08,$09,$0a,$0b,$0c,$0d,$0e,$00,$01,$02,$03,$04,$05
                                    +      $06,$08,$09,$0a,$0b,$0c,$0d,$0e,$00,$01,$02,$03,$04,$05,$06,$08
                                    +      $09,$0a,$0b,$0c,$0d,$0e,$00,$01,$02,$03,$04,$05,$06,$08,$09,$0a
                                    +      $0b,$0c,$0d,$0e,$00,$01,$02,$03,$04,$05,$06,$08,$09,$0a,$0b,$0c
                                    +      $0d,$0e,$00,$01,$02,$03,$04,$05,$06,$08,$09,$0a,$0b,$0c,$0d,$0e
                                    +      $00,$01,$02,$03,$04,$05,$06,$08,$09,$0a,$0b,$0c,$0d,$0e,$00,$01
                                    +      $02,$03,$04,$05,$06,$08,$09,$0a,$0b,$0c,$0d,$0e
be8c: 00 00 00 00+                 .align  $0100 (116 bytes)
                   ; 
                   ; Converts the absolute value of a negative screen X coordinate (1-139) to a
                   ; pixel color offset (0-6,8-14).
                   neg_xc_to_color_idx
bf00: 00 0e 0d 0c+                 .bulk   $00,$0e,$0d,$0c,$0b,$0a,$09,$08,$06,$05,$04,$03,$02,$01,$00,$0e
                                    +      $0d,$0c,$0b,$0a,$09,$08,$06,$05,$04,$03,$02,$01,$00,$0e,$0d,$0c
                                    +      $0b,$0a,$09,$08,$06,$05,$04,$03,$02,$01,$00,$0e,$0d,$0c,$0b,$0a
                                    +      $09,$08,$06,$05,$04,$03,$02,$01,$00,$0e,$0d,$0c,$0b,$0a,$09,$08
                                    +      $06,$05,$04,$03,$02,$01,$00,$0e,$0d,$0c,$0b,$0a,$09,$08,$06,$05
                                    +      $04,$03,$02,$01,$00,$0e,$0d,$0c,$0b,$0a,$09,$08,$06,$05,$04,$03
                                    +      $02,$01,$00,$0e,$0d,$0c,$0b,$0a,$09,$08,$06,$05,$04,$03,$02,$01
                                    +      $00,$0e,$0d,$0c,$0b,$0a,$09,$08,$06,$05,$04,$03,$02,$01,$00,$0e
                                    +      $0d,$0c,$0b,$0a,$09,$08,$06,$05,$04,$03,$02,$01
bf8c: 00 00 00 00+                 .align  $0100 (116 bytes)

Symbol Table

Entry$0800
MainLoop$81fc
Start$8133
StartRedraw$8c2d