161 lines
8.6 KiB
Markdown
161 lines
8.6 KiB
Markdown
# Примеры на ассемблере NTSYS
|
||
Это небольшой набор примеров для ассемблера NTSYS. Для их компиляции используйте:
|
||
```bash
|
||
ntsys --asm имя_файла.asm --out имя_файла.exe --mem 128
|
||
```
|
||
## Hello, world!
|
||
```asm
|
||
main: ; Метка main
|
||
push.string "Hello, world!\n" ; Записываем строку
|
||
push byte, 0x00 ; Запись номера SYSCALL
|
||
syscall ; Системный вызов
|
||
```
|
||
## Выводим имя пользователя
|
||
```asm
|
||
main: ; Метка main
|
||
push.string "echo Ваше имя: $USER\n" ; Запрос к системе
|
||
push byte, 0x03 ; Код
|
||
syscall ; Вызов
|
||
```
|
||
## Пример программной задержки
|
||
```asm
|
||
main: ; Метка main
|
||
push.string "This is example of wait!\n" ; Строка
|
||
push byte, 0x00 ; Номер
|
||
syscall ; Системный вызов
|
||
|
||
mload: ; Функция mload
|
||
push word, 0x00 ; Данные для записи
|
||
push word, 0x00 ; Адрес в VRAM
|
||
mwrt word ; Комманда записи
|
||
|
||
lwait: ; Цикл задержки
|
||
push db, lwait ; Его адрес
|
||
push word, 0x01 ; Увеличивать счетчик на 1
|
||
push word, 0x00 ; Счетчик по адресу 0x00
|
||
mread word ; Читаем
|
||
add word ; Складываем
|
||
push word, 0x00 ; Адрес для записи
|
||
mwrt word ; Записываем обратно
|
||
push word, 0x00 ; Адрес
|
||
mread word ; Читаем
|
||
push word, 0xFFFF ; Значение для сравнения
|
||
neq word ; Если не равно - повторить цикл
|
||
|
||
mloop: ; Главный цикл
|
||
push db, main ; Адрес main
|
||
jmp ; Повторяем цикл
|
||
```
|
||
## Пример инструкции SWAP
|
||
```asm
|
||
main: ; Метка main
|
||
push.string "Hello, world!\n" ; Строка
|
||
push byte 0x00 ; Дескриптор
|
||
syscall ; Системный вызов
|
||
push.string "Hello, world!\n" ; Строка
|
||
push byte 3 ; Кол-во блоков
|
||
swap word ; Блок размером в 2 байта
|
||
push byte 0x00 ; Дескриптор
|
||
syscall ; Системный вызов
|
||
```
|
||
## Запрос ввода у пользователя
|
||
```asm
|
||
global db main ; Точка входа
|
||
|
||
readmem: ; Функция чтения из памяти
|
||
push dw 0x00 ; Адрес
|
||
mread dw ; Читаем
|
||
ret ; Конец функции
|
||
|
||
insub: ; Уменьшение адреса
|
||
push dw 1 ; На сколько уменьшать
|
||
push byte 2 ; Поменять два места
|
||
swap dw ; Тип данных - size_t
|
||
sub dw ; Уменьшить
|
||
ret ; Конец функции
|
||
|
||
writemem: ; Функция записи в память
|
||
push dw 0x00 ; Адрес
|
||
mwrt dw ; Записываем
|
||
ret ; Конец функции
|
||
|
||
decrement: ; Управление данными
|
||
rcall db readmem ; Прочитать
|
||
rcall db insub ; Уменьшить
|
||
rcall db writemem ; Записать
|
||
ret ; Конец функции
|
||
|
||
main: ; Точка входа
|
||
push.string "Введите ваше имя: " ; Строка
|
||
push byte 0x00 ; Дескриптор
|
||
syscall ; Выводим
|
||
|
||
begin: ; Настройка адресов
|
||
push dw 0x02 ; Указатель
|
||
push dw 0x00 ; Адрес
|
||
mwrt dw ; Записываем
|
||
|
||
inloop: ; Цикл чтения символов
|
||
push byte 0x01 ; Дескриптор
|
||
syscall ; Читаем
|
||
copy byte ; Копируем char
|
||
|
||
push dw 0x00 ; Адрес
|
||
mread dw ; Читаем
|
||
|
||
mwrt byte ; Записываем
|
||
|
||
push dw 0x00 ; Читаем
|
||
mread dw ; Указатель
|
||
|
||
push dw 0x01 ; Увеличить
|
||
add dw ; На 1
|
||
|
||
push dw 0x00 ; Адрес
|
||
mwrt word ; Сохраняем указатель
|
||
|
||
push byte 0x0A ; Символ переноса
|
||
push db inloop ; Цикл
|
||
push byte 2 ; Кол-во слов
|
||
swap word ; Меняем их местами
|
||
neq byte ; Если не \n - повторить цикл
|
||
|
||
userhello: ; Приветствие
|
||
push.string "Привет, " ; Текст
|
||
push byte 0x00 ; Дескриптор
|
||
syscall ; Выводим
|
||
rcall db decrement ; Уменьшаем
|
||
push byte 0x00 ; Символ конца строки
|
||
|
||
readcycle: ; Цикл чтения
|
||
push db writeusername ; Конец цикла
|
||
push dw 0x00 ; Адрес
|
||
mread dw ; Указатель
|
||
push dw 0x01 ; Число
|
||
eq dw ; Если равно - выйти
|
||
|
||
push db rdecrem ; Адрес
|
||
|
||
push dw 0x00 ; Иначе
|
||
mread dw ; Читаем указатель
|
||
mread byte ; Читаем байт по указателю
|
||
|
||
push byte 0x0A ; Если символ переноса
|
||
eq byte ; Пропускаем добавление на стек
|
||
|
||
push dw 0x00 ; Иначе
|
||
mread dw ; Читаем указатель
|
||
mread byte ; Читаем байт по указателю
|
||
|
||
rdecrem: ; Уменьшение указателя
|
||
rcall db decrement ; Уменьшаем
|
||
push db readcycle ; Указатель на цикл
|
||
jmp ; Повторить цикл
|
||
|
||
writeusername: ; Выводим имя
|
||
push byte 0x00 ; Дескриптор
|
||
syscall ; Выводим
|
||
push.string "!\n" ; Выводим !
|
||
push byte 0x00 ; Дескриптор
|
||
syscall ; Выводим
|
||
``` |