Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Перехват 16 прерывания 
:(
    Опции темы
MarkedOne
Дата 13.6.2008, 17:37 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 18
Регистрация: 8.2.2008

Репутация: нет
Всего: нет



Написал программу, котороя перехватывает 16 прерывание, если вызвана функция 10h(ожидание нажатия на любую клавишу), то выводится сообщение и управление передается оригинальному обработчику.
Запустил её, потом нажимаю на любую клавишу и выскакивает ошибка:
Цитата(16-разрядная подсистема MS-DOS)

PROG04.com
Процессор NTVDM обнаружил недопустимую инструкцию.
CS:00a7 IP:0094 OP:2e fe d7 28 2e Дла завершения работы приложения нажмите кнопку "Закрыть".


Вот код:
Код

CSEG segment
org 100h

Start:
    jmp Init

    ;обработчик 16 прерывания
    int_16h proc                  
      ;если 10h функция(ожидание нажатия на любую клавишу), то на метку Ok_10h    
      cmp ah, 10h 
      je Ok_10
      ;Иначе вызываем оригинальный обработчик 
      jmp dword ptr cs:[Old_16h] 
    ok_10:
      ;сохраняем используемые регистры
      push ax 
      push dx
      ;В ds - текущий сегмент
      push cs 
      pop ds
      ;Выводим строку на экран
      mov ah, 9 
      mov dx, offset Wait_Mes
      int 21h
      ;Сохраняем флаги  
      pushf 
      ;Вызываем оригинальный обработчик
      call dword ptr cs:[Old_16h] 
      ;Восстанавливаем регистры  
      pop dx 
      pop ax
      ;Выходим из прерывания
      iret      

     ;адрес оригинального прерывания 
      Old_16h dd ?    
      Wait_Mes db 13, 10, 'Нажмите любую клавишу...$' 

    int_16h endp

Init:
    mov ax, 3516h     
    int 21h
    mov word ptr Old_16h, bx
    mov word ptr Old_16h+2, es

    mov ax, 2516h
    mov dx, offset int_16h
    int 21h

    mov dx, offset init
    int 27h

CSEG ends
end Start



PM MAIL WWW   Вверх
Akina
Дата 13.6.2008, 21:04 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20581
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 1
Всего: 454



Из обработчика 16 прерывания нельзя вызывать прерывания ДОС (за редким исключением, причем функция 9 прерывания 21 в этот список не входит).
Используйте для вывода на экран прерывания БИОС.


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
MarkedOne
Дата 14.6.2008, 13:00 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 18
Регистрация: 8.2.2008

Репутация: нет
Всего: нет



Цитата(Akina @  13.6.2008,  21:04 Найти цитируемый пост)
 прерывания БИОС

А какое именно?

PM MAIL WWW   Вверх
MarkedOne
Дата 14.6.2008, 14:11 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 18
Регистрация: 8.2.2008

Репутация: нет
Всего: нет



Я немного переделал программу, и теперь 21h прерывание вызывается подругому:
Код

...
      push dx
      push cs
      pop ds
      mov ah, 9
      mov dx, offset Wait_Mes
      pushf
      call dword ptr cs:[int_21h]  ;Вызываем 21h преывание как процедуру
...
      int_21h dd ? 
...
      Wait_Mes db 13, 10, 'Нажмите любую клавишу...$'
...
    mov ax, 3521h  ;Получаем адрес 21h прерывания
    int 21h
    mov word ptr int_21h, bx
    mov word ptr int_21h+2, es
...


Но ошибка всё равно вылетает. И еще, я заметил что если убрать строки:
Код

 push cs
 pop ds

то ошибки нет, но при вызове 10h функции 16h прерывания ничего не выводится. С помощью этих команд я загружаю в cs текущий сегмент, ведь строка находится в том же сегменте что и прерывание!
PM MAIL WWW   Вверх
Akina
Дата 14.6.2008, 20:36 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20581
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 1
Всего: 454



Цитата(MarkedOne @  14.6.2008,  14:00 Найти цитируемый пост)
А какое именно?

Видео, вывод в режиме TTY

Цитата(MarkedOne @  14.6.2008,  15:11 Найти цитируемый пост)
ошибка всё равно вылетает.

т.е. программеры в МС таки не идиоты...

Цитата(MarkedOne @  14.6.2008,  15:11 Найти цитируемый пост)
я заметил что если убрать строки:

А я вообще не понимаю, почему вы присваиваете себе право менять содержимое регистров? После окончания работы обработчика ВСЕ регистры (кроме IP) должны содержать то же, что и до вызова... меняете AX, DX, DS? озаботьтесь восстановить перед выходом.


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
MarkedOne
Дата 14.6.2008, 21:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 18
Регистрация: 8.2.2008

Репутация: нет
Всего: нет



Точно! Я забыл сохранить регистр DS, а остальные сохранил

Добавлено @ 21:26
Теперь всё нормально запускается. Но строка не выводится.
Цитата(Akina @  14.6.2008,  20:36 Найти цитируемый пост)
Видео, вывод в режиме TTY

Вы про функцию 13h 10h-ого прерывания?
Или про прямой вывод, через видеопамять?

Это сообщение отредактировал(а) MarkedOne - 14.6.2008, 21:48
PM MAIL WWW   Вверх
Akina
Дата 15.6.2008, 22:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Советчик
****


Профиль
Группа: Модератор
Сообщений: 20581
Регистрация: 8.4.2004
Где: Зеленоград

Репутация: 1
Всего: 454



Цитата(MarkedOne @  14.6.2008,  22:18 Найти цитируемый пост)
Вы про функцию 13h 10h-ого прерывания?

да


--------------------
 О(б)суждение моих действий - в соответствующей теме, пожалуйста. Или в РМ. И высшая инстанция - Администрация форума.

PM MAIL WWW ICQ Jabber   Вверх
MarkedOne
Дата 16.6.2008, 14:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 18
Регистрация: 8.2.2008

Репутация: нет
Всего: нет



Спасибо за помощь
PM MAIL WWW   Вверх
mb78
Дата 11.7.2008, 22:48 (ссылка)    | (голосов:1) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 19
Регистрация: 11.7.2008

Репутация: нет
Всего: нет



Вы перепутали! Функция 10h(для DOS) -это видео Bios. А  клавиатура- 16h(32 в 10-тичной системе).
Выясните лучше , 16 или 16h вы хотите перехватить.
Например если 16h-то:
mov AX,16h   если 10h(16)то - mov AX,10h
mov BL,4
mul BL
mov CX,0
mov ES,CX
mov DI,AX
MOV AX,сюда введите строку ,куда перейти, если будет int 16
CLD
STOSW
MOV AX, СЮДА ВВЕДИТЕ СЕГМЕНТ,НА КОТОРЫЙ НУЖНО ПЕРЕЙТИ ,ЕСЛИ ТОТ ЖЕ,ГДЕ САМА ПРОГРАММА,ТО ВВЕДИТЕ CS
STOSW

Все теперь прерывание будет переходить по этому адресу.Можно конечно воспользоваться прерыванием int 21 при ah=25h
для изменения прерывания ,но я это пробовал ,у меня из Windows это не получилось,а когда сделал вручную,то вышло.

Это сообщение отредактировал(а) mb78 - 11.7.2008, 22:56
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Asm для Windows/DOS"
MAKCim
  • Проставьте несколько ключевых слов темы, чтобы её можно было легче найти.
  • Не забывайте пользоваться кнопкой КОД.
  • Телепатов на форуме нет! Задавайте чёткий, конкретный и полный вопрос. Указывайте полностью ошибки компилятора и компоновщика.
  • Новое сообщение должно иметь прямое отношение к разделу форума. Флуд, флейм, оффтопик запрещены.
  • Категорически запрещается обсуждение вареза, "кряков", взлома программ и т.д.

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, MAKCim.

 
 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Asm для Windows/Dos | Следующая тема »


 




[ Время генерации скрипта: 0.0642 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.