МЕНЮ


Фестивали и конкурсы
Семинары
Издания
О МОДНТ
Приглашения
Поздравляем

НАУЧНЫЕ РАБОТЫ


  • Инновационный менеджмент
  • Инвестиции
  • ИГП
  • Земельное право
  • Журналистика
  • Жилищное право
  • Радиоэлектроника
  • Психология
  • Программирование и комп-ры
  • Предпринимательство
  • Право
  • Политология
  • Полиграфия
  • Педагогика
  • Оккультизм и уфология
  • Начертательная геометрия
  • Бухучет управленчучет
  • Биология
  • Бизнес-план
  • Безопасность жизнедеятельности
  • Банковское дело
  • АХД экпред финансы предприятий
  • Аудит
  • Ветеринария
  • Валютные отношения
  • Бухгалтерский учет и аудит
  • Ботаника и сельское хозяйство
  • Биржевое дело
  • Банковское дело
  • Астрономия
  • Архитектура
  • Арбитражный процесс
  • Безопасность жизнедеятельности
  • Административное право
  • Авиация и космонавтика
  • Кулинария
  • Наука и техника
  • Криминология
  • Криминалистика
  • Косметология
  • Коммуникации и связь
  • Кибернетика
  • Исторические личности
  • Информатика
  • Инвестиции
  • по Зоология
  • Журналистика
  • Карта сайта
  • DOS-extender для компилятора Borland C++ 3.1

    {

    asm sti

    if (delay_cnt > 20000l )

    {

    sem_wait(1); // ожидаем установки семафора

    asm cli

    StepLabel(&Label1, &Label2, Buf);

    vi_print(5, 13, Buf, 0x1f);

    flipflop ^= 1;

    delay_cnt = 0l;

    asm sti

    }

    delay_cnt++;

    }

    }

    word keyb_code;

    extern word keyb_status;

    // Эта задача вводит символы с клавиатуры

    // и отображает скан-коды нажатых клавиш

    // и состояние переключающих клавиш на экране.

    // Если нажимается клавиша ESC, задача

    // устанавливает семафор номер 0.

    // Работающая параллельно главная задача

    // ожидает установку этого семафора. Как только

    // семафор 0 окажется установлен, главная задача

    // завершает свою работу и программа возвращает

    // процессор в реальный режим, затем передаёт

    // управление MS-DOS.

    void keyb_task(void)

    {

    vi_print(32, 20, " Key code: .... ", 0x20);

    vi_print(32, 21, " Key status: .... ", 0x20);

    while(1)

    {

    keyb_code = kb_getch();

    vi_put_word(45, 20, keyb_code, 0x4f);

    vi_put_word(45, 21, keyb_status, 0x4f);

    if ((keyb_code & 0x00ff) == 1)

    sem_set(0);

    }

    }

    4.5 Файл SEMAPHOR.C. Содержит процедуры для работы с семафорами.

    #include

    #include

    #include

    #include

    #include "tos.h"

    // Массив из пяти семафоров

    word semaphore[5];

    // Процедура сброса семафора.

    // Параметр sem - номер сбрасываемого семафора

    void sem_clear(int sem)

    {

    asm cli

    semaphore[sem] = 0;

    asm sti

    }

    // Процедура установки семафора

    // Параметр sem - номер устанавливаемого семафора

    void sem_set(int sem)

    {

    asm cli

    semaphore[sem] = 1;

    asm sti

    }

    // Ожидание установки семафора

    // Параметр sem - номер ожидаемого семафора

    void sem_wait(int sem)

    {

    while (1)

    {

    asm cli

    // проверяем семафор

    if (semaphore[sem])

    break;

    asm sti // ожидаем установки семафора

    asm nop

    asm nop

    }

    asm sti

    }

    4.6 Файл TIMER.C. Процедуры для работы с таймером и диспетчер задач.

    Cодержит обработчик аппаратного прерывания таймера, который

    периодически выдаёт звуковой сигнал и инициирует работу диспетчера задач.

    Диспетчер задач циклически перебирает селекторы TSS задач, участвующих в

    процессе разделения времени, возвращая селектор той задачи, которая должна

    стать активной. В самом конце обработки аппаратного прерывания таймера

    происходит переключение именно на эту задачу.

    #include

    #include

    #include

    #include

    #include "tos.h"

    // -------------------------------------------

    // Модуль обслуживания таймера

    // -------------------------------------------

    #define EOI 0x20

    #define MASTER8259A 0x20

    extern void beep(void);

    extern void flipflop_task(void);

    void Timer_int(void);

    word dispatcher(void);

    word timer_cnt;

    // ------------------------------------------

    // Обработчик аппаратного прерывания таймера

    // ------------------------------------------

    void Timer_int(void)

    {

    asm pop bp

    // Периодически выдаём звуковой сигнал

    timer_cnt += 1;

    if ((timer_cnt & 0xf) == 0xf)

    {

    beep();

    }

    // Выдаём в контроллер команду конца

    // прерывания

    asm mov al,EOI

    asm out MASTER8259A,al

    // Переключаемся на следующую задачу,

    // селектор TSS которой получаем от

    // диспетчера задач dispatcher()

    jump_to_task(dispatcher());

    asm iret

    }

    // --------------------------------------

    // Диспетчер задач

    // --------------------------------------

    // Массив селекторов, указывающих на TSS

    // задач, участвующих в параллельной работе,

    // т.е. диспетчеризуемых задач

    word task_list[] =

    {

    MAIN_TASK_SELECTOR,

    FLIP_TASK_SELECTOR,

    KEYBIN_TASK_SELECTOR,

    TASK_2_SELECTOR

    };

    word current_task = 0; // текущая задача

    word max_task = 3; // количество задач - 1

    // Используем простейший алгоритм диспетчеризации -

    // выполняем последовательное переключение на все

    // задачи, селекторы TSS которых находятся

    // в массиве task_list[].

    word dispatcher(void)

    {

    if (current_task < max_task)

    current_task++;

    else

    current_task = 0;

    return(task_list[current_task]);

    }

    4.7 Файл EXCEPT.C. Обработка исключений.

    #include

    #include

    #include

    #include

    #include "tos.h"

    void prg_abort(int err);

    // Номер текущей строки для вывода на экран

    extern unsigned int y;

    // Обработчики исключений

    void exception_0(void) { prg_abort(0); }

    void exception_1(void) { prg_abort(1); }

    void exception_2(void) { prg_abort(2); }

    void exception_3(void) { prg_abort(3); }

    void exception_4(void) { prg_abort(4); }

    void exception_5(void) { prg_abort(5); }

    void exception_6(void) { prg_abort(6); }

    void exception_7(void) { prg_abort(7); }

    void exception_8(void) { prg_abort(8); }

    void exception_9(void) { prg_abort(9); }

    void exception_A(void) { prg_abort(0xA); }

    void exception_B(void) { prg_abort(0xB); }

    void exception_C(void) { prg_abort(0xC); }

    void exception_D(void) { prg_abort(0xD); }

    void exception_E(void) { prg_abort(0xE); }

    void exception_F(void) { prg_abort(0xF); }

    void exception_10(void) { prg_abort(0x10); }

    void exception_11(void) { prg_abort(0x11); }

    void exception_12(void) { prg_abort(0x12); }

    void exception_13(void) { prg_abort(0x13); }

    void exception_14(void) { prg_abort(0x14); }

    void exception_15(void) { prg_abort(0x15); }

    void exception_16(void) { prg_abort(0x16); }

    void exception_17(void) { prg_abort(0x17); }

    void exception_18(void) { prg_abort(0x18); }

    void exception_19(void) { prg_abort(0x19); }

    void exception_1A(void) { prg_abort(0x1A); }

    void exception_1B(void) { prg_abort(0x1B); }

    void exception_1C(void) { prg_abort(0x1C); }

    void exception_1D(void) { prg_abort(0x1D); }

    void exception_1E(void) { prg_abort(0x1E); }

    void exception_1F(void) { prg_abort(0x1F); }

    // ------------------------------

    // Аварийный выход из программы

    // ------------------------------

    void prg_abort(int err)

    {

    vi_print(1, y++,"ERROR!!! ---> Произошло исключение", 0xc);

    real_mode(); // Возвращаемся в реальный режим

    // В реальном режиме выводим сообщение об исключении

    gotoxy(1, ++y);

    cprintf(" Исключение %X, нажмите любую клавишу", err);

    getch();

    textcolor(WHITE);

    textbackground(BLACK);

    clrscr();

    exit(0);

    }

    4.8 Файл INTPROC.C. Заглушки для аппаратных прерываний.

    #include

    #include

    #include

    #include

    #include "tos.h"

    // Заглушки для необрабатываемых

    // аппаратных прерываний.

    void iret0(void)

    { // первый контроллер прерываний

    asm {

    push ax

    mov al,EOI

    out MASTER8259A,al

    pop ax

    pop bp

    iret

    }

    }

    // -----------------------------------------------------------

    // второй контроллер прерываний

    void iret1(void)

    {

    asm {

    push ax

    mov al,EOI

    out MASTER8259A,al

    out SLAVE8259A,al

    pop ax

    pop bp

    iret

    }

    }

    4.9 Файл KEYB.C. Ввод символа с клавиатуры.

    #include

    #include

    #include

    #include

    #include "tos.h"

    extern word key_code;

    // Функция, ожидающая нажатия любой

    // клавиши и возвращающая её скан-код

    unsigned int kb_getch(void)

    {

    asm int 30h

    return (key_code);

    }

    4.10 Файл KEYBOARD.ASM. Процедуры для работы с клавиатурой.

    IDEAL

    MODEL SMALL

    RADIX 16

    P286

    include "tos.inc"

    ; ------------------------------------------

    ; Модуль обслуживания клавиатуры

    ; ------------------------------------------

    PUBLIC _Keyb_int, _Int_30h_Entry, _key_code, _keyb_status

    EXTRN _beep:PROC

    DATASEG

    _key_flag db 0

    _key_code dw 0

    ext_scan db 0

    _keyb_status dw 0

    CODESEG

    PROC _Keyb_int NEAR

    cli

    call _beep

    push ax

    mov al, [ext_scan]

    cmp al, 0

    jz normal_scan1

    cmp al, 0e1h

    jz pause_key

    in al, 60h

    cmp al, 2ah

    jz intkeyb_exit_1

    cmp al, 0aah

    jz intkeyb_exit_1

    mov ah, [ext_scan]

    call Keyb_PutQ

    mov al, 0

    mov [ext_scan], al

    jmp intkeyb_exit

    pause_key:

    in al, 60h

    cmp al, 0c5h

    jz pause_key1

    cmp al, 45h

    jz pause_key1

    jmp intkeyb_exit

    pause_key1:

    mov ah, [ext_scan]

    call Keyb_PutQ

    mov al, 0

    mov [ext_scan], al

    jmp intkeyb_exit

    normal_scan1:

    in al, 60h

    cmp al, 0feh

    jz intkeyb_exit

    cmp al, 0e1h

    jz ext_key

    cmp al, 0e0h

    jnz normal_scan

    ext_key:

    mov [ext_scan], al

    jmp intkeyb_exit

    intkeyb_exit_1:

    mov al, 0

    mov [ext_scan], al

    jmp intkeyb_exit

    normal_scan:

    mov ah, 0

    call Keyb_PutQ

    intkeyb_exit:

    in al, 61h

    mov ah, al

    or al, 80h

    out 61h, al

    xchg ah, al

    out 61h, al

    mov al,EOI

    out MASTER8259A,al

    pop ax

    sti

    iret

    jmp _Keyb_int

    ENDP _Keyb_int

    PROC Keyb_PutQ NEAR

    push ax

    cmp ax, 002ah ; L_SHIFT down

    jnz @@kb1

    mov ax, [_keyb_status]

    or ax, L_SHIFT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb1:

    cmp ax, 00aah ; L_SHIFT up

    jnz @@kb2

    mov ax, [_keyb_status]

    and ax, NL_SHIFT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb2:

    cmp ax, 0036h ; R_SHIFT down

    jnz @@kb3

    mov ax, [_keyb_status]

    or ax, R_SHIFT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb3:

    cmp ax, 00b6h ; R_SHIFT up

    jnz @@kb4

    mov ax, [_keyb_status]

    and ax, NR_SHIFT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb4:

    cmp ax, 001dh ; L_CTRL down

    jnz @@kb5

    mov ax, [_keyb_status]

    or ax, L_CTRL

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb5:

    cmp ax, 009dh ; L_CTRL up

    jnz @@kb6

    mov ax, [_keyb_status]

    and ax, NL_CTRL

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb6:

    cmp ax, 0e01dh ; R_CTRL down

    jnz @@kb7

    mov ax, [_keyb_status]

    or ax, R_CTRL

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb7:

    cmp ax, 0e09dh ; R_CTRL up

    jnz @@kb8

    mov ax, [_keyb_status]

    and ax, NR_CTRL

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb8:

    cmp ax, 0038h ; L_ALT down

    jnz @@kb9

    mov ax, [_keyb_status]

    or ax, L_ALT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb9:

    cmp ax, 00b8h ; L_ALT up

    jnz @@kb10

    mov ax, [_keyb_status]

    and ax, NL_ALT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb10:

    cmp ax, 0e038h ; R_ALT down

    jnz @@kb11

    mov ax, [_keyb_status]

    or ax, R_ALT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb11:

    cmp ax, 0e0b8h ; R_ALT up

    jnz @@kb12

    mov ax, [_keyb_status]

    and ax, NR_ALT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb12:

    cmp ax, 003ah ; CAPS_LOCK up

    jnz @@kb13

    mov ax, [_keyb_status]

    xor ax, CAPS_LOCK

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb13:

    cmp ax, 00bah ; CAPS_LOCK down

    jnz @@kb14

    jmp keyb_putq_exit

    @@kb14:

    cmp ax, 0046h ; SCR_LOCK up

    jnz @@kb15

    mov ax, [_keyb_status]

    xor ax, SCR_LOCK

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb15:

    cmp ax, 00c6h ; SCR_LOCK down

    jnz @@kb16

    jmp keyb_putq_exit

    @@kb16:

    cmp ax, 0045h ; NUM_LOCK up

    jnz @@kb17

    mov ax, [_keyb_status]

    xor ax, NUM_LOCK

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb17:

    cmp ax, 00c5h ; NUM_LOCK down

    jnz @@kb18

    jmp keyb_putq_exit

    @@kb18:

    cmp ax, 0e052h ; INSERT up

    jnz @@kb19

    mov ax, [_keyb_status]

    xor ax, INSERT

    mov [_keyb_status], ax

    jmp keyb_putq_exit

    @@kb19:

    cmp ax, 0e0d2h ; INSERT down

    jnz @@kb20

    jmp keyb_putq_exit

    @@kb20:

    test ax, 0080h

    jnz keyb_putq_exit

    mov [_key_code], ax

    mov al, 0ffh

    mov [_key_flag], al

    keyb_putq_exit:

    pop ax

    ret

    ENDP Keyb_PutQ

    ; Обработчик программного прерывания

    ; для ввода с клавиатуры. По своим функциям

    ; напоминает прерывание INT 16 реального

    ; режима.

    PROC _Int_30h_Entry NEAR

    push ax dx

    ; Ожидаем прерывание от клавиатуры

    keyb_int_wait:

    sti

    nop

    nop

    cli

    ; Проверяем флаг, который устанавливается

    ; обработчиком аппаратного прерывания клавиатуры

    mov al, [_key_flag]

    cmp al, 0

    jz keyb_int_wait

    ; Сбрасываем флаг после прихода прерывания

    mov al, 0

    mov [_key_flag], al

    sti

    pop dx ax

    iret

    ENDP _Int_30h_Entry

    END

    4.11 Файлы SCREEN.H и SCREEN.C – модуль для работы с видеоадаптером.

    4.11.1 SCREEN.H

    #ifndef SCREEN_H

    #define SCREEN_H

    // Границы перемещения бегунков

    #define B_SIZE 70

    // Структура, описывающая бегунок

    typedef struct _TLabel

    {

    char Pos; // Позиция бегунка

    char Dir; // Направление движения

    } TLabel;

    extern void StepLabel(TLabel* Label1, TLabel* Label2, char* Buf);

    #endif

    4.11.2 SCREEN.C

    #include

    #include

    #include

    #include

    #include "tos.h"

    #include "screen.h"

    void vi_putch(unsigned int x, unsigned int y ,char c, char attr);

    char hex_tabl[] = "0123456789ABCDEF";

    // Вывод байта на экран, координаты (x,y),

    // выводится шестнадцатеричное представление

    // байта chr с экранными атрибутами attr.

    void vi_put_byte(unsigned int x,

    unsigned int y, unsigned char chr, char attr)

    {

    unsigned char temp;

    temp = hex_tabl[(chr & 0xf0) >> 4];

    vi_putch(x, y, temp, attr);

    temp = hex_tabl[chr & 0xf];

    vi_putch(x+1, y, temp, attr);

    }

    // Вывод слова на экран, координаты (x,y),

    // выводится шестнадцатеричное представление

    // слова chr с экранными атрибутами attr.

    void vi_put_word(unsigned int x,

    unsigned int y, word chr, char attr)

    {

    vi_put_byte(x, y, (chr & 0xff00) >> 8, attr);

    vi_put_byte(x+2, y, chr & 0xff, attr);

    }

    // Вывод символа c на экран, координаты - (x,y),

    // атрибут выводимого символа - attr

    void vi_putch(unsigned int x,

    unsigned int y ,char c, char attr)

    {

    register unsigned int offset;

    char far *vid_ptr;

    offset = (y*160) + (x*2);

    vid_ptr = MK_FP(VID_MEM_SELECTOR, offset);

    *vid_ptr++=c; *vid_ptr=attr;

    }

    // Вывод строки s на экран, координаты - (x,y),

    // атрибут выводимой строки - attr

    void vi_print(unsigned int x,

    unsigned int y, char *s, char attr)

    {

    while (*s)

    vi_putch(x++, y, *s++, attr);

    }

    // Вывод стоки сообщения о запуске программы

    void vi_hello_msg(void)

    {

    vi_print(0, 0,

    " Threads for DOS, "

    " Version 0.1/i286, Copyright (c) 2000 Eugeny Balahonov ",

    0x30);

    }

    // Вывод бегущей строки

    void StepLabel(TLabel* Label1, TLabel* Label2, char* Buf)

    {

    // Стираем символы меток

    Buf[Label1->Pos] = ' ';

    Buf[Label2->Pos] = ' ';

    // Если двигаемся налево

    if (Label1->Dir == 0)

    {

    // Если не дошли до крайней левой позиции

    if (Label1->Pos > 0)

    {

    Label1->Pos--;

    Buf[Label1->Pos] = '\\';

    }

    else

    {

    Label1->Dir = 1;

    Buf[Label1->Pos] = '/';

    }

    }

    // Если двигаемся направо

    else

    {

    // Если не дошли до крайней правой позиции

    if (Label1->Pos < B_SIZE)

    {

    Label1->Pos++;

    Buf[Label1->Pos] = '/';

    }

    else

    {

    Label1->Dir = 0;

    Buf[Label1->Pos] = '\\';

    }

    }

    // Если двигаемся налево

    if (Label2->Dir == 0)

    {

    // Если не дошли до крайней левой позиции

    if (Label2->Pos > 0)

    {

    Label2->Pos--;

    Buf[Label2->Pos] = '\\';

    }

    else

    {

    Label2->Dir = 1;

    Buf[Label2->Pos] = '/';

    }

    }

    // Если двигаемся направо

    else

    {

    // Если не дошли до крайней правой позиции

    if (Label2->Pos < B_SIZE)

    {

    Label2->Pos++;

    Buf[Label2->Pos] = '/';

    }

    else

    {

    Label2->Dir = 0;

    Buf[Label2->Pos] = '\\';

    }

    }

    }

    4.12 Файл TOSSYST.ASM. Процедуры для инициализации, перехода в защищённый

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

    задач.

    IDEAL

    MODEL SMALL

    RADIX 16

    P286

    DATASEG

    include "tos.inc"

    PUBLIC _beep

    ; Область памяти для инициализации IDTR

    idtr idtr_struc

    ; Область памяти для инициализации GDTR

    gdt_ptr dw (8*15)-1 ; размер GDT, 15 элементов

    gdt_ptr2 dw ?

    gdt_ptr4 dw ?

    ; Область памяти для записи селектора задачи,

    ; на которую будет происходить переключение

    new_task dw 00h

    new_select dw 00h

    ; Область памяти для хранения регистров,

    ; используется для возврата в реальный режим

    real_ss dw ?

    real_sp dw ?

    real_es dw ?

    protect_sel dw ?

    init_tss dw ?

    CODESEG

    PUBLIC _real_mode,_protected_mode,_jump_to_task

    PUBLIC _load_task_register, _load_idtr, _enable_interrupt

    ; -------------------------------------------------------------------

    ; Процедура для переключения в защищённый режим.

    ; Прототип для вызова:

    ; void protected_mode(unsigned long gdt_ptr, unsigned int gdt_size,

    ; unsigned int cseg, unsigned int dseg)

    ; -------------------------------------------------------------------

    PROC _protected_mode NEAR

    push bp

    mov bp,sp

    ; Параметр gdt_ptr

    mov ax,[bp+4] ; мл. слово адреса GDT

    mov dx,[bp+6] ; ст. слово адреса GDT

    mov [gdt_ptr4], dx ; запоминаем адрес GDT

    mov [gdt_ptr2], ax

    ; Параметр gdt_size

    mov ax,[bp+8] ; получаем размер GDT

    mov [gdt_ptr], ax ; и запоминаем его

    ; Параметры cseg и dseg

    mov ax,[bp+10d] ; получаем селектор сегмента кода

    mov dx,[bp+12d] ; получаем селектор сегмента данных

    mov [cs:p_mode_select], ax ; запоминаем для команды

    mov [protect_sel], dx ; перехода far jmp

    ; Подготовка к возврату в реальный режим

    push ds ; готовим адрес возврата

    mov ax,40h ; из защищённого режима

    mov ds,ax

    mov [WORD 67h],OFFSET shutdown_return

    mov [WORD 69h],cs

    pop ds

    ; Запрещаем и маскируем все прерывания

    cli

    in al, INT_MASK_PORT

    and al, 0ffh

    out INT_MASK_PORT, al

    ; Записываем код возврата в CMOS-память

    mov al,8f

    out CMOS_PORT,al

    jmp delay1

    delay1:

    mov al,5

    out CMOS_PORT+1,al

    call enable_a20 ; открываем линию A20

    mov [real_ss],ss ; запоминаем регистры SS и ES

    mov [real_es],es

    ; Перепрограммируем контроллер прерываний

    ; для работы в защищённом режиме

    mov dx,MASTER8259A

    mov ah,20

    call set_int_ctrlr

    mov dx,SLAVE8259A

    mov ah,28

    call set_int_ctrlr

    ; Загружаем регистры IDTR и GDTR

    lidt [FWORD idtr]

    lgdt [QWORD gdt_ptr]

    mov ax, 0001h ; переключаем процессор

    lmsw ax ; в защищённый режим

    ; jmp far flush

    db 0eah

    dw OFFSET flush

    p_mode_select dw ?

    LABEL flush FAR

    mov dx, [protect_sel]

    mov ss, dx

    mov ds, dx

    mov es, dx

    ; Обнуляем содержимое регистра LDTR

    mov ax, 0

    lldt ax

    pop bp

    ret

    ENDP _protected_mode

    ; ----------------------------------------------------

    ; Возврат в реальный режим.

    ; Прототип для вызова

    ; void real_mode();

    ; ----------------------------------------------------

    PROC _real_mode NEAR

    ; Сброс процессора

    cli

    mov [real_sp], sp

    mov al, SHUT_DOWN

    out STATUS_PORT, al

    rmode_wait:

    hlt

    jmp rmode_wait

    LABEL shutdown_return FAR

    ; Вернулись в реальный режим

    mov ax, DGROUP

    mov ds, ax

    assume ds:DGROUP

    mov ss,[real_ss]

    mov sp,[real_sp]

    in al, INT_MASK_PORT

    and al, 0

    out INT_MASK_PORT, al

    call disable_a20

    mov ax, DGROUP

    mov ds, ax

    mov ss, ax

    mov es, ax

    mov ax,000dh

    out CMOS_PORT,al

    sti

    ret

    ENDP _real_mode

    ; -------------------------------------------------------

    ; Загрузка регистра TR.

    ; Прототип для вызова:

    ; void load_task_register(unsigned int tss_selector);

    ; -------------------------------------------------------

    PROC _load_task_register NEAR

    push bp

    mov bp,sp

    ltr [bp+4] ; селектор для текущей задачи

    pop bp

    ret

    ENDP _load_task_register

    ; -------------------------------------------------------

    ; Переключение на задачу.

    ; Прототип для вызова:

    ; void jump_to_task(unsigned int tss_selector);

    ; -------------------------------------------------------

    PROC _jump_to_task NEAR

    push bp

    mov bp,sp

    mov ax,[bp+4] ; получаем селектор

    ; новой задачи

    mov [new_select],ax ; запоминаем его

    jmp [DWORD new_task] ; переключаемся на

    ; новую задачу

    pop bp

    ret

    ENDP _jump_to_task

    ; ------------------------------

    ; Открываем линию A20

    ; ------------------------------

    PROC enable_a20 NEAR

    push ax

    mov al, A20_PORT

    out STATUS_PORT, al

    mov al, A20_ON

    out KBD_PORT_A, al

    pop ax

    ret

    ENDP enable_a20

    ; ------------------------------

    ; Закрываем линию A20

    ; ------------------------------

    PROC disable_a20 NEAR

    push ax

    mov al, A20_PORT

    out STATUS_PORT, al

    mov al ,A20_OFF

    out KBD_PORT_A, al

    pop ax

    ret

    ENDP disable_a20

    ; -----------------------------------------------------------

    ; Готовим структуру для загрузки регистра IDTR

    ; Прототип для вызова функции:

    ; void load_idtr(unsigned long idt_ptr, word idt_size);

    ; -----------------------------------------------------------

    PROC _load_idtr NEAR

    push bp

    mov bp,sp

    mov ax,[bp+4] ; мл. слово адреса IDT

    mov dx,[bp+6] ; ст. слово адреса IDT

    mov bx, OFFSET idtr

    ; Запоминаем адрес IDTR в структуре

    mov [(idtr_struc bx).idt_low], ax

    mov [(idtr_struc bx).idt_hi], dl

    ; Получаем предел IDT и запоминаем его в структуре

    mov ax, [bp+8]

    mov [(idtr_struc bx).idt_len], ax

    pop bp

    ret

    ENDP _load_idtr

    ; ----------------------------------

    ; Установка контроллера прерываний

    ; ----------------------------------

    PROC set_int_ctrlr NEAR

    mov al, 11

    out dx, al

    jmp SHORT $+2

    mov al, ah

    inc dx

    out dx, al

    jmp SHORT $+2

    mov al, 4

    out dx, al

    jmp SHORT $+2

    mov al, 1

    out dx, al

    jmp SHORT $+2

    mov al, 0ffh

    out dx, al

    dec dx

    ret

    ENDP set_int_ctrlr

    ; --------------------------

    ; Выдача звукового сигнала

    ; --------------------------

    PROC _beep NEAR

    push ax bx cx

    in al,KBD_PORT_B

    push ax

    mov cx,80

    beep0:

    push cx

    and al,11111100b

    out KBD_PORT_B,al

    mov cx,60

    idle1:

    loop idle1

    or al,00000010b

    out KBD_PORT_B,al

    mov cx,60

    idle2:

    loop idle2

    pop cx

    loop beep0

    pop ax

    out KBD_PORT_B,al

    pop cx bx ax

    ret

    ENDP _beep

    ; -------------------------------

    ; Задержка выполнения программы

    ; -------------------------------

    PROC _pause NEAR

    push cx

    mov cx,10

    ploop0:

    push cx

    xor cx,cx

    ploop1:

    loop ploop1

    pop cx

    loop ploop0

    pop cx

    ret

    ENDP _pause

    ; -----------------------

    ; Размаскирование прерываний

    ; -----------------------

    PROC _enable_interrupt NEAR

    in al, INT_MASK_PORT

    and al, 0fch

    out INT_MASK_PORT, al

    sti

    ret

    ENDP _enable_interrupt

    end

    5. Выводы.

    Процессоры семейства Intel x86 реализуют необходимые средства для

    организации мультизадачных ОС с разделением адресного пространства и

    виртуальной памяти.

    В процессе написания данного курсового проекта мной были изучена

    организация работы защищенного режима процессоров 80286, адресация ими

    свыше 1 Мб памяти, работа с прерываниями в защищенном режиме процессора,

    организация мультизадачных операционных систем.

    6. Литература.

    1. «Защищенный режим процессоров Intel 80286/80386/80486» © Александр

    Фролов, Григорий Фролов Том 6, М.: Диалог-МИФИ, 1993, 234 стр.

    2. «MS-DOS для программиста» © Александр Фролов, Григорий Фролов

    Том 18, часть 1, М.: Диалог-МИФИ, 1995, 254 стр.

    3. «MS-DOS для программиста» © Александр Фролов, Григорий Фролов

    Том 19, часть 2, М.: Диалог-МИФИ, 1995, 253 стр.

    4. «Язык Ассемблера для IBM PC и программирования» © Питер Абель, М.:

    «Высшая школа», Москва, 1992, 444 стр.

    5. «Язык программирования для персонального компьютера Си», © С.О.

    Бочков, Д.М. Субботин, М.: Диалог-МИФИ, 1990, 383 стр.

    6. Материалы WEB-сервера для разработчиков фирмы Intel

    http://developer.intel.com

    Страницы: 1, 2, 3


    Приглашения

    09.12.2013 - 16.12.2013

    Международный конкурс хореографического искусства в рамках Международного фестиваля искусств «РОЖДЕСТВЕНСКАЯ АНДОРРА»

    09.12.2013 - 16.12.2013

    Международный конкурс хорового искусства в АНДОРРЕ «РОЖДЕСТВЕНСКАЯ АНДОРРА»




    Copyright © 2012 г.
    При использовании материалов - ссылка на сайт обязательна.