1

Тема: Использование портов ввода\вывода(I/O Ports)

Я не смог придумать интересных примеров.
Но просто опишу саму суть.

Для начала работы с портами нужно зарезервировать необходимый диапазон портов с помощью функции ReservePorts,
эта функция в случае успеха возвращает ноль.
Для ввода\вывода можно использовать системные функции InPort и OutPort, определённые в модуле KolibriOS.
Но этот способ гораздо медленнее, чем использование напрямую инструкций процессора in\out.
Как раз такой пример я и приведу.
Для удобства можно создать обёртки для необходимых функций ввода\вывода

procedure PortOut(Data: Byte; Port: Word);
asm
  OUT Port, Data
end;

procedure PortWordOut(Data: Word; Port: Word);
asm
  OUT Port, Data
end;

procedure PortDwordOut(Data: LongWord; Port: Word);
asm
  OUT Port, Data
end;

function PortIn(Port: Word): Byte;
asm
  MOV DX, Port
  IN AL, DX
end;

function PortWordIn(Port: Word): Word;
asm
  MOV DX, Port
  IN AX, DX
end;

function PortDwordIn(Port: Word): LongWord;
asm
  MOV DX, Port
  IN EAX, DX
end;

конечно, лучше их вынести в отдельный модуль и подключать при необходимости.

Надо иметь в виду, что система резервирует за собой следующие диапазоны портов 0..$2d, $30..$4d, $50..$df, $e5..$ff
Их зарезервировать приложению уже нельзя.
Если не зарезервировать диапазон с помощью ReservePorts, то при попытке работы с незарезервированными портами программа должна вылететь с ошибкой "General protection fault".
Освободить зарезервированный диапазон можно с помощью функции FreePorts.

В примере резервируется диапазон портов $2e..$2f
Затем с помощью функции PortIn производится чтение байта из порта $2e и вывод значения в консоль.

program Ports;

{$APPTYPE CONSOLE}

uses
  KolibriOS, CRT;

function PortIn(Port: Word): Byte;
asm
  MOV DX, Port
  IN AL, DX
end;

begin
  if ReservePorts($2e, $2f) = 0{success} then
    WriteLn('Value in port $2e is ', PortIn($2e))
  else
    WriteLn('ReservePorts Error!');
end.

Можно привести для прмера ещё приложения на ассемблере

  • Это работающее с COM-портами: terminal

  • А это показывает информацию по HDD: hdd_info