Files
Sprinter-SDCC/docs/new/03-dss.md
T
snark13 64ce6339eb docs: справочники по железу Sprinter + правка gfx_scroll_h
- docs/new/ — сводные справочники (архитектура, BIOS, DSS, память,
  графика, акселератор, IRQ, порты, ввод, звук, известные баги);
- docs/Original/ — первоисточники, из которых они собраны (BIOS, Estex
  DSS, мануалы, описание акселератора), + Форум.doc/.docx в reference;
- libbgi/common/gfx_scroll_h.c — обход бага скролла при ширине >256
  (правка автора: шаг банды 255 и продвижение указателей на cw; старый
  вариант с 256 оставлен закомментированным с TODO);
- удалён applications/PoP/roomtest/hang_variants.png — рабочая раскладка
  из разбора позы виса, в репозитории ей не место.

Большие архивы (docs/extra ~568 МБ, docs/sources с вложенными git-репо
~68 МБ) в коммит НЕ включены — см. обсуждение.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-29 18:26:31 +03:00

1083 lines
38 KiB
Markdown
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.
# 3. DSS/ESTEX — дисковая подсистема
## 3.1 Общие сведения
DSS (Disk SubSystem) / ESTEX — расширение BIOS для работы с дисковой подсистемой, файловой системой, памятью, клавиатурой и экраном.
| Свойство | Значение |
|----------|----------|
| Способ вызова | `RST 10h` |
| Номер функции | Регистр **C** |
| Успех | CF=0, выходные данные в регистрах |
| Ошибка | CF=1, код ошибки в **A** |
| Стек | Обязательно в `#8000..#BFFF` (W2) |
Документирован в версиях:
| Версия | Источник | Особенности |
|--------|----------|-------------|
| v1.54 | ProgrammerManual.txt | Одна из первых; нумерация файловых функций 10h–1Fh |
| v1.55 | ProgrammerManual.txt (приложение) | Переименование FREEMEM→INFOMEM, RETMEM→FREEMEM |
| v1.6 | DiskSyscalls.txt | Нумерация файловых функций 0Ah–1Fh; добавлены 0Ch/0Dh |
| v1.60 | DSS 1.60 rst 10.txt | Уточнения; добавлены 0Ch/0Dh, SET_CACHE_FLAG, RESET_CACHE_FLAG |
| v1.71 | Исходный код DSS 1.71 | BETA; добавлены SCANDRV, LIB_SUB; удалены 0Ch/0Dh/34h; версия D=01h, E=71 |
> **Смена нумерации между v1.54 и v1.6:** в v1.54 файловые функции занимали диапазон 10h1Fh (OPEN=10h, CLOSE=11h, READ=12h…). Начиная с v1.6 они смещены — CREATE=0Ah, OPEN=11h. В данном справочнике описана версия **DSS 1.71** (исходный код), с указанием отличий от v1.54–v1.60 где применимо.
---
## 3.2 Системные и дисковые функции (00h–0Fh)
### 00h — VERSION
Версия DSS.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `00h` |
| Выход | D | Номер версии (DSS 1.71: 1) |
| Выход | E | Модификация (DSS 1.71: 71) |
| Выход | BC | Номер сборки (build) |
| Выход | HL | `0` (зарезервировано) |
### 01h — CHDISK
Смена текущего диска.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `01h` |
| Вход | A | Номер диска (0=A, 1=B…) |
| Выход (CF=0) | A | Максимальный номер диска (4 для дисков A–E) |
| Выход (CF=1) | A | Код ошибки |
### 02h — CURDISK
Номер текущего диска.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `02h` |
| Выход (CF=0) | A | Текущий номер диска (0=A, 1=B…) |
| Выход (CF=1) | A | Код ошибки |
> **v1.54:** ошибка не возвращается (нет механизма CF=1). Добавлено в v1.6.
### 03h — DSKINFO
Информация о диске.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `03h` |
| Вход | A | Номер диска (0=A, 1=B… `0FFh` = текущий) |
| Выход (CF=0) | A | Размер кластера в секторах |
| Выход (CF=0) | HL | Общее количество кластеров |
| Выход (CF=0) | DE | Количество свободных кластеров |
| Выход (CF=0) | BC | Размер сектора в байтах |
| Выход (CF=1) | A | Код ошибки |
> Слоты `04h–07h` — зарезервированы (заглушки NOPS в DSS 1.71).
### 08h — SCANDRV (DSS 1.71)
Пересканирование драйверов устройств. Обновляет список доступных логических дисков.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `08h` |
| Выход (CF=0) | A | Количество найденных логических дисков |
| Выход (CF=1) | A | Ошибка (KERNEL_PANIC если boot-диск потерян) |
Функция отсутствует в документации v1.54–v1.60. Впервые реализована в DSS 1.71.
### 09h — BOOTDSK
Номер системного диска (с которого загружена ОС).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `09h` |
| Вход | B | `0` |
| Выход (CF=0) | A | Номер системного диска (0=A, 1=B…) |
| Выход (CF=1) | A | Код ошибки |
> **v1.54:** B не указан; ошибка не возвращается.
### 0Ah — CREATE
Создание файла (с перезаписью существующего).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `0Ah` |
| Вход | HL | Указатель на файловую спецификацию |
| Вход | A | Атрибут файла |
| Выход (CF=0) | A | Файловый манипулятор (handle) |
| Выход (CF=1) | A | Код ошибки |
**v1.54:** CREATE находится на `C=18h`. Номер `0Ah` в v1.54 занят другой функцией.
### 0Bh — CREATE_NEW
Создание нового файла (только если не существует).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `0Bh` |
| Вход | HL | Указатель на файловую спецификацию |
| Вход | A | Атрибут файла |
| Выход (CF=0) | A | Файловый манипулятор |
| Выход (CF=1) | A | Код ошибки |
Если файл уже существует — возвращает ошибку.
### 0Ch — SET_CACHE_FLAG (v1.60, удалена в DSS 1.71)
Установка флага кэш-памяти.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `0Ch` |
| Выход (CF=0) | A | Номер страницы для сохранения переключателя |
| Выход (CF=1) | — | Ошибка |
Функция присутствовала в DSS v1.60. В DSS 1.71 заменена на заглушку (возвращает `INVALID_FUNCTION`).
### 0Dh — RESET_CACHE_FLAG (v1.60, удалена в DSS 1.71)
Сброс флага кэш-памяти.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `0Dh` |
| Выход (CF=1) | — | Ошибка |
В DSS 1.71 заменена на заглушку (возвращает `INVALID_FUNCTION`).
### 0Eh — DELETE
Удаление файла.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `0Eh` |
| Вход | HL | Указатель на файловую спецификацию |
| Выход (CF=1) | A | Код ошибки |
> **v1.54** дополнительно требует A = атрибут файла. В v1.6/v1.60 атрибут не используется — HL только.
---
## 3.3 Файловые функции (10h–1Fh)
### 10h — RENAME
Переименование файла.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `10h` |
| Вход | HL | Указатель на старое имя |
| Вход | DE | Указатель на новое имя |
| Выход (CF=1) | A | Код ошибки |
### 11h — OPEN
Открытие существующего файла.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `11h` |
| Вход | HL | Указатель на файловую спецификацию |
| Вход | A | Режим доступа: `0` = чтение/запись, `1` = чтение, `2` = запись |
| Выход (CF=0) | A | Файловый манипулятор |
| Выход (CF=1) | A | Код ошибки |
### 12h — CLOSE
Закрытие файла.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `12h` |
| Вход | A | Файловый манипулятор |
| Выход (CF=1) | A | Код ошибки |
### 13h — READ
Чтение из файла.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `13h` |
| Вход | A | Файловый манипулятор |
| Вход | HL | Адрес буфера в памяти |
| Вход | DE | Количество читаемых байт |
| Выход (CF=0) | DE | Реально прочитано байт |
| Выход (CF=0) | A | `0` = прочитаны все байты, `0FFh` = прочитано меньше |
| Выход (CF=1) | A | Код ошибки |
### 14h — WRITE
Запись в файл.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `14h` |
| Вход | A | Файловый манипулятор |
| Вход | HL | Адрес данных в памяти |
| Вход | DE | Количество записываемых байт |
| Выход (CF=0) | DE | Реально записано байт |
| Выход (CF=1) | A | Код ошибки |
### 15h — MOVE_FP
Перемещение файлового указателя.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `15h` |
| Вход | A | Файловый манипулятор |
| Вход | HL:IX | Смещение |
| Вход | B | Способ: `0` = от начала, `1` = от текущей, `2` = от конца |
| Выход (CF=0) | HL:IX | Новая позиция указателя |
| Выход (CF=1) | A | Код ошибки |
### 16h — ATTRIB
Получение/изменение атрибута файла.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `16h` |
| Вход | HL | Указатель на файловую спецификацию |
| Вход | B | `0` = получить атрибут, `1` = установить |
| Вход | A | Атрибут (для установки) |
| Выход (CF=0) | A | Атрибут файла |
| Выход (CF=1) | A | Код ошибки |
### 17h — GET_D_T
Дата и время файла.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `17h` |
| Вход | A | Файловый манипулятор |
| Выход (CF=0) | D | День |
| Выход (CF=0) | E | Месяц |
| Выход (CF=0) | IX | Год |
| Выход (CF=0) | H | Час |
| Выход (CF=0) | L | Минуты |
| Выход (CF=0) | B | Секунды |
| Выход (CF=1) | A | Код ошибки |
### 18h — PUT_D_T
Установка даты и времени файла.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `18h` |
| Вход | A | Файловый манипулятор |
| Вход | D | День |
| Вход | E | Месяц |
| Вход | IX | Год |
| Вход | H | Час |
| Вход | L | Минуты |
| Вход | B | Секунды |
| Выход (CF=1) | A | Код ошибки |
### 19h — F_FIRST
Поиск первого файла по маске.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `19h` |
| Вход | HL | Указатель на файловую спецификацию (с маской `*`/`?`) |
| Вход | DE | Рабочий буфер: 44 байта (B=0) или 256 байт (B=1) |
| Вход | A | Атрибуты для поиска |
| Вход | B | `0` = имя в формате 11 байт "FilenameExt", `1` = "filename.ext",0 |
| Выход (CF=1) | A | Код ошибки |
После успешного поиска имя первого совпавшего файла — в буфере DE.
### 1Ah — F_NEXT
Поиск следующего файла (после F_FIRST).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `1Ah` |
| Вход | DE | Рабочий буфер (тот же, что в F_FIRST) |
| Выход (CF=1) | A | Код ошибки (0Fh = No more files) |
### 1Bh — MKDIR
Создание каталога.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `1Bh` |
| Вход | HL | Указатель на путь |
| Выход (CF=1) | A | Код ошибки |
### 1Ch — RMDIR
Удаление каталога (каталог должен быть пуст).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `1Ch` |
| Вход | HL | Указатель на путь |
| Выход (CF=1) | A | Код ошибки |
### 1Dh — CHDIR
Смена текущего каталога.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `1Dh` |
| Вход | HL | Указатель на путь |
| Выход (CF=1) | A | Код ошибки |
### 1Eh — CURDIR
Получение текущего каталога.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `1Eh` |
| Вход | HL | Буфер (256 байт) |
| Выход (CF=1) | A | Код ошибки |
---
## 3.4 Дата и время (20h–22h)
### 21h — SYSTIME
Текущие дата и время системы.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `21h` |
| Выход | D | День |
| Выход | E | Месяц |
| Выход | IX | Год |
| Выход | H | Час |
| Выход | L | Минуты |
| Выход | B | Секунды |
| Выход | C | День недели (0=воскресенье) |
### 22h — SETTIME
Установка даты и времени.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `22h` |
| Вход | D | День |
| Вход | E | Месяц |
| Вход | IX | Год |
| Вход | H | Час |
| Вход | L | Минуты |
| Вход | B | Секунды |
| Выход (CF=1) | A | Код ошибки |
---
## 3.5 Функции клавиатуры (30h–37h)
### 30h — WAITKEY
Ожидание и получение символа с клавиатуры (блокирующий).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `30h` |
| Выход | A | Код символа (позиционный/скан-код) |
| Выход | D | Позиционный код |
| Выход | E | ASCII-код |
| Выход | C | Режим клавиатуры (битовое поле, см. ниже) |
| Выход | B | Состояние shift'ов (битовое поле) |
**Регистр C (режим клавиатуры):**
| Бит | Описание |
|-----|----------|
| 7 | RUS/LAT (0=LAT, 1=RUS) |
| 3 | Num Lock |
| 2 | Scroll Lock |
| 1 | Insert |
| 0 | Caps Lock |
**Регистр B (состояние shift'ов):**
| Бит | Описание |
|-----|----------|
| 7 | Left Shift |
| 6 | Right Shift |
| 5 | Ctrl |
| 4 | Alt |
| 3 | Left Ctrl |
| 2 | Left Alt |
| 1 | Right Ctrl |
| 0 | Right Alt |
### 31h — SCANKEY
Опрос клавиатуры без ожидания (неблокирующий).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `31h` |
| Выход (ZF=1) | — | Нет нажатой клавиши |
| Выход (ZF=0) | A | Код символа |
| Выход (ZF=0) | D | Позиционный код |
| Выход (ZF=0) | E | ASCII-код |
| Выход (ZF=0) | C | Режим клавиатуры |
| Выход (ZF=0) | B | Состояние shift'ов |
Поля C и B — те же, что в WAITKEY.
### 32h — ECHOKEY
Ожидание символа с эхо-печатью на экран. Вход/выход — полностью идентичен WAITKEY.
### 33h — CTRLKEY
Получить состояние клавиатуры (без считывания символа).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `33h` |
| Выход | A | `0` = нет символов в буфере |
| Выход | C | Режим клавиатуры |
| Выход | B | Состояние shift'ов |
### 35h — K_CLEAR
Очистить буфер клавиатуры и выполнить подфункцию.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `35h` |
| Вход | B | Номер подфункции: `30h`, `31h`, `32h`, `33h` или `34h` |
| Выход | — | Зависит от подфункции (см. соответствующую функцию) |
Перед вызовом указанной подфункции очищает буфер клавиатуры. Подфункция `34h` (EDIT) присутствовала в v1.54–v1.60, но в DSS 1.71 заменена на заглушку (NOPS).
### 36h — K_SETUP
Управление настройками клавиатуры.
**B = 0** — установить раскладку:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `36h` |
| Вход | B | `0` |
| Вход | A | Номер раскладки: `0`=normal, `1`=shift, `2`=caps, `3`=caps+shift, `4`..`7`=альтернативные |
| Выход | — | — |
**B = 1** — получить состояние звуковых переменных.
**B = 2** — установить звуковые переменные:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `36h` |
| Вход | B | `2` |
| Вход | A | bit0 = сигнал переполнения буфера, bit1 = сигнал смены раскладки |
### 37h — TESTKEY
Опрос буфера клавиатуры (неблокирующий, без снятия символа).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `37h` |
| Выход (ZF=1) | — | Нет символов в буфере |
| Выход (ZF=0) | A | Код символа |
| Выход (ZF=0) | D | Позиционный код |
| Выход (ZF=0) | E | ASCII-код |
| Выход (ZF=0) | C | Режим клавиатуры |
| Выход (ZF=0) | B | Состояние shift'ов |
От SCANKEY отличается тем, что опрашивает буфер, а не физическую клавиатуру.
---
## 3.6 Управление памятью (38h–3Fh)
### 38h — SETWIN
Подключение страницы памяти в произвольное окно.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `38h` |
| Вход | A | Идентификатор блока памяти |
| Вход | B | Номер страницы в блоке (0, 1, 2…) |
| Вход | H | Биты 6–7: номер окна (0–3) |
| Выход (CF=0) | A | Номер замещённой физической страницы |
| Выход (CF=1) | A | Код ошибки |
### 39h — SETWIN1
Подключение страницы в окно 0 (`#0000..#3FFF`).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `39h` |
| Вход | A | Идентификатор блока |
| Вход | B | Номер страницы в блоке |
| Выход (CF=0) | A | Номер замещённой страницы |
| Выход (CF=1) | A | Код ошибки |
### 3Ah — SETWIN2
Подключение страницы в окно 1 (`#4000..#7FFF`).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `3Ah` |
| Вход | A | Идентификатор блока |
| Вход | B | Номер страницы в блоке |
| Выход (CF=0) | A | Номер замещённой страницы |
| Выход (CF=1) | A | Код ошибки |
> **Опечатка в DiskSyscalls v1.6 и DSS 1.60:** обе ошибочно указывают `C=39h` для SETWIN2, что дублирует номер SETWIN1. Правильный номер — `3Ah` (согласно v1.54).
### 3Bh — SETWIN3
Подключение страницы в окно 2 (`#8000..#BFFF`).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `3Bh` |
| Вход | A | Идентификатор блока |
| Вход | B | Номер страницы в блоке |
| Выход (CF=0) | A | Номер замещённой страницы |
| Выход (CF=1) | A | Код ошибки |
### 3Ch — INFOMEM
Информация о распределении памяти.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `3Ch` |
| Выход | HL | Общее количество страниц (16 КБ каждая) |
| Выход | BC | Количество свободных страниц |
> v1.54 называет эту функцию **FREEMEM**. Переименована в INFOMEM начиная с v1.55, однако исходный код DSS 1.71 всё ещё использует метку `FREEMEM`.
### 3Dh — GETMEM
Выделение блока памяти.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `3Dh` |
| Вход | B | Размер блока в страницах (16 КБ каждая) |
| Выход (CF=0) | A | Идентификатор блока |
| Выход (CF=1) | A | Код ошибки (`1` = не хватает памяти) |
### 3Eh — FREEMEM
Освобождение блока памяти.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `3Eh` |
| Вход | A | Идентификатор блока |
| Выход (CF=1) | A | Код ошибки |
> v1.54 называет эту функцию **RETMEM**. Переименована в FREEMEM начиная с v1.55, однако исходный код DSS 1.71 всё ещё использует метку `RETMEM`.
### 3Fh — SETMEM
Изменение размера блока памяти.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `3Fh` |
| Вход | A | Идентификатор блока |
| Вход | B | Новый размер в страницах |
| Выход (CF=1) | A | Код ошибки |
---
## 3.7 Исполнение программ (40h–42h)
### 40h — EXEC
Загрузка и выполнение EXE-файла. После завершения возвращает управление.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `40h` |
| Вход | HL | Указатель на файловую спецификацию |
| Вход | B | `0` = короткое имя, `1` = полный путь |
| Выход (CF=0) | A | Код завершения программы |
| Выход (CF=1) | A | Код ошибки |
### 41h — EXIT (метка в DSS 1.71: LEAVE)
Завершение текущей программы.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `41h` |
| Вход | B | Код завершения |
| Выход (CF=0) | A | Код завершения |
| Выход (CF=1) | A | Код ошибки |
### 42h — WAIT (метка в DSS 1.71: GET_ERR)
Получить код завершения последней выполненной программы (после EXEC).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `42h` |
| Выход | A | Код завершения |
---
## 3.8 Строки и командная строка (43h–45h)
### 43h — GSWITCH
Выделение параметра из командной строки.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `43h` |
| Вход | HL | Указатель на командную строку |
| Вход | DE | Буфер для выделяемого параметра |
| Выход | HL | Указатель на следующий параметр |
| Выход | CF=0 | Есть ещё параметры |
| Выход | CF=1 | Конец строки (в буфере — последний параметр или ноль) |
### 44h — DOSNAME
Преобразование имени файла между форматами.
**B = 0** — из 11-символьного в DOS ("FILENAMEEXT" → "filename.ext"):
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `44h` |
| Вход | B | `0` |
| Вход | HL | 11 символов имени |
| Вход | DE | Буфер для DOS-имени |
**B = 1** — из DOS в 11-символьный:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `44h` |
| Вход | B | `1` |
| Вход | HL | Имя в формате DOS |
| Вход | DE | Буфер (11 байт) |
| Выход (CF=1) | A | Код ошибки |
### 45h — EXCMDLN (метка в DSS 1.71: EX_PATH)
Разбор командной строки. Многорежимная функция.
**Подфункция 0** — разобрать строку (определить, какие компоненты указаны):
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`0` |
| Вход | HL | Указатель на командную строку |
| Выход (CF=0) | A | Битовое поле: bit7=`*`/`?`, bit3=диск, bit2=путь, bit1=расширение, bit0=имя |
| Выход (CF=1) | A | Код ошибки |
**Подфункция 1** — выделить имя диска:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`1` |
| Вход | HL | Командная строка |
| Вход | DE | Буфер (≤13 байт) |
| Выход (CF=0) | A | Номер диска (0=A, 1=B…) |
| Выход (CF=0) | DE | Буфер: `"A:",0` |
**Подфункция 2** — выделить директорию:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`2` |
| Вход | HL | Командная строка |
| Вход | DE | Буфер (≤256 байт) |
| Выход (CF=0) | A | Результат разбора (как в подф. 0) |
| Выход (CF=0) | DE | Буфер: `"DIR1\\DIR2\\",0` |
**Подфункция 3** — выделить имя файла:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`3` |
| Вход | HL | Командная строка |
| Вход | DE | Буфер (≤13 байт) |
| Выход (CF=0) | A | Результат разбора |
| Выход (CF=0) | DE | Буфер: `"FILE.EXT",0` |
**Подфункция 4** — выделить расширение:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`4` |
| Вход | HL | Командная строка |
| Вход | DE | Буфер (≤4 байта) |
| Выход (CF=0) | A | Результат разбора |
| Выход (CF=0) | DE | Буфер: `"TXT",0` или `"C ",0` |
**Подфункция 5** — выделить все компоненты (диск, путь, имя, расширение):
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`5` |
| Вход | HL | Командная строка |
| Вход | DE | Буфер указателей (8 байт, 4 слова) |
| Выход (CF=0) | A | Результат разбора |
| Выход (CF=1) | A | Код ошибки |
Буфер DE — 4 слова (адреса пользовательских буферов):
| Смещение | Размер | Буфер | Максимум |
|----------|--------|-------|----------|
| DE+0 | 2 | Имя диска | 13 байт |
| DE+2 | 2 | Директория | 256 байт |
| DE+4 | 2 | Имя файла | 13 байт |
| DE+6 | 2 | Расширение | 4 байта |
> **Ошибка во всех источниках:** документация (v1.54, v1.6, v1.60) указывает смещения DE+3 и DE+4 для имени файла и расширения. Это накладывает их на одно слово (DE+3 находится внутри адреса директории). Правильные смещения — DE+4 и DE+6.
**Подфункция 7** — выделить параметр командной строки:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`7` |
| Вход | HL | Командная строка (или указатель с предыдущего вызова) |
| Вход | DE | Буфер для параметра |
| Выход | HL | На следующий параметр |
| Выход | CF=0 | Есть ещё |
| Выход | CF=1 | Конец строки |
**Подфункция 8** — 11-символьный → DOS (аналог DOSNAME B=0):
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`8` |
| Вход | HL | 11 символов |
| Вход | DE | Буфер для DOS-имени |
| Выход (CF=1) | A | Код ошибки |
**Подфункция 9** — DOS → 11-символьный (аналог DOSNAME B=1):
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `45h`, B=`9` |
| Вход | HL | Имя в формате DOS |
| Вход | DE | Буфер (11 байт) |
| Выход (CF=1) | A | Код ошибки |
---
## 3.9 Переменные окружения (46h–47h)
### 46h — ENVIRON
Работа с системным окружением.
**B = 0** — получить системное окружение целиком:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `46h`, B=`0` |
| Вход | HL | Буфер |
| Выход (CF=0) | DE | Конец буфера |
**B = 1** — получить переменную окружения:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `46h`, B=`1` |
| Вход | HL | Имя переменной |
| Вход | DE | Буфер для значения |
| Выход (CF=0) | A | `0` = найдена, `0FFh` = не найдена |
**B = 2** — установить/удалить переменную:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `46h`, B=`2` |
| Вход | HL | `"ИМЯ=значение"` (для удаления — `"ИМЯ="`) |
| Выход (CF=0) | A | `0` = успех |
| Выход (CF=1) | A | Код ошибки |
### 47h — APPINFO
Информация о текущем приложении.
**B = 0** — параметры командной строки:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `47h`, B=`0` |
| Вход | HL | Буфер данных |
| Выход (CF=1) | A | Код ошибки |
**B = 1** — полный путь к каталогу программы:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `47h`, B=`1` |
| Вход | HL | Буфер |
| Выход (CF=1) | A | Код ошибки |
**B = 2** — полный путь и имя файла программы:
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `47h`, B=`2` |
| Вход | HL | Буфер |
| Выход (CF=1) | A | Код ошибки |
---
## 3.10 Экран (50h5Ch)
Функции экрана работают с текущим видеорежимом, установленным через SETVMOD. Для работы с окнами через BIOS см. `02-bios.md`.
### 50h — SETVMOD
Установка видеорежима.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `50h` |
| Вход | A | Режим: `02h`=текст 40×32×16, `03h`=текст 80×32×16, `81h`=графика 320×256×256, `82h`=графика 640×256×16 |
| Вход | B | Страница экрана (0/1) |
| Выход (CF=1) | A | Код ошибки |
### 51h — GETVMOD
Текущий видеорежим.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `51h` |
| Выход (CF=0) | A | Текущий режим |
| Выход (CF=0) | B | Страница экрана |
| Выход (CF=1) | A | Код ошибки |
### 52h — LOCATE
Установка позиции курсора.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `52h` |
| Вход | D | Строка |
| Вход | E | Столбец |
| Выход | — | — |
### 53h — CURSOR
Текущая позиция курсора.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `53h` |
| Выход | D | Строка |
| Выход | E | Столбец |
### 54h — SELPAGE
Выбор активной страницы экрана.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `54h` |
| Вход | B | Страница экрана (0/1) |
| Выход (CF=1) | A | Код ошибки |
### 55h — SCROLL
Прокрутка окна.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `55h` |
| Вход | D | Строка верхнего левого угла |
| Вход | E | Столбец верхнего левого угла |
| Вход | H | Высота |
| Вход | L | Ширина |
| Вход | B | `1` = вверх, `2` = вниз |
| Вход | A | `0` = очищать освободившуюся строку |
### 56h — CLEAR
Очистка области экрана.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `56h` |
| Вход | D | Строка верхнего левого угла |
| Вход | E | Столбец |
| Вход | H | Высота |
| Вход | L | Ширина |
| Вход | B | Атрибут заполнения |
| Вход | A | Символ заполнения |
### 57h — RDCHAR
Чтение символа и атрибута с экрана.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `57h` |
| Вход | D | Строка |
| Вход | E | Столбец |
| Выход | A | Символ |
| Выход | B | Атрибут |
### 58h — WRCHAR
Запись символа с атрибутом на экран.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `58h` |
| Вход | D | Строка |
| Вход | E | Столбец |
| Вход | A | Символ |
| Вход | B | Атрибут |
### 59h — WINCOPY
Сохранение области экрана в буфер.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `59h` |
| Вход | D | Строка |
| Вход | E | Столбец |
| Вход | H | Высота |
| Вход | L | Ширина |
| Вход | B | Страница буфера |
| Вход | IX | Адрес буфера |
### 5Ah — WINREST
Восстановление области экрана из буфера. Параметры — идентичны WINCOPY.
### 5Bh — PUTCHAR
Печать символа в текущей позиции курсора.
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `5Bh` |
| Вход | A | Символ |
Курсор сдвигается на одну позицию вправо.
### 5Ch — PCHARS
Печать строки с текущей позиции курсора. Строка завершается нулём.
```asm
LD HL,MSG
LD C,5Ch
RST 10h
; ...
MSG: db "Hello, world!",0Dh,0Ah,0
```
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `5Ch` |
| Вход | HL | Адрес строки (завершается `0`) |
### 5Dh — LIB_SUB (DSS 1.71)
Библиотечная подфункция. В текущей реализации DSS 1.71 содержит одну подфункцию:
**B = 1** — восстановление системных шрифтов (SETUP_CURSORS):
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `5Dh` |
| Вход | B | `1` |
| Выход | — | — |
Функция в стадии развития — список подфункций пополняемый.
---
## 3.11 Принтер (5Fh)
### 5Fh — PRINT
Вывод символа на принтер (без ожидания готовности).
| | Регистр | Описание |
|--|---------|----------|
| Вход | C | `5Fh` |
| Вход | A | Символ |
| Выход | B | Символ (возвращается без изменений) |
| Выход | CF=1 | Принтер не готов |
---
## 3.12 Системная консоль и командный интерпретатор
DSS предоставляет командную строку через EXCMDLN (45h). Командный интерпретатор поддерживает внутренние команды:
`DIR`, `ERA`/`DEL`, `REN`, `COPY`, `TYPE`, `MD`/`MKDIR`, `RD`/`RMDIR`, `CD`/`CHDIR`, `DATE`, `TIME`, `VER`, `FORMAT`, `LABEL`, `VOL`, `SYS`, и др.
Загрузка `.EXE`-файлов: см. EXEC (40h). Переменные окружения: см. ENVIRON (46h).
---
## 3.13 Коды ошибок ESTEX
| Код | Значение |
|-----|----------|
| 00h | Нет ошибки |
| 01h–05h | Диск: не готов, не найден, защищён от записи, ошибка данных |
| 06h | Ресурс не найден |
| 08h | Файл не найден |
| 09h | Путь не найден |
| 0Ah | Нет доступа |
| 0Bh | Invalid access code |
| 0Ch | Invalid drive |
| 0Dh | Unable to remove current directory |
| 0Eh | Not same device |
| 0Fh | No more files |
| 10h–1Fh | Ошибки ввода-вывода |
Коды `1Ch`, `1Dh`, `20h` — зарезервированы (в документации ProgrammerManual).
---
## 3.14 Кросс-ссылки
- Загрузка EXE и модель памяти: `04-memory.md`
- Файловые операции и `FILE*`: проектный `file-buffering-design.md`
- API libc: проектный `libc-reference.md`
- Порты дисков и IDE: `11-ports.md`
- Баги DSS: `12-bugs.md`
- BIOS (окна, графика): `02-bios.md`