How can I call the previous BIOS interrupt from an interrupt I've installed?
It crashes when executing:
Code: Select all
jmp far dword[old10h]
Here is my code. What I want to do is create a program that installs an INT 10h vector that first calls the original video BIOS services and then sets up the VGA registers manually for standard VGA modes 3h, 4h, 12h, 13h, etc. This enables displaying CGA/EGA/VGA graphics under Windows 7 32-bit if you disable video driver/open Alt+Enter fullscreen console/reenable video driver (I've planned to enable this for being able to make use of old graphical DOS programs for which I don't have source under Windows 7 by calling the modified INT 10h regularly every time console graphics become unloaded):
New ISR:
Code: Select all
;nasm 710patch.asm -o 710patch.bin
;Copy it to 7FFF:0000
;or other free 64K segment
org 0
bits 16
old10h:
offset10h dw 4
segment10h dw 0x7FFF
_int10h:
;Save return address:
;;
pop word[_FLAGS]
pop word[_IP]
pop word[_CS]
;Build an IRET return address/FLAGS:
;;
pushf
cli
push cs
push word ret0
jmp far dword[old10h] ;This pointer is set up in zulia.asm
;Control to see if it crashes
;in the very previous line:
;;
ret0:
jmp $
;Build final return address:
;;
push word[_CS]
push word[_IP]
push word[_FLAGS]
iret
_FLAGS dw 0
_IP dw 0
_CS dw 0
_EAX dd 0
_EBX dd 0
_ECX dd 0
_EDX dd 0
_ESI dd 0
_EDI dd 0
_EBP dd 0
align 16
COM program to install the ISR:
Code: Select all
;nasm zulia.asm -o zulia.com
org 100h
bits 16
;Write text mode ZULIA screen
;;
;If patch is already installed, skip:
;;
;If DWORD at 0000h:10h*4 is == 0x7FFF0004,
;we have already installed it.
;
;Just display the splash.
;Copy interrupt vector.
;It's in format:
;
;Word 0 -- Offset
;Word 1 -- Segment
;;
mov esi,10h*4
xor eax,eax
push ds
pop es
push ds
push word 0
pop ds ;DS:SI base == 0 (real mode IVT)
mov edi,[esi] ;Get old IDT vector
mov [es:old10h],edi ;Save in old variable
mov edi,0x7FFF0004 ;Set new vector
mov dword[esi],edi ;Place new pointer
pop ds
;Copy patch to destination segment:
;7FFF:0000:
;;
push es
mov esi,patch10h ;DS:ESI == our embedded ISR
push word 0x7FFF ;ES:EDI - Segment 7FFF:0000
pop es
xor edi,edi
mov ecx,patch10h_SZ
;Align REP instruction to DWORD/WIDEWORD
;to make it faster:
;;
align 4
rep movsb
pop es
mov ax,4C00h
int 21h
;The order of labels according
;of structure:
;;
align 4
old10h:
patch10h:
incbin "710patch.bin"
patch10h_END:
patch10h_SZ equ (patch10h_END-patch10h)/10*10