#ifndef	_STR_BUF_H_
#define	_STR_BUF_H_

/*
  This module is used to write and read from character strings
  It is a simplified, safe replacement for sprintf/sscanf.

  DeclStrBuf(buf, size) declares and initializes a buffer of a given size.
  Use this macro in the declaration part of a function.
*/
typedef struct { char *buf; int dsize, rdpos, wrpos, seen; } StrBuf;

#define DeclStrBuf(BUF,SIZ) static char STR__##BUF[SIZ]; StrBuf BUF={STR__##BUF,SIZ}

/*------------------------------------------------------------------------
  Write content to the buffer, and add separator sep, if sep!=StrNONE
*/
#define StrNONE -1
int StrPut(StrBuf *buf, const char *str, int sep);
int StrPutInt(StrBuf *buf, int val, int sep);
int StrPutFloat(StrBuf *buf, float val, int sep);
int StrPutArray(StrBuf *buf, float val[], int size);

/*------------------------------------------------------------------------
  Read from the buffer until separator sep.
  Use the StrGet macro if the result is a fixed size.
  Special case sep=StrNONE:
  - StrGet reads until the end of the buffer or until the end of a quoted string
  - StrGetInt and StrGetFloat read until the end of a legal number 
*/
char *StrNGet(StrBuf *buf, char *result, int reslen, int sep);
#define StrGet(BUF,RES,SEP) StrNGet(BUF,RES,sizeof(RES),SEP)
int StrGetInt(StrBuf *buf, int *res, int sep);
int StrGetFloat(StrBuf *buf, float *res, int sep);
int StrGetArray(StrBuf *buf, float val[], int maxsize);
#define StrEnd(BUF) ((BUF)->rdpos>=(BUF)->wrpos)

/*------------------------------------------------------------------------
  reset the buffer to read from the beginning
*/
void StrReset(StrBuf *buf);

/*------------------------------------------------------------------------
  Clear the buffer
*/
void StrClear(StrBuf *buf);

/*------------------------------------------------------------------------
  Verify that the end is reached
*/
  int StrGetEnd(StrBuf *buf);

/*------------------------------------------------------------------------
  Link the buffer to a string. The buffer length is set to
  sizeof(STR) or strlen(STR), whichever is greater
*/
#define StrLink(BUF, STR) StrNLink(BUF, STR, sizeof(STR))
void StrNLink(StrBuf *buf, char *str, int size);

#endif /* _STR_BUF_H_ */
