
/***************************************************************************
**
**    $Header:   D:/EPSLDV1/SRC/LOG/ABISUB51.CPP   1.8   20 Jun 1996 09:24:22   ZJRD  $
**
**    $Log:   D:/EPSLDV1/SRC/LOG/ABISUB51.CPP  $
** 
**    Rev 1.8   20 Jun 1996 09:24:22   ZJRD
** EasyPack/SLD Version 1.20a
** 
**    Rev 1.6   10 Jun 1996 10:19:00   ZJRD
** EasyPack/SLD Version 1.20
** 
**    Rev 1.4   29 May 1996 09:27:48   ZJRD
** No change.
** 
**    Rev 1.3   16 May 1996 08:59:28   ZJRD
** No change.
** 
**    Rev 1.2   10 May 1996 09:07:58   ZJRD
** No change.
** 
**    Rev 1.1   02 May 1996 10:22:28   ZJRD
** EasyPack/SLD Version 1.92
** 
**    Rev 1.31   18 Apr 1996 12:52:54   Shirley
** EasyPack/SLD Version 1.91
** 
**    Rev 1.30   12 Apr 1996 10:33:44   Shirley
** EasyPack/SLD Version 1.90
** 
**    Rev 1.28   15 Feb 1996 08:48:08   Shirley
** No change.
** 
**    Rev 1.27   12 Feb 1996 14:01:56   Shirley
** No change.
** 
**    Rev 1.26   06 Feb 1996 15:27:10   Shirley
** No change.
** 
**    Rev 1.25   06 Feb 1996 13:42:48   Shirley
** No change.
** 
**    Rev 1.24   01 Feb 1996 10:11:26   Shirley
** No change.
** 
**    Rev 1.23   26 Jan 1996 09:11:58   Shirley
** No change.
** 
**    Rev 1.22   25 Jan 1996 13:12:38   Shirley
** EasyPack/SLD Version 0.35
** 
**    Rev 1.21   24 Jan 1996 10:32:08   Shirley
** No change.
** 
**    Rev 1.20   23 Jan 1996 11:22:02   Shirley
** No change.
** 
**    Rev 1.19   18 Jan 1996 10:07:26   Shirley
** EasyPack/SLD Version 0.34b
** 
**    Rev 1.18   15 Jan 1996 16:10:12   Shirley
** EasyPack/SLD Version 0.34a
** 
**    Rev 1.17   04 Jan 1996 11:07:40   Shirley
** EasyPack/SLD Version 0.34
** 
**    Rev 1.16   30 Nov 1995 09:08:10   Shirley
** No change.
** 
**    Rev 1.15   28 Nov 1995 15:29:02   Shirley
** No change.
** 
**    Rev 1.14   21 Nov 1995 11:17:58   Shirley
** EasyPack/SLD Version 0.31
** 
**    Rev 1.13   13 Nov 1995 09:27:56   Shirley
** No change.
** 
**    Rev 1.12   12 Nov 1995 11:31:28   Shirley
** No change.
** 
**    Rev 1.11   08 Nov 1995 16:28:02   Shirley
** No change.
** 
**    Rev 1.10   08 Nov 1995 12:41:16   Shirley
** EasyPack/SLD Version 0.22
** 
**    Rev 1.9   02 Nov 1995 10:06:56   Shirley
** No change.
** 
**    Rev 1.8   27 Oct 1995 16:51:22   Shirley
** No change.
** 
**    Rev 1.7   27 Oct 1995 13:44:10   Shirley
** EasyPack/SLD Version 0.1g
** 
**    Rev 1.6   25 Oct 1995 14:25:58   Shirley
** No change.
** 
**    Rev 1.5   18 Oct 1995 14:47:32   Shirley
** No change.
** 
**    Rev 1.4   13 Oct 1995 13:18:16   Shirley
** EasyPack/SLD Version 0.1d
** 
**    Rev 1.3   29 Sep 1995 09:47:40   Shirley
** EasyPack/SLD Version 0.1c
** 
**    Rev 1.2   20 Sep 1995 10:52:24   Shirley
** No change.
** 
**    Rev 1.1   15 Sep 1995 09:43:30   Shirley
** No change.
** 
**    Rev 1.0   07 Sep 1995 09:53:16   Shirley
** Initial revision.
**
****************************************************************************/

