Index: /trunk/Ohana/Makefile
===================================================================
--- /trunk/Ohana/Makefile	(revision 5272)
+++ /trunk/Ohana/Makefile	(revision 5273)
@@ -69,8 +69,8 @@
 
 # Required libraries depends on the architecture
-LIBS-linux = libfits libohana libdummy
-LIBS-lin64 = libfits libohana libdummy
-LIBS-sid   = libfits libohana libdummy
-LIBS-sol   = libfits libohana
+LIBS-linux = libohana libfits libdvo libdummy
+LIBS-lin64 = libohana libfits libdvo libdummy
+LIBS-sid   = libohana libfits libdvo libdummy
+LIBS-sol   = libohana libfits libdvo 
 
 # general build targets:
Index: /trunk/Ohana/src/addstar/Makefile
===================================================================
--- /trunk/Ohana/src/addstar/Makefile	(revision 5272)
+++ /trunk/Ohana/src/addstar/Makefile	(revision 5273)
@@ -88,17 +88,13 @@
 SERVER = \
 $(SRC)/SocketOps.$(ARCH).o \
-$(SRC)/IOBufferOps.$(ARCH).o \
 $(SRC)/ConfigInit.$(ARCH).o \
 $(SRC)/args_server.$(ARCH).o \
 $(SRC)/CheckPassword.$(ARCH).o \
-$(SRC)/NewImage.$(ARCH).o \
-$(SRC)/CommOps.$(ARCH).o
+$(SRC)/NewImage.$(ARCH).o 
 
 CLIENT = \
 $(SRC)/SocketOps.$(ARCH).o \
-$(SRC)/IOBufferOps.$(ARCH).o \
 $(SRC)/ConfigInit.$(ARCH).o \
-$(SRC)/args_client.$(ARCH).o \
-$(SRC)/CommOps.$(ARCH).o
+$(SRC)/args_client.$(ARCH).o
 
 default: $(PROGRAM)
@@ -114,6 +110,6 @@
 autocode: $(COMMOBJ)
 
-ADDSTARC = $(SRC)/addstarc.$(ARCH).o $(CLIENT) $(COMMOBJ)
-ADDSTARD = $(SRC)/addstard.$(ARCH).o $(SERVER) $(COMMOBJ)
+ADDSTARC = $(SRC)/addstarc.$(ARCH).o $(CLIENT)
+ADDSTARD = $(SRC)/addstard.$(ARCH).o $(SERVER)
 
 $(ADDSTARC) : $(INC)/addstar.h
@@ -121,11 +117,9 @@
 $(ADDSTAR)  : $(INC)/addstar.h
 
-$(INC)/addstar.h       : $(INC)/commcode.h
-
 addstar                : $(BIN)/addstar.$(ARCH)
 $(BIN)/addstar.$(ARCH) : $(ADDSTAR)
 
 addstard                : $(BIN)/addstard.$(ARCH)
-$(BIN)/addstard.$(ARCH) : $(SRC)/addstard.$(ARCH).o $(SERVER) $(COMMOBJ)
+$(BIN)/addstard.$(ARCH) : $(ADDSTARD)
 
 addstarc                : $(BIN)/addstarc.$(ARCH)
Index: /trunk/Ohana/src/addstar/include/addstar.h
===================================================================
--- /trunk/Ohana/src/addstar/include/addstar.h	(revision 5272)
+++ /trunk/Ohana/src/addstar/include/addstar.h	(revision 5273)
@@ -1,3 +1,3 @@
-# include "base.h" 
+# include <ohana.h>
 # include <dvo.h>
 # include <signal.h>
@@ -9,6 +9,6 @@
 # include <arpa/inet.h>
 
-/* this is generated locally from the entries in addstar/def */
-# include "commcode.h"
+/* this is generated locally from the entries in addstar/def 
+# include "commcode.h" */
 
 /* used in find_matches, find_matches_refstars */
Index: /trunk/Ohana/src/libautocode/Makefile
===================================================================
--- /trunk/Ohana/src/libautocode/Makefile	(revision 5272)
+++ /trunk/Ohana/src/libautocode/Makefile	(revision 5273)
@@ -48,5 +48,7 @@
 $(SRC)/smpdata.$(ARCH).o \
 $(SRC)/spectrum.$(ARCH).o \
-$(SRC)/spectrum-ascii.$(ARCH).o
+$(SRC)/spectrum-ascii.$(ARCH).o \
+$(SRC)/Stars.$(ARCH).o \
+$(SRC)/AddstarClientOptions.$(ARCH).o
 
 LIBINC = \
@@ -76,5 +78,7 @@
 $(INC)/smpdata.h \
 $(INC)/spectrum.h \
-$(INC)/spectrum-ascii.h
+$(INC)/spectrum-ascii.h \
+$(INC)/Stars.h \
+$(INC)/AddstarClientOptions.h
 
 objects: $(LIBOBJ)
@@ -82,4 +86,6 @@
 install: $(DESTINC)/autocode.h $(DESTLIB)/libautocode.a
 	@echo done install
+
+test: $(DESTINC)/autocode.h
 
 autocode: $(INC)/autocode.h $(LIB)/libautocode.$(ARCH).a 
Index: /trunk/Ohana/src/libautocode/def/AddstarClientOptions.d
===================================================================
--- /trunk/Ohana/src/libautocode/def/AddstarClientOptions.d	(revision 5273)
+++ /trunk/Ohana/src/libautocode/def/AddstarClientOptions.d	(revision 5273)
@@ -0,0 +1,18 @@
+STRUCT  AddstarClientOptions
+EXTNAME OPTIONS
+TYPE    BINTABLE
+SIZE    52
+
+FIELD  	  mode,             MODE,                 int,            data source mode
+FIELD  	  existing_regions, EXISTING_REGIONS,     int,            use only existing regions
+FIELD  	  only_match,       ONLY_MATCH,           int,            only update matched stars
+FIELD  	  skip_missed,      SKIP_MISSED,          int,            .
+FIELD  	  replace,          REPLACE,              int,            .
+FIELD  	  closest,          CLOSEST,              int,            .
+FIELD  	  nosort,           NOSORT,               int,            .
+FIELD  	  update,           UPDATE,               int,            .
+FIELD  	  only_images,      ONLY_IMAGES,          int,            .
+FIELD  	  calibrate,        CALIBRATE,            int,            .
+FIELD  	  mosaic,           MOSAIC,               int,            does this image require a mosaic coordinate system?
+FIELD  	  photcode,         PHOTCODE,             int,     	  photocode of input data
+FIELD  	  timeref,          TIMEREF,              e_time,  	  time/date of input data (REFLIST only?)
Index: /trunk/Ohana/src/libautocode/def/Stars.d
===================================================================
--- /trunk/Ohana/src/libautocode/def/Stars.d	(revision 5273)
+++ /trunk/Ohana/src/libautocode/def/Stars.d	(revision 5273)
@@ -0,0 +1,22 @@
+STRUCT  Stars
+EXTNAME STARS
+TYPE    BINTABLE
+SIZE    112
+
+FIELD     X,                X,            	  double,         x coordinate on image
+FIELD     Y,                Y,            	  double,         y coordinate on image
+FIELD     R,                R,            	  double,         ra coordinate on sky
+FIELD     D,                D,            	  double,         dec coordinate on sky
+FIELD     M,                M,            	  double,         instrumental mag
+FIELD     dM,               DM,           	  double,         error on mag
+FIELD     sky,              SKY,          	  double,         local sky counts
+FIELD     fx,               FX,           	  double,         object FWHM x-dir
+FIELD     fy,               FY,           	  double,         object FWHM y-dir
+FIELD     df,               DF,           	  double,         object position angle
+FIELD     Mgal,             MGAL,         	  double,         alternative (galaxy) magnitude
+FIELD     Map,              MAP,          	  double,         alternative (aperture) magnitude
+FIELD     found,            FOUND,        	  int,            found in database catalog?
+FIELD     t,                T,            	  e_time,         date/time of exposure (UNIX)
+FIELD     code,             CODE,         	  short,          .
+FIELD     dophot,           DOPHOT,       	  char,           dophot type code
+FIELD     dummy,            DUMMY,         	  char[5],        .
Index: /trunk/Ohana/src/libautocode/def/autocode.c
===================================================================
--- /trunk/Ohana/src/libautocode/def/autocode.c	(revision 5272)
+++ /trunk/Ohana/src/libautocode/def/autocode.c	(revision 5273)
@@ -73,2 +73,52 @@
   return (TRUE);
 }
+
+int Send_$STRUCT (int device, $STRUCT *data, int Ndata, int copy) {
+
+  int Nbytes;
+  $STRUCT *tmpdata;
+
+  Nbytes = Ndata * sizeof ($STRUCT);
+
+  if (copy) {
+    ALLOCATE (tmpdata, $STRUCT, Ndata);
+    memcpy (tmpdata, data, Nbytes);
+  } else {
+    tmpdata = data;
+  }
+
+  fits_convert_$STRUCT (tmpdata, sizeof ($STRUCT), Ndata);
+
+  SendCommand (device, 16, "NVALUE: %6d", Ndata);
+  SendCommand (device, 16, "NBYTES: %6d", Nbytes);
+  write (device, tmpdata, Nbytes);
+  
+  /* perform handshaking? */
+
+  return (TRUE);
+}
+
+int Recv_$STRUCT (int device, $STRUCT **data, int *Ndata) {
+
+  int ndata;
+  IOBuffer message;
+  $STRUCT *tmpdata;
+
+  ExpectCommand (device, 16, 1.0, &message);
+  sscanf (message.buffer, "%*s %d", &ndata);
+  FreeIOBuffer (&message);
+  
+  /* what is reasonable for timeout? */
+  ExpectMessage (device, 1.0, &message);
+  
+  tmpdata = ($STRUCT *) message.buffer;
+  fits_convert_$STRUCT (tmpdata, sizeof ($STRUCT), *Ndata);
+
+  /* double-check data length? */
+  /* perform handshaking? */
+
+  *Ndata = ndata;
+  *data = tmpdata;
+
+  return (TRUE);
+}
Index: /trunk/Ohana/src/libautocode/def/autocode.h
===================================================================
--- /trunk/Ohana/src/libautocode/def/autocode.h	(revision 5272)
+++ /trunk/Ohana/src/libautocode/def/autocode.h	(revision 5273)
@@ -6,2 +6,4 @@
 int      fits_table_mkheader_$STRUCT (Header *header);
 int      fits_convert_$STRUCT ($STRUCT *data, int size, int nitems);
+int Send_$STRUCT (int device, $STRUCT *data, int Ndata, int copy);
+int Recv_$STRUCT (int device, $STRUCT **data, int *Ndata);
Index: /trunk/Ohana/src/libdvo/Makefile
===================================================================
--- /trunk/Ohana/src/libdvo/Makefile	(revision 5272)
+++ /trunk/Ohana/src/libdvo/Makefile	(revision 5273)
@@ -68,5 +68,7 @@
 $(ASRC)/smpdata.$(ARCH).o \
 $(ASRC)/spectrum.$(ARCH).o \
-$(ASRC)/spectrum-ascii.$(ARCH).o
+$(ASRC)/spectrum-ascii.$(ARCH).o \
+$(ASRC)/Stars.$(ARCH).o \
+$(ASRC)/AddstarClientOptions.$(ARCH).o
 
 ACOM = $(ADEF)/autocode.c $(ADEF)/autocode.h $(ADEF)/common.h
Index: /trunk/Ohana/src/libohana/Makefile
===================================================================
--- /trunk/Ohana/src/libohana/Makefile	(revision 5272)
+++ /trunk/Ohana/src/libohana/Makefile	(revision 5273)
@@ -35,4 +35,6 @@
 $(SRC)/config.$(ARCH).o		 \
 $(SRC)/Fread.$(ARCH).o		 \
+$(SRC)/IOBufferOps.$(ARCH).o	 \
+$(SRC)/CommOps.$(ARCH).o	 \
 $(SRC)/version.$(ARCH).o
 
Index: /trunk/Ohana/src/libohana/include/ohana.h
===================================================================
--- /trunk/Ohana/src/libohana/include/ohana.h	(revision 5272)
+++ /trunk/Ohana/src/libohana/include/ohana.h	(revision 5273)
@@ -87,4 +87,13 @@
 # endif /* FOPEN */
 
+/* socket / pipe communication buffer */
+typedef struct {
+  char *buffer;
+  int   Nalloc;
+  int   Nreset;
+  int   Nblock;
+  int   Nbuffer;
+} IOBuffer;
+
 extern double hypot();
 
@@ -143,4 +152,18 @@
 int     str_to_radec           PROTO((double *ra, double *dec, char *str1, char *str2));
 
+/* IO Buffer functions */
+int InitIOBuffer (IOBuffer *buffer, int Nalloc);
+int FlushIOBuffer (IOBuffer *buffer);
+int ReadtoIOBuffer (IOBuffer *buffer, int fd);
+int EmptyIOBuffer (IOBuffer *buffer, int Nmax, int fd);
+void FreeIOBuffer (IOBuffer *buffer);
+
+/* communication functions */
+int ExpectMessage (int device, double timeout, IOBuffer *message);
+int ExpectCommand (int device, int length, double timeout, IOBuffer *buffer);
+int SendMessage (int device, char *format, ...);
+int SendCommand (int device, int length, char *format, ...);
+int SendCommandV (int device, int length, char *format, va_list argp);
+
 /*
 #   define F_SETFL         4   
Index: /trunk/Ohana/src/libohana/src/CommOps.c
===================================================================
--- /trunk/Ohana/src/libohana/src/CommOps.c	(revision 5273)
+++ /trunk/Ohana/src/libohana/src/CommOps.c	(revision 5273)
@@ -0,0 +1,114 @@
+# include <ohana.h>
+
+int ExpectMessage (int device, double timeout, IOBuffer *message) {
+
+  int status, length;
+  IOBuffer command;
+
+  status = ExpectCommand (device, 16, timeout, &command);
+  if (status != 0) {
+    FreeIOBuffer (&command);
+    return (status);
+  }
+
+  /* buffer contains an EOL NULL, we can just sscan it */
+  sscanf (command.buffer, "%*s %d", &length);
+  FreeIOBuffer (&command);
+  
+  status = ExpectCommand (device, length, timeout, message);
+  return (status);
+}
+
+int ExpectCommand (int device, int length, double timeout, IOBuffer *buffer) {
+
+  /* read from device until we have length bytes, or timeout */
+
+  int Nread;
+  double dtime;
+  struct timespec request, remain;
+  struct timeval start, stop;
+
+  gettimeofday (&start, NULL);
+
+  /* avoid blocking on waitpid, test every 1000 usec, up to timeout msec */
+  request.tv_sec = 0;
+  request.tv_nsec = 1000000;
+
+  InitIOBuffer (buffer, length + 1);
+
+  while (buffer[0].Nbuffer < length) {
+    Nread = read (device, &buffer[0].buffer[buffer[0].Nbuffer], length - buffer[0].Nbuffer);
+    
+    if (Nread > 0) {
+      buffer[0].Nbuffer += Nread;
+      continue;
+    }
+
+    if (Nread == -1) {
+      switch (errno) {
+	case EAGAIN:
+	case EIO:
+	  /** no data available in pipe, wait a bit, check for timeout **/
+	  nanosleep (&request, &remain);
+	  break;
+	default:
+	  /** error reading from pipe **/
+	  perror ("ReadtoIOBuffer read error");
+	  return (-2);
+      }
+    }
+
+    if (Nread == 0) return (-3);
+
+    gettimeofday (&stop, NULL);
+    dtime = DTIME (stop, start);
+    if (dtime > timeout) return (-1);
+  }
+  return (0);
+}
+
+/* send a message of arbitrary size, sending the size first */
+int SendMessage (int device, char *format, ...) {
+
+  int Nbyte, status;
+  char tmp;
+  va_list argp;  
+
+  va_start (argp, format);
+  Nbyte = vsnprintf (&tmp, 0, format, argp);
+  va_end (argp);
+
+  if (!Nbyte) return (FALSE);
+
+  va_start (argp, format);
+  SendCommand (device, 16, "NBYTES: %6d", Nbyte);
+  status = SendCommandV (device, Nbyte, format, argp);
+  va_end (argp);
+  return (status);
+}
+
+int SendCommand (int device, int length, char *format, ...) {
+
+  int status;
+  va_list argp;  
+
+  va_start (argp, format);
+  status = SendCommandV (device, length, format, argp);
+  va_end (argp);
+  return (status);
+}
+  
+int SendCommandV (int device, int length, char *format, va_list argp) {
+
+  char *string;
+
+  /* I allocated and zero 1 extra byte */
+  ALLOCATE (string, char, length + 1);
+  memset (string, 0, length + 1);
+  vsnprintf (string, length + 1, format, argp);
+
+  /* fprintf (stderr, "msg: %s\n", string); */
+  write (device, string, length);
+  free (string);
+  return (TRUE);
+}
Index: /trunk/Ohana/src/libohana/src/IOBufferOps.c
===================================================================
--- /trunk/Ohana/src/libohana/src/IOBufferOps.c	(revision 5273)
+++ /trunk/Ohana/src/libohana/src/IOBufferOps.c	(revision 5273)
@@ -0,0 +1,85 @@
+# include <ohana.h>
+
+int InitIOBuffer (IOBuffer *buffer, int Nalloc) {
+
+  buffer[0].Nalloc = Nalloc;
+  buffer[0].Nreset = Nalloc;
+  buffer[0].Nblock = Nalloc / 2;
+  buffer[0].Nbuffer = 0;
+
+  ALLOCATE (buffer[0].buffer, char, buffer[0].Nalloc);
+  bzero (buffer[0].buffer, buffer[0].Nalloc);
+
+  return (TRUE);
+}
+
+int FlushIOBuffer (IOBuffer *buffer) {
+
+  buffer[0].Nbuffer = 0;
+  buffer[0].Nalloc = buffer[0].Nreset;
+  REALLOCATE (buffer[0].buffer, char, buffer[0].Nalloc);
+  bzero (buffer[0].buffer, buffer[0].Nalloc);
+
+  return (TRUE);
+}
+
+int ReadtoIOBuffer (IOBuffer *buffer, int fd) {
+
+  int Nread, Nfree;
+
+  if (fd == 0) {
+    /* pipe is closed */
+    return (0);
+  }
+
+  Nfree = buffer[0].Nalloc - buffer[0].Nbuffer;
+  if (Nfree < buffer[0].Nblock) {
+    buffer[0].Nalloc += 2*buffer[0].Nblock;
+    REALLOCATE (buffer[0].buffer, char, buffer[0].Nalloc);
+    Nfree = buffer[0].Nalloc - buffer[0].Nbuffer;
+    bzero (buffer[0].buffer + buffer[0].Nbuffer, Nfree);
+  }
+
+  Nread = read (fd, &buffer[0].buffer[buffer[0].Nbuffer], buffer[0].Nblock);
+
+  if (Nread >= 0) {
+    buffer[0].Nbuffer += Nread;
+    return (Nread);
+  }
+
+  if (Nread == -1) {
+    switch (errno) {
+    case EAGAIN:
+    case EIO:
+      /** no data available in pipe **/
+      return (-1);
+    default:
+      /** error reading from pipe **/
+      perror ("ReadtoIOBuffer read error");
+      return (-2);
+    }
+  }
+  return (Nread);
+}
+
+/* read until buffer is empty (Nmax retries) */
+int EmptyIOBuffer (IOBuffer *buffer, int Nmax, int fd) {
+
+  int i, status;
+
+  status = -1;
+  for (i = 0; (status != 0) && (i < Nmax); i++) {
+    status = ReadtoIOBuffer (buffer, fd);
+    if (status == -1) usleep (10000);
+    if (status > 0) i = 0;
+  }
+  if (status == -1) return (FALSE);
+  return (TRUE);
+}
+
+void FreeIOBuffer (IOBuffer *buffer) {
+
+  if (buffer[0].buffer != (char *) NULL) {
+    free (buffer[0].buffer);
+  }
+}
Index: /trunk/Ohana/src/libohana/src/ohana_allocate.c
===================================================================
--- /trunk/Ohana/src/libohana/src/ohana_allocate.c	(revision 5272)
+++ /trunk/Ohana/src/libohana/src/ohana_allocate.c	(revision 5273)
@@ -235,4 +235,5 @@
   S[3] = 'X';
   Ns[0] = Ns[1] = Ns[2] = Ns[3] = 0;
+  N = 0;
 
   for (i = 0; i < Nmemlist; i++) {
