| ioPAC RTU Controllers C/C++ Sample Code Programming Guide

- Main Page
- Modules
- Data Structures
- Files

- File List
- Globals

Macros | Functions
server_tcp_echo.c File Reference

Server TCP Echo More...

`#include <stdio.h>`
`#include <stdlib.h>`
`#include <errno.h>`
`#include <string.h>`
`#include <unistd.h>`
`#include <netinet/in.h>`
`#include <sys/types.h>`
`#include <sys/socket.h>`
`#include <sys/wait.h>`
`#include <sys/time.h>`
`#include <pthread.h>`

## Macros
#define | BUFFER_SIZE 32

## Functions
void | connectionThread (void *parameter)
int | main (int argc, char *argv[])

## Detailed Description

Server TCP Echo

Copyright
  Moxa Inc.

Date
  04-10-2013

Author
  Eddy Kao

Version
  V1.0
  Server TCP Echo

    Introduction:
    The Server will echo each byte that is sent by the Client.
    Example:
    1. Using default: ./server_tcp_echo
    2. Setting port: ./server_tcp_echo -p1234
    Default:
    Port = 2323
    Help:

    root@Moxa:/tmp#./server_tcp_echo -h
    Echo Server, server program.

    Usage: ./server_tcp_echo [OPTIONS]

    Options:
            -p       Port [0-65535]. Default port = 2323

## Macro Definition Documentation

#define BUFFER_SIZE 32

## Function Documentation

void connectionThread | ( | void * | parameter | ) |

int main | ( | int | argc,
|  | char * | argv[]
| ) |  |

/*******************************************************************************
* Copyright Moxa Inc.
*
* Echo Server(server)
*
* Date Author Comment
* 04-10-2013 Eddy Kao Created.
******************************************************************************/
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <unistd.h>
#include <netinet/in.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/wait.h>
#include<sys/time.h>
#include<sys/types.h>
#include <pthread.h>
#define BUFFER_SIZE 32
void connectionThread(void *parameter)
{
int newfd = (int)parameter;
int idleTimeout = 30; //30 seconds
int exitFlag = 0;
int nBytes = 0;
char buf[BUFFER_SIZE];
fd_set fdread;
fd_set fdwrite;
struct timeval timeout;
FD_ZERO(&fdread);
FD_SET(newfd, &fdread);
FD_ZERO(&fdwrite);
FD_SET(newfd, &fdwrite);
while(1)
{
timeout.tv_sec = idleTimeout;
timeout.tv_usec = 0;
switch(select(newfd + 1, &fdread, NULL, NULL, &timeout))
{
case -1:
printf("Server: connection[%d] closed.\r\n", newfd);
exitFlag = 1;
close(newfd);
break;
case 0:
printf("Server: connection[%d] timeout, closed.\r\n", newfd);
exitFlag = 1;
close(newfd);
break;
default:
if(FD_ISSET(newfd, &fdread))
{
timeout.tv_sec = idleTimeout;
timeout.tv_usec = 0;
//Receive
memset(buf, 0, sizeof(buf));
nBytes = read(newfd, buf, sizeof(buf));
if(nBytes == -1 || nBytes == 0)
{
printf("Server: connection[%d] closed.\r\n", newfd);
exitFlag = 1;
close(newfd);
break;
}
printf("Server: connection[%d] reads %d bytes.\r\n", newfd, nBytes);
timeout.tv_sec = idleTimeout;
timeout.tv_usec = 0;
if(select(newfd + 1, NULL, &fdwrite, NULL, &timeout) > 0)
{
if(FD_ISSET(newfd, &fdwrite))
{
//Send
nBytes = write(newfd, buf, nBytes);
if(nBytes == -1 || nBytes == 0)
{
printf("Server: connection[%d] closed.\r\n", newfd);
exitFlag = 1;
close(newfd);
break;
}
}
}
printf("Server: connection[%d] writes %d bytes.\r\n", newfd, nBytes);
}
break;
}
if(exitFlag == 1) break;
}
}
int main(int argc, char* argv[])
{
int rc = 0;
int sinSize = 0;
int sockfd = 0;
int newfd = 0;
int backlog = 10;
unsigned short port = 2323; //Default port
int reuseaddr = 1;
socklen_t reuseaddr_len = sizeof(reuseaddr);
pthread_t thread;
struct sockaddr_in sockAddress;
struct sockaddr_in clientAddress;
while((rc = getopt(argc, argv, "hp:")) != -1)
{
switch(rc)
{
case 'p':
port = atoi(optarg);
break;
case '?':
case 'h':
default:
printf("Echo Server, server program.\n\n");
printf("Usage: ./server_tcp_echo [OPTIONS]\n\n");
printf("Options:\n");
printf("\t%-8s Port [%d-%d]. Default port = %d\n", "-p", 0, 65535, port);
printf("\n");
return 0;
}
}
if((sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1) //TCP connection
{
perror("socket");
exit(1);
}
sockAddress.sin_family = AF_INET;
sockAddress.sin_port = htons(port);
sockAddress.sin_addr.s_addr = htonl(INADDR_ANY);
bzero(&(sockAddress.sin_zero), 8);
setsockopt(sockfd, SOL_SOCKET, SO_REUSEADDR, &reuseaddr, reuseaddr_len);
if(bind(sockfd, (struct sockaddr*)&sockAddress, sizeof(struct sockaddr)) == -1)
{
close(sockfd);
perror("bind");
exit(1);
}
if(listen(sockfd, backlog) == -1)
{
close(sockfd);
perror("listen");
exit(1);
}
sinSize = sizeof(struct sockaddr_in);
printf("Server: started at port:%d.\r\n", port);
while(1)
{
if((newfd = accept(sockfd, (struct sockaddr*)&clientAddress, &sinSize)) == -1)
{
close(sockfd);
perror("accept");
exit(1);
}
rc = pthread_create(&thread, NULL, (void *)connectionThread, (void *)newfd);
if(rc != 0)
{
close(newfd);
continue;
}
else
{
pthread_detach(thread);
printf("Server: connection[%d] established.\r\n", newfd);
}
}
close(sockfd);
return 0;
}