#ifndef _COC_UTIL_H_
#define _COC_UTIL_H_

#include <netinet/in.h>
#include "str_buf.h"

int CocCreateSockAdr(
    struct sockaddr_in *sockaddrPtr,    /* Socket address */
    const char *host,                   /* Host.  NULL implies INADDR_ANY */
    int port);                          /* Port number */
/*
  compose internet address
*/

int CocRecv(int fd, Str_Buf *buf);
/*
  receive data
*/

typedef struct {
  /* private */
  void *next;
  char name[32];
  void *var;
  int *flag;
  int type;
  void *strucType;
} CocVar;

extern int CocRD; /* readonly variable (used as argument for CocDefXXX) */
extern int CocWR; /* read/write variable (used as argument for CocDefXXX) */
CocVar *serverVarList; /* variable list for the server process */

CocVar *CocDefVar(const char *name, void *var, int type, int *flag);
void CocDefVarS(const char *name, const char *tname, void *var, int type);
/*
  Define variables. Call this routines not directly, but through
  one of the macros below.
*/

void CocVarList(CocVar **varlist);
/*
  print a variable list (for debugging purposes)
*/
void CocFreeVarList(CocVar **varList);
/*
  free a variable list
*/
CocVar *CocFindVar(CocVar *varList, const char *name, void **adr);
/*
  find a variable. returns NULL if not found.
*/
int CocPutVar(CocVar *varList, Str_Buf *buf, const char *name, int secure);
/*
  put a variable named <name> of variable list <varList> to the buffer <buf>
  if <secure>, access rights are checked
*/
int CocGetVar(CocVar *varList, Str_Buf *buf, const char *name, int secure);
/*
  get a variable named <name> of variable list <varList> from the buffer <buf>
  if <secure>, access rights are checked
*/
void CocDelay(int msec);
/*
  system independent delay function with msec resolution
*/
#define COC_INT -1
#define COC_FLT -2
#define COC_PTR -3
#define COC_STRUCT -4
#define COC_TYPE -5
#define COC_ALIAS -6

/* macros to define variables */
#define CocDefInt(V,F)      CocDefVar(#V,&V,COC_INT,&F)
#define CocDefFlt(V,F)      CocDefVar(#V,&V,COC_FLT,&F)
#define CocDefStr(V,F)      CocDefVar(#V,V,sizeof(V),&F)
#define CocDefPtr(V,S)      CocDefVarS(#V,#S,&V,COC_PTR*(V!=(S *)NULL));
#define CocDefStruct(V,S)   CocDefVarS(#V,#S,&V,COC_STRUCT*(&V!=(S *)NULL));
#define CocIntFld(S,V,F)    CocDefVar(#S":"#V,&((S *)NULL)->V,COC_INT,&F);
#define CocFltFld(S,V,F)    CocDefVar(#S":"#V,&((S *)NULL)->V,COC_FLT,&F);
#define CocStrFld(S,V,F)    CocDefVar(#S":"#V,((S *)NULL)->V,sizeof(((S *)NULL)->V),&F);
#define CocDefCmd(V)        CocDefVar("$",V,sizeof(V),&CocWR)
#define CocDefStrPtr(V,S,F) CocDefVar(#V,V,S,&F)
#define CocAlias(A,V)       CocDefVar(#A, #V, COC_ALIAS, &CocRD);

#endif /* _COC_UTIL_H_ */