/***************************************************************************
**
** File name : ABISUB51.CPP
**
** Changing :
**
** Programmer: Frank Chang
**
**    Copyright (C) 1995 Microtek International, Inc.
**    All Rights Reserved
**
****************************************************************************/

/***************************************************************************
**
**    Include files
**
***************************************************************************/
#include "stdafx.h"

#include <dos.h>
#include <conio.h>
#include <time.h>
#include <string.h>

#include "abibase.h"
#include <stdio.h>                                        
#include <time.h>
#include "cpust.h"

////////////////////////////////////////////////////////////////////////
//
extern void ExitEpsld();
extern STATUS AbiGetRegLen(UINT *);

extern int OpenAbiComDlg(int); //Frank, 12/27/95

typedef enum {
    LEAD_CODE   = ':',
    HEAD_OK     = 0x55,
    HEAD_FAIL   = 0xaa,
    REC_OK      = 0x5a,
    REC_FAIL    = 0xa5
} ECHO_CODE;

//////////////////////////////////////////////////////////////////////
// IO_lOOP adjust the communication speed between PC and MICE
// EasyPack new Firmware cannot fluently communicate with each other
// while IO_lOOP = 4000, now enlarge to 0xFFFF
// Frank, 06/27/95
//
// IO_LOOP become non-important, please see "time()" function, 11/06/95, Frank
const int ESC = 27;

extern BOOL bNewFrankEric;

const UINT  IO_LOOP = 0xFFFF;
const WORD  wHeadLoop = 0x0a;

#ifdef _TEST_BOX
    unsigned char inputStream[2048];
    unsigned char outputStream[512];
#else
    unsigned char *inputStream;
    unsigned char *outputStream;
#endif

static BOOL isInSetup = TRUE;    
//added by john 96.3 because the static attribute of isInSetup
BOOL GetIsInSetup() { return isInSetup; }
/**************************************************************************
**
** Local define
**
***************************************************************************/

#define     inportb(a)           inp(a)
#define     outportb(a,b)        outp(a,b)
#define     HighByte(x)          ((UCHAR)((UINT)(x) >> 8))
#define     LowByte(x)           ((UCHAR)(x))

//extern int TestKey(WORD);
/**************************************************************************
**
** function prototype declaration
**
***************************************************************************/

BOOL SetCommType(int nTempCommType);
BOOL SetupCommunication(UINT pData);
 
STATUS SendReceive(UINT wLoop, int tcount);
STATUS SendReceiveNoRelink(UINT wLoop, int tcount);
STATUS SendStream(UCHAR* stream, UINT len) ;
STATUS ReceiveStream(UCHAR* inStream, UINT *inStreamLen, time_t waitSec);

int sendB(UCHAR txData);
int receiveB(UCHAR *rcvByte);
int sendWait(UCHAR txData);
int receiveWait(time_t waitSec, UCHAR *rcvByte);
BOOL IsEscape();

//int ChkRxReady(void);
//int GetRxData(void);
//int ChkTxReady(void);
//int SendTxData(UCHAR tx_data);



/**************************************************************************
**
** Local variables
**
***************************************************************************/

const int   RV_RDY  = 1;  // status of receive ready is 00000001
const int   SD_RDY  = 2;  // status of send ready is    00000010


enum STATUS_PORT {
   P_I_B0   =      0x08, // input data bit 0 is XXXX1XXX
   P_I_B1   =      0x10, // input data bit 1 is XXX1XXXX
   P_I_B2   =      0x20, // input data bit 2 is XX1XXXXX
   P_I_B3   =      0x80, // input data bit 3 is 1XXXXXXX
   P_I_MASK =      0xB8,
   P_IRQ    =      0x40  // input IRQ\ signal is X1XXXXXX
};

