{ * Interface unit for the X00 device driver. This unit supports all * comm fossil calls needed to do most communication tasks. * * Author Gordon Tackett * Date 01-31-91 * * $Revision: 1.0 $ } {$IFDEF LOCAL} Program X00; {$ELSE} Unit X00; Interface {$ENDIF} Uses Dos; Type { * Driver Information Block. * This record holds all of the current settings from the * X00 driver after a call to funciton $1B } DvrInfo = Record Size : Word; Spec : byte; Rev : Byte; ID : Pointer; Ibuf : Word; Iavl : Word; OBuf : Word; Oavl : Word; Width : Byte; Height: Byte; Baud : Byte; End; { * Timer Fuctions & Pointers * This procedure type is used to define a pointer the the procedure * that may be sent to the X00 driver for calling during a timer * tick. These procedures must be declared far } TimerFunction = Procedure; TimerFunctionPtr = ^TimerFunction; { * X00 Driver object * This is the main object for this module. It has all the interface * routines and data needed to call all the major functions of the * X00 device driver. } X00Dvr = Object Port : Word; Baud : Word; Size : Word; Parity : Char; Stops : Word; Status : Word; MaxFuncs : Word; RevLevel : Word; CtrlCFlags : Byte; CurInfo : DvrInfo; Constructor Init(Prt,Bd,Sz : Word; Prty : Char; StpBts : Word); Function GetLastStatus : Word; Function GetInfoSize : Word; Function GetInfoSpec : Word; Function GetInfoRev : Word; Function GetInfoId : Pointer; Function GetInfoIbuf : Word; Function GetInfoIavl : Word; Function GetInfoOBuf : Word; Function GetInfoOAvl : Word; Function GetInfoCrtW : Word; Function GetInfoCrtH : Word; Function GetInfoBaud : Word; Function GetPort : Word; Function GetBaud : Word; Function GetSize : Word; Function GetParity : Char; Function GetStops : Word; Function GetMaxFuncs : Word; Function GetRevLevel : Word; Procedure SetBaud(Bd,Sz : Word; Prty : Char; StpBts : Word); Procedure TxChar(Ch : Char); Function RxChar : Char; Function GetStatus : Word; Procedure InitFossil; Procedure DeinitFossil; Procedure DropDTR; Procedure RaseDTR; Procedure SystemTimerParams(Var TicksPerSec,MsPerTick : Word); Procedure FlushBuffer; Procedure PurgeOutputBuffer; Procedure PurgeInputBuffer; Procedure TxCharNoWait(Ch : Char); Function RXPeekChar(Var Ch : Char) : Boolean; Function KBPeekChar(Var Ch : Word) : Boolean; Function KBRead : Word; Procedure FlowControl(XONCTS : Byte); Procedure CtrlCChkOn; Procedure CtrlCChkOff; Procedure XmitOff; Procedure XmitOn; Procedure GotoXY(X,Y : Word); Procedure GetCursorLoc(Var X,Y : Word); Procedure AnsiWriteChar(Ch : Char); Procedure EnableWatchDog; Procedure DisableWatchDog; Procedure WriteChar(Ch : Char); Function InsertTimerFunction(TF : TimerFunctionPtr) : Boolean; Function DeleteTimerFunction(TF : TimerFunctionPtr) : Boolean; Procedure Reboot(Tp : Boolean); Procedure RecvBuffer(Buffer : Pointer; Var Sz : Word); Procedure SendBuffer(Buffer : Pointer; Sz : Word); Procedure StopBreak; Procedure GetInfo; {7e} {7f} End; Const OutputBuffEmpty = $4000; OutputBuffNotFull = $2000; InputBuffOverrun = $0200; CharInInputBuff = $0100; CarrierDetect = $0080; TxXonXoff = $01; TXCts = $02; RxXonXoff = $03; Var Comm1 : X00Dvr; Comm2 : X00Dvr; {$IFNDEF LOCAL} Implementation {$ENDIF} Var Regs : Registers; { register structure used in X00 calls} Const CommVect = $14; {X00 interrupt vector} { * Init - set up object and init port. * This routine will clear unused bytes to 0 and will init the * X00 fossil driver to the baud,size,parity,and stops as needed * by the user application. -----------------------------------------------------------------------------} Constructor X00Dvr.Init(Prt,Bd,Sz : Word; Prty : Char; StpBts : Word); Begin Port := Prt; CtrlCFlags := 0; InitFossil; If MaxFuncs = 0 Then Exit; SetBaud(Bd,Sz,Prty,StpBts); End; { * Get Last Status * * Interface function to get a copy of the status word storied in the * object body. -----------------------------------------------------------------------------} Function X00Dvr.GetLastStatus : Word; Begin GetLastStatus := Status; End; { * Get Information Size * * Interface function to get a copy of the word size from the info block. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoSize : Word; Begin GetInfoSize := CurInfo.Size; End; { * Get Information Specification * * Interface function to get a copy of the fossil interface spec supported * by this driver. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoSpec : Word; Begin GetInfoSpec := CurInfo.Spec; End; { * Get Information Revision * * Interface function to get a copy of the fossil document revision supported * by this driver. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoRev : Word; Begin GetInfoRev := CurInfo.Rev; End; { * Get Information ID * * Interface function to get a copy of the pointer to the ascii * string containing the name of the driver. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoId : Pointer; Begin GetInfoId := CurInfo.Id; End; { * Get Information Input Buffer Size * * Interface function to get a copy of the size of the input buffer * in bytes. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoIbuf : Word; Begin GetInfoIBuf := CurInfo.IBuf; End; { * Get Information Input Buffer Avaliable * * Interface function to get a copy of the amount of input buffer that is * avaliable for use. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoIavl : Word; Begin GetInfoIavl := CurInfo.Iavl; End; { * Get Information Output Buffer Size * * Interface function to get a copy of the size of the output buffer * in bytes. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoOBuf : Word; Begin GetInfoOBuf := CurInfo.OBuf; End; { * Get Information Output Buffer Avaliable * * Interface function to get a copy of the amount of Output buffer that is * avaliable for use. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoOAvl : Word; Begin GetInfoOAvl := CurInfo.OAvl; End; { * Get Information Current CRT Width * * Interface function to get a copy of the width of the CRT -----------------------------------------------------------------------------} Function X00Dvr.GetInfoCrtW : Word; Begin GetInfoCrtW := CurInfo.Width; End; { * Get Information Current CRT Height * * Interface funciton to get a copy of the height of the CRT -----------------------------------------------------------------------------} Function X00Dvr.GetInfoCrtH : Word; Begin GetInfoCrtH := CurInfo.Height; End; { * Get Information Current Baud Rate * * Interface function to get a copy of the current baud rate as returned * in the curinfo structure. -----------------------------------------------------------------------------} Function X00Dvr.GetInfoBaud : Word; Begin GetInfoBaud := CurInfo.Baud; End; { * Get the port number * * Interface function to return the port number that was used to call * the constructor Init. Once this constructor is called the port value * can't be changed. -----------------------------------------------------------------------------} Function X00Dvr.GetPort : Word; Begin GetPort := Port; End; { * Get the Baud Rate * * Interface function that is used to get the last baud rate sent to * this object from an application. This may not be the current correct * baud rate. -----------------------------------------------------------------------------} Function X00Dvr.GetBaud : Word; Begin GetBaud := Baud; End; { * Get the Word Size * * Interface function that is used to get the last word size sent to * this object from an application. This is always correct -----------------------------------------------------------------------------} Function X00Dvr.GetSize : Word; Begin GetSize := Size; End; { * Get the Parity * * Interface function that is used to get the last parity value that was * sent to this object from an application. this is always correct. -----------------------------------------------------------------------------} Function X00Dvr.GetParity : Char; Begin GetParity := Parity; End; { * Get Stop Bits * * Interface function that is used to get the last number of stop bits * that was sent to this object from an application. This is always correct. -----------------------------------------------------------------------------} Function X00Dvr.GetStops : Word; Begin GetStops := Stops; End; { * Get Maximum Function * * Interface function to return the maximum functions supported * by this fossil driver. -----------------------------------------------------------------------------} Function X00Dvr.GetMaxFuncs : Word; Begin GetMaxFuncs := MaxFuncs; End; { * Get Fossil Rev * * Interface function to return the revision level of the fossil * that is in use. -----------------------------------------------------------------------------} Function X00Dvr.GetRevLevel : Word; Begin GetRevLevel := RevLevel; End; { * Set Baud Rate * * BaudRate code in AL: * Bits [7:5] 000 = 19200, 001 = 38400, 010 = 300, 011 = 600, 100 = 1200, * 101 = 2400, 110 = 4800, 111 = 9600. Parity: [4:3] 00 or 10 = none, * 01 = odd, 11 = even. StopBits: [2:2] 0 = 1, 1 = 2 * CharLength: 5 bits plus value [1:0] Support for [4:0] = 00011 required of * driver, others optional -----------------------------------------------------------------------------} Procedure X00Dvr.SetBaud(Bd,Sz : Word; Prty : Char; StpBts : Word); Var Bits : Word; Begin Baud := Bd; Size := Sz; Parity := Prty; Stops := StpBts; Regs.Dx := Port; Case Baud of 300 : Bits := 2; 600 : Bits := 3; 1200 : Bits := 4; 2400 : Bits := 5; 4800 : Bits := 6; 9600 : Bits := 7; 19200 : Bits := 0; 38400 : Bits := 1; Else Exit; End; Bits := Bits Shl 2; If Parity = 'E' Then Bits := Bits + 3 Else if Parity = 'O' Then { c¾îºD‘B6´= Bits + 1;} Bits := Bits Shl 1; If Stops = 2 then Bits := Bits + 1; Bits := Bits Shl 2; Case Size Of 6 : Bits := Bits + 1; 7 : Bits := Bits + 2; 8 : Bits := Bits + 3; Else Bits := Bits + 3; End; Regs.Al := Bits; Regs.Ah := $00; Intr(CommVect,Regs); Status := Regs.AX; End; { * Transmit Character * * Character is queued for transmission. If there is room in the transmitter * buffer when this call is made, the character will be stored and control * returned to caller. If the buffer is full, the driver will wait for room. * This can be dangerous when used in combination with flow control (see * Function 0Fh) -----------------------------------------------------------------------------} Procedure X00Dvr.TxChar(Ch : Char); Begin Regs.al := Ord(Ch); Regs.Ah := $01; Regs.Dx := Port; Intr(CommVect,Regs); Status := Regs.AX; End; { * Receive Character * * The next character in the input ring buffer is returned to the caller. If * none available, the driver will wait for input. -----------------------------------------------------------------------------} Function X00Dvr.RxChar : Char; Begin Regs.Dx := Port; Regs.Ah := $02; Intr(CommVect,Regs); RxChar := Char(Regs.Al); End; { * Get Status * * Bits are: * AH[6:6] 1 = Output buffer empty * AH[5:5] 1 = Output buffer not full * AH[1:1] 1 = Input buffer overrun * AH[0:0] 1 = Characters in input buffer * AL[7:7] 1 = Carrier Detect signal * AL[3:3] 1 = Always (never 0) -----------------------------------------------------------------------------} Function X00Dvr.GetStatus : Word; Begin Regs.Dx := Port; REgs.Ah := $03; Intr(CommVect,Regs); GetStatus := Regs.Ax; Status := Regs.AX; End; { * Init Fossil Driver * * Required before I/O can take place on comm port. When DX = 00FFh, then * any initialization needed to make the keyboard/display available for FOSSIL * use should be performed. BX = 4F50h signals that ES:CX points to a flag * byte in the application that the driver should increment when its * keyboard routines detect a Ctl-C. -----------------------------------------------------------------------------} Procedure X00Dvr.InitFossil; Begin Regs.Dx := Port; Regs.Ah := $04; Regs.Bx := 0; Intr(CommVect,Regs); If Regs.Ax <> $1954 Then Begin MaxFuncs := 0; RevLevel := 0; End Else Begin MaxFuncs := Regs.Bl; RevLevel := Regs.Bh; End; End; { * De-Init Fossil Driver * * Disengages driver from comm port. Should be done when operations on the * port are complete. IF DX = 00FFh, then the initialization that was * performed when FOSSIL function 04h with DX = 00FFh should be undone. -----------------------------------------------------------------------------} Procedure X00Dvr.DeinitFossil; Begin If MaxFuncs < $05 Then Exit; Regs.Dx := Port; Regs.Ah := $05; Intr(CommVect,Regs); End; { * Drop Dtr Line * * Used to control Data Terminal Ready signal line on com port. This line * usually has some effect on modem operation (most modems will drop * carrier if DTR is lowered, for example). -----------------------------------------------------------------------------} Procedure X00Dvr.DropDTR; Begin If MaxFuncs < $06 Then Exit; Regs.Dx := Port; Regs.Ah := $06; Regs.Al := 0; Intr(CommVect,Regs); End; { * Rase Dtr Line * * Used to control Data Terminal Ready signal line on com port. This line * usually has some effect on modem operation (most modems will drop * carrier if DTR is lowered, for example). -----------------------------------------------------------------------------} Procedure X00Dvr.RaseDTR; Begin If MaxFuncs < $06 Then Exit; Regs.Dx := Port; Regs.Ah := $06; Regs.Al := 1; Intr(CommVect,Regs); End; { * Get System Timming Parameters * * Returns statistics needed to do some critical timing in any MS-DOS system. * The interrupt number in AL can be used to intercept a timer interrupt * that happens (AH) times per second. DX is essentially 1000/AH. Function * 16h is the preferred way to install timer tick code. AH and DX should * be accurate for the 16h timer tick. -----------------------------------------------------------------------------} Procedure X00Dvr.SystemTimerParams(Var TicksPerSec,MsPerTick : Word); Begin If MaxFuncs < $07 Then Exit; Regs.Ah := $07; Intr(CommVect,Regs); TicksPerSec := Regs.Ah; MsPerTick := Regs.Dx; End; { * Flush Output Buffer * * This is used to wait for all output to complete. If flow control is active * it is possible for this code never to return control to the caller. (See * function 0Fh) -----------------------------------------------------------------------------} Procedure X00Dvr.FlushBuffer; Begin If MaxFuncs < $08 Then Exit; Regs.Dx := Port; Regs.Ah := $08; Intr(CommVect,Regs); End; { * Purge Output Buffer * * Zero the output buffer. Returns to the caller immediately. Characters * that have not been transmitted yet are lost. -----------------------------------------------------------------------------} Procedure X00Dvr.PurgeOutputBuffer; Begin If MaxFuncs < $09 Then Exit; Regs.Dx := Port; Regs.Ah := $09; Intr(CommVect,Regs); End; { * Purge Input Buffer * * Zeroes the input buffer. If any flow control restraint has been employed * (dropping RTS or transmitting XOFF) the port will be "released" (by doing * the reverse, raising RTS or sending XON). Returns to caller immediately. -----------------------------------------------------------------------------} Procedure X00Dvr.PurgeInputBuffer; Begin If MaxFuncs < $0A Then Exit; Regs.Dx := Port; Regs.Ah := $0A; Intr(CommVect,Regs); End; { * Transmit Character without wait * * Character is queued for transmission. If there is room in the transmitter * buffer when this call is made, the character will be stored and control * returned to caller with AX=1. If the buffer is full, control is returned * to caller with AX=0. This allows the application to make its own decisions * on how to deal with "buffer full". -----------------------------------------------------------------------------} Procedure X00Dvr.TxCharNoWait(Ch : Char); Begin Repeat If MaxFuncs < $0B Then Exit; Regs.Dx := Port; Regs.Ah := $0B; Regs.Al := Ord(Ch); Intr(CommVect,Regs); Until (Regs.Ax <> 0); End; { * Keyboard Peek Character * * The next character in the input ring buffer is returned to the caller. If * none available, the driver returns a value of FFFFH. This "read" does not * actually remove a character from the input buffer! -----------------------------------------------------------------------------} Function X00Dvr.RXPeekChar(Var Ch : Char) : Boolean; Begin If MaxFuncs < $0C Then c¾îºD‘B6Q| Regs.DX := Port; Regs.AH := $0C; Intr(CommVect,Regs); Ch := Char(Regs.AL); If Regs.AX = $FFFF Then RxPeekChar := False Else RxPeekChar := True; End; { * Keyboard Peek Character * * The next character in the keyboard buffer is returned to the caller. If * none available, the driver returns a value of FFFFH. This "read" does not * actually remove a character from the input buffer! For function keys, IBM * PC scan codes must be returned. -----------------------------------------------------------------------------} Function X00Dvr.KBPeekChar(Var Ch : Word) : Boolean; Begin If MaxFuncs < $0D Then Exit; Regs.DX := Port; Regs.AH := $0D; Intr(CommVect,Regs); Ch := Regs.AX; If Regs.AX = $FFFF Then KBPeekChar := False Else KBPeekChar := True; End; { * Keyboard Read Character * * Return the next character from the keyboard buffer. Wait for a keystroke * if the buffer is empty. For function keys, IBM PC scan codes are required. -----------------------------------------------------------------------------} Function X00Dvr.KBRead : Word; Begin If MaxFuncs < $0E Then Exit; Regs.AH := $0E; Intr(CommVect,Regs); KBRead := Regs.AX; End; { * Flow Control * * AL[0:0] 1= enables remote to restrain FOSSIL transmitter using XON/XOFF; * AL[1:1] 1= enables modem restraint of FOSSIL transmitter using CTS and * FOSSIL restraint of modem using RTS * AL[3:3] 1= enables FOSSIL to restrain remote using XON/XOFF. -----------------------------------------------------------------------------} Procedure X00Dvr.FlowControl(XONCTS : Byte); Begin If MaxFuncs < $0F Then Exit; Regs.Dx := Port; Regs.Ah := $0F; Regs.Al := XonCTS; Intr(CommVect,Regs); End; { * Ctrl C Checking On * * AL[0:0] 1 = enable/disable CtlC/CtlK check (driver will set internal flag * which is returned by this function when it detects a CtlC/CtlK). * AL[1:1] 1 = stop transmitter * 0 = release previous stop * This is used primarily for programs that can't trust XON/XOFF * at FOSSIL level (such as BBS software). -----------------------------------------------------------------------------} Procedure X00Dvr.CtrlCChkOn; Begin If MaxFuncs < $10 Then Exit; Regs.Dx := Port; Regs.AH := $10; CtrlCFlags := CtrlCFlags Or 1; Regs.AL := CtrlCFlags; Intr(CommVect,Regs); End; { * Ctrl C Checking Off * * AL[0:0] 1 = enable/disable CtlC/CtlK check (driver will set internal flag * which is returned by this function when it detects a CtlC/CtlK). * AL[1:1] 1 = stop transmitter * 0 = release previous stop * This is used primarily for programs that can't trust XON/XOFF * at FOSSIL level (such as BBS software). -----------------------------------------------------------------------------} Procedure X00Dvr.CtrlCChkOff; Begin If MaxFuncs < $10 Then Exit; Regs.Dx := Port; Regs.AH := $10; CtrlCFlags := CtrlCFlags And Not 1; Regs.AL := CtrlCFlags; Intr(CommVect,Regs); End; { * Transmitter On * * AL[0:0] 1 = enable/disable CtlC/CtlK check (driver will set internal flag * which is returned by this function when it detects a CtlC/CtlK). * AL[1:1] 1 = stop transmitter * 0 = release previous stop * This is used primarily for programs that can't trust XON/XOFF * at FOSSIL level (such as BBS software). -----------------------------------------------------------------------------} Procedure X00Dvr.XmitOn; Begin If MaxFuncs < $10 Then Exit; Regs.Dx := Port; Regs.AH := $10; CtrlCFlags := CtrlCFlags And Not 2; Regs.AL := CtrlCFlags; Intr(CommVect,Regs); End; --- FD 1.99c * Origin: If you clone around you'll end up talking to yourself! (1:105/324.1) Ä Turbo Pascal ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ PASCAL Ä Msg : 351 of 400 From : Gordon Tackett 1:105/324.1 01 Apr 91 10:44 To : Roland Frederic 2:292/500.0 Subj : BBS Program in TP. Part 5 of 5 ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ { * Transmitter Off * * AL[0:0] 1 = enable/disable CtlC/CtlK check (driver will set internal flag * which is returned by this function when it detects a CtlC/CtlK). * AL[1:1] 1 = stop transmitter * 0 = release previous stop * This is used primarily for programs that can't trust XON/XOFF * at FOSSIL level (such as BBS software). -----------------------------------------------------------------------------} Procedure X00Dvr.XmitOff; Begin If MaxFuncs < $10 Then Exit; Regs.Dx := Port; Regs.AH := $10; CtrlCFlags := CtrlCFlags Or 2; Regs.AL := CtrlCFlags; Intr(CommVect,Regs); End; { * Goto XY * * Identical to IBM PC BIOS INT 10h, subfunction 02h. FOSSIL should do * sanity checks but software should not assume that that is the case. -----------------------------------------------------------------------------} Procedure X00Dvr.GotoXY(X,Y : Word); Begin If MaxFuncs < $11 Then Exit; Regs.Dh := Lo(Y-1); Regs.Dl := Lo(X-1); Regs.AH := $11; Intr(CommVect,Regs); End; { * Get Cursor Location * * Identical to IBM PC BIOS INT 10h, subfunction 03h. -----------------------------------------------------------------------------} Procedure X00Dvr.GetCursorLoc(Var X,Y : Word); Begin If MaxFuncs < $12 Then Exit; Regs.AH := $12; Intr(CommVect,Regs); Y := Regs.Dh + 1; X := Regs.Dl + 1; End; { * Ansi Write Character * * ANSI processing is a requirement of this call. It therefore should not be * considered re-entrant, since DOS might be used (via ANSI.SYS) -----------------------------------------------------------------------------} Procedure X00Dvr.AnsiWriteChar(Ch : Char); Begin If MaxFuncs < $13 Then Exit; Regs.Al := Ord(Ch); Regs.AH := $13; Intr(CommVect,Regs); End; { * Enable Watch Dog * * FOSSIL will force the system to reboot if Carrier Detect on the specified * port drops while "watchdog" is ON. It is not necessary for the port to * be "active" (Function 04h) for this function to be used. -----------------------------------------------------------------------------} Procedure X00Dvr.EnableWatchDog; Begin If MaxFuncs < $14 Then Exit; Regs.AL := 1; Regs.Dx := Port; Regs.Ah := $14; Intr(CommVect,Regs); End; { * disable Watch Dog * * FOSSIL will force the system to reboot if Carrier Detect on the specified * port drops while "watchdog" is ON. It is not necessary for the port to * be "active" (Function 04h) for this function to be used. -----------------------------------------------------------------------------} Procedure X00Dvr.DisableWatchDog; Begin If MaxFuncs < $14 Then Exit; Regs.AL := 0; Regs.Dx := Port; Regs.Ah := $14; Intr(CommVect,Regs); End; { * Write Character * * Write character to screen using re-entrant code. ANSI processing may * not be assumed. This call may be used by DOS device drivers. -----------------------------------------------------------------------------} Procedure X00Dvr.WriteChar(Ch : Char); Begin If MaxFuncs < $15 Then Exit; Regs.AL := Ord(Ch); Regs.AH := $15; Intr(CommVect,Regs); End; { * Insert Timer Function * * Allows FOSSIL to manage timer tick chain, which provides some measure of * security over just snagging the interrupt. Use "insert" instead of * grabbing the vector and "remove" in place of restoring it. -----------------------------------------------------------------------------} Function X00Dvr.InsertTimerFunction(TF : TimerFunctionPtr) : Boolean; Begin If MaxFuncs < $16 Then Exit; Regs.AH := $16; Regs.AL := 1; Regs.ES := Seg(TF^); Regs.Dx := Ofs(TF^); Intr(CommVect,Regs); If Regs.Ax = 0 Then InsertTimerFunction := True Else InsertTimerFunction := False; End; Function X00Dvr.DeleteTimerFunction(TF : TimerFunctionPtr) : Boolean; Begin I„ÎîºD‘B6ñ9 < $16 Then Exit; Regs.AH := $16; Regs.AL := 0; Regs.ES := Seg(TF^); Regs.Dx := Ofs(TF^); Intr(CommVect,Regs); If Regs.Ax = 0 Then DeleteTimerFunction := True Else DeleteTimerFunction := False; End; { * Reboot * * Provides a machine-independent way for a "troubled" application to reset * the system. Some machines may not support both "flavors" of bootstrap, * in which case the setting of AL will not have any effect. -----------------------------------------------------------------------------} Procedure X00Dvr.Reboot(Tp : Boolean); Begin If MaxFuncs < $17 Then Exit; Regs.AH := $17; Regs.Al := 0; If Tp Then Regs.Al := 1; Intr(CommVect,Regs); WriteLn('System Error - Unable to ReBoot'); While (True) Do; End; { * Receive Buffer * * Transfer as many characters as are available into the specified user * buffer, up to the maximum specified in CX. ES and DI will not be modified * by this call. The actual number of characters transferred will be in AX. * This function does not wait for more characters to become available if the * number in CX exceeds the number of characters currently stored. -----------------------------------------------------------------------------} Procedure X00Dvr.RecvBuffer(Buffer : Pointer; Var Sz : Word); Begin If MaxFuncs < $18 Then Exit; If (Self.GetStatus And $0100) = 0 Then Begin Size := 0; Exit; End; Regs.Dx := Port; Regs.Es := Seg(Buffer^); Regs.Di := Ofs(Buffer^); Regs.Cx := Sz; Regs.Ah := $18; Intr(CommVect,Regs); Size := Regs.Ax; End; { * Send Buffer * * Transfer as many characters as will fit, from the specified user buffer * into the output buffer, up to the maximum specified in CX. ES and DI * will not be modified by this call. The actual number of characters * transferred will be in AX. -----------------------------------------------------------------------------} Procedure X00Dvr.SendBuffer(Buffer : Pointer; Sz : Word); Var Cptr : ^Char; I : Integer; Begin If MaxFuncs < $19 Then Exit; Cptr := Buffer; Regs.Dx := Port; Regs.Es := Seg(Buffer^); Regs.Di := Ofs(Buffer^); Regs.Cx := Sz; Regs.Ah := $19; Intr(CommVect,Regs); If Regs.Ax <> Sz Then Begin Regs.Di := Regs.Di + Regs.Ax; Cptr := Ptr(Regs.Es, Regs.Di); For I := Regs.Ax To Sz Do Begin Self.TxChar(Cptr^); Cptr := Ptr(Seg(Cptr^),Ofs(Cptr^) + 1); End; End; End; { * Stop Break * * Used for special applications such as certain high speed modems. Resets * all transmit flow control restraints (such as an XOFF received from remote) * Init (Function 4) or UnInit (Function 5) will stop an in-progress Break. * Note: the application must determine the "length" of the BREAK. -----------------------------------------------------------------------------} Procedure X00Dvr.StopBreak; Begin If MaxFuncs < $1A Then Exit; Regs.Dx := Port; Regs.Ah := $1A; Regs.Al := 0; Intr(CommVect,Regs); End; { * Send Break * * Used for special applications such as certain high speed modems. Resets * all transmit flow control restraints (such as an XOFF received from remote) * Init (Function 4) or UnInit (Function 5) will stop an in-progress Break. * Note: the application must determine the "length" of the BREAK. -----------------------------------------------------------------------------} Procedure X00Dvr.SendBreak; Begin If MaxFuncs < $1A Then Exit; Regs.Dx := Port; Regs.Ah := $1A; Regs.Al := 1; Intr(CommVect,Regs); End; { * Get Info Block * * Get The Info Block Record from Fossil to usable memory. An Info Block is: * * Offset 0 (word) = Structure size * 2 (byte) = FOSSIL spec version * 3 (byte) = Driver rev level * 4 (dwrd) = Pointer to ASCII ID * 8 (word) = Input buffer size * 0A (word) = Bytes avail (input) * 0C (word) = Output buffer size * 0E (word) = Bytes avail (output) * 10 (byte) = Screen width, chars * 11 (byte) = Screen height, chars * 12 (byte) = Baud rate mask * (See call 00h) -----------------------------------------------------------------------------} Procedure X00Dvr.GetInfo; Begin If MaxFuncs < $1B Then Exit; Regs.Cx := Sizeof(CurInfo); Regs.Es := Seg(CurInfo); Regs.Di := Ofs(CurInfo); Regs.Dx := Port; Regs.Ax := $1B; Intr(CommVect,Regs); End; { * * * Used to install user appendages into the INT 14h dispatcher. Appendage * codes 80h - BF are supported. Codes 80h - 83h are reserved. The error * return, BH = 00h and AX = 1954h, should mean that another appendage * has already been installed with the code specified in AL. The appendage * will be entered via a far call whenever INT 14h call is made with AL * equal to the appendage code. The appendage should return to the INT * 14h dispatcher via a far return. The INT 14h dispatcher should not modify * any registers prior to making the far call to the appendage and after the * appendage returns control to the dispatcher. -----------------------------------------------------------------------------} {7E} { * * * Used to remove a user appendage that was installed using function 7Fh. An * error return means that either the entry point specified in ES:DX did * not match the entry point currently in the dispatcher table for the code * given in AL, or that no entry for the code given in AL currently exits. -----------------------------------------------------------------------------} {7F} {$IFDEF LOCAL} Var t1,t2,t3 : Word; Begin Comm1.Init(0,2400,8,'N',2); {$ENDIF} End. --- FD 1.99c * Origin: If you clone around you'll end up talking to yourself! (1:105/324.1)