Пытаюсь установить собственное прерывание int 49, например ..... lidt [idtr] mov eax,int49_handler mov [idt+49*8],ax mov word [idt+49*8+2],0x8 mov word [idt+49*8+4],0x8E00 shr eax,16 mov [idt+49*8+6],ax sti int 49 int49_handler: mov al,'+' mov [0xB8000],al iret ..комп перезагружается на iret Подскажите пожалуйста, в чем дело?
Narkomanius опкод у них одинаков 0CFh - Это завист от режима... speck У меня тоже прикол с прерываниями в 16 битном работают как надо а в 32х битном - прерывание выполняется но по IRET не возвращается - а вызывает исключение общей защиты и фиг знает почему
А у меня, почему-то, прерывание выполняется и по IRET возвращается, но вызывает "Двойную ошибку". В чем может быть проблема и как правильно описывать обработчики эксепшнов?
Возможно sti разрешает аппаратные прерывания которые ты не обрабатываешь А для вызова своего прерывания программно это не нужно - попробуй убрать
не так уж и важно - в 16 битах ведь работает. а вот вылет по #DF указывает на то что было #GP и кто то еше - #PF может? скорее всего тут мы имеем дело со не правильнобитнымстеком. давай сюда код оброботчика и дескрипторы которые юзаются
[BITS 16] [ORG 0x9000] _start: cli mov ax, cs mov ds, ax mov ss, ax mov sp, _start in al,70h or al,80h out 70h,al in al,0x92 or al,2 out 0x92,al lgdt [GDTR] lidt [IDTR] mov eax,cr0 or al,1 mov cr0,eax jmp 0x08:_protected [BITS 32] _protected: mov ax,0x10 mov ds,ax mov ss,ax mov es,ax mov esp,9000 call setup_idt sti int 4 ;Например... Врезультате получаю int 4 + #DF p: jmp p ;-------------------------------- setup_idt: mov ecx,0 mov eax,isr00 call set_int_descriptor mov eax,isr01 call set_trap_descriptor mov eax,isr02 call set_int_descriptor mov eax,isr03 call set_trap_descriptor mov eax,isr04 call set_trap_descriptor mov eax,isr05 call set_int_descriptor ..................... mov eax,isr13 call set_int_descriptor set_idt_descriptor: mov [IDT+ecx*8],ax mov word [IDT+ecx*8+2],0x8 mov word [IDT+ecx*8+4],0x8E00 shr eax,16 mov [IDT+ecx*8+6],ax inc ecx ret set_int_descriptor: mov dx,0x8E00 call set_idt_descriptor ret set_trap_descriptor: mov dx,0x8F00 call set_idt_descriptor ret ;------------------------------------------------ isr00: mov al,'0' mov [0xB8000+2],al iretd isr01: mov al,'1' mov [0xB8000],al iretd isr02: mov al,'2' mov [0xB8000+2],al iretd isr03: mov al,'3' mov [0xB8000+2],al iretd ................. isr13: mov al,'d' mov [0xB8000+2],al iretd ;------------------------------------------------ GDT: dw 0, 0, 0, 0 db 0xFF,0xFF,0x00,0x00,0x00,10011010b,0xCF,0x00 db 0xFF,0xFF,0x00,0x00,0x00,10010010b,0xCF,0x00 GDTR: dw 8192 dd GDT IDT: resw 256*8 IDTR: dw (256*8)-1 dd IDT
Спасибо... уже разобрался... Это таймер вызывает 8 исключение, т.к. я не перенапрравляю его прерывание.. Тогда дайте пожалуйста ссылочку или объясните кратенько прицип работы и програмитрования контроллера прарываний..
2 stel123, кратенько: В AT используются (или эмулируются) два контроллера прерываний (8259A): ведущий обслуживает IRQ0-7 (IRQ2 не используется), ведомый - IRQ8-15. Каждый контроллер использует два однобайтных порта: ведущий - 20h-21h, ведомый - A0h-A1h. Для инициализации контроллеров используются т. н. ICW1-4 (initialisation control word). Сначала в порт 20h (A0h) посылается ICW1, затем в порт 21h (A1h) - ICW2-4, последовательно. ICW1-4 для ведущего контроллера - 11h, int0, 4, 1Fh, для ведомого - 11h, int8, 2, 1Bh, где int0 и int8 - номер прерывания (кратный восьми) для IRQ0 (08) и IRQ8 (70h). Для управления используются OCW1-3 (из которых нужны только первые два), их можно посылать в любое время и в любом количестве. OCW1 посылается в порт 21h (A1h), остальные - в 20h (A0h). OCW1: установленные биты 0-7 избирательно запрещают IRQ0-7 (IRQ8-15). После инициализации контроллера все прерывания разрешены. OCW2: 20h - EOI (end of interrupt). Необходимо послать EOI ведущему конроллеру (для IRQ8-15 - еще и ведомому) перед IRET(D), иначе больше прерываний не будет. (Вся изложенная информация проверена мной на практике).
stel123 imho не думаю что дело в таймере, если ты не инициализировал контроллер прерываний есть предположение: если ты этот код грузиш с boot sectora дискеты то у тебя просто не помещается в 512b IDTR (хотя непонятно почему в таком случае org 0x9000, а не 0x7c00)
2 Narkomanius может надо 66 cf ? Гыгыгы - я такого не где не встречал - Этот кусок тебе интересен? _787454340__123.txt