/***************************************************************************
 *   Copyright (C) 2006 by EVER Sp. z o.o.                                 *
 *                                                                         *
 *   This program is free software; you can redistribute it and/or modify  *
 *   it under the terms of the GNU General Public License as published by  *
 *   the Free Software Foundation; either version 2 of the License, or     *
 *   (at your option) any later version.                                   *
 *                                                                         *
 *   This program is distributed in the hope that it will be useful,       *
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
 *   GNU General Public License for more details.                          *
 *                                                                         *
 *   You should have received a copy of the GNU General Public License     *
 *   along with this program; if not, write to the                         *
 *   Free Software Foundation, Inc.,                                       *
 *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
 ***************************************************************************/
#ifndef FTCCOMM_H
#define FTCCOMM_H

#include <sys/types.h>
#include <sys/stat.h>
#include <sys/ioctl.h>
#include <fcntl.h>
#include <termios.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>

#include "ccomm.h"
#include "libftdi/ftd2xx.h"

typedef enum _eftcomm_status_
{
	FT_CTS = 0x10, FT_DSR = 0x20, FT_RING = 0x40, FT_RLSD = 0x80

} eftcomm_status;

typedef enum _eftcomm_lines_
{
	FT_S_RTS, FT_S_DTR
} eftcomm_lines;

class FTCComm {
private:
	FT_HANDLE fd;			// device descriptor
	FT_STATUS fStatus;		// device status buffer
	int	lasterror;			// last errno
	char	*device;		// device name to open
	int	baudrate;			// device transmission speed
	bool bIsInitialized;	// initialization flag
	bool bIsLocked;			// lock status flag
	bool bIsSimpleSig;		// simple signalling mode flag

public:
	/* class constructor/destructor */
	FTCComm();
	~FTCComm();
	
	int init(char *devSerNum, speed_t speed) {
		if (devSerNum!=NULL) {
			if (device!=NULL)	
				free(device);
			device=strdup(devSerNum);
		}
		if (speed!=0)
			baudrate=speed;
	};
	int open();
	int open_simplesignalling();
	int close();
	/* status lines checking/setting functions */
	unsigned long getStatus();
	int getStatus(unsigned long *pflags);
	int setStatus(unsigned long flags);
	int status_check(eftcomm_status eFlag);
	int set_line(eftcomm_lines eline);
	int clr_line(eftcomm_lines eline);
	/* communication functions */
	int send(unsigned char data);
	int send(unsigned char *pdata, int len);
	int send2b(unsigned int *pdata);
	int send2b(unsigned int *pdata, int len2b);
	int receive(unsigned char *pdata);
	int receive(unsigned char *pdata, int len);
	/* receive specified number of bytes and convert it to 16 bits data */ 
	int receive2b(unsigned int *pdata, int len2b);
	/* receive specified number of bytes and convert it to 16 bits data reversing bytes */ 
	int receive2brev(unsigned int *pdata, int len2b);
	/* CRC versions of two function above */
	int receive2b(unsigned int *pdata, int len2b, unsigned long *pcrc);
	int receive2brev(unsigned int *pdata, int len2b, unsigned long *pcrc);

	int receive() {
		unsigned char rdata=0;
		if (receive(&rdata)!=COMM_FAILURE)
			return (int)rdata;
		else
			return COMM_FAILURE;
	};
	void flush(bool i, bool o) {
		if (bIsInitialized) {
			if (i) FT_Purge(fd, FT_PURGE_RX);
			if (o) FT_Purge(fd, FT_PURGE_TX);
		}
	};
	int lock_port();
	int unlock_port();
	bool isInitialized() {
		return bIsInitialized;
	};
};

#endif//FTCCOMM_H