// in control port: 37A/27A/3BE
enum CONTROL_PORT {
  P_W_PCE    =    1,   // output to write PCE from LPT is XXXXXXX1
  P_R_PCE    =    2,   // output to read PCE from LPT is XXXXXX1X
  P_S_RDY    =    0x08,// SWITCH = 1, from portInp
  P_R_RDY    =    0x10,// SWITCH = 1, from portInp
  P_SWITCH   =    0,   // SWITCH\ = 1, portStatus
  P_NORMAL   =    8    // let all control to output disactive
};

static int nCommType;
static UINT portAddr, portStatus, portInp;

            
            /*****************************
            **
            ** Execution codes
            ** 
            *****************************/


/**************************************************************************
**
** Name : SetCommType
**
** Function
**
**    Input  :  0: serial_port, 1: PCE card  2:parallel_port
**    Output :
**    Return : valid or not
** Notes:
**
**************************************************************************/
BOOL SetCommType(int nTempCommType)
{
    if (nTempCommType >= 0 && nTempCommType <=2 ) {
        nCommType = nTempCommType;
        return(TRUE);
    }
    else return(FALSE);

}

/**************************************************************************
**
** Name : SetupCommunication
**
** Function
**
**    Input  :
**
**    Output :
**
** Notes:
**
**************************************************************************/
BOOL SetupCommunication(UINT pData)
{
    UINT uintTemp;

    switch(nCommType) {
        case 0: // RS-232
       //  return(open_pcport()) ;
            break;
        case 2:   // LPT
            portAddr = pData;
            portStatus = pData+2;
            portInp  = pData+1 ;
            outportb(portStatus, P_SWITCH) ;
            break ;
        case 1:   // PCE
        default:
            portAddr = pData;
            portStatus = pData+1;
            break;
    }
     
    if ( AbiGetRegLen(&uintTemp) == ICE_OK ) {
        isInSetup = FALSE;
        return (TRUE);
    }    
    else return(FALSE);
}
 
/**************************************************************************
**
** Name : SendReceive
**
** Function  to call SendStream() and ReceiveStream()
**
**    Input  :
**
**    Output :
**
** Notes:
**
**************************************************************************/
STATUS SendReceive(UINT wLoop, int tcount)
{             
    
    GetXviewAppJohn()->m_bCanTimer = FALSE;
    
    STATUS status;
    UINT inputStreamLen;
    int nYesNo;
RE_LINK:  

    _disable();       
    
    status = SendStream(outputStream,wLoop);
    
    if (status == ICE_TIME_OUT){
        _enable();
        if (isInSetup == FALSE) {
    
            nYesNo = OpenAbiComDlg(1);
            
            if (nYesNo == IDOK) 
                goto RE_LINK; 
            else {
                ExitEpsld(); 
            }    
        }   
        GetXviewAppJohn()->m_bCanTimer = TRUE;     
        return(status);
    } 

   // _disable();
    status = ReceiveStream(inputStream,&inputStreamLen,tcount);
    _enable();

    if (status == ICE_TIME_OUT){
        if (isInSetup == FALSE) {
      
            nYesNo = OpenAbiComDlg(1);

            if (nYesNo == IDOK)
                goto RE_LINK; 
            else {
                ExitEpsld();
            }    
        }                 
        GetXviewAppJohn()->m_bCanTimer = TRUE;
        return(status);
    }             

    status = (STATUS) inputStream[0];
  //  if ( bCanTrace ) TRACE("SR e %2.1f\n",(double)clock());   
    GetXviewAppJohn()->m_bCanTimer = TRUE;
    return status;
    
}                         


/**************************************************************************
**
** Name : SendReceiveNoRelink
**
** Function  to call SendStream() and ReceiveStream()
**
**    Input  :
**
**    Output :
**
** Notes:
**
**************************************************************************/
STATUS SendReceiveNoRelink(UINT wLoop, int tcount)
{             
//    GetXviewAppJohn()->m_bCanTimer = FALSE;
    STATUS status;
    UINT inputStreamLen;
    int nYesNo;
    
    _disable();       
    
    status = SendStream(outputStream,wLoop);
    
    if (status == ICE_TIME_OUT){
        _enable();
        if (isInSetup == FALSE) {
    
            return ICE_NO_RESPONSE;
        }   
        return(status);
    } 

   // _disable();
    status = ReceiveStream(inputStream,&inputStreamLen,tcount);
    _enable();

    if (status == ICE_TIME_OUT){
        if (isInSetup == FALSE) {
        	return ICE_NO_RESPONSE;
        }                 
        return(status);
    }             

    status = (STATUS) inputStream[0];
    return status;
    
}                         



