📄 raw_vcpi.asm
字号:
jmp @@Use16Bit12
@@Use32Bit12: mov ax,w[CallBackProt+4+bx]
mov w[@@CallB0+4],ax
mov eax,d[CallBackProt+bx]
mov d[@@CallB0],eax
@@Use16Bit12: push bx ;save call back structure pointer.
;
@@oops: ;
;Setup stack referance.
;
pushm eax,ebx,esi,edi,es
movzx esi,es:Real_SS[edi]
shl esi,4
mov ax,KernalZero
mov es,ax
movzx eax,w[CallBackStackSel+bx]
and ax,not 7
mov edi,GDTLinear
add edi,eax
mov es:[edi+2],si ;store low word of linear base.
shr esi,16
mov bx,si
mov es:[edi+4],bl ;store mid byte of linear base.
mov es:[edi+7],bh ;store high byte of linear base.
popm eax,ebx,esi,edi,es
mov ds,w[CallBackStackSel+bx]
movzx esi,es:Real_SP[edi]
;
assume ds:nothing
test cs:RawSystemFlags,1
jz @@Use32Bit13
pushf
call cs:d[@@CallB0]
jmp @@Use16Bit13
@@Use32Bit13: pushfd
call cs:f[@@CallB0]
@@Use16Bit13: cli
assume ds:_cwRaw
mov ax,KernalDS ;make our data addresable.
mov ds,ax
pop bx ;restore call back structure.
;
movzx esi,es:Real_SS[edi] ;point to stacked registers.
mov w[VCPI_SP+2],si
shl esi,4
movzx eax,es:Real_SP[edi]
sub eax,(2)+(4+4+4+4+4+4+4)+(2+2+2+2)+(2+2)
mov w[VCPI_SP],ax
add esi,eax
mov ax,KernalZero ;/
mov fs,ax ;/
mov ax,es:Real_GS[edi]
mov fs:[esi],ax
mov ax,es:Real_FS[edi]
mov fs:[esi+2],ax
mov ax,es:Real_ES[edi]
mov fs:[esi+4],ax
mov ax,es:Real_DS[edi]
mov fs:[esi+6],ax
mov eax,es:Real_EBP[edi]
mov fs:[esi+8],eax
mov eax,es:Real_EDI[edi]
mov fs:[esi+12],eax
mov eax,es:Real_ESI[edi]
mov fs:[esi+16],eax
mov eax,es:Real_EDX[edi]
mov fs:[esi+20],eax
mov eax,es:Real_ECX[edi]
mov fs:[esi+24],eax
mov eax,es:Real_EBX[edi]
mov fs:[esi+28],eax
mov eax,es:Real_EAX[edi]
mov fs:[esi+32],eax
mov ax,es:Real_Flags[edi]
mov fs:[esi+36],ax
mov ax,es:Real_IP[edi]
mov fs:[esi+38],ax
mov ax,es:Real_CS[edi]
mov fs:[esi+40],ax
;
;Switch back to v86 mode.
;
mov cx,VCPI_SP+2
mov dx,VCPI_SP
call Protected2Real
add RawStackPos,RawStackDif
popm eax,ebx,ecx,edx,esi,edi,ebp,ds,es,fs,gs
popf
retf
@@CallB0: ;
df ?,0
RAWCallBack endp
;-------------------------------------------------------------------------------
RAWICallBack proc near
cli
assume ds:nothing
pop cs:RetAdd ;get return address.
;
;Check if this call back is busy.
;
pushm ax,bx,dx
mov ax,cs:RetAdd ;get return address.
sub ax,CallBackSize ;back to start of call back entry.
sub ax,offset ICallBackList ;offset from start of list.
xor dx,dx
mov bx,CallBackSize
div bx ;entry number.
mov bx,size CallBackStruc
mul bx ;get offset into table.
mov bx,offset CallBackTable
add bx,ax ;point to this entry.
mov cs:w[@@CallTab],bx
;
cmp cs:InWindows,0
jnz @@ForceOld
;
test cs:CallBackFlags[bx],128 ;call back busy?
jz @@NotBusy
;
;This is a busy int call back so pass control to old real mode vector.
;
@@ForceOld: mov ax,cs:w[CallBackReal+2+bx] ;fetch old real mode vector address.
mov cs:w[@@tVCPI_SP+2],ax
mov ax,cs:w[CallBackReal+bx]
mov cs:w[@@tVCPI_SP],ax
popm ax,bx,dx
jmp cs:d[@@tVCPI_SP] ;pass onto old handler.
@@tVCPI_SP: ;
dd ?
;
@@NotBusy: or cs:CallBackFlags[bx],128 ;mark it as busy.
mov bx,sp
mov ax,ss:[bx+(2+2+2)+(2+2)]
and ax,0000110011010101b
or ax,0000000000000010b
mov cs:w[@@FlagsStore],ax
popm ax,bx,dx
;
;Switch to new stack.
;
mov cs:w[@@tVCPI_SP],sp ;store current stack.
mov cs:w[@@tVCPI_SP+2],ss
mov ss,cs:RawStackReal ;_cwRaw ;use new stack.
mov esp,cs:RawStackPos
sub cs:RawStackPos,RawStackDif
push cs:d[@@tVCPI_SP] ;put old stack onto new one.
;
;Preserve registers.
;
pushm eax,ebx,ecx,edx,esi,edi,ebp,ds,es,fs,gs
;
;Make our data addresable.
;
mov ax,_cwRaw
mov ds,ax ;make our data addresable.
assume ds:_cwRaw
mov w[@@tVCPI_SP],sp
mov w[@@tVCPI_SP+2],ss
;
;Switch to protected mode.
;
mov cx,KernalSS
xor edx,edx
mov dx,sp
; mov edx,RawStackPos
; sub RawStackPos,RawStackDif
call Real2Protected
;
;Get protected mode code address.
;
mov bx,w[@@CallTab]
mov bl,CallBackNum[bx] ;get int number.
pushm ax,ebx,ds
mov ax,KernalDS
mov ds,ax
movzx eax,bl
mov ebx,eax
shl ebx,1 ;*2
mov eax,ebx
shl ebx,1 ;*4
add ebx,eax ;*6
assume ds:_cwDPMIEMU
add ebx,offset InterruptTable
assume ds:_cwRaw
push ds
mov ax,DpmiEmuDS
mov ds,ax
mov edx,[ebx] ;get offset.
mov cx,4[ebx] ;get segment selector.
pop ds
popm ax,ebx,ds
test RawSystemFlags,1
jz @@Use32Bit12
mov w[@@CallB0+2],cx
mov w[@@CallB0],dx
jmp @@Use16Bit12
@@Use32Bit12: mov w[@@CallB0+4],cx
mov d[@@CallB0],edx
@@Use16Bit12: ;
;Retrieve register values.
;
mov ax,KernalZero
mov fs,ax
movzx esi,w[@@tVCPI_SP+2]
shl esi,4
movzx eax,w[@@tVCPI_SP]
add esi,eax ;Point to stacked registers.
pushfd
pop eax
shr eax,16
mov w[@@FlagsStore+2],ax
mov eax,fs:[esi+32]
mov ebx,fs:[esi+28]
mov ecx,fs:[esi+24]
mov edx,fs:[esi+20]
mov edi,fs:[esi+12]
mov ebp,fs:[esi+8]
mov esi,fs:[esi+16]
push d[@@tVCPI_SP]
push w[@@CallTab]
push ds
test RawSystemFlags,1
jz @@Use32Bit13
push w[@@FlagsStore]
; pushf ;dummy return flags.
push cs ;dummy return address.
push w[@@zero] ;/
push w[@@FlagsStore]
call d[@@CallB0]
lea esp,[esp+(2*3)]
; pushf
; add sp,2*3
; popf
jmp @@Use16Bit13
@@Use32Bit13:
; pushfd ;dummy return flags.
push d[@@FlagsStore]
push 0 ;\
push cs ;dummy return address.
push d[@@zero]
push d[@@FlagsStore]
call f[@@CallB0]
lea esp,[esp+(4*3)]
@@Use16Bit13: ;
pop ds
pushfd
cli
pop d[@@FlagsStore]
pop w[@@CallTab]
pop d[@@tVCPI_SP]
pushm esi,eax
mov ax,KernalZero
mov fs,ax
movzx esi,w[@@tVCPI_SP+2]
shl esi,4
movzx eax,w[@@tVCPI_SP]
add esi,eax ;Point to stacked registers.
;
;Set new register values.
;
pop eax
mov fs:[esi+32],eax
mov fs:[esi+28],ebx
mov fs:[esi+24],ecx
mov fs:[esi+20],edx
pop eax
mov fs:[esi+16],eax
mov fs:[esi+12],edi
mov fs:[esi+8],ebp
;
;Update flags.
;
movzx eax,fs:w[(2+2+2+2)+(4+4+4+4+4+4+4)+esi]
movzx esi,fs:w[(2+2+2+2)+(4+4+4+4+4+4+4)+(2)+esi]
shl esi,4
add esi,eax
mov ax,w[@@FlagsStore]
and ax,1111100011111111b
and fs:w[(2+2)+esi],0000011100000000b
or fs:[(2+2)+esi],ax
;
mov bx,w[@@CallTab] ;restore call back structure.
and CallBackFlags[bx],255-128 ;clear busy flag.
;
;Switch back to v86 mode.
;
mov cx,w[@@tVCPI_SP+2]
mov dx,w[@@tVCPI_SP]
call Protected2Real
; add RawStackPos,RawStackDif
;
popm eax,ebx,ecx,edx,esi,edi,ebp,ds,es,fs,gs
assume ds:nothing
lss sp,[esp] ;restore origional stack.
add cs:RawStackPos,RawStackDif
assume ds:_cwRaw
iret
;
@@CallB0: ;
df ?,0
@@FlagsStore: ;
dd 0
@@CallTab: ;
dw ?
@@zero: ;
dd 0
RAWICallBack endp
;-------------------------------------------------------------------------------
;
;Install relavent A20 handler for this machine.
;
InstallA20 proc far
;
@@IAChkPS2: ; Are we on a PS/2?
;
call IsPS2Machine
cmp ax,1
jne @@IAOnAT
mov A20HandlerCall,offset A20_PS2
jmp @@0
;
@@IAOnAT: ;Assume we're on an AT.
;
mov A20HandlerCall,offset A20_AT
;
@@0: ret
InstallA20 endp
;-------------------------------------------------------------------------------
IsPS2Machine proc near
mov ah,0C0h ; Get System Description Vector
stc
int 15h
jc @@IPMNoPS2 ; Error? Not a PS/2.
;
; Do we have a "Micro Channel" computer?
;
mov al,byte ptr es:[bx+5] ; Get "Feature Information Byte 1"
test al,00000010b ; Test the "Micro Channel Implemented" bit
jz @@IPMNoPS2
;
@@IPMFoundIt: xor ax,ax ; Disable A20. Fixes PS2 Ctl-Alt-Del bug
call A20_PS2
mov ax,1
ret
;
@@IPMNoPS2: xor ax,ax
ret
IsPS2Machine endp
;-------------------------------------------------------------------------------
;
;Control A20 with whatever method is apropriate.
;
A20Handler proc far
push ds
push ax
mov ax,MainDS
mov ds,ax
assume ds:_cwMain
cmp ProtectedType,0
assume ds:_cwRaw
pop ax
pop ds
jnz @@A20DoneOther
cmp XMSPresent,0
jz @@A20Raw
cmp ax,2 ;restore?
jz @@XMSA20OFF
or ax,ax
jnz @@XMSA20ON
@@XMSA20OFF: sub esp,size v86CallStruc
mov ax,ss
mov es,ax
mov edi,esp
mov ax,w[XMSControl]
mov es:Real_IP[edi],ax
mov ax,w[XMSControl+2]
mov es:Real_CS[edi],ax
mov ah,06h
mov es:Real_EAX[edi],eax
mov es:Real_SS[edi],0
mov es:Real_SP[edi],0
call RawSimulateFCALL
add esp,size v86CallStruc
jmp @@A20Done
;
@@XMSA20ON: sub esp,size v86CallStruc
mov ax,ss
mov es,ax
mov edi,esp
mov ax,w[XMSControl]
mov es:Real_IP[edi],ax
mov ax,w[XMSControl+2]
mov es:Real_CS[edi],ax
mov ah,05h
mov es:Real_EAX[edi],eax
mov es:Real_SS[edi],0
mov es:Real_SP[edi],0
call RawSimulateFCALL
mov ax,w[XMSControl]
mov es:Real_IP[edi],ax
mov ax,w[XMSControl+2]
mov es:Real_CS[edi],ax
mov ah,7
mov es:Real_EAX[edi],eax
mov es:Real_SS[edi],0
mov es:Real_SP[edi],0
call RawSimulateFCALL
mov eax,es:Real_EAX[edi]
xor ax,1
add esp,size v86CallStruc
or ax,ax
jmp @@A20Done
;
@@A20Raw: call A20HandlerCall
;
@@A20Done: ret
@@A20DoneOther: xor ax,ax
ret
A20Handler endp
;-------------------------------------------------------------------------------
A20_AT proc near
or ax,ax
jz @@AAHDisable
cmp ax,2
jnz @@AAHEnable
cmp A20Flag,0
jz @@AAHDisable
@@AAHEnable: call @@Sync8042 ; Make sure the Keyboard Controller is Ready
jnz @@AAHErr
mov al,0D1h ; Send D1h
out 64h,al
call @@Sync8042
jnz @@AAHErr
mov al,0DFh ; Send DFh
out 60h,al
call @@Sync8042
jnz @@AAHErr
;
; Wait for the A20 line to settle down (up to 20usecs)
;
mov al,0FFh ; Send FFh (Pulse Output Port NULL)
out 64h,al
call @@Sync8042
jnz @@AAHErr
jmp @@AAHExit
;
@@AAHDisable: call @@Sync8042 ; Make sure the Keyboard Controller is Ready
jnz @@AAHErr
mov al,0D1h ; Send D1h
out 64h,al
call @@Sync8042
jnz @@AAHErr
mov al,0DDh ; Send DDh
out 60h,al
call @@Sync8042
jnz
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -