home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
kermit.columbia.edu
/
kermit.columbia.edu.tar
/
kermit.columbia.edu
/
mskermit
/
msxhp1.asm
< prev
next >
Wrap
Assembly Source File
|
2018-01-01
|
56KB
|
2,040 lines
name msxhp1
; File MSXHP1.ASM
include mssdef.h
; Copyright (C) 1982,1991, Trustees of Columbia University in the
; City of New York. Permission is granted to any individual or
; institution to use, copy, or redistribute this software as long as
; it is not sold for profit and this copyright notice is retained.
; System dependent module for HP150.
; Use with file MSUHP1.ASM (keyboard translator)
; Edit history
; 2 March 1991 version 3.10
; Nov. 24, 1990. Remove references to prserr to make linker happy.
; Nov. 21, 1990. Dump capture buffer (cptdmp) when exiting connect mode. [jan]
; Sept. 1990. Read 20 characters a time from dcomm. Read keyboard
; once every 16 reads of dc port. Start port at 7 bits so firmware
; flow control works. Disable our own flow control. Now works at 4800
; baud with no flow control.
; August 1990 update to 3.0. Incorporate tektronix. Add replay. [jan].
; John Nyenhuis, Purdue University, School of Electrical Engineering
; West Lafayette, Indiana 47907 USA (317)494-3524 nyenhuis@ecn.purdue.edu
; 1 July 1988 Version 2.31
; 11 Jan 1988 update to 2.30 consistency level.
; 1 Jan 1988 version 2.30
writechar macro saying
pushf
push dx
push ax
mov ah,2
mov dl,saying
int dos
pop ax
pop dx
popf
endm
writestring macro saying
pushf
push ax
push dx
mov ah,prstr
mov dx,offset saying
int dos
pop dx
pop ax
popf
endm
saveregs macro
push ax
push bx
push cx
push dx
push es
push di
push si
push ds
push bp
pushf
endm
restoreregs macro
popf
pop bp
pop ds
pop si
pop di
pop es
pop dx
pop cx
pop bx
pop ax
endm
;; below 40 publics are the minimum necessary
public baudst, ihostr, bdtab, getbaud, chrout, pcwait, putmod
public serrst, trnprs, prtchr, poscur, outchr, dtrlow, vts, puthlp
public vtstat, coms, cquery, ctlu, shomodem, portval, getmodem
public term, dumpscr, cmblnk, cquit, locate, clearl, machnam, lclini
public sendbl, comptab, sendbr, clrmod, cstatus, termtb, serhng
public clrbuf, beep, serini
;;additional system dependent publics
public termtog, kclrscn, kdos, snull, cquit, cquery
public toterminal, klogtog, setchtab, vtstbl
false equ 0
true equ 1
instat equ 6
print_out equ 05h ; dos function to print to printer
prtscr equ 80h ; print screen pressed
wrdev equ 40H
rddev equ 3fH
open equ 3dH
close equ 3eH
rdchan equ 2
e_send_break equ 6
e_ioctl equ 44h ; DOS i/o control function
passall equ 0803h ; Port transparency mode [WHM]
xofcnt equ 32 ; number of characters to send xoff
xoncnt equ 16 ; number of characters to send xon
dos201 equ 201h
dos211 equ 20bh ; dosnum for 2.11
data segment public 'data'
extrn lclexit:word, flags:byte, trans:byte, dmpname:byte
extrn kbdflg:byte, rxtable:byte, denyflg:word, repflg:byte
extrn diskio:byte ; for replay feature
extrn dosnum:word, agiosbuff:byte
extrn sloghnd:word ; session log handle from msster
extrn prnhand:word
machnam db 'HP-150$'
erms40 db cr,lf,'?Warning: Unrecognized baud rate$'
erms41 db cr,lf,'?Warning: Cannot open com port$'
noimp db cr,lf,'Command not implemented.$'
hngmsg db cr,lf,' The phone should have hungup.',cr,lf,'$'
hnghlp db cr,lf,' The modem control lines DTR and RTS for the current'
db ' port are forced low (off)'
db cr,lf,' to hangup the phone. Normally, Kermit leaves them'
db ' high (on) when it exits.'
db cr,lf,'$'
msmsg1 db cr,lf,' Communications port is not ready.$'
msmsg2 db cr,lf,' Communications port is ready.$'
rdbuf db 80 dup (0) ; temp buf
setktab db 0
setkhlp db 0
shkmsg db '?Not implemented.'
shklen equ $-shkmsg
anspflg db 0 ; printing active status
crlf db cr,lf,'$'
delstr db BS,BS,' ',BS,BS,'$' ; Delete string
clrlin db cr,ESCAPE,'K$'
xofsnt db 0 ; Say if we sent an XOFF
xofrcv db 0 ; Say if we received an XOFF
invseq db ESCAPE,'&dJ$' ; Reverse video
nrmseq db ESCAPE,'&d@$' ; Normal mode
ivlseq db 80 dup (' '),ESCAPE,'A','$' ; [ak] Make a line inverse video
keydelay db 0 ; delay for keyboard reads
tmp db 0,'$'
temp dw 0
temp1 dw 0
temp2 dw 0
eightstatustxt db 'No. Bits: $'
eightflg db eightbitnum
transparencytxt db 'Port Status: $'
transparentflg db transonnum
rawtxt db 'Port Mode: $'
rawflg db rawonnum
tekstatustxt db 'Tek Auto Entry: $'
tekbyte db tekonnum ; tek auto entry
temp3 dw 0
; structure for status information table sttab.
stent struc
sttyp dw 0 ; type (actually routine to call)
msg dw 0 ; message to print
val2 dw 0 ; needed value: another message, or tbl addr
tstcel dw 0 ; address of cell to test, in data segment
basval dw 0 ; base value, if non-zero
stent ends
; table with datacomm status for the status command
vtstbl stent <srchkw,eightstatustxt,termtb,eightflg> ; tell 7 or 8 bits
stent <srchkw,transparencytxt,termtb,transparentflg> ; tell if transparent
stent <srchkw,rawtxt,termtb,rawflg> ; tell if raw or cooked
stent <srchkw,tekstatustxt,termtb,tekbyte> ; tell if raw or cooked
dw 0 ; end of table
; Entries for choosing communications port
comptab db 4 ; four entries
mkeyw '1',1
mkeyw '2',2
mkeyw 'COM1',1
mkeyw 'COM2',2
port1 prtinfo <0FFFH,0,defpar,1,0,defhand,floxon,0>
port2 prtinfo <0FFFH,0,defpar,1,0,defhand,floxon,0>
portval dw port1 ; Default is to use port 1
bdtab db 9 ; baud rate table
mkeyw '110',0
mkeyw '150',1
mkeyw '300',2
mkeyw '600',3
mkeyw '1200',4
mkeyw '2400',5
mkeyw '4800',6
mkeyw '9600',7
mkeyw '19200',8
; mappings for baud settings from hp to our table
ourbdtab db 0,0 ; not applicable
db 1,0 ; na
db 2,0 ; 110
db 3,0 ; na
db 4,1 ; 150
db 5,2 ; 300
db 6,3 ; 600
db 7,4 ; 1200
db 8,0 ; na
db 9,0 ; na
db 10,5 ; 2400
db 11,0 ; na
db 12,6 ; 4800
db 13,0 ; na
db 14,7 ; 9600
db 15,8 ; 19200
; mappings for baud setting from our table to hp
ourbdtab1 db 0,2 ; 300
db 1,4 ; 150
db 2,5 ; 300
db 3,6 ; 600
db 4,7 ; 1200
db 5,10 ; 2400
db 6,12 ; 4800
db 7,14 ; 9600
db 8,15 ; 19200
setchtab db 1; set file character-set table
mkeyw 'CP437',437
sevenbitnum equ 7
eightbitnum equ 8
transonnum equ 9
transoffnum equ 10
rawonnum equ 11
rawoffnum equ 12
tekonnum equ 13
tekoffnum equ 14
termtb db 10 ; entries for Status, not Set
mkeyw 'HP150',ttgenrc
mkeyw 'Tek4014',tttek
mkeyw '7bit',sevenbitnum
mkeyw '8bit',eightbitnum
mkeyw 'OnTransparency',transonnum
mkeyw 'OffTransparency',transoffnum
mkeyw 'Raw',rawonnum
mkeyw 'Cooked',rawoffnum
mkeyw 'EnableTek',tekonnum
mkeyw 'DisableTek',tekoffnum
; variables for serial interrupt handler
source db bufsiz DUP(?) ; Buffer for data from port
bufout dw 0 ; buffer removal ptr
count dw 0 ; Number of chars in int buffer
bufin dw 0 ; buffer insertion ptr
telflg db 0 ; Are we acting as a terminal
clreol db ESCAPE,'K$'
prttab dw com1,com2
com1 db 'COM1',0
com2 db 'COM2',0
blank db ESCAPE,'H',ESCAPE,'J$'
movcur db ESCAPE,'&a'
colno db 20 dup (0)
ten db 10
prthnd dw 0
argadr dw 0 ; address of arg blk from msster.asm
parmsk db 0ffh ; 8/7 bit parity mask, for reception
flowoff db 0 ; flow-off char, Xoff or null (if no flow)
flowon db 0 ; flow-on char, Xon or null
captrtn dw cptchr ; routine to call for captured output
logflag db false ; if true, we are logging session
; (we have taken cptchr from msster and placed in
; in msxhp1 to avoid flow control problems)
tempbuf dw 10 dup(0)
ourarg termarg <>
;;new stuff to scan escape sequences from comm port [jan]
stringtab dw tekst1,tekst2 ; strings for matching
dw tekst3
numstrings equ 3 ; number of strings to match
disptab dw toteknoplay,totekplay ; dispatch table
dw leavetek
dw ignoreall, ignoreall
tekst1 db escape,'[?38h',0 ;1st string to get into tek mode [jan]
tekst2 db escape,FF,0 ;2nd string to get into tek mode [jan]
tekst3 db escape,'[?38l',0 ; string to exit tekmode
stringchekbuff db 16 dup (0)
stringchekcnt dw 0 ; characters already in buffer
matchsofar dw false ; no match yet
match dw 0
playem db false ; don't play back switch characters
; end of data for string scannine
prtrdy db true ; if false, we get out of connect mode
capbuf db cptsiz dup (0) ; session logging buffer
capbp dw capbuf
caplft dw cptsiz
capterr db escape,'Error in writing log file ','$'
alpha_disp db escape,'&s0P',escape,'&s0Q','$' ; alpha active
tek_disp db escape,'&s1P',escape,'&s0Q',escape,'*t1D','$' ; tek active
alpha_on db escape,'*dE','$' ; turn on alpha display
alpha_off db escape,'*dF','$' ; turn off alpha display
tek_on db escape,'*dC','$' ; turn on tek display
tek_off db escape,'*dD','$' ; turn off tek display
alpha_clear db escape,'H',escape,'J', '$' ; clear alpha
tek_clear db escape,'*dA',escape,'*dL',escape,'*d0,380O','$'; clear tek
to_term_msg db 'Entering Firmware terminal '
db 'Press SHIFT STOP to return to Kermit','$'
;;;; Data for reading data comm configuration in firmware
;*******************************************
;
e_cnp_rom_segment equ 0000h
e_cnp_entry equ 045ch
e_dhp_entry equ 0425h
e_dhp_driver equ 042ah
e_long_call equ 09ah
;
e_port1_read equ 2
e_port2_read equ 4
e_port1_save equ 2
e_port2_save equ 11
e_port1 equ 1 ; values for the two physcial ports.
e_port2 equ 2
e_true equ 1
e_false equ 0
;
;************** LOCAL DECLARATIONS **************
;
;
CONFIGURATION_DATA_AREA struc
predef_values db ?
barrel_index db ?
dc_port db ?
dc_bool1 db ?
dc_bool2 db ?
dc_baud_rate db ?
dc_parity db ?
dc_clock db ?
dc_asterisk db ?
dc_recv_pace db ?
dev_token dw ?
CONFIGURATION_DATA_AREA ends
dc_status_struc struc ; status for datacomm
eightbit db 0 ; true if 8 bit, false if 7 bit
transparent db 0 ; true if transparent, false if not transparent
raw db 0 ; true if raw, false if cooked
dc_status_struc ends
; scratch space.
;
err_flag db 0
readid dw 0
saveid dw 0
work_config CONFIGURATION_DATA_AREA <>
dc_status dc_status_struc <true,true,true>
;
;************************************
;
; Macros for absolute long calls.
;
;************************************
;
call_cnp_entry macro
db e_long_call
dw e_cnp_entry
dw e_cnp_rom_segment
endm
call_dhp_entry macro
db e_long_call
dw e_dhp_entry
dw e_cnp_rom_segment
endm
call_dhp_driver macro
db e_long_call
dw e_dhp_driver
dw e_cnp_rom_segment
endm
baud_port equ 0ch ; port address of baud rate controller
;
; table to print out value of a nibble on the screen
asciitab db '0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'
;
porta_baud db 0 ; stored baud codes
portb_baud db 0
start_porta_baud db 0
start_portb_baud db 0
data ends
code segment public 'code'
extrn comnd:near, dopar:near, atoi:near, prompt:near
extrn sleep:near,statc:near, srchkw:near
extrn msuinit:near, keybd:near ; in msuhp1.asm
extrn keybdopen:near, keybdclose:near ; in msuhp1.asm
extrn getkey:near ; in msuhp1.asm
extrn clearlabels:near, labelsoftkeys:near ; in msuhp1.asm
extrn displaylogoffkey:near, displaylogonkey:near ; in msuhp1
extrn pntchr:near, pntflsh:near
assume cs:code, ds:data, es:nothing
; Clear the input buffer before sending a packet.
CLRBUF PROC NEAR
cmp repflg,0 ; doing replay?
je clrb0 ; e => no replay
ret ; don't clear if replaying
clrb0: push ax ; need to save for CROSHAIR in msggri
cli
mov ax,offset source
mov bufin,ax
mov bufout,ax
mov count,0
sti
clrb1: call prtchr ; get a character
jnc clrb1 ; until there aren't any more
nop
pop ax
ret
CLRBUF ENDP
; Common routine to clear to end-of-line
CLEARL PROC NEAR
push ax
push dx
mov dx,offset clreol
mov ah,prstr
int dos
pop dx
pop ax
ret
CLEARL endp
; Set the baud rate for the current port, based on the value
; in the portinfo structure. Returns carry clear.
BAUDST PROC NEAR
mov dx,offset bdtab ; baud rate table, ascii
xor bx,bx ; help is the table itself
mov ah,cmkey ; get keyword
call comnd
jc baudst1 ; c = failure
push bx ; save result
mov ah,cmeol ; get confirmation
call comnd
pop bx
jc baudst1 ; c = failure
mov si,portval
mov ax,[si].baud ; remember original value
mov [si].baud,bx ; set the baud rate
call dobaud ; use common code
clc
baudst1:ret
BAUDST ENDP
; on entrance bx has baud rate from bdtab
dobaud proc near ; updated by [jan] to set baud
mov ax,portval
cmp ax,offset port1 ; using port 1?
jne dobaud1 ; ne => not using port 1
mov al,1 ; port 1 set
mov ah,bl ; baud code
call set_baud ; set the baud rate
ret
dobaud1:mov al,2 ; set port 2 baud
mov ah,bl ; ah has baud code
call set_baud
ret
dobaud endp
; Send the break signal out data comm
sendbl: ; long break (same as regular h
sendbr: mov al,e_send_break ; regular break
call dc_ioctl
clc ; clear carry bit (stay in Connect)
ret
; Set some data comm ioctl option. AL has function code
dc_ioctl proc near
push ax ; save regs
push bx
push cx
push dx
mov ah,8h
mov tempbuf,ax
mov dx,offset tempbuf
mov ah,e_ioctl
mov al,3
mov bx,prthnd
mov cx,2
int dos
pop dx ; restore regs
pop cx
pop bx
pop ax
ret
dc_ioctl endp
shomodem proc near
mov ah,cmeol ; get a confirm
call comnd
jnc shomod00 ; nc => success
ret ; get out if failure
shomod00:
cmp prthnd,0 ; Got a handle yet?
jne shmod0 ; Yup just go on
call opnprt ; Else 'open' the port
shmod0: mov dx,offset msmsg1 ; say port is not ready
mov bx,prthnd
mov al,7 ; output status command
mov ah,ioctl ; ask DOS to look for us
int dos
jc shmod1 ; c = call failed, device not ready
or al,al
jz shmod1 ; not ready
mov dx,offset msmsg2 ; say port is ready
shmod1: mov ah,prstr
int dos
clc
ret
shomodem endp
getmodem proc near
mov al,0
ret
getmodem endp
; Put the char in AH to the serial port. This assumes the
; port has been initialized. Should honor xon/xoff. Skip returns on
; success, returns normally if the character cannot be written
outchr proc near
push cx
or ah,ah ; sending a null?
jz outch2 ; z = yes
xor cx,cx ; clear counter
cmp ah,flowoff ; sending xoff?
jne outch1 ; ne = no
mov xofsnt,false ; supress xon from chkxon buffer routine
outch1: cmp xofrcv,true ; Are we being held?
jne outch2 ; No - it's OK to go on
loop outch1 ; held, try for a while
mov xofrcv,false ; timed out, force it off and fall thru
outch2: push dx ; Save register
mov al,ah ; Parity routine works on AL
call dopar ; Set parity appropriately
; Begin revised output routine
mov byte ptr temp,al ; put data there
cmp prthnd,0 ; Got a handle yet?
jne outch3 ; Yup just go on
call opnprt ; Else 'open' the port
outch3: push bx
mov bx,prthnd ; port handle
mov cx,1 ; one byte to write
mov dx,offset temp ; place where data will be found
mov ah,write2 ; dos 2 write to file/device
int dos
pop bx ; restore registers
pop dx
pop cx
clc
ret
outchr endp
; Get a file handle for the communications port. Use DOS call to get the
; next available handle. If it fails, ask user what value to use (there
; should be a predefined handle for the port, generally 3). The open
; will fail if the system uses names other than "COM1" or "COM2".
opnprt proc near
mov al,flags.comflg
dec al ; flags.comflg is 1 for com1, 2 for com2
mov ah,0
push si
mov si,ax
shl si,1 ; double index
mov dx,prttab[si]
pop si
mov ah,open2
mov al,2
int dos
jnc opnpr2
mov ah,prstr ; it didn't like the string
mov dx,offset erms41
int dos
ret
opnpr2: mov prthnd,ax ; Call succeeded
call set_port_param ; set appropriate parameters
call serini ; set appropriate parameters
ret
opnprt endp
; This routine blanks the screen.
CMBLNK PROC NEAR ; This is stolen from the IBM example
push ax
push dx
mov ah,prstr
mov dx,offset blank
int dos
pop dx
pop ax
ret
CMBLNK ENDP
LOCATE PROC NEAR
mov dx,0 ; Go to top left corner of screen
jmp poscur ; Go and move the cursor
LOCATE ENDP
; To get the baud, it is likely we would need to
; directly access the UART. Not implemented.
GETBAUD PROC NEAR
ret
GETBAUD ENDP
; Carry set if no character available at the port. If carry clear,
; returns with char in al, # of chars in buffer in dx.
PRTCHR PROC NEAR
cmp repflg,0 ; doing replay?
je prtch0 ; e=> not doing replay
jmp getrepchr ; get replay character if in replay
prtch0:
push bx
push cx
push si
cmp prthnd,0 ; have a handle yet?
jne prtch1 ; yes, keep going
call opnprt
prtch1: cmp count,0 ; no characters?
jne prtch2 ; no, go fill buffer
mov bx,prthnd
mov al,rdchan
mov ah,ioctl
mov dx,offset source ; buffer to read into
mov cx,20 ; read 20 characters at a time
; More characters cause problems for
; early firmware versions
int dos
jc prtch4 ; c = error
mov count,ax ; reset count
mov keydelay, -1 ; read keyboard next go around
mov dx,ax ; needed to obey rules
or ax,ax
jz prtch4 ; still no chars
mov bufout,offset source ; this is output ptr
prtch2: dec count
mov dx,count ; return count in dx
mov si,bufout
cld
lodsb ; get character
mov bufout,si ; update ptr
prtch3: pop si
pop cx
pop bx
clc ; clc if there is a character
ret ; exit success
prtch4: pop si
pop cx
pop bx
stc ; set carry if no characters
ret
PRTCHR ENDP
; IHOSTS - Initialize the host by sending XON, or equivalent, and enter the
; cycle of clear input buffer, wait 1 second, test if buffer empty then exit
; else repeat cycle. Requires that the port be initialized before hand.
; Ihosts is used by the local send-file routine just after initializing
; the serial port.
; 22 March 1986 [jrd]
IHOSTS PROC NEAR
push ax ; save the registers
push bx
push cx
push dx
mov bx,portval ; port indicator
mov ax,[bx].flowc ; put Go-ahead flow control char in ah
or ah,ah ; don't send null if flow = none
jz ihosts1 ; z = null
call outchr ; send it (release Host's output queue)
ihosts1:call clrbuf ; clear out interrupt buffer
pop dx ; empty buffer. we are done here
pop cx
pop bx
pop ax
ret
IHOSTS ENDP
; IHOSTR - initialize the remote host for our reception of a file by
; sending the flow-on character (XON typically) to release any held
; data. Called by receive-file code just after initializing the serial
; port. 22 March 1986 [jrd]
IHOSTR PROC NEAR
push ax ; save regs
push bx
push cx
mov bx,portval ; port indicator
mov ax,[bx].flowc ; put Go-ahead flow control char in ah
or ah,ah ; don't send null if flow = none
jz ihostr1 ; z = null
call outchr ; send it (release Host's output queue)
ihostr1:pop cx
pop bx
pop ax
ret
IHOSTR ENDP
DTRLOW PROC NEAR ; Global proc to Hangup the Phone by making
mov ah,cmline ; allow text to be able to display help
mov bx,offset rdbuf ; dummy buffer
mov dx,offset hnghlp ; help message
call comnd ; get a confirm
jnc dtrlow1 ; nc => success
ret ; get out if failure
dtrlow1:call serhng ; drop DTR and RTS
writestring hngmsg ; tell user of success
clc ; success
ret
DTRLOW ENDP
; Hang up the Phone. Similar to SERRST except it just forces DTR and RTS low
; to terminate the connection. 29 March 1986 [jrd]
; Calling this twice without intervening calls to serini should be harmless.
; Returns normally. Implemented by [jan].
SERHNG PROC NEAR
mov al,5 ; modem disconnect code
call dc_ioctl
clc ; stay in connect mode
ret
SERHNG ENDP
; Position the cursor according to contents of DX
POSCUR PROC NEAR
push ax ; save regs
push dx
push di
push es
mov ax,ds
mov es,ax ; address data segment
cld
mov di,offset colno
mov al,dl ; column
call nout
mov al,'c'
stosb
mov al,dh ; row
call nout
mov al,'Y'
stosb
mov al,'$'
stosb
mov dx,offset movcur
mov ah,prstr
int dos ; print the sequence
pop es ; restore regs
pop di
pop dx
pop ax
ret
POSCUR ENDP
NOUT PROC NEAR
cbw ; extend to word
div byte ptr ten ; divide by 10
or al,al ; any quotient?
jz nout1 ; no, forget this
push ax ; save current result
call nout ; output high order
pop ax ; restore
nout1: mov al,ah ; get digit
add al,'0' ; make printable
stosb
ret ; put in buffer and return
NOUT endp
; Write a line in inverse video at the bottom of the screen...
; the line is passed in dx, terminated by a $. Returns normally.
putmod proc near
push dx ; preserve message
mov dx,24 * 100H ; line 24
call poscur
mov dx,offset invseq ; put into inverse video
mov ah,prstr
int dos
pop dx
int dos
mov dx,offset nrmseq ; normal videw
int dos
ret ; and return
putmod endp
; Clear the mode line written by putmod. Returns normally.
clrmod proc near
mov dx,24 * 100H
call poscur
call clearl
ret
clrmod endp
; Put a help message one the screen in reverse video. Pass
; the message in AX, terminated by a null. Returns normally.
; The message is put wherever the cursor currently is located.
puthlp proc near
push ax ; save some regs
push si
push dx
push ax
mov ah,prstr ; Leave some room before the message
mov dx,offset crlf
int dos
pop si ; Put message address here
puth0: mov ah,prstr
mov dx,offset invseq ; Put into reverse video
int dos
mov ah,prstr
mov dx,offset ivlseq ; Make line inverse video
int dos
cld
puth1: lodsb
cmp al,0 ; Terminated with a null
je puth2
mov dl,al
mov ah,conout
int dos
cmp al,lf ; Line feed?
je puth0 ; e = yes, clear the next line
jmp puth1 ; else, just keep on writing
puth2: mov dx,offset crlf
mov ah,prstr
int dos
mov dx,offset nrmseq ; Normal video
int dos
pop si
pop dx
pop ax
ret
puthlp endp
; Perform a delete.
DODEL PROC NEAR
push ax
push dx
mov ah,prstr
mov dx,offset delstr ; Erase character
int dos
pop dx
pop ax
ret
DODEL ENDP
; Perform a Control-U.
CTLU PROC NEAR
push ax
push dx
mov ah,prstr
mov dx,offset clrlin
int dos
pop dx
pop ax
ret
CTLU ENDP
COMS PROC NEAR
mov dx,offset comptab ; comms port table
mov bx,0 ; use keywords as help
mov ah,cmkey ; parse keyword
call comnd
jnc coms1 ; nc => success
ret ; get out if failure
coms1: push bx
mov ah,cmeol
call comnd ; Get a confirm
jc comx ; didn't get a confirm
call serrst ; close existing port before opening
pop bx ; the new one
mov flags.comflg,bl ; Set the comm port flag
cmp flags.comflg,1 ; Using Com 1?
jne coms2 ; ne = no
mov portval,offset port1
call serini ; initialize new port
ret
coms2: mov portval,offset port2 ; use Com2
call serini ; initialize port
ret
comx: pop bx
ret
COMS ENDP
VTS PROC NEAR ; Set Term code
mov dx, offset termtb
mov bx,0
mov ah,cmkey
call comnd
jnc vts1 ; nc => success
ret ; return if failure
vts1: push bx
mov ah,cmeol
call comnd
jnc vts2 ; nc=> success
pop bx
ret ; return if failure
vts2: pop bx ; bl has number from termtb
mov di,offset dc_status
cmp bl,eightbitnum ; doing 8 bits?
jne vts3
mov [di].eightbit,true
call set_port_param ; set port parameters
clc
ret
vts3: cmp bl,sevenbitnum ; doing 7 bits?
jne vts4 ; ne => not 7 bits
mov [di].eightbit,false
call set_port_param ; set port parameters
clc
ret
vts4: cmp bl,transonnum ; transparency on?
jne vts5
mov [di].transparent,true
call set_port_param ; set port parameters
clc
ret
vts5: cmp bl,transoffnum ; transparency off?
jne vts6
mov [di].transparent,false
call set_port_param ; set port parameters
clc
ret
vts6: cmp bl,rawonnum ; make port raw?
jne vts7
mov [di].raw,true
call set_port_param ; set port parameters
clc
ret
vts7: cmp bl,rawoffnum ; cook the port?
jne vts7a
mov [di].raw,false
call set_port_param ; set port parameters
clc
ret
vts7a: cmp bl,tekonnum ; enable tek?
jne vts7b ; ne => don't enable
and denyflg,not tekxflg ; clear tekx bit
mov tekbyte,bl ; for status display
clc
ret
vts7b: cmp bl,tekoffnum ; disable tek
jne vts8 ; ne => don't disable
or denyflg,tekxflg ; set tek deny bit
mov tekbyte,bl ; for status display
clc
ret
vts8: cmp bl,ttgenrc ; hp150 emulation selected?
jne vts9
mov flags.vtflg,bl ; set emulator type
clc
ret
vts9: cmp bl,tttek ; tek emulation selected?
jne vts10
mov flags.vtflg,bl
vts10: clc
ret ; success
VTS ENDP
VTSTAT PROC NEAR ; For Status display
mov bx,offset vtstbl ; table of things to show
jmp statc ; common status code
VTSTAT ENDP
; Save the screen to a buffer and then append buffer to a disk file. [jrd]
; Default filename is Kermit.scn; actual file can be a device too. Filename
; is determined by mssset and is passed as pointer dmpname.
DUMPSCR PROC NEAR ; Dumps screen contents to a file. Just Beeps here
call beep
ret
DUMPSCR ENDP
lclini proc near
saveregs
call read_baud ; use firmware to read baud rates
mov lclexit,offset lclose ; routine to call when closing
mov prtrdy,true ; port is ready
mov flags.vtflg,0 ; no terminal emulation. [jrd]
mov prthnd,0 ; no port handle yet. [jrd]
call msuinit ; initialize keyboard module msugen
call serini ; initialize port
restoreregs
ret
lclini endp
; Wait for the # of milliseconds in ax, for non-IBM compatibles.
; Thanks to Bernie Eiben for this one.
pcwait proc near
mov cx, 180 ; hp150 has effective clock of only 3.6 MHz!!!
pcwai1: sub cx,1 ; inner loop takes 20 clock cycles
jnz pcwai1
dec ax ; outer loop counter
jnz pcwait ; wait another millisecond
ret
pcwait endp
; Initialization for using serial port. Returns normally.
; Attempts to put port device in binary mode. [jrd]
SERINI PROC NEAR
cld ; Do increments in string operations
cmp prthnd,0 ; Got a handle yet?
jne serin0
push bx
call opnprt ; Else 'open' the port
pop bx
serin0: push bx
mov bx,portval ; get port [jrd]
mov parmsk,0ffh ; parity mask, assume parity is None
cmp [bx].parflg,parnon ; is it None?
je serin1 ; e = yes
mov parmsk,07fh ; no, pass lower 7 bits as data
serin1: mov bx,[bx].flowc ; get flow control chars
mov flowoff,bl ; xoff or null
mov flowon,bh ; xon or null
pop bx
clc ; carry clear for success
ret
SERINI ENDP
SERRST PROC NEAR
push bx ; save reg
push di
mov bx,prthnd
cmp bx,0 ; none there?
je serrs6 ; no, don't try to close
; return the port to the orignal status
mov bx, prthnd ; handle
call cookedon ; cook the port first
mov al, e_port1 ; assume port 1
mov bx, offset port1
cmp portval, bx ; are we using port 1?
je serrs2
mov al, e_port2 ; using port 2
serrs2: call get_config_values ; read configuration di points to work_config
mov al, 1 ; assume 7 bit mode
test [di].dc_bool2, 2 ; if bit2 set => 7 bit
jnz serrs3 ; nx => yes 7 bit
mov al,2 ; 2 for 8 bit
serrs3: call dc_ioctl ; update the number of bits
mov al, 4 ; disable data comm transparency
call dc_ioctl
mov bx, prthnd ; port handle in bx for close
mov ah,close
int dos ; close handle
mov prthnd,0 ; the port is now closed
serrs6: pop di
pop bx
ret ; All done
SERRST ENDP
; Generate a short beep.
BEEP PROC NEAR
mov dl,bell
mov ah,conout
int dos
ret
BEEP ENDP
; Dumb terminal emulator. Doesn't work too well above 1200 baud (and
; even at 1200 baud you sometimes lose the first one or two characters
; on a line). Does capture (logging), local echo, debug display, tests
; for printer/logging device not ready. 27 Sept 86 [jrd].
term proc near
mov argadr,ax ; save argument ptr
mov si,ax ; this is source
mov di,offset ourarg ; place to store arguments
push es ; save register
push ds
pop es ; make es point to datas segment
mov cx,size termarg
cld
rep movsb ; copy into our arg blk
pop es ; recover reg
mov ax,ourarg.captr
;;; mov captrtn,ax ; buffer capture routine
call pntflsh ; flush printer buffer
mov keydelay,0 ; initizize keyboard counter [jan]
mov parmsk,0ffh ; parity mask, assume parity = None
call keybdopen ; turn on keycode mode
call labelsoftkeys
call displaylogkey ; decide whehter to display logging softkey
cmp flags.vtflg,tttek ; in tektronix emulation?
jne term0 ; ne=> doing alpha
call tekini ; initialize emulator
term0: mov parmsk,0ffh ; 8 bit parity by default
cmp ourarg.parity,parnon ; is parity None?
je term1 ; e = yes, keep all 8 bits
mov parmsk,07fh ; else keep lower 7 bits
term1: cmp prtrdy,false ; ready to read port?
jne term2 ; ne = yes
mov kbdflg,'C' ; so we exit connect mode
mov prtrdy,true ; get ready for next connect
jmp term5 ; get out
term2: call portchr ; get char from port, mask parity
jnc short term4 ; nc = no char, go on
call stringchek ; check the string for escape sequence
jnc short term4 ; nc => no key to show
term3: call outtty ; display and capture char
term4: inc keydelay ; increment counter
mov ah,keydelay ; move into ah
and ah,15 ; clear high bits and read keyboard
jne term1 ; once each 16 reads of serial port
call keybd ; call keyboard translator in msu
jnc term1 ; nc = no char or have processed it
term5: ; carry set = quit Connect mode
call pntflsh ; flush printer buffer
call clearlabels ; blank softkey labels
call keybdclose ; turn off keycode mode
writestring alpha_disp ; make sure we are in alpha upon exit
writestring alpha_on ; turn on alpha
writestring tek_off ; turn off tek
call test_baud_change ; check for baud change
call cptdmp ; empty the capture buffer
ret
term endp
; put the character in al to the screen, do capture and printing,
; does translation for Set Input command.
; Adapted from msyibm.asm [jrd]
outtty proc near
test flags.remflg,d8bit ; keep 8 bits for displays?
jnz outnp8 ; nz = yes, 8 bits if possible
and al,7fh ; remove high bit
outnp8: cmp rxtable+256,0 ; is translation off?
je outnp7 ; e = yes, off
push bx ; Translate incoming char
mov bx,offset rxtable ; address of translate table
xlatb ; new char is in al
pop bx
outnp7: cmp logflag,true ; are we logging?
jne outnoc ; ne => no, forget logging
push ax ; save char
call captrtn ; give it captured character
pop ax ; restore character and keep going
outnoc: test anspflg,prtscr ; should we be printing?
jz outnop ; no, keep going
call pntchr ; queue char for printer
jnc outnop ; nc = successful print
push ax
call beep ; else make a noise and
call trnprs ; turn off printing
pop ax
outnop: cmp flags.vtflg,0 ; emulating a terminal?
jnz outnop1 ; nz = yup, go do something smart
test ourarg.flgs,trnctl ; debug? if so use dos tty mode
jz outnp4 ; z = no
mov ah,conout
cmp al,7fh ; Ascii Del char or greater?
jb outnp1 ; b = no
je outnp0 ; e = Del char
push ax ; save the char
mov dl,7eh ; output a tilde for 8th bit
int dos
pop ax ; restore char
and al,7fh ; strip high bit
outnp0: cmp al,7fh ; is char now a DEL?
jne outnp1 ; ne = no
and al,3fH ; strip next highest bit (Del --> '?')
jmp outnp2 ; send, preceded by caret
outnp1: cmp al,' ' ; control char?
jae outnp3 ; ae = no
add al,'A'-1 ; make visible
outnp2: push ax ; save char
mov dl,5eh ; caret
int dos ; display it
pop ax ; recover the non-printable char
outnp3: mov dl,al
int dos
ret
outnp4: ;cmp al,bell ; bell (Control G)?
;jne outnp5 ; ne = no
;jmp beep ; use short beep, avoid char loss
outnop1:
outnp5:
mov dl,al ; write without intervention
mov ah,6 ; direct console i/o
int dos ; else let dos display char
ret ; and return
outtty endp
; send the character in al out to the serial port; handle echoing.
; Can send an 8 bit char while displaying only 7 bits locally.
outprt proc near
test ourarg.flgs,lclecho ; echoing?
jz outpr1 ; z = no, forget it
push ax ; save char
call outtty ; print it
pop ax ; restore
outpr1: mov ah,al ; this is where outchr expects it
call outchr ; output to the port
ret
outprt endp
; Get a char from the serial port manager
; returns with carry on if a character is available
portchr proc near
call prtchr ; character at port?
jnc portc1 ; nc = yes there is a character
portc0: clc ; no carry -> no character
ret ; and return
portc1: and al,parmsk ; apply 8/7 bit parity mask
stc ; have a character
ret ; and return
portchr endp
;; keyboard translator action routines, system dependent, called from msugen.
; These are invoked by a jump instruction. Return carry clear for normal
; processing, return carry set to exit Connect mode (kbdflg has transfer char)
chrout proc near
cmp repflg,0 ; in replay mode?
je chrout1 ; e=> not doing replay
jmp repchrout ; display the replay character
chrout1:call outprt ; put char in al to serial port
clc ; stay in Connect mode
ret
chrout endp
trnprs: push ax ; toggle Copy screen to printer
test anspflg,prtscr ; should we be printing?
jnz trnpr2 ; nz = yes, its on and going off
mov ah,ioctl
mov al,7 ; get output status of printer
push bx
mov bx,prnhand ; file handle for system printer
int dos
pop bx
jc trnpr1 ; c = printer not ready
cmp al,0ffh ; Ready status?
je trnpr2 ; e = Ready
trnpr1: call beep ; Not Ready, complain
jmp short trnpr3 ; and ignore request
trnpr2: xor anspflg,prtscr ; toggle print flag
trnpr3: pop ax
clc
ret
displaylogkey proc near ; display logging softkey?
test flags.capflg, logses ; session logging enables?
jz displaylogkey3 ; z= no, forget it
cmp logflag, true ; are we logging?
jne displaylogkey1 ; ne => not logging
call displaylogoffkey ; off key if capturing
jmp displaylogkey2 ; make a good exit
displaylogkey1:
call displaylogonkey ; show log on function key
displaylogkey2:
clc
ret
displaylogkey3:
mov logflag, false ; not logging
clc
ret
displaylogkey endp
klogtog proc near ; toggle session logging key
test flags.capflg, logses ; session logging enables?
jz klogtogn ; z= no, forget it
cmp logflag, true ; are we capturing?
jne klogtog1 ; ne => not logging
mov logflag, false ; turn off loggin
push bx
mov bx, argadr
and [bx].flgs, not capt ; tell kermit we are stopping capture
and ourarg.flgs, not capt ; turn off local capture flag
pop bx ; restore the register
call displaylogkey ; turn on appropriate log key
call cptdmp ; dump the capture buffer to file
jmp klogtog2
klogtog1:
mov logflag, true ; turn on logging
push bx
mov bx, argadr
or [bx].flgs, capt ; tell kermit we are resuming capture
or ourarg.flgs, capt ; turn on local capture flag
pop bx ; restore the register
call displaylogkey ; turn on log off key
klogtog2: clc
ret
klogtogn: mov logflag, false ; not logging so turn off flag
clc
ret
klogtog endp
snull: mov ah,0 ; send a null
call outchr ; send without echo or logging
clc
ret
kdos: mov al,'P' ; Push to DOS
jmp short cmdcom
cstatus:
mov al,'S' ; these commands exit Connect mode
jmp short cmdcom
cquit:
mov al,'C'
jmp short cmdcom
cquery:
mov al,'?'
jmp short cmdcom
cmdcom: mov kbdflg,al ; pass char to msster.asm via kbdflg
stc ; say exit Connect mode
ret
;; end of action routines
; set comm port parameters based on dc_status structure
set_port_param proc near
push di
cmp prthnd,0 ; got a handle yet
jne set_port_param1 ; ne = yes
call opnprt
jmp set_port_param5 ; opnprt calls this so don't repeat
set_port_param1:
mov di,offset dc_status
cmp [di].eightbit,true ; doing 8 bit?
je set_port_param2 ; e=> yes, doing 8 7 bit
mov eightflg,sevenbitnum ; so status knows we have seven bits
mov al,1 ; dc_ioctl code for 7 bit
call dc_ioctl
jmp set_port_param2a ; check transparent
set_port_param2:
mov eightflg,eightbitnum ; so status knows we have eight bits
mov al,2 ; code for 8 bit
call dc_ioctl
set_port_param2a:
cmp [di].transparent,true ; in transparency mode?
je set_port_param3 ; e=> yes
mov transparentflg,transoffnum ; so status knows transparency off
mov al,4 ; code to disable transparency
call dc_ioctl
jmp set_port_param3a ; check raw/cooked situation
set_port_param3:
mov transparentflg,transonnum ; so status knows transparency on
mov al,3 ; code to enable transparency
call dc_ioctl
set_port_param3a:
cmp [di].raw,true ; raw mode set?
je set_port_param4 ; e => raw on
mov rawflg,rawoffnum ; so status knows we're cooked
mov bx,prthnd ; cooked on needs port handle
call cookedon
jmp set_port_param5 ; done
set_port_param4:
mov rawflg,rawonnum ; tell status port is raw
mov bx,prthnd ; port handle for raw on
call rawon
set_port_param5:
pop di
clc
ret
set_port_param endp
;check string to see if we need to do something special
stringchek proc near
cmp stringchekcnt,0 ; nobody in yet?
jne stringchek1 ; ne => already have characters
cmp al,escape ; is this escape?
je stringchek1 ; it is escape, so go and process
cmp al,escape+80h ; in case parity is odd
je stringchek1 ; process escape
stc ; display the character
ret ; return quickly if nothing to do
stringchek1: ; here is escape already in
saveregs
and al,07fh ;strip high bit
mov bx,stringchekcnt
mov stringchekbuff[bx],al ;put character in buffer
inc stringchekcnt ;one more character in buffer
call stringtest ; does the string in stringchekbuff match?
cmp match,0 ; 0 means no match
je stringchek2
mov si,match ; here means we have a match
shl si,1 ; multiply by 2
dec si
dec si ; 1=0, 2=1 etc
call disptab[si] ; call appropriate function
call stringbuffplay ; play back the buffer
clc ; don't display
jmp stringchek3 ; return and don't display character
stringchek2:
clc ; don not display
cmp matchsofar,true ; do we have a match so far
je stringchek3 ; e=true , get out
mov playem,true
call stringbuffplay ; clean out the buffer
clc ; don't display character
stringchek3:
restoreregs
ret
stringchek endp
;test to see if input string is a match to toggle terminal [jan]
; stringtab gives addresses of 0 terminated strings
; teststring in stringchekbuff
; numstrings is the number to checked
; matchsofar will have be true if there is a possilbe match
; match will be non-zero 1, 2, 3 indicating number of match if a match
; if no match yet, match will be 0
; severaal registers get destroyed
stringtest proc near
mov matchsofar,false ; assume no match
mov match,0 ; no match
xor si,si ; pointer to string tab
dec si
dec si ; step back 1 item
mov cx,0 ; cx points to number of string
strtst1:
inc cx ; strings number
cmp cx,numstrings ; done parsing table?
ja strtst5 ; we're done, get out of here
mov di,offset stringchekbuff
inc si
inc si ; point to next item
mov bx,stringtab[si] ; offset of string
strtst2:
mov al,[di] ; stringchekbuff in al
mov ah,[bx] ; string element to test in ah
cmp al,0 ; end of stringchekbuff
jne strtst2a ; ne=> not at end of buffer
mov matchsofar,true ; we have a match so far
jmp strtst5 ; return to caller
strtst2a:
cmp ah,0 ; at end of string?
je strtst1 ; failure, go to next string
cmp ah,al ; match?
jne strtst1 ; no match, on to next string
; here if match
mov ah,[bx+1] ; next byte from string
cmp ah,0 ; are we done with string?
je strtst3 ; e => yes, a match
inc bx ; next element in string
inc di ; next character in stringchekbuff
jmp strtst2 ; check next item in string
strtst3: ; here if we have a match
mov match,cx
mov matchsofar,true
strtst5:ret
stringtest endp
;play back characters in string buffer ..called by stringchek
stringbuffplay proc near
xor bx,bx
mov cx,stringchekcnt
stringbuffplay1:
mov al,stringchekbuff[bx]
cmp playem,true ; playback characters?
jne stringbuffplay2 ; ne = no don't play back
push bx ; save index
push cx ; save count
call outtty ; print the character
pop cx ; restore count
pop bx ; restore index
stringbuffplay2:
mov stringchekbuff[bx],0 ; set to 0
inc bx ; point to next character
loop stringbuffplay1 ; repeat until buffer is empty
mov stringchekcnt,0 ; now no characters in buffer
ret
stringbuffplay endp
ignoretek proc near ; ignore this escape sequence in tek mode
mov playem,false
cmp flags.vtflg,tttek ; are in in tek emulation
je ignoretek1 ; e=yes do not play back
mov playem,true
ignoretek1:ret
ignoretek endp
ignoreall proc near ; always ignore this escape sequence
mov playem,false
call beep ; let user know of illegal sequence
ret
ignoreall endp
totekplay proc near ; turn on tektronix
mov playem,true ; play back characters
jmp totek
totekplay endp
toteknoplay proc near
mov playem,false
jmp totek
toteknoplay endp
totek proc near ; turn on tektronix
test denyflg,tekxflg ; tek auto entry enabled?
jz totek1
mov playem,true ; play back characters
ret
totek1: cmp flags.vtflg,tttek ; already doing tek
je totek2
call termtog ; toggle to tektronix
totek2: ret
totek endp
leavetek proc near ; turn off tektronix
mov playem,false ; don't play back characters
test denyflg,tekxflg ; tek auto entry/exit enabled?
jz leavetek1
mov playem,true ; play back characters
ret
leavetek1:
cmp flags.vtflg,tttek ; already doing tek
jne leavetek2 ; ne => doing alpha so ignore
call termtog ; toggle to alpha
leavetek2:ret
leavetek endp
getrepchr proc near ; get replay character for file
mov ah,readf2 ; read from replay file
mov bx,diskio.handle
mov cx,1 ; read 1 character
mov dx,offset rdbuf ; to this buffer
int dos
jc getrepchr1 ; c => failure
cmp ax,cx ; read the byte?
jne getrepchr1
mov al,rdbuf ; al has character
clc ; character available in al
ret
getrepchr1:
call beep ; announce file is done
call beep
call waitkey ; wait for a key to be pressed
mov prtrdy,false ; so we exit connect mode
stc
ret ; no character available
getrepchr endp
repchrout proc near ; process key in al while replaying
and al,7fh ; strip parity
repchrout1:
cmp al,'C'-40h ; Control C?(to exit playback mode)
je repchrout3 ; e=> yes, return failure
cmp al,XOFF ; user wants to stop?
jne repchrout2 ; ne => ok to continue
call waitkey ; wait and get a key
jmp repchrout1 ; now process this key
repchrout2:
clc ; return success
ret
repchrout3:
mov prtrdy,false ; exit terminal
stc ; exit connect mode
ret
repchrout endp
termtog proc near ; toggle terminal type [jan]
cmp flags.vtflg,tttek ; doing tek emulation ?
jne termtog1 ; ne means doing tek
writestring tek_off ; turn off tek
writestring alpha_disp ; turn on alpha
writestring alpha_on ; and turn on the alpha
mov flags.vtflg,ttgenrc ; turn on alpha display
clc
ret
termtog1:mov flags.vtflg,tttek ; turn on tek display
writestring alpha_off ; turn off alpha
writestring tek_disp
writestring tek_on ; and turn on the tek
clc ; do not exit Connect mode
ret ; stay in connect mode
termtog endp
kclrscn proc near ; clear the screen
cmp flags.vtflg,tttek ; doing tek emulation
je kclrscn1 ; e=> yes
writestring alpha_clear ; clear the alpha
clc ; stay in connect mode
ret ; return to caller
kclrscn1:writestring tek_clear ; clear the tektronix
clc ; stay in connect mode
ret
kclrscn endp
waitkey proc near ; wait for a key to be pressed
waitkey0:call getkey ; get a key; carry set => no key; code in ax
jc waitkey0 ; repeat until its pressed
ret
waitkey endp
tekini proc near ; initialize tek emulator
writestring alpha_off
writestring tek_disp ; enable tektronix
writestring tek_on ; turn on tek
ret
tekini endp
toterminal proc near ; go to firmware terminal mode
cmp dosnum,dos211 ; dos 2.11 or above?
jae toterminal1 ; ae=> ok to go to terminal
mov ah,2
mov dl,7
int dos ; ring the bell
clc ; stay in connect mode
ret
toterminal1:
call clearlabels ; blank softkey labels
call keybdclose ; get out of keycode
writestring to_term_msg
mov ax,1750
call pcwait ; 1 3/4 second time to read message
mov bx,offset agiosbuff
mov word ptr [bx],26 ; function code to get into terminal
mov ax,4403h ; io control write
mov bx,1 ; console handle
mov cx,2 ; 2 bytes in buffer
mov dx,offset agiosbuff
int dos ; now in terminal mode
call labelsoftkeys ; turn keys on when we return
call keybdopen ; back to keycode mode
clc ; stay in connect mode
ret ; back to terminal
toterminal endp
cookedon proc near ; cook handle in bx
push ax
push dx ; save registers
push bx ; save handle
mov ax,4400h ; get device information
int dos
xor dh,dh ; clear high byte
and dl,0dfh ; clear raw bit without changing other bits
mov ax,4401h ; put device information
pop bx ; restore handle
int dos ; turn off raw mode
pop dx ; restore registers
pop ax
clc ; always returns success
ret
cookedon endp
rawon proc near
push ax
push dx ; save registers
push bx ; save handle
mov ax,4400h ; get device information
int dos
xor dh,dh ; clear high byte
or dl,20h ; set raw bit
mov ax,4401h ; put device information
pop bx ; restore handle
int dos ; turn on raw mode
pop dx
pop ax ; restore registers
clc ; always returns success
ret
rawon endp
;;;cptchr and cptdmp taken from msster to fix the problem
; of com buffer overflow with logging the session
cptchr proc near ; session capture routine, char in al
push di
mov di,capbp ; buffer pointer
mov byte ptr [di],al
inc capbp
pop di
dec caplft ; decrement chars remaining
jg cptch1 ; more room, forget this part
call cptdmp ; dump the info
cptch1: ret
cptchr endp
cptdmp proc near ; empty the capture buffer
push ax
push bx
push cx
push dx
mov bx,sloghnd ; get file handle
cmp bx,0 ; is file open?
jle cptdm1 ; le = no, skip it
push bx ; save handle
mov bx,portval ; doing flow control?
cmp [bx].floflg,0 ; e = no
je cptdmp01
cmp xofsnt,true ; have we sent xoff?
je cptdmp01 ; don't send it again
mov ah,flowoff ; get the xoff
or ah,ah ; null (no flow control?)
jz cptdmp01
call outchr ; send xoff to port
mov xofsnt,true ; remember we've sent it
cptdmp01:pop bx ; restore handle
mov cx,cptsiz ; original buffer size
sub cx,caplft ; minus number remaining
jl cptdm2 ; means error
jcxz cptdm1 ; z = nothing to do
mov dx,offset capbuf ; the capture routine buffer
mov ah,write2 ; write with filehandle
int dos ; write out the block
jc cptdm2 ; carry set means error
mov capbp,offset capbuf
mov caplft,cptsiz ; init buffer ptr & chrs left
jmp short cptdm1
cptdm2: and flags.capflg,not logses ; so please stop capturing
; and targ.flgs,not capt ; so please stop capturing
and ourarg.flgs, not capt ; so please stop capturing
mov dx,offset capterr ; tell user the bad news
mov ah,prstr
int dos
cptdm1: cmp xofsnt, true ; xoff sent
jne cptdm02
mov ah,flowon ; get the xon
or ah,ah ; null?
jz cptdm02
call outchr ; send xon
mov xofsnt,false ; remember we've sent it
cptdm02:pop dx
pop cx
pop bx
pop ax
ret
cptdmp endp
test_baud_change proc near ; check if firmware baud changed
mov al,e_port1
call get_config_values
mov al,[di].dc_baud_rate
cmp al,start_porta_baud ; baud rate changed by firmware (via user)
je test_baud_change1 ; e = not changed
call read_bauda ; redo port a baud
test_baud_change1:
mov al,e_port2 ; check if port 2 changed
call get_config_values
mov al,[di].dc_baud_rate
cmp al,start_portb_baud
je test_baud_change2 ; e = not changed
call read_baudb ; read port b baud
test_baud_change2:
ret
test_baud_change endp
read_baud proc near
call read_bauda ; read port 1 baud
call read_baudb ; read port 2 baud
ret
read_baud endp
read_bauda proc near ; read baud on port 1 and update port info
mov al,e_port1
call get_config_values ; get port 1 configuration
mov si,offset port1
mov di,offset work_config
mov bl,[di].dc_baud_rate ; baud rate into bl
mov start_porta_baud,bl ; remember startup baud
mov portb_baud,bl ; remember startup baud
mov di,offset ourbdtab ; translate hp baud into kermit code
shl bl,1 ; multiply by 2 for 2 bytes per entry
xor bh,bh
mov bl,[di+bx+1]
mov [si].baud,bx ; write baud in port 1 info
ret
read_bauda endp
; Read the port 2 status
read_baudb proc near
mov al,e_port2
call get_config_values ; get port 2 configuration
mov si,offset port2
mov di,offset work_config
mov bl,[di].dc_baud_rate ; baud rate into bl
mov start_portb_baud,bl ; remember startup baud
mov portb_baud,bl ; current baud on port b
mov di,offset ourbdtab ; translate hp baud into kermit code
shl bl,1 ; multiply by 2 since 2 bytes per entry
xor bh,bh
mov bl,[di+bx+1]
mov [si].baud,bx ; write baud in port 2 info
ret
read_baudb endp
;;; read data comm configuration. taken off dc.asm from compuserve
;*******************************************
;
; Firmware Programming Notes:
;
; 1) The firmware has a modular structure and generally consists
; of a bunch of processing modules which all have a separate
; logical segment and a limited number of entry points
; (generally only one).
; 2) The desired processing is accessed by passing the required
; parameters and the proper function code on entry to a
; module.
; 3) A call to a procedure outside the logical module is always
; a long call and inter segment (logical segment).
; 4) Parameters for a call to a procedure outside the logical
; module are pushed on the stack. This includes the function
; code. The procedure called has the responsibility of
; cleaning up the stack.
; 5) The procedure called should always return status in AX.
; Registers BX, CX, and DX may also contain outputs.
; 6) The caller should always assume registers AX, BX, CX, and
; DX have been modified. The caller should always assume
; registers SI, DI, SP, BP, DS, ES, and SS are the same on
; return.
; 7) Calls to external procedures are made through jump tables
; at the beginning of each rom. Thus the application is
; insulated from re-releases of the HP150 firmware.
;
;*******************************************
page;
;*************** GRYPHON DECLARATIONS ************
; To simplify external linking to absolute firmware jump locations,
; we include the long calls as constants. Note that we still have
; some measure of ROM independence because we entry the routines
; through fixed jump tables at the start of the RAM.
;
;-------------------------------------------
;
; COMMENTS:
; 1) The bytes PREDEF_VALUES and BARREL_INDEX are used by
; configuration processing during normal operation where a
; configuration form is brought onto the screen. Their
; values can be set and then ignored.
; 2) The bytes DC_PORT through DC_RECV_PACE are the actual
; datacomm configuration values.
; 3) The word DC_DEVICE_TOKEN is used to access the datacomm
; device.
;
;-------------------------------------------
;*******************************************
;
; The data format for the datacomm configuration values are as
; follows:
;
; 1) DC_PORT= 2 (port 1)
; 11 (port 2)
;
; 2) DC_BOOL1 (a graphical representation follows)
; 3) DC_BOOL2
;
; HP Point-to-Point Boolean Bit Positions
;
; 7 6 5 4 3 2 1 0
; +-------+-------+-------+-------+-------+-------+-------+-------+
; | 1 Stop| CS(CB)| SRR | RR(CF)| SRR | SR(CH)| Chk | ENQ |
; | Bit | Xmit | Invert| Recv | Xmit | | Parity| ACK |
; +-------+-------+-------+-------+-------+-------+-------+-------+
; | TR(CD)| DM(CC)| | | | | 7 Data| Xmit |
; | | Xmit | | | | | Bits | Pace |
; +-------+-------+-------+-------+-------+-------+-------+-------+
;
; DC_BOOL1:
;
; Bit 0: 0 = No 1 = Yes
; Bit 1: 0 = No 1 = Yes
; Bit 2: 0 = Lo 1 = Hi
; Bit 3: 0 = No 1 = Yes
; Bit 4: 0 = No 1 = Yes
; Bit 5: 0 = No 1 = Yes
; Bit 6: 0 = No 1 = Yes
; Bit 7: 0 = 2 Stop Bits 1 = 1 Stop Bit
;
; DC_BOOL2:
;
; Bit 0: 0 = None 1 = Xon/Xoff
; Bit 1: 0 = 8 Data Bits 1 = 7 Data Bits
; Bit 6: 0 = No 1 = Yes
; Bit 7: 0 = Lo 1 = Hi
;
; 4) DC_BAUD_RATE = 02H (110 Baud)
; 04H (150 Baud)
; 05H (300 Baud)
; 06H (600 Baud)
; 07H (1200 Baud)
; 0AH (2400 Baud)
; 0CH (4800 Baud)
; 0EH (9600 Baud)
; 0FH (19200 Baud)
;
; 5) DC_PARITY = 0 (Zeros)
; 1 (Ones)
; 2 (Even)
; 3 (Odd)
; 4 (None)
;
; 6) DC_CLOCK = 0 (INT CLOCK)
; 1 (EXT X1 CLOCK)
; 2 (EXT X16 CLOCK)
;
; 7) DC_ASTERISK = 0 (No Asterisk)
; 1 (DM Asterisk)
; 2 (RR Asterisk)
; 3 (Line Asterisk)
; 4 (CS Asterisk)
;
; 8) DC_RECV_PACE = 0 (No Recv Pace)
; 1 (Xon/Xoff Recv Pace)
; 2 (TR(CD) Recv Pace)
;
;*******************************************
;
;
;-------------------------------------------
;
; PROCEDURE NAME: GET_CONFIG_VALUES
;
; FUNCTION:
; 1) Specify a block of configuration parameters to be obtained
; by config processing. The parameters define how datacomm
; is configured.
; 2) Config processing will get the data out of NVRAM. The
; values reflect the current configuration of the 150.
; 3) The data is written into the data area supplied by the
; caller and is in the format used by the datacomm driver.
;
; INPUTS:
; 1) DS - segment of CONFIGURATION_DATA_AREA
; 2) DI - offset of CONFIGURATION_DATA_AREA
;
; OUTPUTS:
; The configuration data area will have all the necessary
; values needed to specify the datacomm configuration. These
; can be modified so when they are passed to the datacomm
; driver, the new configuration will take effect.
;
; REGISTERS MODIFIED: ax, bx, cx, dx
;
;-------------------------------------------
GET_CONFIG_VALUES proc near
mov readid,e_port1_read
mov saveid,e_port1_save
cmp al,e_port1
je init90
mov readid,e_port2_read
mov saveid,e_port2_save
init90: mov di,offset work_config
;----------------------------------------
; Initialize the variables of the config data area required
; by config processing.
;----------------------------------------
mov [di].PREDEF_VALUES,3
mov [di].BARREL_INDEX,6
mov ax,readid
mov [di].DC_PORT,al
;----------------------------------------
; Get the datacomm configuration values.
;----------------------------------------
mov ah,al ; Port X config type in AH
mov al,4 ; full duplex, hardwired form.
push ax
mov ax,0201h ; 01 -> Personality ID
push ax ; C02 -> Config values are required.
push ds ; segment of CONFIGURATION_DATA_AREA
push di ; pointer to start of data area
lea ax,[di].DC_PORT ; pointer to start of config values
push ax
mov ax,3 ; function code for CNP_GET_DEV_CONFIG
push ax
CALL_CNP_ENTRY
mov ax,saveid
mov [di].dc_port,al
ret
GET_CONFIG_VALUES endp
; Set baud port (1 or 2) in al, Kermit baud code from bdtab in ah.
; First translate Kermit baud into HP baud
set_baud proc near
mov dx,ax ; save baud and port
mov di,offset ourbdtab1
mov bl,ah ; put baud code in bl
xor bh,bh ; bh=0 for indexing
shl bl,1 ; x2 since two bytes per baud entry
mov al,[di+bx+1] ; al now has hp baud code
cmp dl,1 ; is it port 1?
je set_baud1 ; e = yes
mov portb_baud,al ; save it
mov cl,4
shl al,cl ; port b in left nibble
or al,porta_baud ; port a baud in right nibble
out baud_port,al ; write the port a and port b baud
clc ; success
ret
set_baud1: ; set port 1 baud
mov porta_baud,al ; save the baud
mov dl,portb_baud
mov cl,4
shl dl,cl
or al,dl ; port a in right nibble , port b in left nibble
out 0ch,al ; write the port a and port b baud
clc ; success
ret
set_baud endp
lclose proc near ; this gets called when kermit quits
mov al,e_port1 ; reset baud to match firmware values
call get_config_values
mov al,[di].dc_baud_rate ; port a baud rate
push ax ; save this baud
mov al,e_port2
call get_config_values
mov bl,[di].dc_baud_rate ; port 2 baud rate
mov cl,4
shl bl,cl ; port b baud in left nibble
pop ax ; al has port a baud
or al,bl ; both bauds in al
out baud_port,al ; write the baud rate
ret
lclose endp
code ends
end