/****************************************************************************
**
**  SendStream
**
**  Description: Send command protocol to communication port.
**
**  Parameters:
**     input:
**
**     output:
**
**        return data --
**
****************************************************************************/
STATUS SendStream(UCHAR* stream, UINT len)
{  
	if ( !::bNewFrankEric ) {
		UCHAR uchChecksum, uchHighLen, uchLowLen;
		UINT wLoop;
		UCHAR uchEcho;
		               
		//if ( bCanTrace ) TRACE("S b %2.1f\n",(double)clock());                  
		    uchChecksum = 0;
		    for (wLoop = 0; wLoop < len; wLoop++){
		        uchChecksum = (UCHAR)(uchChecksum + stream[wLoop]);  
		    }    
		    stream[len] = (UCHAR)(~uchChecksum + 1);
		    len++;
		
		    uchLowLen = LowByte(len);
		    uchHighLen = HighByte(len);
		    uchChecksum = (UCHAR)(~(uchLowLen+ uchHighLen) + 1);
		   
		   
		    time_t startTime,currentTime;
		
		                       
		    time(&startTime);
		
		    while (1) {
		       // if ( 1 == TestKey(VK_ESCAPE) ) return(ICE_TIME_OUT);
		        if (sendWait(LEAD_CODE) == ABI_OK) {
		            if (sendB(uchLowLen) == ABI_OK) {
		                if (sendB(uchHighLen) == ABI_OK) {
		                    if (sendB(uchChecksum) == ABI_OK)
		                        break;
		                }
		            }
		        }           
		
		        time(&currentTime);
		        if ((currentTime - startTime) > 5)
		            return(ICE_TIME_OUT);
		    }   
		    
		    if ( receiveB(&uchEcho) == ABI_OK) {
		        if ( uchEcho != (UCHAR) HEAD_OK ) {
		       //    MessageBeep(-1);
		         //   printf(" Send echo head error!\n");
		            return(ICE_TIME_OUT);
		        }
		    }
		    else return(ICE_TIME_OUT);
		          
		    for (wLoop = 0; wLoop < len; wLoop++){
		         if (sendB(stream[wLoop]) != ABI_OK){
		     //       MessageBeep(-1);             
		        //  printf(" Send data error!\n");
		            return(ICE_TIME_OUT);
		         }
		    }   
		    if ( receiveB(&uchEcho) == ABI_OK) {
		        if (uchEcho == (UCHAR) REC_OK) 
		         { 
		  //        if ( bCanTrace ) TRACE("S e %2.1f\n",(double)clock());   
		          return ICE_OK;
		          }
		        else {
		        //    printf ("Send rec_ok error!\n");
		            return (ICE_TIME_OUT);
		        }
		    }
		    else return(ICE_TIME_OUT);
	}
	else {
		UCHAR uchChecksum, uchHighLen, uchLowLen;
		UINT wLoop, ii;
		UCHAR uchEcho;
	               
	    uchChecksum = 0;
	    for (wLoop = 0; wLoop < len; wLoop++){
	        uchChecksum = (UCHAR)(uchChecksum + stream[wLoop]);  
	    }    
	    stream[len] = (UCHAR)(~uchChecksum + 1);
	    len++;
	
	    uchLowLen = LowByte(len);
	    uchHighLen = HighByte(len);
	    uchChecksum = (UCHAR)(~(uchLowLen+ uchHighLen) + 1);
	
	    time_t startTime,currentTime;
	    time(&startTime);
	
	    while (1) {
	SEND_HEAD:
	        time(&currentTime);
	        if ((currentTime - startTime) > 15)
	            return(ICE_TIME_OUT);
	
	   //     if (sendWait(LEAD_CODE) != ABI_OK)
	   //         return(ICE_TIME_OUT);
	
	        if (sendWait(LEAD_CODE) != ABI_OK )
	            return(ICE_TIME_OUT);
	
	        if (sendB(uchLowLen) != ABI_OK) {
	            receiveB(&uchEcho);
	            if (uchEcho == HEAD_OK)
	                goto SEND_DATA;
	            else if (uchEcho == HEAD_FAIL)
	                continue;
	            else {
	                AfxMessageBox("Head sending nosense");
	                return(ICE_TIME_OUT);
	            }
	        }
	
	        if (sendB(uchHighLen)   != ABI_OK) {
	            receiveB(&uchEcho);
	            if (uchEcho == HEAD_OK)
	                goto SEND_DATA;
	            else if (uchEcho == HEAD_FAIL)
	                continue;
	            else {
	                AfxMessageBox("Head sending nosense");
	                return(ICE_TIME_OUT);
	            }
	        }
	
	        if (sendB(uchChecksum)  != ABI_OK) {
	            receiveB(&uchEcho);
	            if (uchEcho == HEAD_OK)
	                goto SEND_DATA;
	            else if (uchEcho == HEAD_FAIL)
	                continue;
	            else {
	                AfxMessageBox("Head sending nosense");
	                return(ICE_TIME_OUT);
	            }
	
	        }
	
	        if ( receiveWait(2, &uchEcho) != ABI_OK)
	            return(ICE_TIME_OUT);
	
	        if ( uchEcho == (UCHAR) HEAD_FAIL )
	            continue;
	        else if (uchEcho == (UCHAR) HEAD_OK);
	        else {
	            AfxMessageBox("not equal to HEAD_OK or HEAD_FAIL");
	            return(ICE_TIME_OUT);
	        }
	
	SEND_DATA:
	        for (wLoop = 0; wLoop < len; wLoop++){
	             if (sendB(stream[wLoop]) != ABI_OK) {
	                receiveB(&uchEcho); // return(ICE_TIME_OUT);
	                if (uchEcho == REC_OK) {
	                    AfxMessageBox("S/W has not finished sending, but F/W said data OK.");
	                    return(ICE_OK);
	                }
	                else if (uchEcho == REC_FAIL) {
	                    goto SEND_HEAD;
	                }
	                else {
	                    AfxMessageBox("Data sending nosense.");
	                    return(ICE_OK);
	                }
	             }
	        }
	        if ( receiveWait(2, &uchEcho) == ABI_OK ) {
	            if (uchEcho == (UCHAR) REC_OK)
	                return ICE_OK;
	        }
	        else if (uchEcho == (UCHAR) REC_FAIL) ;
	        else {
	            AfxMessageBox("Data echo is nosense.");
	            return (ICE_TIME_OUT);
	        }
	
	    } //end of while
	    return(ICE_TIME_OUT);
	}
}

