Files
Sprinter-SDCC/applications/PoP/roomtest/pop_sfx_cold.c
T
snark13 f4b4852d51 QuickSave F6/F9 в roomtest; bank_load_file/bank_save_file/gfx_w0_page_prepare; sprinter-cc: авто n_banks
roomtest:
- QuickSave/QuickLoad (F6/F9): снапшот 'POPQ' v3 в POP.SAV/POP.BAK на HDD,
  транзакционная запись (POP.NEW -> rename, откат при ошибке), XOR-контрольная
  сумма payload'а; сериализация всех игровых переменных через W0-примитивы
  pop_qs_*; pop_qsave_process() на границе кадра вне Char-окон
- pop_qsave_restore_room(): полная перезагрузка комнаты после загрузки
  (карта/края/швы, сброс bake-кэша, перерисовка обеих страниц, инвалидация
  кэшей спрайтов и HP)
- сериализаторы в pop_map/pop_loose_mob/pop_trob/pop_guard_ai
  (+ восстановление инвариантов: mobs_live, trob_drawn, redraw)
- immortal-чит 2 уровня: уровень 2 поглощает только малый урон Kid'а

libc/libbgi:
- bank_load_file()/bank_save_file() — резидентное файловое I/O в банк,
  без правила W3 (путь читается до переключения страницы)
- gfx_w0_page_prepare(page) — подготовка W0-окна (IRQ/NMI-стабы) одной
  функцией; atlas_load.c и roomtest переведены на новые примитивы;
  ручные ISR-стабы удалены

sprinter-cc / сборка:
- --bank N=FILE.c: автогенерация n_banks (_n_banks_auto.c), ручные
  const n_banks удалены из тестов
- roomtest/app.mk: ресурсы через stamp-файлы (.resource-stamps/) — один
  запуск упаковщика на группу вместо N под -B; HDD_PACK_ARGS
2026-08-22 11:53:10 +03:00

99 lines
4.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.
/*
* pop_sfx_cold.c — ХОЛОДНАЯ половина звука: поднять набор и открыть CBL.
* Отрабатывает один раз за запуск, поэтому живёт в банке 8; горячая
* половина (насос, запуск эффекта) — в резиденте, см. pop_sfx.c.
*/
#include <stdint.h>
#include <sprinter_mem.h>
#include <cbl.h>
#include "pop_sfx.h"
#define POP_SND_FILES /* имена файлов нужны ТОЛЬКО здесь, см. pop_sound_tbl.h */
#include "_pop_sfx.h"
static uint8_t snd_blk; /* блок EMM под весь набор */
int pop_sfx_init(void) __banked
{
uint8_t i, blk;
if (pop_snd_ok) return 0;
/* Одним блоком: страницы блока идут подряд по логическому индексу, и
* таблица звуков адресует их именно так (page = смещение >> 14). */
blk = mem_alloc_pages(POP_SND_PAGES);
if (!blk) return -1;
for (i = 0; i < POP_SND_PAGES; i++) {
pop_snd_page[i] = mem_get_page(blk, i);
if (!pop_snd_page[i] ||
bank_load_file(pop_snd_page[i],0,pop_snd_files[i],16384) != 16384) {
mem_free_block(blk);
return -1;
}
}
snd_blk = blk;
pop_snd_want = 1; /* набор есть — звук по умолчанию включён */
return 0;
}
/* ЗАПУСТИТЬ ВЫВОД — ОТДЕЛЬНО ОТ ЗАГРУЗКИ, и это не косметика.
*
* Пока идёт чтение файлов, CBL держать открытым НЕЛЬЗЯ: ESTEX уходит в
* диск надолго, насос не успевает долить очередные 128 байт, и железо
* крутит по кругу хвост своего 256-байтового буфера. На слух это
* сплошной скрежет (поймано пользователем на старте, 2026-08-20).
* Поэтому загрузка страниц и открытие CBL разведены: грузим молча,
* включаем звук последним действием, а на время загрузки уровня глушим
* (pop_sfx_pause).
*
* Параметры: 10 937,5 Гц, 8 бит моно — формат данных один в один
* (sound_plan.md). OTIR, а не акселератор: тот нужен только для 16 бит.
* cbl_open, а не cbl_open_silence: тишину насос льёт СВОЮ (первый блок
* набора), и просить у libc буфер через malloc не надо — куча в резиденте
* W2 тесная, и её отказ ронял бы весь звук. Заодно так malloc вообще не
* приезжает в резидент (275 Б, см. libc/cbl/_cbl_open_raw.c). */
int pop_sfx_start(void) __banked
{
if (pop_snd_ok) return 0;
if (!pop_snd_want) return 0; /* выключено пользователем (Ctrl+S) */
if (!snd_blk) return -1; /* набор не загружен */
if (cbl_open(CBL_FREQ_10K9, CBL_FMT_MONO8, CBL_PUMP_OTIR,
pop_sfx_fill) != 0)
return -1;
pop_snd_ok = 1;
return 0;
}
void pop_sfx_pause(void) __banked
{
if (!pop_snd_ok) return;
pop_sfx_stop();
cbl_close();
pop_snd_ok = 0;
}
void pop_sfx_close(void) __banked
{
pop_sfx_pause();
if (snd_blk) { mem_free_block(snd_blk); snd_blk = 0; }
}
/* Ctrl+S — порт `turn_sound_on_off((!is_sound_on) * 15)` из SDLPoP
* (seg000:657). Выключение реально ЗАКРЫВАЕТ CBL, а не глушит сэмпл:
* иначе насос продолжал бы отдавать блоки тишины 85 раз в секунду, а это
* 3,3 % процессорного времени ни за что (замер: 8 001 такт на прерывание
* при периоде 245 759). Открытие обратно дешёвое — cbl_open только
* настраивает железо, страницы набора никуда не девались. */
void pop_sfx_toggle(void) __banked
{
if (pop_snd_want) {
pop_sfx_pause(); /* pause сам не трогает want... */
pop_snd_want = 0; /* ...поэтому гасим его следом */
} else {
pop_snd_want = 1;
/* Набора может не быть вовсе (файлы не прочитались, страницы не
* дались) — тогда откатываем флаг, чтобы индикация не врала. */
if (pop_sfx_start() != 0) pop_snd_want = 0;
}
}