    .ifndef WITH_QUICKGAME_CPU
    .equ WITH_QUICKGAME_CPU,0
    .endif
    .ifndef WITH_ALLSTAR_CPU
    .equ WITH_ALLSTAR_CPU,0
    .endif
| Current policy: Quickgame human splits; Allstar also offers1vsCPU.
| Legacy builds retain the preceding Quickgame-only CPU option exactly.
| +0 enter, +4 player label, +8 player step, +12 side commit.
| F84C active, F84E choice0..3 humans, optional4 CPU. Both survive native game-RAM clearing B000..D03D.
    .equ ACTIVE,0xFFFFF84C
    .equ CHOICE,0xFFFFF84E
    .text
    .globl _start
_start:
    bra.w enter
    bra.w label
    bra.w step
    bra.w sides
    bra.w gameend
    bra.w table_gate
    bra.w prelist_gate
    bra.w shootout_pad
    bra.w attempt_gate
    bra.w demo_gate
effective:
    move.w CHOICE,%d0
    .if WITH_QUICKGAME_CPU
    .if WITH_ALLSTAR_CPU
    cmpi.w #1,0xFFFFF850
    bne.s human_choice            | CPU is available ONLY in the selected Allstar mode
    .else
    tst.w 0xFFFFF850               | Allstar retains exactly its four human splits
    bne.s human_choice
    .endif
    cmpi.w #4,%d0
    beq.s ready                   | CPU opponent works with ordinary two-port pads too
human_choice:
    .endif
    cmpi.w #3,%d0
    bls.s choice_valid
    moveq #0,%d0
choice_valid:
    tst.w 0xFFFFD046
    bne.s ready
    moveq #0,%d0                   | without adapter only two physical pads exist
ready:
    rts
encoding:
    .if WITH_QUICKGAME_CPU
    cmpi.w #4,%d0
    bne.s human_encoding
    moveq #1,%d3                  | native one human, home side; CPU away
    move.w %d3,0xFFFFD04A
    clr.w 0xFFFFF07C
    rts
human_encoding:
    .endif
    move.w %d0,%d3
    cmpi.w #2,%d3
    bcs.s short_count
    moveq #2,%d3
short_count:
    addq.w #4,%d3                  | native4=two opponents,5=three,6=four
    move.w %d3,0xFFFFD04A
    clr.w 0xFFFFF07C               | never dispatch the cooperative count override
    rts
enter:
    move.w #1,ACTIVE
    clr.w 0xFFFFD048               | native exhibition uses regular-game engine
    clr.w 0xFFFFD074
    movem.l %d0/%d3,-(%sp)
    .if WITH_QUICKGAME_CPU
    bsr.w effective
    move.w %d0,CHOICE
    bsr.w encoding
    .else
    bsr.s effective
    bsr.s encoding
    .endif
    movem.l (%sp)+,%d0/%d3
    rts
label:
    move.l %a0,-(%sp)
    .if WITH_QUICKGAME_CPU
    bsr.w effective
    .else
    bsr.s effective
    .endif
    mulu.w #22,%d0
    lea labels(%pc),%a0
    adda.w %d0,%a0
    move.l %a0,%d0
    movea.l (%sp)+,%a0
    rts
step:
    movem.l %d0-%d1,-(%sp)
    .if WITH_QUICKGAME_CPU
    bsr.w effective
    .else
    bsr.s effective
    .endif
    tst.w 0xFFFFD046
    .if WITH_QUICKGAME_CPU
    bne.s adapter_step
    .if WITH_ALLSTAR_CPU
    cmpi.w #1,0xFFFFF850
    bne.s selected                | no adapter: human-only Quickgame remains1v1
    .else
    tst.w 0xFFFFF850
    bne.s selected                | legacy no adapter: Allstar remains1v1
    .endif
    eori.w #4,%d0                 | permitted mode:1v1 <->1vsCPU
    bra.s selected
adapter_step:
    .else
    beq.s selected
    .endif
    tst.w %d2
    bmi.s left
    addq.w #1,%d0
    bra.s wrap
left:
    subq.w #1,%d0
wrap:
    .if WITH_QUICKGAME_CPU
    .if WITH_ALLSTAR_CPU
    cmpi.w #1,0xFFFFF850
    bne.s four_humans             | Quickgame remains exactly its four human splits
    .else
    tst.w 0xFFFFF850
    bne.s four_humans
    .endif
    tst.w %d0
    bpl.s cpu_wrap_high
    moveq #4,%d0
    bra.s selected
cpu_wrap_high:
    cmpi.w #4,%d0
    bls.s selected
    moveq #0,%d0
    bra.s selected
four_humans:
    .endif
    andi.w #3,%d0
selected:
    move.w %d0,CHOICE
    .if WITH_QUICKGAME_CPU
    bsr.w encoding
    .else
    bsr.s encoding
    .endif
    movem.l (%sp)+,%d0-%d1
    rts
sides:
    jsr 0x2EA614                   | reset all adapter keeper input latches on new game
    movem.l %d0/%a0,-(%sp)
    bsr.w effective
    lsl.w #3,%d0
    lea assignments(%pc),%a0
    adda.w %d0,%a0
    move.l (%a0)+,0xFFFFC328
    move.l (%a0)+,0xFFFFC32C
    clr.w 0xFFFFF07C
    lea 0xFFFFCE66,%a0
    moveq #7,%d0