/****************************************************************************
**
**  ReceiveStream
**
**  Description: Receive output command protocol to communication port.
**
**  Parameters:
**     input:
**
**     output:
**
**        return data --
**
****************************************************************************/
STATUS ReceiveStream(UCHAR* inStream, UINT *inStreamLen, time_t waitSec)
{
	if ( !::bNewFrankEric ) {
	UCHAR uchEcho;
	UINT len;
	UCHAR uchChecksum,finalFlag;
	UINT wLoop, i;
	UCHAR receiveBuf[2048];
	//if ( bCanTrace ) TRACE("R b %2.1f\n",(double)clock());   
	    for (i=0; i<wHeadLoop; i++) {
	        if (ABI_OK != receiveWait(waitSec, &uchEcho)) {
	        //  printf(" receiveWait error!\n");
	            return(ICE_TIME_OUT);
	        }
	        receiveBuf[0] = (UCHAR)uchEcho;
	        finalFlag = 1;//ON;
	        for(wLoop = 1; wLoop < 4; wLoop++){
	            if ( ABI_OK == receiveB(&uchEcho) )
	                receiveBuf[wLoop] = (UCHAR)uchEcho;
	            else {
	                finalFlag = 0;//OFF;
	                break;
	            }
	        }
	        if (finalFlag == 0) return(ICE_OK); //continue;
	        else break;
	    }
	    if (i >= wHeadLoop) {
	    //  printf(" Receive Head Error!\n");
	        return(ICE_TIME_OUT);
	    }
	    len = *(UINT *)&receiveBuf[1];   /* data length */
	    uchChecksum = 0;
	    for(wLoop = 1; wLoop < 4; wLoop++)
	        uchChecksum=(UCHAR)(uchChecksum+ receiveBuf[wLoop]); 
	        
	    if ((uchChecksum == 0) && (receiveBuf[0] == LEAD_CODE)) {
	        if ( sendB(HEAD_OK) != ABI_OK) {
	    //        printf(" send head_ok error");
	            return(ICE_TIME_OUT);
	        }
	        finalFlag = 1;//ON;
	        for (wLoop = 0; wLoop < (UINT)len; wLoop++) {
	            if ( receiveB(&uchEcho) == ABI_OK)
	                receiveBuf[wLoop] = (UCHAR)uchEcho;
	            else {
	                finalFlag = 0;//OFF;
	                break;
	            }
	            uchChecksum =(UCHAR)(uchChecksum+ receiveBuf[wLoop]);
	        }
	        if (finalFlag == 0 /*OFF*/) {
	            return(ICE_OK);
	        }    
	        if (uchChecksum == 0) {
	            *inStreamLen = len;
	            memcpy(inStream,&receiveBuf[0],len);
	            if (sendB(REC_OK) != ABI_OK) {
	      //        printf(" cannot send Rec_OK!\n"); 
	                return(ICE_TIME_OUT);//continue;
	            }    
	            else 
	             { 
	       //       if ( bCanTrace ) TRACE("R e %2.1f\n",(double)clock());   
	              return(ICE_OK);
	              }
	        }
	        else if (sendB(REC_FAIL) != ABI_OK) {
	       //   printf(" Cannot send rec_fail!\n");
	            return(ICE_TIME_OUT);//continue;   
	        }    
	    }
	    
	//    printf("checksum error!\n"); 
	    return(ICE_TIME_OUT);
	}
	else {
		UCHAR uchEcho;
		UINT len;
		UCHAR uchChecksum,finalFlag;
		UINT wLoop, i, ii;
		UCHAR receiveBuf[2048];
		
		    for (i=0; i<wHeadLoop; i++) {
		        if (ABI_OK != receiveWait(waitSec, &uchEcho))
		            return(ICE_TIME_OUT);
		
		        if (uchEcho == LEAD_CODE);
		        else continue;
		
		        receiveBuf[0] = (UCHAR)uchEcho;
		        finalFlag = 1;//ON;
		        for (wLoop = 1; wLoop < 4; wLoop++) {
		            if ( ABI_OK == receiveB(&uchEcho) )
		                receiveBuf[wLoop] = (UCHAR)uchEcho;
		            else {
		                finalFlag = 0;//OFF;
		                sendB(HEAD_FAIL);
		                break;
		            }
		        }
		        if ( finalFlag == 0 ) //head cannot receive completely, should to
		                              //receive from head again.
		            continue;
		
		        len = *(UINT *)&receiveBuf[1];   /* data length */
		        uchChecksum = 0;
		        for(wLoop = 1; wLoop < 4; wLoop++)
		            uchChecksum=(UCHAR)(uchChecksum+ receiveBuf[wLoop]);
		
		        if ((uchChecksum == 0) && (receiveBuf[0] == LEAD_CODE)) {
		            sendB(HEAD_OK); //THINK_MORE
		
		            for (wLoop = 0; wLoop < (UINT)len; wLoop++) {
		                if ( receiveB(&uchEcho) == ABI_OK) {
		                    receiveBuf[wLoop] = (UCHAR)uchEcho;
		                    uchChecksum =(UCHAR)(uchChecksum+ receiveBuf[wLoop]);
		                }
		                else {
		                    finalFlag = 0;//OFF;
		                    uchChecksum = 0;
		                    sendB(REC_FAIL);
		                    break;
		                }
		            }
		            if ( finalFlag == 1 && uchChecksum == 0) {
		                sendWait(REC_OK);
		                *inStreamLen = len;
		                memcpy (inStream, &receiveBuf[0], len);
		                return(ICE_OK);
		            }
		            else sendWait(REC_FAIL);
		        }
		        else sendB(REC_FAIL);
		    }
		    return(ICE_TIME_OUT);
	}
}
              
              
/**************************************************************************
**
** Name : sendB()
**
** Function
**
**    Input  :
**
**    Output :
**
** Notes:
**
**************************************************************************/
int sendB(UCHAR txData)
{
    UINT i; 
    //if ( bCanTrace ) TRACE("SB b %2.1f\n",(double)clock());      

    switch(nCommType) {
        case 0: /* RS-232 */                  /*  wait for          */
            for (i = 0; i < IO_LOOP; i++ ) {   /*  transmit (TBE)    */
                if ((inportb(portStatus) & 0x20) && /*  holding register  */
                    (inportb(portAddr+6) & 0x20)) { /* DSR = high */
                    outportb(portAddr, txData) ;
                    return(ABI_OK) ;
                }
            }
            break ;
      case 2: /* LPT */
         for (i = 0; i < IO_LOOP; i++ )     
            if ((!(inportb(portInp) & P_S_RDY)) && (!(inportb(portInp) & P_S_RDY)) ){
		       outportb(portAddr,txData);
               outportb(portStatus, (P_SWITCH | P_W_PCE)); /* STROBE\ = low SWITCH=high xsq */
               outportb(portStatus, P_SWITCH); /* STROBE\ = high, SWITCH = high */
               return(ABI_OK) ;
            }  
         break ;
      case 1: /* PCE */
      default:    
         for (i = 0; i < IO_LOOP; i++)
//          if (TRUE == IsEscape()) return (!ABI_OK);
            if (inportb(portStatus) & SD_RDY) {
               outportb(portAddr,txData);
               return(ABI_OK) ;
            }
         break ;
   }        
   //AfxMessageBox("Send Fail");
   return(!ABI_OK);
}        /* end of sendB() */

