/*
 * _gfx_hfill256_segment — горизонтальный Fill-burst акселератора (register-ABI).
 *
 * ВХОД (регистры; вызывается ТОЛЬКО из asm — raw-примитивами):
 *   HL = CPU-адрес начала строки (base + x)
 *   C  = цвет
 *   B  = длина (0 = 256 — конвенция акселератора)
 *   E  = y (строка для Port_Y)
 * Клоббер: A, F.  Сохраняет BC/DE/HL/IX/IY — все опкоды акселератора это
 * `ld r,r`, т.е. no-op'ы по регистрам, поэтому color(C)/len(B)/y(E) переживают
 * accel-последовательность (это и есть смысл register-ABI — без скретча в _DATA).
 * Pre: W3 замаплен на видеобанк (вызывающий сделал _bgi_begin).
 *
 * Опкоды (docs/converted/accel_r.txt):
 *   LD D,D (0x52)  режим «задать размер блока»; СЛЕДУЮЩИЙ байт — длина,
 *                  ОБЯЗАН быть immediate-операндом LD A,n (0x3E) → SMC-патч.
 *   LD C,C (0x49)  горизонтальный Fill (LD (HL),A заливает n байт)
 *   LD B,B (0x40)  выключить акселератор
 * Другой `ld a,#n` между LD C,C и стреляющим LD (HL),A вставлять нельзя —
 * FSM акселератора перечитает immediate как новый размер блока.
 */

#include "../_bgi.h"

void _gfx_hfill256_segment(void) __naked
{
    __asm
        ld    a, b
        ld    (_hfill256_len_imm), a   ; SMC: размер блока <- B
        ld    a, e
        out   (#0x89), a               ; Port_Y <- E (y)
        di
        ld    d, d                     ; 0x52 — режим размера блока
        ld    a, #0
    _hfill256_len_imm = . - 1
        ld    c, c                     ; 0x49 — горизонтальный Fill (C=color, no-op)
        ld    a, c                     ; 0x79 — A = цвет
        ld    (hl), a                  ; выстрел; заливает len байт
        ld    b, b                     ; 0x40 — выключить (B=len, no-op)
        ei
        ret
    __endasm;
}