no_other_matches:
    move.w #4,8(%a0)              | no CPU-only other-game highlights in an exhibition
    adda.w #16,%a0
    dbra %d0,no_other_matches
    movem.l (%sp)+,%d0/%a0
    rts
assignments:
    .word 1,2,0,0                 | P1 home / P2 away
    .word 1,2,2,0                 | P1 home / P2,P3 away
    .word 1,2,2,2                 | P1 home / P2,P3,P4 away
    .word 1,1,2,2                 | P1,P2 home / P3,P4 away
    .if WITH_QUICKGAME_CPU
    .word 1,0,0,0                 | P1 home versus entirely CPU away
    .endif
labels:
    .word 22
    .ascii "1 vs 1 - Humans     "
    .word 22
    .ascii "1 vs 2 - Humans     "
    .word 22
    .ascii "1 vs 3 - Humans     "
    .word 22
    .ascii "2 vs 2 - Humans     "

    .if WITH_QUICKGAME_CPU
    .word 22
    .ascii "1 vs CPU            "
    .endif

gameend:
    tst.w ACTIVE
    bne.s exhibition_end
    jmp 0x2F8000                  | unchanged native season write code and every legacy PC
exhibition_end:
    jmp 0xFF88E                   | replay native housekeeping, record no season game
table_gate:
    tst.w ACTIVE
    bne.s no_season_table
    jmp 0x2FC000                  | unchanged season table/standalone tree
no_season_table:
    rts
prelist_gate:
    tst.w ACTIVE
    beq.s ordinary_prelist
    lea 0x22B000,%a0
    movea.l (%a0,%d0.w),%a0
    rts
ordinary_prelist:
    jmp 0x2AA010                  | unchanged slot helper and SRAM commit addresses

| Native OT keeps its AI keeper and attempt rules. Every shooting team must
| choose a real pad from its original side, including P3/P4 in2v2 and1v3.
shootout_pad:
    move.w %sr,-(%sp)
    movem.l %d0-%d7/%a0-%a4,-(%sp)
    tst.w ACTIVE
    beq.w so_done
    cmpi.w #1,0xFFFFF090
    bne.w so_done                 | leave native standalone/penalty shots unchanged
    bsr.w effective
    lsl.w #3,%d0
    lea assignments(%pc),%a1
    adda.w %d0,%a1
    move.w 0xFFFFD594,%d7
    addq.w #1,%d7                 | shooting side1/2
    moveq #0,%d2
    moveq #0,%d4
so_count:
    cmp.w (%a1,%d4.w),%d7
    bne.s so_next_count
    addq.w #1,%d2
so_next_count:
    addq.w #2,%d4
    cmpi.w #8,%d4
    bcs.s so_count
    tst.w %d2
    beq.w so_done                 | invalid context: no division by zero
    move.w %d7,%d0
    subq.w #1,%d0
    add.w %d0,%d0
    lea 0xFFFFF09C,%a0
    moveq #0,%d1
    move.w (%a0,%d0.w),%d1
    divu.w %d2,%d1
    swap %d1                      | own-side attempt index modulo actual pad count
    moveq #0,%d4
so_choose:
    cmp.w (%a1,%d4.w),%d7
    bne.s so_next_choice
    subq.w #1,%d1
    bmi.s so_selected
so_next_choice:
    addq.w #2,%d4
    cmpi.w #8,%d4
    bcs.s so_choose
    bra.s so_done
so_selected:
    move.w 0xFFFFD406,%d5          | real native designated shooter; never invent an actor
    cmpi.w #11,%d5
    bhi.s so_done
    lea 0xFFFFC320,%a2
    lea 0xFFFFC328,%a3
    moveq #3,%d6
so_release_old:
    move.w (%a2),%d1
    moveq #-1,%d0
    jsr 0xC0F8                    | native ownership release, including object human flag
    move.w %d0,(%a2)+
    clr.w (%a3)+
    dbra %d6,so_release_old
    move.w %d5,%d0
    moveq #-1,%d1
    jsr 0xC0F8                    | native human actor admission
    lea 0xFFFFC320,%a2
    lea 0xFFFFC328,%a3
    move.w %d0,(%a2,%d4.w)
    move.w %d7,(%a3,%d4.w)
so_done:
    movem.l (%sp)+,%d0-%d7/%a0-%a4
    move.w (%sp)+,%sr
    rts

attempt_gate:
    jsr 0x2DAA04                  | unchanged native countdown/rules preparation
    jmp shootout_pad

| Native7C58 already checkedP1/P2. A sole P3/P4 shooter is human too:
| skip the attract/demo any-button exit, retaining the normal actor loop.
demo_gate:
    tst.w ACTIVE
    beq.s original_demo_poll
    tst.w 0xFFFFC32C
    bne.s human_extra_pad
    tst.w 0xFFFFC32E
    beq.s original_demo_poll
human_extra_pad:
    addq.l #4,%sp                 | discard only the replaced7C68JSR return
    jmp 0xA9D4                    | exact original human-present destination
original_demo_poll:
    jmp 0x11340                   | original poll, original7C6Ereturn untouched
