Skip to content

Instantly share code, notes, and snippets.

@EV21
Created May 26, 2017 16:11
Show Gist options
  • Save EV21/21721e81bc114b17eb690bc55d8118dc to your computer and use it in GitHub Desktop.
Save EV21/21721e81bc114b17eb690bc55d8118dc to your computer and use it in GitHub Desktop.
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <netdb.h>
#include <dirent.h>
#define MSG_LEN 2000
#define CMND_LEN 4
#define LIST "List"
#define GET "Get "
#define PUT "Put "
#define QUIT "Quit"
//#define SRV_PORT 7777
/*
* A Client Application for a http-like protocol
* with simple Get, Put, and List Commands for server interaction
*/
int main(int argc, char *args[])
{
int s_tcp; /* socket descriptor */
char *port; // server port
char *srv_adr; // server address
struct addrinfo *result, *p;
struct addrinfo hints;
int n;
char msg[MSG_LEN]; // message
char buffer[MSG_LEN]; // buffer for send and receive
srv_adr = args[1]; // first main parameter for destination address
if (argc == 3)
{
port = args[2]; // second main parameter for destination port
}
else if (argc == 2)
{
port = NULL;
}
else
{
perror("incorrect parameters");
return 1;
}
memset(&hints, 0, sizeof hints);
hints.ai_family = AF_UNSPEC; // use of IPv4 or IPv6 possible
hints.ai_socktype = SOCK_STREAM; // TCP Stream
/* serveradress as dns name oder ip address will be parsed
* and the information will be put into the struct addrinfo
* with specified IP-Address families
*/
if (getaddrinfo(srv_adr, port, &hints, &result) != 0)
{
perror("getaddrdinfo failed");
return 1;
}
/*
* result as p is a linked list
* it will be iterated to establish a connection
*/
for (p = result; p != NULL; p = p->ai_next)
{
if ((s_tcp = socket(p->ai_family, p->ai_socktype, p->ai_protocol)) == -1)
{
perror("TCP Socket");
continue;
}
if (connect(s_tcp, p->ai_addr, p->ai_addrlen) == -1)
{
perror("Connect");
continue;
}
break;
}
/*
* if a serverconnection with the infomation addrinfo is not possible
* the client will terminate
*/
if (p == NULL)
{
fprintf(stderr, "client: failed to connect\n");
return 2;
}
freeaddrinfo(result);
while (1)
{
printf("Enter command: \n");
fgets(msg, MSG_LEN, stdin);
if (strncmp(msg, QUIT, CMND_LEN) == 0)
{
printf("connection terminated\n");
close(s_tcp);
return 0;
}
else if ((strncmp(msg, PUT, CMND_LEN) == 0))
{
char *fname;
FILE *fp;
int fc;
char str[10];
char tmp[MSG_LEN];
int c;
fname = strtok(msg, " ");
fname = strtok(NULL, "\n");
fp = fopen(fname, "r");
if (fp == NULL)
{
perror("error file");
}
else
{
while ((c = fgetc(fp)) != EOF)
{
sprintf(str, "%c", c);
strncat(tmp, str, sizeof(tmp));
}
fclose(fp);
}
sprintf(msg, "%s", tmp);
}
/*
* other commands than Quit or Put will be send direct to the server
* the server decides if they are correct or not
*/
if ((send(s_tcp, msg, strlen(msg), 0)) > 0)
{
printf("Message %s sent.\n", msg);
}
/*
* received server messages will be print to console
*/
if (n = (recv(s_tcp, buffer, sizeof(buffer), 0)) > 0)
{
printf("%s\n", buffer);
}
memset(buffer, 0, strlen(buffer));
memset(msg, 0, strlen(msg));
}
close(s_tcp);
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment