Files
Sprinter-SDCC/libbgi/bgi256/_bgi_vspan_raw.c
T
snark13 38bfabb2ca libbgi: __preserves_regs(d,e) на raw-примитивы (контракт, без эффекта сейчас)
plot/read/hspan/vspan_raw читают D/E (y в DE), но не пишут — аннотация
задокументирована в _bgi.h.  Честное измерение (полная пересборка с/без,
diff всех .asm в common/ и bgi256/): кодогенерация SDCC 4.5 НЕ меняется —
вызывающие держат локали в IX-фрейме и перезагружают DE перед каждым
вызовом, спасений DE вокруг вызовов не было.  Оставлено как контракт на
будущее (изменение вызывающих/компилятора); при правке asm сверять
клоббер-лист.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-10 19:35:32 +03:00

65 lines
2.8 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/*
* _bgi_vspan_raw — вертикальная линия len пикселей от (x,y), mode 0x81,
* через Vertical Fill акселератора (один burst = колонка до 256 строк).
*
* "Raw" leaf: тонкий, БЕЗ клиппинга диапазона. Проверка (без GFX_NOCHECK)
* отсекает лишь грубый выход за экран по одной координате — (unsigned)x>=320
* и (unsigned)y>=256 → тихий возврат (единый стиль с _bgi_hspan_raw).
*
* ---- ОГРАНИЧЕНИЯ ВЫЗОВА (ответственность вызывающего) --------------
* - W3-скобка: вызывать ТОЛЬКО между _bgi_begin/_bgi_end.
* - Клиппинга диапазона НЕТ: требуется 0 <= y и y+len <= 256, иначе
* burst вылезет за низ колонки и затрёт чужую видеопамять. По
* сознательному решению safe-версия проверяет валидность только x/y,
* но НЕ y+len; отрицательный y и y+len>256 НЕ обрезаются (в отличие от
* прежней версии) — координаты обязаны быть уже валидны.
* - Диапазон len: 1..256. len==0: safe-версия (с проверками) тихо
* вернётся; fast (GFX_NOCHECK) из-за конвенции акселератора (B=0 =
* «256») зальёт 256 строк.
*
* __sdcccall(1): x→HL, y→DE(E=y), len→стек(4/5(ix)), color→стек(6(ix)),
* __naked → callee-pops 3 байта (len+color). В _gfx_vfill256_segment:
* HL=addr, C=color, B=len, E=y (без глобального скретча).
*/
#include "../_bgi.h"
void _bgi_vspan_raw(int x, int y, int len, uint8_t color) __naked __preserves_regs(d,e)
{
__asm
.globl __gfx_addr_base
.globl __gfx_vfill256_segment
push ix
ld ix, #0
add ix, sp
#ifndef GFX_NOCHECK
ld a, l
sub a, #0x40
ld a, h
sbc a, #0x01
jr NC, vs_ret ; (unsigned)x >= 320
ld a, d
or a, a
jr NZ, vs_ret ; (unsigned)y >= 256
ld a, 4 (ix)
or a, 5 (ix)
jr Z, vs_ret ; len == 0 (иначе B=0 «256»)
#endif
ld c, l
ld b, h ; BC = x
ld hl, (__gfx_addr_base)
add hl, bc ; HL = base + x
ld a, 6 (ix)
ld c, a ; C = color
ld a, 4 (ix)
ld b, a ; B = len (256 -> 0)
call __gfx_vfill256_segment
vs_ret:
pop ix
pop hl
pop af
inc sp
jp (hl)
__endasm;
}