#include "stdafx.h"
#include "comm.h" 
#include "conio.h" 
#include <dos.h> 

#include "abitype.h"
//#include "abimacro.h"


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

//#define SaveId(cmdId,count) \
//       count = 0;\
//       outputStream[count] = (unsigned char)cmdId;\
 //       count++        


CCommunication::CCommunication()
{
    nCommType=2;
    PortInp=0x379;
    PortDataAdr=0x378;
    PortStatusAdr=0x37a;
}



CCommunication::~CCommunication()
{
}



BOOL CCommunication::TransmitByte(unsigned char Tchar)
{
      unsigned char DataOutFlag;
      DataOutFlag = 0;

	  switch ( nCommType ) {
        case 1: // PCE card
	    while(DataOutFlag == 0) {
                DataOutFlag = inportb(PortStatusAdr) & 0x02;
        }
	    outportb(PortDataAdr,Tchar);
	    break;
	case 2: // LPT
	    outportb(PortDataAdr,Tchar);
	    for(i=0;i<m_uLoop;i++){
		 if ((!(inportb(PortInp) & P_S_RDY)) &&
		    (!(inportb(PortInp) & P_S_RDY)) ){
		    outportb(PortStatusAdr, (P_SWITCH | P_W_PCE)); /* STROBE\ = low SWITCH=high xsq */
		    outportb(PortStatusAdr, P_SWITCH); /* STROBE\ = high, SWITCH = high */
		    return TRUE ;
	      }              
		return FALSE;
        }
	default:
	    return TRUE;
    }
}



unsigned char CCommunication::ReceiveByte(void)
{
    unsigned char DataInFlag;
    unsigned char DataChar;
    unsigned char tmp,tmp1, tmp2 ;

    DataInFlag = 0;

    switch (nCommType) {
	case 1: //PCE card
	    while (DataInFlag == 0) {
		DataInFlag = inportb(PortStatusAdr) & 0x01;
        }
	    DataChar = inportb(PortDataAdr);
	    return DataChar;

	case 2: //LPT
	    outportb(PortStatusAdr, P_SWITCH) ; /* portInp switch to status */
	    for(i=0;i<m_nLoop;i++){
		if ( !(inportb(PortInp) & P_R_RDY) &&
		     !(inportb(PortInp) & P_R_RDY)) {
		    outportb(PortStatusAdr, P_NORMAL );
		    outportb(PortStatusAdr, (P_NORMAL | P_R_PCE));
		    tmp = P_I_MASK ; /* delay, wait data send from PCE */
		    tmp1 = tmp2 = 0x80 ;
		    tmp &= inportb(PortInp) ;  /* Get high nibble */
		    outportb(PortStatusAdr, 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(PortStatusAdr, P_SWITCH);

		    tmp2 &= (~tmp) ;
		    tmp2 |= ((tmp << 1) & 0x70) ;
		    tmp2 >>= 4 ;
		    DataChar = tmp1 | tmp2;
		    return (DataChar);
		}
	    }
	    return 0;        
    }//end of case
    return (0);
}



BOOL CCommunication::TransmitStream(unsigned int TranStrLen)
{
	unsigned char chksum,lenH,lenL;
	unsigned int i;

	lenL = (unsigned char)(TranStrLen & 0x00ff);
	lenH = (unsigned char)(TranStrLen/256);

	chksum = ~(lenH+lenL)+1;

	if(TransmitByte(':') ) return FALSE;
	if(TransmitByte(lenL) ) return FALSE;
	if(ransmitByte(lenH) ) return FALSE;
	if(TransmitByte(chksum) ) return FALSE;

	if( ReceiveByte() != HEAD_OK ){
//	   AfxMessageBox("Head Transmit Fail!",MB_OK);	 
       return FALSE;            
     }   

	chksum = 0;
	for(i = 0;i < TStreamLen-1 ;i++)
		chksum = chksum + TransmitBuf[i];
	TransmitBuf[TStreamLen-1] = ~chksum + 1;

	for(i = 0;i < TStreamLen;i++)
		if(TransmitByte(TransmitBuf[i]) ) return FALSE;
	if( ReceiveByte() != REC_OK ) {
//	   AfxMessageBox("Command Transmit Fail!",MB_OK);
       return FALSE;                        
     }  
    return TRUE;
}

unsigned char CCommunication::ReceiveStream(void)
{

	unsigned char aa[4]="",chksum=0;
	unsigned int lp=0;

	while( lp < 4 )
	{
		aa[lp] = ReceiveByte();
		lp ++;
		if(aa[0]!=LEAD_CODE) lp = 0;
	 }

	for(lp = 1 ; lp < 4 ; lp ++)chksum+= aa[lp];

	if( (aa[0]==LEAD_CODE) && (chksum==0) )
	{

		RStreamLen = aa[1] + (unsigned int) (aa[2]*256);
		TransmitByte(HEAD_OK);
    }
	else
	{
		TransmitByte(HEAD_FAIL);
		AfxMessageBox("Receive Head Fail!",MB_OK);
    	return 1;	/* receive head failure */
	}
	chksum = 0;
	for(lp = 0;lp < RStreamLen;lp++)
	{
		ReceiveBuf[lp] = ReceiveByte();
		chksum = chksum + ReceiveBuf[lp];
	}
	if(chksum == 0)
	{
		TransmitByte( REC_OK );
		return 0;
	}
	else
	{
		AfxMessageBox("Receive Stream Fail!",MB_OK);
		TransmitByte( REC_FAIL );
		return 2;
	}
}

