#ifndef HP34COMM_H
#define HP34COMM_H

#include "mbed.h"
#include "CircularBuffer.h"

/***** HP 34970A communication class ***/

#define MAX_ERRS 10
#define MAX_BUFF 16
#define BUF_SIZE 16

class HPSerial {

public:
  enum TrState {
        Idle = 0,
        Tx,
        Rx,
    };
  typedef struct _CMD
  {
    TrState direction;
    uint8_t cmd;
    uint8_t size;
    char value[MAX_BUFF+1];
    unsigned long id;
  } CMD;


  
  HPSerial(PinName rx);
  
  bool cmd_available(void);
  bool pop(CMD& cmd);
  bool cmd_buf_full(void);
  unsigned int nerrors(uint8_t errorno);
		     
  
private:
  void reset(uint8_t errorno=0xFF);
  void handleAck(uint8_t val);
  void pushCmd(TrState direction, uint8_t cmd, uint8_t size, char *payload);
  void handleChar(uint8_t val);
  void setstatedbg(void);    
  void rxIrq(void);
  void timeout(void);

 private:
  RawSerial serial_rx;
  uint8_t buf[BUF_SIZE];
  uint8_t head;
  uint8_t tx_state;
  uint8_t tx_cmd;
  uint8_t tx_len;
  bool tx_ack;
  CircularBuffer<CMD, 32> cmdbuf;
  unsigned long ncmd;
  unsigned int errs[MAX_ERRS];
  Ticker timeouter;
};

#endif
