"""Static P1blue/P2red/P3green/P4yellow markers, optional brighter green; no runtime hook."""
PALETTES=(0x59934,)
TAIL=bytes.fromhex('0aac088e064c0c8602ac0ea802220ec8')
def recolor(blob,old,new):
    return bytes(((new if x>>4==old else x>>4)<<4)|(new if x&15==old else x&15) for x in blob)
def legacy_install(data,assemble,patch):
    p1=bytes(data[0x7C144:0x7C1C4]);p2=bytes(data[0x7C1C4:0x7C244]);p4=bytes(data[0x9E624:0x9E6A4])
    assert set(p1.hex())==set('09') and set(p2.hex())==set('0a') and set(p4.hex())==set('0c')
    assert recolor(p1,9,10)==p2 and recolor(p1,9,12)==p4,'native star shapes must match exactly'
    # P2 gets indexB in its existing four tiles and selects the fixed rink palette1.
    patch(0x7C1C4,p2,recolor(p2,10,11))
    for at in (0x205744,0x20574C,0x2085FC,0x208604):
        old=bytes(data[at:at+2]);assert old in (bytes.fromhex('0005'),bytes.fromhex('0805'))
        patch(at,old,(int.from_bytes(old,'big')|0x2000).to_bytes(2,'big'))
    # P3 uses P1's identical-shape index9 art through palette1 red; P1 keeps palette0.
    for at in (0x2085DA,0x2085E2):patch(at,bytes.fromhex('0f1a'),bytes.fromhex('0f16'))
    patch(0x9E624,p4,recolor(p4,12,13))
    for tail in PALETTES:
        assert data[tail:tail+16]==TAIL
        for delta,old,new in [(18,0x600,0xE),(22,0x20,0xE0),(26,6,0xEE)]:
            at=tail+16+delta;patch(at,old.to_bytes(2,'big'),new.to_bytes(2,'big'))

# Native sprite keys are SIGNED words (EXT.L at16866), in32-byte units from
#5DE84. Low-ROM padding therefore supports new art without changing DMA code.
STAR_ART=0x4004
STAR_KEY=((STAR_ART-0x5DE84)//32)&0xFFFF
assert ((STAR_KEY^0x8000)-0x8000)*32+0x5DE84==STAR_ART

def install(data,assemble,patch,legacy=False,neon=False):
    if legacy:return legacy_install(data,assemble,patch)
    # P1 palette1/index9 blue, P2 palette1/indexA red; P3 new indexB green;
    # P4 original palette0/indexC gold/yellow. All four fixed rink palettes
    # remain byte exact. In particular goal's palette1/indexD is native red.
    p1=bytes(data[0x7C144:0x7C1C4])
    assert set(p1.hex())==set('09')
    assert data[0x59956:0x59960]==bytes.fromhex('0600000e0020004a0006')
    art=recolor(p1,9,11)
    patch(STAR_ART,b'\xff'*len(art),art)
    for at in (0x205744,0x20574C):
        old=bytes(data[at:at+2]);assert old in (bytes.fromhex('0005'),bytes.fromhex('0805'))
        patch(at,old,(int.from_bytes(old,'big')|0x2000).to_bytes(2,'big'))
    for at in (0x2085DA,0x2085E2):
        patch(at,bytes.fromhex('0f1a'),STAR_KEY.to_bytes(2,'big'))

    if neon:
        # Palette1/indexB is shared with small native crowd green details.
        # Preserve every other fixed entry, all team palettes, P1/P2/P4 and goal.
        patch(0x5995A,bytes.fromhex('0020'),bytes.fromhex('00e0'))
