#ifndef PORT_H
#define PORT_H

#include "libusbeventhandler.h"
#include <libusb-1.0/libusb.h>

#define INTERF 1             // interface numbre
#define READ_ENDPOINT 0x81   // read endpoint
#define WRITE_ENDPOINT 0x01  // write endpoint
#define BUFFER_LEN 32768 * 5 // input buffer length
#define READ_TIMEOUT 2       // read timeout

class LIBUSBPort : public QObject {
  Q_OBJECT
public:
  LIBUSBPort();
  ~LIBUSBPort();

private:
  libusb_device *device;            // device
  libusb_device_handle *dev_handle; // device handler
  libusb_transfer *readTransfer;    // read transfer
  libusb_transfer *writeTransfer;   // write transfer

  unsigned char inBuff[BUFFER_LEN]; // input buffer
  int bufferLenAvailable;           // free space in buffer
  QByteArray toEmit;                // data to emit

  unsigned char *outBuff;    // output buffer
  QList<QByteArray> outQueu; // output data queu
  volatile bool sendDone;    // output buffer sent

  volatile bool opened; // device opened

  unsigned char *controlBuff;    // control transfer buffer
  QList<QByteArray> controlQueu; // control tranfers queu

  LIBUSBEventHandler
      *eventHandler; // event handler - running in different thread

  static void LIBUSB_CALL
  readDone(struct libusb_transfer *transfer); // read done callback
  static void LIBUSB_CALL
  writeDone(struct libusb_transfer *transfer); // write done callback
  static void LIBUSB_CALL conrolWriteDone(
      struct libusb_transfer *transfer); // control write done callback
  void setRead();                        // set read transfer
  void sendControlQueu();                // send control transfers queu

signals:
  void newData(const QByteArray &); // emit data
  void openStatus(bool);            // emit open status
  void close();                     // emit close port

public slots:
  void requestToStop();              // request to stop port
  void requestOpen(libusb_device *); // request to open port
  void requestSend(QByteArray);      // request to send data
  void closeAll();                   // close port
};

#endif // PORT_H
