#ifndef __MSG_QUEUE__H__
#define __MSG_QUEUE__H__

#include <pthread.h>

/*
  pop, push, and the like copy the argument rather than use it directly.  
  Copying is slower, but probably not as slow as mallocs.  If the class 
  didn't perform the copy, the user would have had to anyway to get the
  data from the DMA bufffer.
*/

struct MsgQueue {
  int size;
  void ** queue;
  
  int front;
  int back;
  //int peek_p;
  
  pthread_cond_t * cond;  //used for waking thread blocked on pop
  pthread_mutex_t * cond_lock; 

  pthread_mutex_t * lock; //used for protecting front/back
};

#ifdef __cplusplus
extern "C" {
#endif

  void msg_init(struct MsgQueue * fq, int slots);
  
  void * msg_pop(struct MsgQueue * fq);
  
  int msg_push(struct MsgQueue * fq, void *);


  int msg_length(struct MsgQueue * fq);

  //struct frame * msg_view_pos(struct MsgQueue * fq, int pos);
  //struct frame * msg_peek(struct MsgQueue * fq);
  //void msg_reset_peek(struct MsgQueue * fq);
  

  int msg_is_full(struct MsgQueue * fq);
  int msg_is_empty(struct MsgQueue * fq);
  void msg_print(struct MsgQueue * fq);

#ifdef __cplusplus
}
#endif

#define QUEUE_OK 0
#define QUEUE_FULL -1
#define QUEUE_EMPTY -2
#define QUEUE_POS_PAST_END -4
#define QUEUE_PEEK_FAIL QUEUE_POS_PAST_END

#endif
