📄 tsrsub.asm
字号:
IDEAL
P386
SMART
MODEL COMPACT,C
GLOBAL C int8h_proc:FAR
GLOBAL C int10h_proc:FAR
GLOBAL C set_old10h_proc:NEAR
GLOBAL C generic_oldint10h_for_c_code:NEAR
GLOBAL C get_reg:NEAR
GLOBAL C set_reg:NEAR
EXTRN C int8h_sub:PROC
EXTRN C int10h_sub:PROC
ofsAX equ 10h
ofsBX equ 0Eh
ofsCX equ 0Ch
ofsDX equ 0Ah
ofsES equ 08h
ofsDS equ 06h
ofsSI equ 04h
ofsDI equ 02h
ofsBP equ 00h
NEXT_STACK equ 512
STACK_SIZE equ (NEXT_STACK * 8)
CODESEG
PROC set_old10h_proc NEAR value:dword
USES EAX
mov eax, [value]
mov [dword ptr cs:self_modifying_code+1], eax
ret
ENDP
PROC generic_oldint10h_for_c_code NEAR
;
; in regtop:word
;
push bp
mov bp, sp
mov bp, [bp + 4]
call generic_oldint10h
pop bp
ret
ENDP
PROC generic_oldint10h NEAR
;
; in bp regtop
;
push ax bx cx dx es ds si di bp
mov ax, [bp + ofsAX]
mov bx, [bp + ofsBX]
mov cx, [bp + ofsCX]
mov dx, [bp + ofsDX]
push [word ptr bp + ofsES]
pop es
push [word ptr bp + ofsDS]
pop ds
mov si, [bp + ofsSI]
mov di, [bp + ofsDI]
mov bp, [bp + ofsBP]
pushf
self_modifying_code:
call far 0000h:0000h
push bp
mov bp, sp
mov bp, [bp + 02h]
mov [bp + ofsAX], ax
mov [bp + ofsBX], bx
mov [bp + ofsCX], cx
mov [bp + ofsDX], dx
mov ax, es
mov [bp + ofsES], ax
mov ax, ds
mov [bp + ofsDS], ax
mov [bp + ofsSI], si
mov [bp + ofsDI], di
pop ax
mov [bp + ofsBP], ax
pop bp di si ds es dx cx bx ax
ret
ENDP
PROC int10h_proc FAR
cli
inc [byte ptr cs:re_entrant]
cmp [byte ptr cs:re_entrant], STACK_SIZE / NEXT_STACK
jne L01
sti ; too many nest
L02: ; we can not prepare own stack any longer
jmp L02 ; start infinite loop
L01:
push [word ptr cs:prev_ss]
push [word ptr cs:prev_sp]
mov [word ptr cs:prev_ss], ss
mov [word ptr cs:prev_sp], sp
mov sp, cs
mov ss, sp
mov sp, OFFSET my_stack + STACK_SIZE ; we must prepare own stack
sub sp, [word ptr cs:next_sp_offset] ; because there will be only
add [word ptr cs:next_sp_offset], NEXT_STACK ; 60bytes for stack when
; called from DPMI service
push ax bx cx dx es ds si di bp
mov bp, DGROUP
mov ds, bp
mov bp, sp
sub sp, 108
FSAVE [bp - 108] ; save 80387 state
push bp ; top address of 8086 register structure
; for calling old int10h
call int10h_sub ; call C routine in TSR.C
pop bp
FRSTOR [bp - 108] ; restore 80387 state
add sp, 108
test ax, ax
jnz Lret ; done it
call generic_oldint10h
Lret:
pop bp di si ds es dx cx bx ax
cli
mov ss, [word ptr cs:prev_ss] ; restore stack
mov sp, [word ptr cs:prev_sp] ;
pop [word ptr cs:prev_sp] ;
pop [word ptr cs:prev_ss] ;
dec [byte ptr cs:re_entrant] ; nest -= 1;
sub [word ptr cs:next_sp_offset], NEXT_STACK
iret
ENDP
PROC get_reg NEAR regtop:word, offset:word
USES BX
mov bx, [regtop]
add bx, [offset]
mov ax, [word ptr ss:bx]
ret
ENDP
PROC set_reg NEAR regtop:word, offset:word, value:word
USES AX,BX,DI
mov ax, [value]
mov bx, [regtop]
mov di, [offset]
mov [word ptr ss:bx + di], ax
ret
ENDP
PROC int8h_proc FAR
cli
mov [word ptr cs:prev_ss_int8h], ss
mov [word ptr cs:prev_sp_int8h], sp
mov sp, cs
mov ss, sp
mov sp, OFFSET my_stack_int8h
push ax bx cx dx es ds si di bp
mov bp, DGROUP
mov ds, bp
sub sp, 108
mov bp, sp
FSAVE [bp] ; save 80387 state
call int8h_sub ; call C routine in TSR.C
mov bp, sp
FRSTOR [bp] ; restore 80387 state
add sp, 108
pop bp di si ds es dx cx bx ax
cli
mov ss, [word ptr cs:prev_ss_int8h] ; restore stack
mov sp, [word ptr cs:prev_sp_int8h] ;
iret
ENDP
DB 1024 DUP (0)
my_stack_int8h:
my_stack:
DB STACK_SIZE DUP (0)
prev_ss_int8h:
DW 0
prev_sp_int8h:
DW 0
prev_ss:
DW 0
prev_sp:
DW 0
next_sp_offset:
DW 0
re_entrant:
DB 0
END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -