#include "xbugchess.h"
#define MAXHOSTNAME 40


int establish(portnum)
     u_short portnum;
{ char   myname[MAXHOSTNAME+1];
  int    s;
  struct sockaddr_in sa;
  struct hostent *hp;
  auto int on=1;


  bzero(&sa,sizeof(struct sockaddr_in));      /* clear our address */
  gethostname(myname,MAXHOSTNAME);            /* who are we? */
  hp= gethostbyname(myname);                  /* get our address info */
  if (hp == NULL)                             /* we don't exist !? */
    return(-1);
  sa.sin_family= hp->h_addrtype;              /* this is our host address */
  sa.sin_port= htons(portnum);                /* this is our port number */
  if ((s= socket(AF_INET,SOCK_STREAM,0)) < 0) /* create socket */
    return(-1);
  if (setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &on, sizeof on) < 0)
    perror("setsockopt");
  if (bind(s,&sa,sizeof sa,0) < 0) {
    close(s);
    return(-1);                               /* bind address to socket */
  }
  listen(s, 4);                               /* max # of queued connects */
  return(s);
}

int get_connection(s)
     int s;                    /* socket created with establish() */
{ struct sockaddr_in isa; /* address of socket */
  int i,t;                  /* size of address */

  i = sizeof(isa);                   /* find socket's address */
  getsockname(s,&isa,&i);            /* for accept() */

  if ((t = accept(s,&isa,&i)) < 0)   /* accept connection if there is one */
    return(-1);
  return(t);
}


int read_data(s,buf,n)
     int  s;                /* connected socket */
     char *buf;             /* pointer to the buffer */
     int  n;                /* number of characters (bytes) we want */
{ int bcount,          /* counts bytes read */
    br;              /* bytes read this pass */

  bcount= 0;
  br= 0;
  while (bcount < n) {             /* loop until full buffer */

    if ((br= read(s,buf,n-bcount)) > 0) {
      bcount += br;                /* increment byte counter */
      buf += br;                   /* move buffer ptr for next read */
    }

    if (br < 1)                    /* signal an error to the caller */
      return(br);

  }
  return(bcount);
}



int write_data(s,buf,n)
     int  s;                /* connected socket */
     char *buf;             /* pointer to the buffer */
     int  n;                /* number of characters (bytes) we want */
{ int bcount,          /* counts bytes read */
    br;              /* bytes read this pass */

  bcount= 0;
  br= 0;
  while (bcount < n) {             /* loop until full buffer */
    if ((br= write(s,buf,n-bcount)) > 0) {
      bcount += br;                /* increment byte counter */
      buf += br;                   /* move buffer ptr for next read */
    }
    if (br < 0) { 
      perror("write_data");        /* signal an error to the caller */
      return(-1);
    }
  }
  return(bcount);
}

int call_socket(hostname, portnum)
     char *hostname;
{ struct sockaddr_in sa;
  struct hostent     *hp;
  int s;

  if ((hp= gethostbyname(hostname)) == NULL) { /* do we know the host's */
    errno= ECONNREFUSED;                       /* address? */
    return(-1);                                /* no */
  }

  bzero(&sa,sizeof(sa));
  bcopy(hp->h_addr,(char *)&sa.sin_addr,hp->h_length); /* set address */
  sa.sin_family= hp->h_addrtype;
  sa.sin_port= htons((u_short)portnum);

  if ((s= socket(hp->h_addrtype,SOCK_STREAM,0)) < 0)   /* get socket */
    return(-1);
  if (connect(s,&sa,sizeof sa) < 0) {                  /* connect */
    close(s);
    return(-1);
  }
  return(s);
}

