Skip to content
Nikita Zimin edited this page Nov 13, 2023 · 9 revisions

Настройка окружения для написания программ под УКНЦ

В этой статье описывается разработка на макро-ассемблере для УКНЦ.

Прикинем, что нам нужно делать при разработке:

  • редактирование исходников
  • сборка: компиляция и линковка
  • подготовка образов дисков для загрузки
  • запуск и отладка в эмуляторе

Начнём с простого примера, а затем посмотрим, какие инструменты у нас есть для решения этих задач.

Hello, world

Простейшая программа на MACRO может выглядеть например так:

        .TITLE  PROG
        .MCALL  .TTYOUT,.EXIT

START::
        MOV     #MSG,R1          ; Начальный адрес строки
1$:     MOVB    (R1)+,R0         ; берём следующий символ
        BEQ     DONE             ; если ноль, то выходим из цикла
        .TTYOUT                  ; печатаем символ
        BR      1$               ; повторяем цикл
DONE:   .EXIT

MSG:    .ASCIZ /Hello, world!/

        .END    START

Здесь используются макроопределения .TTYOUT и .EXIT, обычно это означает, что программу нужно линковать с системной макро-библиотекой SYSMAC.SML.

Типичные команды сборки программы PROG.MAC под RT-11 выглядят так:

> MACRO PROG

> LINK PROG

При этом сначала происходит компиляция PROG.MAC -> PROG.OBJ, затем линковка PROG.OBJ -> PROG.SAV.

Если нет ошибок, то после этих команд мы можем запустить нашу программу:

> RU PROG

Hello, world!

Посмотрим, как компилятор показывает ошибки. Например, закомментируем строчку с командой .EXIT, тогда метка DONE будет неизвестна. Это приведёт к ошибке компиляции:

> MACRO PROG

A     7 000006  001777                          BEQ     DONE             ; если ноль, то выходим из цикла
?MACRO-E-Errors detected: 1
DK:PROG=DK:PROG

Здесь показана строка листинга, тип ошибки обозначен буквенным кодом в начале строки. Коды и описание ошибок можно найти в документе MACRO-11 Language Reference Manual, Приложение D.1 MACRO-11 ERROR CODES.

Бывает полезно получать полный файл листинга при компиляции, сделать это можно так:

> MACRO/LIST:DK: PROG.MAC

При линковке, наиболее частая ошибка это Undefined globals. Например, если указать в тексте программы несуществующий символ, при линковке получим ошибку:

> LINK PROG

?LINK-W-Undefined globals:
MSG2

Редактирование исходников

Что требуется от редактора кода:

  • поддержка используемой кодировки символов
  • кастомизация: цветовая схема, пробелы/табы
  • подсветка синтаксиса — комментариев, меток, инструкций
  • запуск компиляции и линковки по комбинации клавиш
  • (в идеале) разбор выдачи компилятора, получение списка ошибок, подсветка ошибок в тексте

На данный момент нет редактора, который полностью соответствовал бы всем этим требованиям. Поэтому используем любимый универсальный редактор, настраивая его под данную задачу, насколько это возможно.

Sublime Text 3: есть плагин подсветки синтаксиса — VWarlock/sublime-text-pdp11asm — помимо подсветки синтаксиса имеет команды для запуска скриптов компиляции и эмуляции.

Visual Studio Code: есть плагин подсветки синтаксиса — nzeemin/macro11-syntax-vscode — его можно найти и установить прямо из вкладки Extensions в VSCode.

Компиляция и линковка

Родные для RT-11 инструменты сборки это MACRO и LINK, их можно их использовать прямо на живой железной УКНЦ или в эмуляторе. Неудобства: мы ограничены средствами редактирования, которые есть на УКНЦ; на экране умещается только 25 строк по 80 символов. Также большая проблема MACRO — короткие идентификаторы, всего 6 символов. Названия файлов в RT-11 также ограничены 6-ю символами, плюс 3 символа расширения.

Документация по MACRO и LINK:

TODO: ошибки от MACRO и LINK, как их понять и исправить

Уже довольно давно есть rt11.exeэмулятор PDP-11 совместимой машины + операционной системы RT-11, работающий из командной строки Windows.

Пример командного файла Windows, использующего rt11.exe для компиляции и линковки программы, состоящей из одного файла PROG.MAC (считаем что rt1.exe лежит в одной из директорий из PATH):

rt11.exe MACRO/LIST:DK: PROG.MAC

for /f "delims=" %%a in ('findstr /B "Errors detected" PROG.LST') do set "errdet=%%a"
if "%errdet%"=="Errors detected:  0" (
  echo COMPILED SUCCESSFULLY
) ELSE (
  findstr /RC:"^[ABDEILMNOPQRTUZ] " PROG.LST
  echo ======= %errdet% =======
  exit /b
)

rt11.exe LINK PROG /MAP:PROG.MAP

for /f "delims=" %%a in ('findstr /B "Undefined globals" PROG.MAP') do set "undefg=%%a"
if "%undefg%"=="" (
  type PROG.MAP
  echo.
  echo LINKED SUCCESSFULLY
) ELSE (
  echo ======= LINK FAILED =======
  exit /b
)

Здесь мы сначала выполняем компиляцию программой MACRO с выдачей листинга (файл с расширением .LST), по листингу определяем есть ли ошибки, если они есть, то показываем из листинга строки с ошибками. Далее выполняем линковку программой LINK с выдачей карты (файла .MAP), проверяем на ошибку Undefined globals.

Существует реализация ассемблера macro11 на Си, допускает длинные имена идентификаторов, на выходе выдаёт .SAV файл либо .OBJ файл:

Вместо "классического" LINK из RT-11, можно использовать pclink11: nzeemin/pclink11

Ассемблер PDPy11 pdpy11/pdpy11 часто используется для разработки под БК, но может использоваться и для УКНЦ. Документация: https://github.com/purplesyringa/PDPy11/blob/master/docs.md. PDPy11 написан на Python, допускает длинные имена меток. Не требует отдельного линковщика, но и не позволяет использовать готовые объектные модули (.OBJ файлы). Используем команду make_sav для получения исполнимого .SAV файла.

TODO: Инструменты под Linux

Подготовка образа для загрузки

УКНЦ позволяет использовать несколько способов загрузки: гибкий диск, жёсткий диск, картридж ПЗУ, магнитофон, локальная сеть, Стык С2.

Основным способом является загрузка с диска, при этом обычно мы загружаем операционную систему RT-11, под которой уже запускаем нашу программу. Соответственно, для загрузки .SAV файла нам нужно поместить его на подготовленный образ диска. Для работы с образами дисков есть два способа:

  1. Утилита rt11dsk TODO: ссылка, пример использования
  2. Плагин к Total Commander TODO: ссылка

Для загрузки с картриджа ПЗУ используется образ такого картриджа размером 24 КБ. Есть утилита Sav2Cart, позволяющая создать образ картриджа из .SAV файла. Важное ограничение: ваша программа не должна использовать системные вызовы — при загрузке из картриджа системы в памяти нет.

Для загрузки с магнитофонного входа мы используем .WAV файл, который готовится утилитой Sav2Wav. Здесь также есть ограничение на использование системных вызовов.

Эмуляторы

От эмулятора нам нужно: собственно эмуляция целевой машины, передача подготовленного образа диска, автозапуск, отладка программы.

Для УКНЦ на данный момент есть всего два эмулятора — EmuStudio от Titus и UKNCBTL.

TODO: Эмулятор от Titus: только под Windows

TODO: UKNCBTL: под Windows и Qt версия (Linux, Mac)

Заключение

Как мы видим, Для УКНЦ нет устоявшегося набора инструментов, который подошёл бы всем. Кто-то предпочитает оставаться в рамках "классических" MACRO и LINK, кто-то предпочитает более "современные" инструменты. В любом случае, стоит оценить набор альтернатив и подобрать подходящий инструментарий под свои предпочтения и стоящие перед вами задачи.