Изучение основных принципов организации и обслуживания аппаратных прерываний в ОС DOS и QNX, страница 5

disptime:

      ;читаем часы

      mov   al, 4

      out   70h, al

      in    al, 71h

      ;печатаем часы

      print_sm 0, al

      print 4, ':'

      ;читаем минуты

      mov   al, 2

      out   70h, al

      in    al, 71h

      ;печатаем минуты

      print_sm 6, al

      print 10, ':'    

      ;читаем секунды

      mov   al, 0

      out   70h, al

      in    al, 71h

      ;печатаем секунды

      print_sm 12, al  

      ret

dispdate:

      ;читаем день

      mov   al, 7

      out   70h, al

      in    al, 71h

      ;печатаем день

      print_sm 0, al

      print 4, '.'

      ;читаем месяц

      mov   al, 8

      out   70h, al

      in    al, 71h

      ;печатаем месяц

      print_sm 6, al

      print 10, '.'    

      ;читаем год

      mov   al, 9

      out   70h, al

      in    al, 71h

      ;печатаем год

      print_sm 12, al  

      ret

Результаты испытаний:

После нажатия на кнопку d:

После нажатия на кнопку t:

3.4. Программа, маскирующую клавиатуру на 5 секунд.

Текст программы для QNX:

#include <stdio.h>

//для работы с прерываниями

#include <sys/neutrino.h>

//для обработки ошибок

#include <errno.h>

int main (void) {

      int mask;

      //запрос на использование привиллегированного ввода/вывода

      //(для возможности использования прерываний)

      ThreadCtl(_NTO_TCTL_IO,0);

      mask=InterruptMask(1,-1);

      //проверка на наличие ошибок

      if (mask == -1) {

            printf("%s\n",strerror(errno));

            return 1;

      }

      sleep(5);

      mask=InterruptUnmask(1,-1);

      if (mask == -1) {

            printf("%s\n",strerror(errno));

            return 1;  

      }

      return 0;

}

Результаты испытаний:

# ./klav_mask.out

# fffffg

Текст программы для DOS:

jmp   main

old_addr    dd    ?

flag        db    0

cnt         db    0

main:

      ;сохраняем адрес старого обработчика (прерывание №8, от таймера)

      mov   ax, 035 by 8

      int   021

      mov w old_addr, bx

      mov w old_addr+2, es

      ;загружаем адрес нового обработчика (прерывание №8, от таймера)

      lea   dx, TIsr

      mov   ax, 025 by 8

      int   021  

      ;маскируем прерывание от клавиатуры

      mov   al,00000010xb

      out   21h,al

      ;ждем некоторое время

wait_t:

      mov   al, cnt

      cmp   al, 60

      jne   wait_t

;прерывание от клавиатуры размаскировано

mov   al,0

      out   21h,al

      ;восстанавливаем старый обработчик

      lds   dx, old_addr

      mov   ax, 025 by 9

      int   021

      int   020

;собственный обработчик

TIsr:

      inc cnt

      ;переход на системный обработчик

      cs jmp      old_addr

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

Текст программы для QNX:

#include <stdio.h>

//для работы с прерываниями