/**************************************************************************
**
** Name : receiveB()
**
** Function
**
**    Input  : none
**
**    Output :
**
** Notes:
**
**************************************************************************/
int receiveB(UCHAR *rcvByte)
{
UINT i;
UCHAR tmp, tmp1, tmp2 ;

//if ( bCanTrace ) TRACE("RB b %2.1f\n",(double)clock());   
    switch (nCommType) {
         case 0: /* RS-232 */
        //    for (i = 0; i < IO_LOOP; i++ ) {
        //      if (TRUE == IsEscape()) return (-1);
        //          if ((tmp = inportb(portStatus)) & 1) /* RxDRDY == 1 */
        //              return((UINT)inportb(portAddr)) ;
         //   }      
            break ;
         case 2: /* LPT */             
            outportb(portStatus, P_SWITCH) ; /* portInp switch to status */
//          outportb(portStatus, P_NORMAL);
            for (i = 0; i < IO_LOOP; i++) {
//              if (TRUE == IsEscape()) return (!ABI_OK);
                if ((!(inportb(portInp) & P_R_RDY)) && (!(inportb(portInp) & P_R_RDY))) {
                  outportb(portStatus, P_NORMAL ); /* switch = LOW  xsq */
                  outportb(portStatus, (P_NORMAL | P_R_PCE)); /* PC-RD-PCE\ = low */
                  tmp = P_I_MASK ; /* delay, wait data send from PCE */
                  tmp1 = tmp2 = 0x80 ;
                  tmp &= inportb(portInp) ;  /* Get high nibble */
                  outportb(portStatus, P_NORMAL); /* PC-RD-PCE\ = high */
                  outportb(portStatus, P_NORMAL); /* PC-RD-PCE\ = high */
                  tmp1 &= (~tmp) ;
                  tmp1 |= ((tmp << 1) & 0x70) ;
                  tmp = P_I_MASK ; /* delay, wait high/low nibble switch ready */
                  tmp &= inportb(portInp) ; /* Get low  nibble */
                  outportb(portStatus, P_SWITCH);
                  tmp2 &= (~tmp) ;
                  tmp2 |= ((tmp << 1) & 0x70) ;
                  tmp2 >>= 4 ;
                  *rcvByte = (UCHAR) (tmp1 | tmp2);
                  return(ABI_OK);
               } 
            }                            
            break ;
         case 1: /* PCE */
         default:
            for (i = 0; i < IO_LOOP; i++) {        
                if (inportb(portStatus) & RV_RDY) {
                    *rcvByte = (UCHAR) (inportb(portAddr));
                    return(ABI_OK);
                }
            }       
            break ;
    }
   //AfxMessageBox("Receive Fail");
    return(!ABI_OK);
} // end of receiveB()

