# Sprinter Commander: результаты копирования P4.1 Дата: 7 сентября 2026 года. Статус: `PASS` в MAME 0.288 / BIOS 3.06 / DSS 1.71.57 на HDD `D:` для однофайлового F5, прогресса, отмены, запрета overwrite и нулевого файла. Связанные документы: [требования](commander-requirements.md), [архитектура](commander-architecture.md), [roadmap](commander-roadmap.md), [носители тестов](test-media.md). ## Реализация - F5 берёт обычный файл активной панели и каталог пассивной панели; - каталоги и виртуальный маркер DSS явно отклоняются; - source и уникальный temp открыты одновременно — не более двух fd; - блок 4096 байт находится только в четвёртой EMM-странице `ScApp` и временно отображается в W3 функциями `bank_read_page()` и `bank_write_page()`; - счётчики размера/позиции 32-битные; - temp создаётся через `O_CREAT|O_EXCL`, на ошибке или Esc закрывается и удаляется; - перед commit конечное имя проверяется повторно; - commit вызывает DSS `RENAME` двумя basename в каталоге пассивной панели и восстанавливает глобальный CWD; - после успеха пассивная панель перечитывается. UI-оркестрация и форматирование прогресса вынесены из резидентного W2 в `sc_copy_ui.c` (BANK2). Полноразмерного статического буфера нет ни в W2, ни в банке кода. ## Найденная особенность DSS RENAME Первый HDD-прогон перенёс все 131109 байт во временный файл, но завершился `errno 16` (`EINAME`), а валидатор CHD подтвердил отсутствие результата. Причина установлена не по одиночному кадру, а по сочетанию: 1. позднего прогресса `122880/131109`; 2. отдельного итогового кадра с `errno 16`; 3. извлечённого состояния HDD; 4. исходника `DSS/API/Rename.asm`: операция переименовывает записи текущего каталога, а полный новый путь не является допустимым новым именем. Исправление ограничено commit-фазой: job сохраняет CWD, временно входит в target-dir, передаёт два коротких имени и восстанавливает CWD на всех обычных путях возврата. ## Матрица MAME Образ создаёт `tests/make_p4_copy_hdd.sh`, сценарий выполняет `tests/mame_p4_copy_hdd.lua`, итог проверяет `tests/check_p4_copy_hdd.sh`. | Сценарий | Результат | |---|---| | `LARGE.BIN`, 131109 байт | скопирован, passive refresh показывает файл; содержимое побайтно совпало | | `EXIST.TXT` | F5 отказал до изменения существующего целевого файла | | `CANCEL.BIN`, 4194341 байт | виден промежуточный прогресс; Esc удалил temp и не создал target | | `EMPTY.ZRO`, 0 байт | создан корректный пустой файл и показан passive refresh | | cleanup/exit | временных `~SC*.TMP` нет; возврат в `D:\>` | Артефакты: - [успешный файл больше 64 КБ](../artifacts/mame-p4/copy/hdd-copy-success.png); - [отказ overwrite](../artifacts/mame-p4/copy/hdd-existing-refused.png); - [прогресс до Esc](../artifacts/mame-p4/copy/hdd-cancel-progress.png); - [состояние после отмены](../artifacts/mame-p4/copy/hdd-cancel-cleanup.png); - [успешный нулевой файл](../artifacts/mame-p4/copy/hdd-zero-copy-success.png); - [чистый выход на HDD](../artifacts/mame-p4/copy/hdd-clean-exit.png); - [низкоуровневый read/write EMM-page probe](../artifacts/mame-p4/copy/bank-page-io.png). Финальный файловый валидатор сообщил: ```text PASS: LARGE/EMPTY скопированы; EXIST сохранён; cancel/temp отсутствуют. ``` ## Размер сборки Конфигурация: `--memory big --safe --max-allocs 3000`. | Область | Размер | |---|---:| | `_CODE` W2 | 8795 байт | | данные W2 | 3161 байт | | свободная куча W2 | 2892 байта | | стек | 1279 байт | | BANK1: scan/sort/copy job | 4327 / 16384 байт | | BANK2: draw/copy UI | 4411 / 16384 байт | | `SPRCMD.EXE` | 42372 байта | `check_bank_calls.py` — чисто. Общий `make size-check` — 67 программ без роста; отдельно отмечается уже существующий новый тест `hello3`, не связанный с Commander. P4.1 закрыт для требований PoC `REQ-COPY-01..12`; запуск `.EXE` и вся стабилизация PoC продолжены в отчётах P4.2 и P5.