home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Power-Programmierung
/
CD1.mdf
/
basic
/
library
/
pb
/
library3
/
diablo.asm
< prev
next >
Wrap
Assembly Source File
|
1990-10-20
|
20KB
|
669 lines
;Program Name : Diablo.asm
;Author : Mark Winkler, Consultant
;Date : 10-20-90
;Compuserve # : 73210,611
;Description : Supports X-On, X-off as a TSR
;Tech Support BBS: 813-625-1721, PC-Board, 8,N,1 USR HST 300 - 14.4, 24hrs
;Tech Support Fax: 813-625-1698 G2 & G3 compatible
;Tech Support Voc: 813-625-1172 Voice
;
;
; Diablo Driver
;
; Intercepts calls to Int 17 (printer) and converts them
; to Int 14 (communications) and does either x-on/x-off or
; Etx logic
;
; Command Format: Diablo L C X B P L S N
; | | | | | | | |
; | | | | | | | - Nulls
; | | | | | | --- Stop bits
; | | | | | ----- Word lenght
; | | | | ------- Parity
; | | | --------- Baud Rate
; | | ----------- Protocol (E)tx,(X)on,(R)edirect
; | ------------- Com device 0,1,2,3
; --------------- LPT Device 0,1,2
;
; or
;
; diablo * -- activates or deactivates an existing driver
;
;
; Note:
; Pins 5,6 must be hooked up.
; If simple hook up tie pin 20 to 5,6.
;
;
; update history
;
; 10/24/87 init dtr and rts lines on start of program
; 12/24/87 added switch for nulls
code segment byte public 'code'
etxbyte equ 03h
ackbyte equ 06h ;
passbyte equ 01 ;pass through byte
xonbyte equ 11h
xoffbyte equ 13h
;
etries equ 20 ;number of error tries before reporting error
;the exact time depends on what is located at
;40:7c rs-232 timeout values
assume cs:code,ds:code,es:code
org 80h
comlength db 0
org 100h
beg: jmp start
;
;
resident db 'Diablo'
int17:
pop dx ;pop registers
pop ds
;
db 0eah ;jmp far instruction
intdword dd 0 ;double word ptr to int 17
activefg db 0ffh
intdwd dd 0 ;storage for point to intercept
;
;
protocol db 0 ;protocol byte
comdevice dw 0 ;which com port to use
lptdevice dw 0 ;which printer device to use
errtries db 0 ;storage for errors
;
;
baud db 0
parity db 0
wordlen db 0
stopbit db 0
;
nulls db 0 ;number of nulls to insert
;
int17catch:
push ds ;save segment
push dx
push cs ;place on stack
pop ds ;update ds register
cmp dx,lptdevice ;intercept this call ?
jnz int17 ;no
cmp ah,0 ;maybe
jnz initstat
cmp protocol,etxbyte
jz etx ;
cmp protocol,passbyte
jz passthru
jmp xon ;do xon stuff
;
initstat:
mov ah,10010000b ;set printer status
jmp int17ret
;
int17ret:
pop dx
pop ds
iret
;
; redirected and pass thru, no protocol
;
passthru:
mov errtries,etries ;set error tries
trypassagain:
call sendtocom ;send the byte
and ah,80h ;check for timeout
jz rettocaller ;return, a-ok
dec errtries
jnz trypassagain ;try again maybe busy (pin 20)
jmp error
;
; ETX Routines
;
ETX:
call sendtocom
and ah,80h ;check for timeout
jnz error
cmp al,0dh ;carriage return
jnz rettocaller
mov al,etxbyte ;send etx to printer
call sendtocom
mov al,0dh ;place byte back encase error
and ah,80h
jnz error
mov errtries,etries
tryetxagain:
call recfromcom ;get character
and ah,80h
jz chkack
dec errtries ;decrement number of tries
jnz tryetxagain
;
mov al,0dh ;place org. back in
jmp error
chkack:
and al,7fh ;throw any extra bits away
cmp al,ackbyte
jnz tryetxagain
mov al,0dh ;place orginal byte back in
rettocaller:
mov ah,10010000b ;set printer status
jmp int17ret
;
sendtocom:
mov ah,1 ;send character in al
mov dx,comdevice ;get device number
int 14h ;send it
test ah,80h ;error
jnz sendcomret ;return if error
;
cmp al,0dh ;carriage return
jnz sendcomret
;
push cx
mov cl,nulls ;get the number of nulls
or cl,cl ;if zero skip it
jz endnull
;
nulloop:
mov ah,1 ;send character in al
mov al,0h ;send the null
mov dx,comdevice ;get device number
int 14h ;send it
test ah,80h ;error
jnz endnull ;return if error
dec cl
jnz nulloop ;if more send it
endnull:
pop cx
mov al,0dh
sendcomret:
ret
;
recfromcom:
mov ah,2 ;rec character
mov dx,comdevice
int 14h
ret
;
getstatcom:
mov ah,3 ;get status of port
mov dx,comdevice
int 14h
ret
;
error:
mov ah,1 ;show printer busy
jmp int17ret
;
;
; xon/xoff protocol
;
xon: push ax ;save the character to send
call getstatcom ;get the status
and ah,1 ;data ready
jz xon1
call recfromcom ;get the character
cmp al,xoffbyte ;xoff character
jnz xon1
;
mov errtries,etries
xonwait:
call recfromcom ;get character
and ah,80h
jz chkxon
dec errtries ;decrement number of tries
jnz xonwait
pop ax ;restore the character
jmp error
;
chkxon:
and al,7fh ;throw any extra away
cmp al,xonbyte
jnz xonwait
;
xon1: pop ax ;rtestore character
call sendtocom ;send the character
jmp rettocaller ;and return to the caller
lastbyte db 0
;
;
clrspace:
cmp byte ptr [bx],20h
jnz clrret
inc bx
dec cl
jnz clrspace
clrret: ret
;
abort:
mov ah,9 ;print the string
mov dx,offset message
int 21h ;
mov ah,0 ;terminate program
int 21h
hlt
start:
mov ah,9 ;print signon
mov dx,offset signon
int 21h
;
mov cl,comlength ;get the command length
and cl,0ffh ;if zero abort
jz abort
mov bx,offset comlength+1
;
; check for 1st parameter lpt
;
call clrspace ;get rid of spaces
jz abort ;if zero abort
mov al,[bx]
cmp al,'*' ;check for special (act or deact)
jz chkdrv
jmp chkpar
;
; activate or deactivate exisiting driver
;
chkdrv:
sub ax,ax ;clear reg
mov es,ax ;page zero
cld ;set the direction flag
look1:
mov di,ax
lookagain:
mov si,offset resident ;point to message
cmpsb ;compare a byte
jz maybefound
cmp di,0 ;top of 64k boundary
jnz lookagain
mov ax,es ;get es
add ax,1000h ;next 64k block
cmp ax,0a000h ;top of memory
jz nofind ;
mov es,ax
jmp lookagain
maybefound:
mov ax,di ;save pointer incase of no match
cmpsw ;foure more words to match
jnz look1
cmpsw
jnz look1
cmpsw
jnz look1
cmpsw
jnz look1
mov dx,es:[di]
or dx,dx ;find valid driver
jnz founddr ;yes so do flip/flop
jmp look1
nofind:
mov dx,offset notvalid ;not found
mov ah,9
int 21h
mov ah,0 ;terminate
int 21h
hlt
;
; found driver in memory
;
founddr:
inc di ;get segment value of int 17
inc di
mov cx,es:[di]
inc di ;point to active flag
inc di
mov ah,es:[di] ;get the value
or ah,ah ;set the flag
not ah ;complement it
mov es:[di],ah ;flip it
jz actdrv ;restore the driver
;
; deactivate driver
;
push ds
mov ah,25h
mov al,17h ;int 17 (printer)
mov ds,cx ;place in the segment
;dx register has offset
int 21h ;place in the vector
pop ds
mov dx,offset deactmsg
flipmsg:
mov ah,9
int 21h
mov ah,0 ;terminate program
int 21h ;
hlt
actdrv:
inc di ;point to offset of driver
mov dx,es:[di]
inc di ;and then segment
inc di
mov cx,es:[di]
push ds
mov ds,cx
mov ah,25h
mov al,17h ;int 17 (printer)
int 21h
pop ds
mov dx,offset actmsg
jmp flipmsg
abort1: jmp abort
;
; check for valid printer parameter
;
chkpar:
cmp al,30h ;check if valid
jb abort1 ;error
cmp al,33h ;check if valid
jae abort1 ;if equal or above abort
sub al,30h ;subtract offset
mov ah,0 ;zero out ah
mov lptdevice,ax ;update printer device
inc bx ;move to next byte
;
; check for com device
;
call clrspace ;get rid of spaces
jz abort1 ;if zero abort
mov al,[bx]
cmp al,30h ;check if valid
jb abort1 ;error
cmp al,34h ;check if valid
jae abort1 ;if equal or above abort
sub al,30h ;subtract offset
mov ah,0 ;zero out ah
mov comdevice,ax ;update printer device
inc bx ;move to next byte
;
; check for protocol
call clrspace ;get rid of spaces
jz abort1 ;if zero abort
mov al,xonbyte
and byte ptr [bx],5fh ;convert to upper case
cmp byte ptr [bx],'X' ;check if valid
jz proto
mov al,etxbyte
cmp byte ptr [bx],'E' ;check if valid
jz proto ;if equal or above abort
mov al,passbyte
cmp byte ptr [bx],'R'
jnz abort1
proto: mov protocol,al ;place in the protocol byte
;
; check for valid baud rate
; 110,150,300,600,1200,2400,4800,9600,19200
inc bx ;point to next byte
call clrspace
jz abort1
mov ax,[bx] ;get the next two bytes
push bx
mov ch,0 ;zero counter
mov bx,offset baudtab
baudloop:
cmp ax,[bx]
jz foundbaud
inc bx ;point to next value
inc bx
inc ch ;bump counter
cmp ch,9 ;check if not found
jnz baudloop
abort2: jmp abort
baudtab:
db '11' ;110 baud
db '15'
db '30'
db '60'
db '12'
db '24'
db '48' ;4800
db '96' ;9600
db '19' ;19200
;
foundbaud:
mov baud,ch ;save baud rate
pop bx ;get pointer back
inc bx
inc bx ;bump to next value
clrtospace:
cmp byte ptr [bx],20h
jz gotspace
dec cl ;run out yet
jz abort2 ;yes so abort
inc bx
jmp clrtospace
;
gotspace:
call clrspace ;clear spaces
jz abort2
mov al,[bx]
and al,5fh ;upper case
mov ch,0 ;zero count
cmp al,'N' ;none
jz chkword
inc ch
cmp al,'O' ;odd
jz chkword
mov ch,3
cmp al,'E' ;even
jnz abort2
chkword:
mov parity,ch ;save parity
inc bx
call clrspace
jz abort2
mov al,[bx] ;get wordlength
mov ch,2
cmp al,'7'
jz chkstop
inc ch
cmp al,'8'
jz chkstop
abort3: jmp abort ;error abort
;
chkstop:
mov wordlen,ch ;save wordlength
inc bx
call clrspace
jz abort3
mov al,[bx]
mov ch,0
cmp al,'1'
jz patch34
inc ch
cmp al,'2'
jnz abort3
patch34:
mov stopbit,ch
;
;
inc bx ;move to next character
call clrspace ;move to next parameter
jz patcom34 ;nothing so continue on
mov al,[bx]
cmp al,'1' ;1 to
jb abort3
cmp al,'9' ;9 nulls
ja abort3
sub al,30h ;sub ascii bias
mov nulls,al ;keep nulls
;
; patch in address of com3 and com4
;
patcom34:
push ds
mov ax,40h ;set for low page
mov ds,ax
mov bx,4 ;set up the offset
mov [bx],03e8h ;patch in com3
inc bx
inc bx ;point to next port area
mov [bx],02e8h ;patch in com4
pop ds ;restore ds reg
;
;
; set the baud rate,parity,stop bits and data bits
;
;
mov al,baud ;get the baud rate
mov cl,5 ;5 bits to shift
shl al,cl
mov ah,parity ;get parity
mov cl,3 ;move in parity
shl ah,cl
or al,ah ;place in al
mov ah,stopbit
mov cl,2 ;two bits to shift
shl ah,cl
or al,ah
mov ah,wordlen ;word length
or al,ah ;al has all parameters
mov wordlen,al ;save 19200 maybe
;
mov ah,0 ;init sio chip
mov dx,comdevice ;get device to setup
int 14h ;tell bios
;
; set dtr and rts lines of port
;
mov cx,comdevice ;get device number
shl cx,1 ;muliply by 2,word offset
push ds
mov ax,40h ;set for low page
mov ds,ax
mov bx,0 ;zero bx
add bx,cx ;add in device number
mov dx,[bx] ;get base of port
add dx,4 ;add four for modem control reg
pop ds ;restore ds
mov al,3 ;dtr and rts
out dx,al
;
;
; check if special 19200
;
cmp baud,8 ;if 8 special
jnz patchint
;
; special case for 19200
;
mov cx,comdevice ;get device number
shl cx,1 ;muliply by 2,word offset
push ds
mov ax,40h ;set for low page
mov ds,ax
mov bx,0 ;zero bx
add bx,cx ;add in device number
mov dx,[bx] ;get base of port
push dx ;save it
add dx,3 ;add three for line control reg
in al,dx
mov ah,al ;save for later
or al,80h ;set divisor latch bit
out dx,al
pop dx ;get base port back
inc dx
mov al,0
out dx,al ;high reg.
dec dx
mov al,6 ;divisor for 19200
out dx,al
add dx,3 ;back to line control
mov al,ah
out dx,al ;set back to what it was
pop ds ;restore ds reg
;
;
; patch in the intercept vector
;
patchint:
mov ah,35h ;get a vector
mov al,17h ;printer vector
int 21h ;call dos
mov word ptr intdword,bx
mov word ptr intdword+2,es
mov ah,25h ;set a vector
mov al,17h
mov dx,offset int17catch
int 21h ;do it
;
mov word ptr intdwd,offset int17catch ;save catch routine for flip
mov ax,cs ;get the cs valid
mov word ptr intdwd+2,ax ;and save code value
;
;
mov dx,offset lastbyte
int 27h ;terminate but stay resident
hlt
;
;
message db 0dh,0ah
db 'Command Format: Diablo L C X B P W S N',0dh,0ah
db ' | | | | | | | |',0dh,0ah
db ' | | | | | | | - Nulls 1-9 (blank = 0)'
db 0dh,0ah
db ' | | | | | | --- Stop bits (1-2)'
db 0dh,0ah
db ' | | | | | ----- Word Length (7-8)'
db 0dh,0ah
db ' | | | | ------- Parity (N,O,E)',0dh,0ah
db ' | | | --------- Baud Rate'
db ' (110 to 19200)',0dh,0ah
db ' | | '
db '----------- Protocol (E)tx,(X)on,(R)edirected',0dh,0ah
db ' | ------------- Com device 0,1,2,3'
db 0dh,0ah
db ' --------------- LPT Device 0,1,2'
db 0dh,0ah,0dh,0ah
db 'All seven parameters must be entered !!!!'
db 0dh,0ah,0dh,0ah
db 'Diablo * - activates or deactivates existing driver in '
db 'memory'
db 0dh,0ah,'$'
;
signon db 0dh,0ah,'Diablo Driver v1.6 C-1986 Mark Winkler',0dh,0ah,'$'
notvalid db 0dh,0ah,'Error --- Diablo driver not installed$'
deactmsg db 0dh,0ah,'Diablo Driver deactivated$'
actmsg db 0dh,0ah,'Diablo Driver activated$'
code ends
end beg