📄 int21h.asm
字号:
mov fs:w[PSP_Handles],cx ;set new number.
xor ax,ax
clc
jmp @@sh0
;
@@shb2: ;Couldn't get the memory at the protected mode end of things
;so we need to put the DOS version back to its origional size.
;
mov ds,cs:Int21hDSeg
assume ds:_cwMain
mov ax,TotalHandles ;get total count needed.
assume ds:nothing
push ds
pop es
or ax,1
mov edi,offset Int21Buffer
mov es:Real_EAX[edi],6700h
mov es:Real_EBX[edi],eax
mov bl,21h
sys IntXX
stc
;
@@sh0: ;Finaly we pass our results back to the caller.
;
mov [ebp+Int_AX],ax
DOS4GExtend w[ebp+Int_EAX+2]
pushf
pop ax
and al,1
call Int21hAL2Carry ;Set carry.
ret
endif
Int21hSetHandles endp
;------------------------------------------------------------------------------
;
;Function 6C emulation.
;
Int21hExtendOpen proc near
mov ds,[ebp+Int_DS]
mov esi,[ebp+Int_ESI]
call Int21hExtend_DS_ESI ;Extend [E]SI.
xor al,al
call Int21hStringLen
inc ecx
mov es,fs:w[EPSP_TransProt]
xor edi,edi
rep movsb
mov edi,offset Int21Buffer
mov es,cs:Int21hDSeg
mov eax,[ebp+Int_EAX]
mov es:Real_EAX[edi],eax
mov eax,[ebp+Int_EBX]
mov es:Real_EBX[edi],eax
mov eax,[ebp+Int_ECX]
mov es:Real_ECX[edi],eax
mov eax,[ebp+Int_EDX]
mov es:Real_EDX[edi],edx
mov es:Real_ESI[edi],0
mov ax,fs:w[EPSP_TransReal]
mov es:Real_DS[edi],ax
mov bl,21h
sys IntXX
mov eax,es:Real_EAX[edi]
mov [ebp+Int_AX],ax
DOS4GExtend w[ebp+Int_EAX+2]
mov eax,es:Real_ECX[edi]
mov [ebp+Int_CX],ax
DOS4GExtend w[ebp+Int_ECX+2]
mov ax,es:Real_Flags[edi]
and al,1
call Int21hAL2Carry ;Set carry.
ret
Int21hExtendOpen endp
;------------------------------------------------------------------------------
;
;Function FF, DOS4G detection.
;
Int21hDOS4GTest proc near
;
;This check only allowed for 32-bit programs which is what DOS4G uses.
;
test cs:Int21hSystemFlags,1
jnz Int21hNotOurs
;
;Check register setup.
;
cmp b[ebp+Int_AL],0 ;AX=0FF00h
jnz Int21hNotOurs
cmp w[ebp+Int_DX],78h ;DX=0078h
jnz Int21hNotOurs
; changed for dummy segment modification
; mov w[ebp+Int_GS],ds
mov d[ebp+Int_EAX],4734ffffh
;
;Flag DOS4G mode for INT handling.
;
push ds
push eax
push ebx
push ecx
mov ecx,ds ; save application DS value
assume ds:nothing
mov ds,cs:Int21hDDSeg
assume ds:_Int21h
; give Watcom a dummy segment for it to stuff silly __D16SegInfo
; values in without trashing things, MED 12/12/95
mov ax,DOS16DummySegment
test ax,ax
jne setgs
push ecx ; save application DS value
; MED 07/15/97
DUMMYSEGMENTSIZE EQU 48h ; must be multiple of four
; mov ecx,44h ; dummy segment size
mov ecx,DUMMYSEGMENTSIZE
sys GetMem32 ; allocate the memory
jnc zerodummy ; no error allocating memory
pop ebx
push ebx ; use application DS value if can't create dummy value
jmp savedummy
; MED 07/15/97, zero out dummy segment
zerodummy:
push edx
push ds
mov ds,bx
mov ecx,DUMMYSEGMENTSIZE-4
dumloop:
mov DWORD PTR ds:[ecx],0
sub ecx,4
jns dumloop
pop ds
pop edx
savedummy:
add esp,4 ; throw away application DS value
mov DOS16DummySegment,bx
mov eax,ebx ; allocated memory or application DS selector to put in GS
setgs:
mov WORD PTR [ebp+Int_GS],ax
mov ds,cs:Int21hDSeg
assume ds:_cwMain
or DOS4GFlag,-1
assume ds:nothing
mov ds,cs:Int21hDDSeg
assume ds:_Int21h
or Int21hDOS4GFlag,-1
assume ds:nothing
pop ecx
pop ebx
pop eax
pop ds
;
ret
Int21hDOS4GTest endp
;------------------------------------------------------------------------------
;
;Get extended error information.
;
Int21hGetErrorInfo proc near
mov edi,offset Int21Buffer
mov es,cs:Int21hDSeg
mov eax,[ebp+Int_EAX]
mov es:Real_EAX[edi],eax
mov eax,[ebp+Int_EBX]
mov es:Real_EBX[edi],eax
mov bl,21h
sys IntXX
mov eax,es:Real_EAX[edi]
mov [ebp+Int_AX],ax
DOS4GExtend w[ebp+Int_EAX+2]
mov eax,es:Real_EBX[edi]
mov [ebp+Int_BX],ax
DOS4GExtend w[ebp+Int_EBX+2]
mov eax,es:Real_ECX[edi]
mov [ebp+Int_CX],ax
DOS4GExtend w[ebp+Int_ECX+2]
;
;LABEL string?
;
cmp w[ebp+Int_AX],22h
jnz @@done
mov ds,cs:Int21hDSeg
assume ds:_cwMain
mov ds,RealSegment
assume ds:nothing
mov eax,es:Real_EDI[edi]
movzx eax,ax
movzx esi,es:Real_ES[edi]
shl esi,4
add esi,eax
mov es,fs:[EPSP_TransProt]
mov [ebp+Int_ES],es
mov w[ebp+Int_DI],0
DOS4GExtend w[ebp+Int_EDI+2]
xor edi,edi
mov ecx,11
rep movsb
;
@@done: ret
Int21hGetErrorInfo endp
;------------------------------------------------------------------------------
;
;Extend SI into ESI if DS's limit is < 64K
;
;On Entry:
;
;DS:[E]SI - Pointer to convert.
;
;On Exit:
;
;DS:ESI - Valid [extended] pointer.
;
;All other registers preserved.
;
Int21hExtend_DS_ESI proc near
push eax
xor eax,eax
mov ax,ds
lsl eax,eax
cmp eax,10000h
jnc @@32Bit
movzx esi,si
@@32Bit: pop eax
ret
Int21hExtend_DS_ESI endp
;------------------------------------------------------------------------------
;
;Extend DI into EDI if ES's limit is < 64K
;
;On Entry:
;
;ES:[E]DI - Pointer to convert.
;
;On Exit:
;
;ES:EDI - Valid [extended] pointer.
;
;All other registers preserved.
;
Int21hExtend_ES_EDI proc near
push eax
xor eax,eax
mov ax,es
lsl eax,eax
cmp eax,10000h
jnc @@32Bit
movzx edi,di
@@32Bit: pop eax
ret
Int21hExtend_ES_EDI endp
;------------------------------------------------------------------------------
;
;Fing length of a string.
;
;On Entry:
;
;AL - Termination value.
;DS:ESI - String to find length of.
;
;On Exit:
;
;ECX - Length of string EXCLUDEING terminator.
;
;All other registers preserved.
;
Int21hStringLen proc near
pushm edi,es
push ds
pop es
mov edi,esi
or ecx,-1
repne scasb
mov ecx,edi
sub ecx,esi
dec ecx
popm edi,es
ret
Int21hStringLen endp
;------------------------------------------------------------------------------
Int21hAL2Carry proc near
test cs:Int21hSystemFlags,1
jz @@32Bit
or b[ebp+Int_Flags16],al
ret
@@32Bit: or b[ebp+Int_Flags32],al
ret
Int21hAL2Carry endp
;------------------------------------------------------------------------------
;
;The jump table used to pass control to the right routine.
;
Int21hTable label dword
dd 8 dup (Int21hNotOurs) ;00-07
;
dd Int21hNotOurs
dd Int21hPrintString ;09
dd Int21hGetString ;0A
dd 4 dup (Int21hNotOurs) ;0B-0E
dd Int21hInvalid ;0F
;
dd 8 dup (Int21hInvalid) ;10-17
;
dd 2 dup (Int21hNotOurs) ;18-19
dd Int21hSetDTA ;1A
dd 5 dup (Int21hNotOurs) ;1B-1F
;
dd Int21hNotOurs ;20
dd 4 dup (Int21hInvalid) ;21-24
dd Int21hSetVect ;25
dd 2 dup (Int21hInvalid) ;26-27
;
dd 2 dup (Int21hInvalid) ;29
dd 5 dup (Int21hNotOurs) ;2A-2E
dd Int21hGetDTA ;2F
;
dd 5 dup (Int21hNotOurs) ;30-34
dd Int21hGetVect ;35
dd 2 dup (Int21hNotOurs) ;36-37
;
dd Int21hGetSetCountry ;38
dd Int21hCreateDIR ;39
dd Int21hCreateDIR ;3A
dd Int21hCreateDIR ;3B
dd Int21hCreateFile ;3C
dd Int21hOpenFile ;3D
dd Int21hNotOurs ;3E
dd Int21hReadFile ;3F
;
dd Int21hWriteFile ;40
dd Int21hOpenFile ;41
dd Int21hNotOurs ;42
dd Int21hCreateFile ;43
dd Int21hIOCTLDispatch ;44
dd 2 dup (Int21hNotOurs) ;45-46
dd Int21hGetCurDir ;47
;
dd Int21hAllocMem ;48
dd Int21hRelMem ;49
dd Int21hResMem ;4A
dd Int21hExecFile ;4B
dd 2 dup (Int21hNotOurs) ;4C-4D
dd Int21hFindFirstFile ;4E
dd Int21hFindNextFile ;4F
;
dd Int21hSetPSP ;50
dd Int21hGetPSP ;51
dd 4 dup (Int21hNotOurs) ;52-55
dd Int21hRenameFile ;56
dd Int21hNotOurs ;57
;
dd Int21hNotOurs ;58
dd Int21hGetErrorInfo ;59
dd Int21hCreateTemp ;5A
dd Int21hCreateFile ;5B
dd 2 dup (Int21hNotOurs) ;5C-5D
dd Int21hMSNet ;5E
dd Int21hNotOurs ;5F
;
dd 2 dup (Int21hNotOurs) ;60-61
dd Int21hGetPSP ;62
dd 4 dup (Int21hNotOurs) ;63-66
dd Int21hSetHandles ;67
;
dd 4 dup (Int21hNotOurs) ;68-6B
dd Int21hExtendOpen ;6C
dd 3 dup (Int21hNotOurs) ;6D-6F
;
dd (16*9)-1 dup (Int21hNotOurs) ;70-FE
;
dd Int21hDOS4GTest ;FF
;=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
;
;Setup int 21h patch.
;
Int21hOpen proc near
assume ds:_Int21h
assume es:_cwMain
mov Int21hDSeg,es ;Store cwCode selector.
mov Int21hCSeg,cs ;store this segment.
mov Int21hDDSeg,ds
;
mov bl,21h
sys GetVect
test es:SystemFlags,1
jz @@Use32
movzx edx,dx
@@Use32: mov d[OldInt21h],edx
mov w[OldInt21h+4],cx
@@Use0: mov edx,offset Int21h
mov cx,cs
mov bl,21h
sys SetVect
;
mov eax,es:SystemFlags
mov Int21hSystemFlags,eax
;
assume es:nothing
assume ds:nothing
clc
@@9: ;
db 66h
retf
Int21hOpen endp
;=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
;
;Remove int 21h patch.
;
Int21hClose proc near
push ds
mov ds,cs:Int21hDDSeg
assume ds:_Int21h
cmp d[OldInt21h+2],0
jz @@9
mov edx,d[OldInt21h]
mov cx,w[OldInt21h+4]
mov bl,21h
sys SetVect
assume ds:nothing
@@9: pop ds
;
db 66h
retf
Int21hClose endp
;==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==-==
Bord21 proc near
pushm ax,dx
mov ah,al
mov dx,3dah
in al,dx
mov dl,0c0h
mov al,11h
out dx,al
mov al,ah
out dx,al
mov al,20h
out dx,al
popm ax,dx
ret
Bord21 endp
;=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
OldInt21h df 0
Int21hCSeg dw ?
Int21hDSeg dw ?
Int21hDDSeg dw ?
Int21hSystemFlags dd ?
;
Int21hCountryTab db size RealRegsStruc dup (?)
;
Int21hDOS4GFlag db 0
;
DOS16DummySegment DW 0
Int21hEnd label byte
_Int21h ends
.286
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -