/*
 * Example of client using TCP protocol, adapted from
 *   W.R. Stevens' "Unix Network Programming", 1st ed. 
 */

#include  <stdio.h>
#include  <sys/types.h>
#include  <sys/socket.h>
#include  <netinet/in.h>
#include  <arpa/inet.h>

#include  <stdio.h>
#include  <strings.h> // bzero
#include  <stdlib.h>  // exit
#include  <unistd.h>  // close

#include <stdint.h>   // uint8_t

#define SERV_TCP_PORT   5051
#define SERV_HOST_ADDR  "127.0.0.1"  

void str_cli(int);


int main(argc, argv)
int	argc;
char	*argv[];
{
     int sockfd;
     struct sockaddr_in	serv_addr;

     /*
      * Fill in the structure "serv_addr" with the address of the
      * server that we want to connect with.
      */
     
     bzero((char *) &serv_addr, sizeof(serv_addr));
     serv_addr.sin_family      = AF_INET;  /* Internet! */

     // These values are formatted for immediated use with a packet's fields,
     //   hence they are represented exactly as they'd appear in a packet.
     serv_addr.sin_addr.s_addr = inet_addr(SERV_HOST_ADDR); /* string to 4-byte IPv4 address */
     serv_addr.sin_port        = htons(SERV_TCP_PORT);      /* must be network-ordered! */
     
     /*
      * Open a TCP socket (an Internet stream socket).
      */
     
     if ( (sockfd = socket(AF_INET, SOCK_STREAM, 0)) < 0){  /* AF_INET is 2, SOCK_STREAM is 1 */
          perror("tcp client: can't open stream socket");
          exit(1);
     }

     /*
      * Connect to the server.
      */
     
     if (connect(sockfd, (struct sockaddr *) &serv_addr,
                 sizeof(serv_addr)) < 0){
          perror("tcp client: can't connect to server");
          exit(1);
     }
     
     str_cli(sockfd);

     close(sockfd);
     return 0;
}

#define MAXLINE 250

/*
 *  Read from STDIN, write into the socket, so long as STDIN lasts.
 */
void str_cli(sockfd)
{
     int     n;
     char    sendline[MAXLINE], recvline[MAXLINE + 1];
     
     while (fgets(sendline, MAXLINE, stdin) != NULL) {
          n = strlen(sendline);
          if (write(sockfd, sendline, n) != n)
               perror("str_cli: writen error on socket"); 
          
          /*
           * Now read a line from the socket and write it to
           * our standard output.
           */
          
          n = read(sockfd, recvline, MAXLINE);
          if (n < 0){
               perror("str_cli: readline error");
               exit(1);
          }
          recvline[n] = 0;        /* null terminate */
          fputs(recvline, stdout);
     }
}
