home *** CD-ROM | disk | FTP | other *** search
- page 58,132
-
- ; asio.asm
- ; contains: as_getc(),as_putc(),as_stat(),as_iniw(),as_rts(),as_dtr()
- ; contains: as_break(),as_reset()
- ;
-
- include model.h
- include prologue.h
- name asio
- pseg asio
-
- ;****
- ; _as_wcts Usage: This variable's value is transferred in to this
- ; local variable when the asiinit() function is called. When set to 0,
- ; NO DELAY is taken to wait for CTS or DSR on transmit or receive. To use
- ; the normal (per delay constants in "asports.h") delay, say _as_wcts=1;
- ; before calling the asiinit() function.
-
- as_wcts dw 0
-
- ;==>-- int as_getc(port,timeout)
- ;
- ;; ARGUMENTS:
- ; (unsigned) port - base I/O address of 8250
- ; (int) timeout - timeout constant 0=get status once
- ;
- ;; DESCRIPTION:
- ; Read character (if available) from comm port
- ;
- ;; RETURNS:
- ; Either a character or -1 if (a) no character available, or (b)
- ; there is an error on receive.
- ;
- ;; AUTHOR:
- ; Copyright (C)1987-1990 Greenleaf Software Inc. All Rights Reserved.
- ;
- ;; MODIFICATIONS:
- ;
- ;;;
- cproc as_getc
- mov dx,parm1_ ;get port i/o address base
- add dx,6 ;address modem status register
- mov bl,parm2_ ;get timeout constant to BL
- cmp cs:as_wcts,0
- jz assk2
- mov bh,00100000b ;check for DSR bit
- call wfs ;wait for status
- jnz asgrm1 ;hop if NOT OK
- assk2: dec dx ;point to line status register
- mov bh,000000001b ;Buffer Full bit
- call wfs ;wait for status
- jnz asgrm1 ;hop if NOT OK
- in al,dx ;get status again
- test al,00011110b ;see if any errors
- jnz asgrm1 ;if any, return -1
- mov dx,parm1_ ;get data reg i/o address
- in al,dx ;read the character
- jmp short asgret
- asgrm1: mov ax,-1 ;not OK so return -1
- asgret:
- cproce
-
- ;==>-- int as_putc(port,timeout,character)
- ;
- ;; ARGUMENTS:
- ; (unsigned) port - base I/O address of 8250
- ; (int) timeout - timeout constant 0=get status once
- ; (char) character - character to transmit
- ;
- ;; DESCRIPTION:
- ; Transmit the character out the COMM port.
- ;
- ;; RETURNS:
- ; Status if successful, -1 if lost CTS or DSR, or if Tx
- ; holding register was not empty.
- ;
- ;; AUTHOR:
- ; Copyright (C)1987-1990 Greenleaf Software Inc. All Rights Reserved
- ;
- ;; MODIFICATIONS:
- ;
- ;;;
- cproc as_putc
- mov dx,parm1_ ;get port number
- add dx,6 ;point dx to modem status register
- cmp cs:as_wcts,0
- jz assk1
- mov bl,parm2_ ;bl = timeout
- mov bh,00110000b ;DSR, CTS bits
- call wfs ;wait for status..
- jnz asprm1 ;not OK so return -1
- assk1: dec dx ;point to line status reg
- mov bh,00100000b ;Tx Hold reg empty
- call wfs ;wait for status
- jnz asprm1
- sub dx,5 ;address data port
- mov al,@ab+4[bp] ;get the char to send
- out dx,al ;send him
- jmp short aspret
- asprm1: mov ax,-1 ; not OK so return -1
- aspret:
- cproce
-
- ;==>-- unsigned as_stat(port)
- ;
- ;; ARGUMENTS:
- ; (unsigned) port - base i/o address of 8250
- ;
- ;; DESCRIPTION:
- ; Get line and modem status to AH and AL respectively
- ;
- ;; RETURNS:
- ; modem status in high order 8 bits, line status in low
- ; order 8 bits
- ;
- ;; AUTHOR:
- ; Copyright (C)1987-1990 Greenleaf Software Inc. All Rights Reserved.
- ;;;
- cproc as_stat
- mov dx,@ab[bp] ;get i/o addr base
- add dx,5 ;address line status port
- in al,dx ;..and get line status
- jmp short _fpf3
- _fpf3:
- mov ah,al ;..to AH
- inc dx ;point to modem status port
- in al,dx ;get modem status
- cproce
-
- ;==>-- int as_iniw(port,baudrate,controlword,aswcts)
- ;
- ;; ARGUMENTS:
- ; (unsigned) port - base i/o address of 8250
- ; (int) baudrate - baud rate multiplier
- ; (int) controlword -
- ; (int) aswcts - how long to wait for CTS
- ;
- ; bits: 7 6 5 => not used here due to baud multiplier above.
- ; 4 3 => parity
- ; 2 => stopbits: 0=1 1=2
- ; 1 0 => word length: 10 = 7, 11 = 8
- ;
- ;; DESCRIPTION:
- ; Initialize Port - Worker. Drive from "asinit"
- ;
- ;; SIDE EFFECTS:
- ; operating parameters of 8250 will be changed
- ;
- ;; RETURNS:
- ; status or -1 if argument is out of range
- ;
- ;; AUTHOR:
- ; Copyright (C)1987-1990 Greenleaf Software Inc. All Rights Reserved.
- ;;;
- cproc as_iniw
- mov ax,@ab+6[bp] ;get value of _as_wcts
- mov cs:as_wcts,ax
- mov dx,@ab[bp] ;get port i/o address base
- add dx,3 ;address 8250 control register
- mov al,80h ;set DLAB = 1
- out dx,al ;..to enable loading the baud rate
- jmp short _fpf4
- _fpf4:
- mov ax,@ab+2[bp] ;get baud multiplier
- mov dx,@ab[bp] ;get port i/o address base = LSB
- out dx,al ;Least Significant Byte here
- jmp short _fpf5
- _fpf5:
- inc dx ;point to MSB latch
- mov al,ah ;.put MSB in AL
- out dx,al ;..and output that
- jmp short _fpf6
- _fpf6:
- inc dx
- inc dx ;point to line control register
- mov ax,@ab+4[bp] ;get control word to AL
- and al,00111111b ;turn off DLAB, break, stick_parity
- out dx,al ;..initialize word_length,stop_bits,parity
- jmp short _fpf7
- _fpf7:
- dec dx
- dec dx ;point to interrupt enable register
- sub al,al ;get a 0
- out dx,al ;set int enables all off
- jmp short _fpf8
- _fpf8:
- add dx,4 ;point to line status register
- in al,dx ;get line status
- jmp short _fpf9
- _fpf9:
- mov ah,al ;..to AH
- inc dx ;point to modem status reg
- in al,dx ;...get that to AL
- cproce
-
- ;==>-- void as_rts(port,control)
- ;
- ;; ARGUMENTS:
- ; (unsigned) port - Base I/O address of 8250
- ; (int) control - 1=Assert RTS, 0=Deassert RTS
- ;
- ;; DESCRIPTION:
- ; Function to control RTS
- ;
- ;; SIDE EFFECTS:
- ; rts will change
- ;
- ;; AUTHOR:
- ; Copyright (C)1987-1990 Greenleaf Software Inc. All Rights Reserved.
- ;;;
- cproc as_rts
- mov dx,@ab[bp] ;get port i/o base address
- add dx,4 ;address modem control register
- in al,dx ;read current command
- mov bx,@ab+2[bp] ;get control argument
- cmp bx,1 ;is it ON ?
- jne asrts0 ;hop if OFF instead
- or al,2 ;set the RTS bit
- jmp short asrtsw ;now write modified command
- ;back to the modem ctrl register
- asrts0: and al,11111101b ;turn OFF the RTS bit here.
- asrtsw: out dx,al ;update command to device
- cproce
-
- ;==>-- void as_dtr(port,control)
- ;
- ;; ARGUMENTS:
- ; (unsigned) port - base I/O address of 8250
- ; (int) control - 1=Assert DTR, 0=DeAssert DTR
- ;
- ;; DESCRIPTION:
- ; Control state of DTR signal
- ;
- ;; SIDE EFFECTS:
- ; DTR signal will change
- ;
- ;; AUTHOR:
- ; Copyright (C)1987-1990 Greenleaf Software Inc. All Rights Reserved.
- ;;;
- cproc as_dtr
- mov dx,@ab[bp]
- add dx,4 ;address modem ctrl reg
- in al,dx ;read current command
- mov bx,@ab+2[bp] ;get control argument
- cmp bx,1 ;is it ON ?
- jne asdtr0 ;nop if OFF instead
- or al,1 ;set the DTR bit
- jmp short asdtrw ;now write modified command
- asdtr0: and al,11111110b ;turn DTR OFF.
- asdtrw: out dx,al ;write updated command
- cproce
-
- ;==>-- int as_break(port,timeout)
- ;
- ;; ARGUMENTS:
- ; (unsigned) port - base I/O address of 8250
- ; (int) timeout - multiple of 1ms
- ;
- ;; DESCRIPTION:
- ;
- ; Send break of duration 200 milliseconds. If it is desired to change
- ; this period, the user may, within the range 1-32768 ms, change as
- ; indicated below.
- ;
- ; Timeout argument is multiple of 1 ms to use for initial status - if
- ; DSR and RTS are not high initially, wait this long for them to be
- ; high, if not found high within timeout period, return (-1).
- ; Else return 0.
- ;
- ;; RETURNS:
- ; (see description)
- ;
- ;; AUTHOR:
- ; Copyright (C)1987-1990 Greenleaf Software Inc. All Rights Reserved.
- ;;;
- cproc as_break
- mov dx,@ab[bp] ;get port address base
- add dx,6 ;point to modem status reg
- mov bx,@ab+2[bp] ;get write timeout constant
- mov bh,00110000b ;DSR and CTS bits
- call wfs ;wait for status..
- jz asbrk1 ;OK so proceed
- mov ax,-1 ;NOT OK, return -1
- pop bp
- ret
- asbrk1: mov dx,@ab[bp] ;get port address base
- add dx,3 ;address line control reg
- in al,dx ;get current line ctrl word
- jmp short _fpf10
- _fpf10:
- mov ah,al ;store this for later..
- push ax
- or al,01000000b ;set BREAK, xmit spacing..
- out dx,al ;update control word.
- mov bx,128 ;load multiple of 1 ms.
- asbrk2: call asbdly ;go delay 1 ms.
- dec bx ;decrement multiplier
- jnz asbrk2 ;loop while not zero multiplier
- mov al,ah ;get original command word
- pop ax
- out dx,al ;..turn BREAK off now.
- cproce
-
- ;==>-- void as_reset(port)
- ;
- ;; ARGUMENTS:
- ; (unsigned) port - base I/O address of 8250
- ;
- ;; DESCRIPTION:
- ; Reset an 8250 to quiescent state with 300 baud, odd parity,
- ; 1 stop-bit, 8 data bits, DTR and RTS OFF.
- ;
- ;; SIDE EFFECTS:
- ; internal 8250 settings will be changed
- ;
- ;; AUTHOR:
- ; Copyright (C)1987-1990 Greenleaf Software Inc. All Rights Reserved.
- ;;;
- cproc as_reset
- mov dx,@ab[bp] ;get port i/o base address
- add dx,4 ;point to modem control reg
- mov al,0 ;turn off all bits..
- out dx,al ;do it.
- jmp short _fpf11
- _fpf11:
- dec dx ;point to line control reg
- mov al,00001011b ;odd parity, 1 stop bit, 8 data bits
- out dx,al
- jmp short _fpf12
- _fpf12:
- mov al,10001011b ;turn on DLAB = 1
- out dx,al
- jmp short _fpf13
- _fpf13:
- mov dx,@ab[bp] ;address LSB reg for divisor
- mov ax,384 ;divisor for 300 bps
- out dx,al
- jmp short _fpf14
- _fpf14:
- mov al,ah ;get MSB for 300 bps
- inc dx ;point to MSB register
- out dx,al
- jmp short _fpf15
- _fpf15:
- inc dx
- inc dx ;point to line control reg again
- mov al,00001011b ;be kind - turn off DLAB bit.
- out dx,al
- cproce
-
-
- ;********************
- ;
- ; Wait for Status.
- ;
- ; Input: Physical Port address in DX
- ; BL = number of iterations before timeout
- ; BH = status bits to match
- ; Output: AH = last status read
- ; Zero Flag set if timeout occurred
- ;
- ; Depending upon the time constant (TC) stored at _rswtc[n], this function
- ; will wait a certain number of iterations in a loop waiting for a match
- ; between the status obtained from physical port DX and the bits in BH.
- ;
- ; However, if (global) _as_wcts = 0, do not wait at all.
- ;
- ; If TC = 0, return with Zero Flag ON if match on status, else OFF
- ; If match found between status read and BH, return Zero Flag ON
- ; If iterations exahsted and no match on status, return Zero Flag OFF
-
- wfs proc near
- push bx ;preserve this
- cmp cs:as_wcts,0 ; *5/31*
- jnz wfscx ;if no override on wait *5/31*
- mov bl,0 ;else just get status and return *5/31*
- wfscx: call wfsx
- pop bx ;restore time constant and mask
- ret
- wfs endp
-
- ;***********
- ;
- ; Alternate "Wait-For-Status" routine
- ;
- wfsx proc near
- cmp bl,0 ;is loop count zero ?
- jne wfsxst ;if not do the loop
- in al,dx ;read status
- mov ah,al ;position for output
- and al,bh ;check these bits
- cmp al,bh ; just like this
- ret ;indicate status to caller.
- ;
- ; Nonzero Time Constant, so return only after status match or timeout
- ;
- ; For 4.77 mhz clock, inner loop is 37 clocks @ 210 ns = 7.75 usec;
- ; ..129 x 7.75 = 1000 usec = 1 msec per external time constant.
- ;
- wfsxst:
- wfsx0: mov cx,129 ;inner loop count
- wfsx1: in al,dx ;read status
- jmp short _fpf16 ;*5/31*
- _fpf16:
- mov ah,al ;position it for output
- and al,bh ;check these bits
- cmp al,bh ;just as they are
- je wfsxe ; and hop out if status same
- loop wfsx1 ; else do inner loop here
- dec bl ; ..now do outer loop
- jnz wfsx0 ; ..here
- ;If you get here you have a timeout with no status match.
- or bh,bh ;set Zero Flag OFF
- wfsxe: ret
- wfsx endp
-
-
- ;**********
- ;
- ; Delay 1 ms. This is used in as_break to time the break
- ;
- asbdly proc near
- push cx
- ;
- ; The instructions at absdl1 and absdl2 together use 33 clock periods
- ; if the loop transfers back up to absdl1. In the IBM PC, each clock
- ; period is 210 ns, so each time thru the loop is 6.93 usec. To delay
- ; a total of about 1 millisecond, do this 144 times.
- ;
- asbdl0: mov cx,144
- asbdl1: jmp short asbdl2 ;15 clocks
- nop ;never get here.. for clarity only.
- asbdl2: loop asbdl1 ;18 clocks if CX not 0 yet
- pop cx ;done ! Restore this and exit
- ret
- asbdly endp
- endps
- end
-