mcdonald@uxe.cso.uiuc.edu (09/06/87)
A recent poster asked how to stop a process with <cntl>break while it
is doing no IO at all, like maybe it was doing a long calculation.
I have solved this by writing the following TSR routine, which you put
into your autoexec.bat file along with BREAK = ON.
It is to be assembled woth MASM and then it MUST be converted to
a .COM file with EXE2BIN.
...............cut here..................................................
;Resident program to enable cntl-break even if no DOS call is made
;This is done by doing a dummy DOS call when break key is let up
;THIS WON'T WORK WITHOUT DOING A break on STATEMENT IN DOS
;If cntl-break fails you may try CNTL-ALT-4 (the 4 on the top row)
;which is somewhat more powerful. If you break out of BASIC this way
;the NEXT time BASIC is run, it will hang, requiring a reboot
;Other programs (games?) may or may not respond. If they do respond,
;they may hang up DOS.
cseg segment para public 'code'
org 100h
BREAKL proc far
assume cs:cseg,ds:cseg
jmp install ;this installation code used only once
oldint9 dd 0 ;storage for old int 9 vector
int9loc equ 9h*4 ;location of int 9
kbflag equ 417h ;keyboard "held down" status address
ctrl equ 04 ;bit in kbflag for cntl
alt equ 08 ;bit in kbflag for alt
brkup equ 0c6h ;scan code for release of scroll lock
cntl4 equ 05h ;scan code for 4
newint9: ;comes here from the hardware int 9
sti ;restart interrupt
push es ;save registers
push di
push ax
push cx
push dx
pushf
mov ax,0 ;get cntl and alt status into ah
mov es,ax
mov di,kbflag
mov ah,es:[di]
test ah,ctrl ;test for cntl held down
jz return ;if cntl is up, go to previous handler code
in al,60h ;get scan code into al
cmp al,brkup ;if not release of scroll lock or...
je doit
cmp al,cntl4 ;4 key, go to previous code
jne return
test ah,alt ;if alt not down with cntl-4
jz return ;go to previous code
doit:
mov cl,al ;put a pulse in interrupt port
in al,61h ;for some obscure reason
mov ah,al ;copied form BIOS listing
or al,80h
out 61h,al
mov al,ah
out 61h,al
cli ;stop interrupt
mov al,20h ;clear keyboard
out 20h,al
sti ;restart interrupts
cmp cl,cntl4 ;test for cntl-alt-4
je fun4c ;if it is cntl-alt-4 go to code for that
mov ah,19h ;DOS func call for read default disk. This
int 21h ;is a dummy call to make DOS look for break
popf ;restore registers in case DOS break
pop dx ;didn't work
pop cx
pop ax
pop di
pop es
iret ;this may never be used
fun4c:
mov al,01h ;error code for cntl-break
mov ah,4ch ;DOS func call to terminate program
int 21h
iret
return:
popf ;this code simply passes control to the
pop dx ;keyboard handler present before this
pop cx ;resident program was loaded
pop ax
pop di
pop es
jmp cs:[oldint9] ;this jump doesn't change stack
install:
mov ax,0 ;get old int 9 vector into
mov es,ax
mov di,int9loc
mov ax,es:[di] ;ax and bx
mov bx,es:[di+2]
mov si,offset oldint9 ;then put them into
mov [si],ax ;location "oldint9" in this program
mov [si+2],bx
mov ax,0
mov es,ax
mov bx,ds
cli ;stop inteppupts
mov di,int9loc ;put pointer to this program into
mov ax,offset newint9 ;int 9 vector
mov es:[di],ax
mov es:[di+2],bx
sti ;restore interrupts
mov dx,offset install ;don't keep the install code
int 27h ;terminate and stay resident
BREAKL endp
cseg ends
end BREAKL
...........................cut here...........................
Doug McDonald
A