/**************************************************************************
**
** Name : sendWait()
**
** Function
**
**    Input  :
**
**    Output :
**
** Notes:
**
**************************************************************************/
int sendWait(UCHAR txData)
{
	if ( !::bNewFrankEric ) {
		time_t startTime,currentTime;
		   
		   //if ( bCanTrace ) TRACE("SW b %2.1f\n",(double)clock());   
		   time(&startTime);
		   
		
		   while(1) {               
		//        if (TRUE == IsEscape()) return (!ABI_OK);
		//        if ( 1 == TestKey(VK_ESCAPE) ) return( !ABI_OK);
		        if (sendB(txData) == ABI_OK)
		            return(ABI_OK) ;
		        time(&currentTime);
		        if ((currentTime - startTime) > 5) return(!ABI_OK);
		   }
	}
	else {
		UCHAR uchEcho;
		time_t startTime,currentTime;
		   
		   //if ( bCanTrace ) TRACE("SW b %2.1f\n",(double)clock());   
		   time(&startTime);
		   
		
		   while(1) {               
		        if (sendB(txData) == ABI_OK)
		            return(ABI_OK) ;
		        receiveB(&uchEcho);
		        
		//06/19/96, Eric--Frank
		//        if (sendB(txData) == ABI_OK)
		//            return(ABI_OK) ;
		
		        time(&currentTime);
		        if ((currentTime - startTime) > 3) return(!ABI_OK);
		   }
	}
}        /* end of sendWait() */

/**************************************************************************
**
** Name :  receiveWait()
**
** Function
**
**    Input  :
**
**    Output :
**
** Notes:
**
**************************************************************************/
int receiveWait(time_t waitSec, UCHAR *rcvByte)
{
	if ( !::bNewFrankEric ) {
			
			//UCHAR rxData;
			time_t startTime,currentTime;  
			//if ( bCanTrace ) TRACE("RW b %2.1f\n",(double)clock());   
			
			    time(&startTime);
			
			//     for ( i = 0; i < IO_LOOP; i++ )
			//      if (inportb(portStatus) & RV_RDY) {
			//          rxData = inportb(portAddr);
			//          return(GetRxData());
			//      }
			
			    while (1) {
			//        if ( 1 == TestKey(VK_ESCAPE) ) return (!ABI_OK);
			        if ( receiveB(rcvByte) == ABI_OK )
			            return(ABI_OK);
			        time(&currentTime);
			        if ((currentTime - startTime) > waitSec) return(!ABI_OK);
			   }
	}
	else {

		time_t startTime,currentTime;  
		
		    time(&startTime);
		
		    while (1) {       
		     	if ( receiveB(rcvByte) == ABI_OK )
		            return(ABI_OK);
		        sendB(HEAD_FAIL);
		
		//06/19/96, Eric--Frank        
		//	        if ( receiveB(rcvByte) == ABI_OK )
		//	            return(ABI_OK);
		
		        time(&currentTime);
		        if ((currentTime - startTime) > waitSec) return(!ABI_OK);
		   }

	
	}
			   
} /* end of receiveWait() */

/**************************************************************************
**
** Name :  IsEscape()
**
** Function
**
**    Input  :
**
**    Output :
**
** Notes:
**
**************************************************************************/
BOOL IsEscape()
{
/*    int nEcho;
    
    if (kbhit()) {
        nEcho = getch();
        if (nEcho == ESC) 
            return (TRUE);
        else 
            return (FALSE); 
    }
    else 
*/
    return(FALSE); 
    
}
/**************************** End of File **********************************/

