socket基于tcp服务端实例

socket基于tcp服务端实例

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
#include <stdlib.h>
#include <stdio.h>
#include <stdbool.h>
#include <assert.h>

#include <fcntl.h>              // Flags for open()
#include <sys/stat.h>           // Open() system call
#include <sys/types.h>          // Types for open()
#include <unistd.h>             // Close() system call
#include <string.h>             // Memory setting and copying
#include <getopt.h>             // Option parsing
#include <errno.h>              // Error codes
#include<sys/socket.h>
#include<netinet/in.h>
#include <pthread.h>


#define DEFAULT_PORT 7
#define MAXLINE 4096

int    socket_fd, connect_fd;
int    flag1;

struct test {
	int    flag1;
};

/*----------------------------------------------------------------------------
 * DMA File Transfer Functions
 *----------------------------------------------------------------------------*/

void *receive_file(void *arg)
{
	struct test *my = (struct test *)arg;
    while (1) {
    	if (my->flag1 == 1) {
    		printf("test1\n");
    	} else if (my->flag1 == 2) {
    		printf("test2\n");
    	}
    	sleep(1);
    }
//    pthread_exit(NULL);
    return NULL;
}

/*----------------------------------------------------------------------------
 * Main
 *----------------------------------------------------------------------------*/

int main(void)
{
	// Socket相关变量
    struct sockaddr_in     servaddr;
	unsigned char    buff[MAXLINE];
	int     n;
	int err;
	pthread_t tid;
	struct test *ts = (struct test *)malloc(sizeof(struct test));
	ts->flag1 = 0;


    //初始化Socket
	if( (socket_fd = socket(AF_INET, SOCK_STREAM, 0)) == -1 ) {
		printf("create socket error: %s(errno: %d)\n",strerror(errno),errno);
		exit(0);
	}
	// 解决 Address already in use 问题
    int opt = 1;
    setsockopt(socket_fd, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt));
	//初始化
	memset(&servaddr, 0, sizeof(servaddr));
	servaddr.sin_family = AF_INET;
	servaddr.sin_addr.s_addr = htonl(INADDR_ANY);//IP地址设置成INADDR_ANY,让系统自动获取本机的IP地址。
	servaddr.sin_port = htons(DEFAULT_PORT);//设置的端口为DEFAULT_PORT

	//将本地地址绑定到所创建的套接字上
	if( bind(socket_fd, (struct sockaddr*)&servaddr, sizeof(servaddr)) == -1) {
		printf("bind socket error: %s(errno: %d)\n",strerror(errno),errno);
		exit(0);
	}
	//开始监听是否有客户端连接
	if( listen(socket_fd, 2) == -1) {
		printf("listen socket error: %s(errno: %d)\n",strerror(errno),errno);
		exit(0);
	}
	printf("======waiting for client's request======\n");

	// 启动线程
	if ((err = pthread_create(&tid, NULL, &receive_file, ts)) != 0) {
		printf("err = %d, can't create thread", err);
	}
	pthread_detach(tid); //分离线程,避免僵尸进程

	while (1) {
		//阻塞直到有客户端连接,不然多浪费CPU资源。
		if( (connect_fd = accept(socket_fd, (struct sockaddr*)NULL, NULL)) == -1) {
			printf("accept socket error: %s(errno: %d)",strerror(errno),errno);
			continue;
		}
		while (1) {
			//接受客户端传过来的数据
			n = recv(connect_fd, buff, MAXLINE, 0);
			if(n > 0) {
				// 判断是开始还是停止
				if (buff[0] == 0xFA && buff[7] == 0x01) {
					ts->flag1 = 1;
					printf("start\n");
				}
				else if (buff[0] == 0xFA && buff[7] == 0x02) {
					ts->flag1 = 2;
					// 停止
					printf("stop\n");
				} else if (buff[0] == 0xFA && buff[7] == 0x03) {
					ts->flag1 = 3;
				}
			} else {
				close(connect_fd);
				break;
			}
		}
		usleep(100);
	}

    close(connect_fd);
    close(socket_fd);
    return 0;
}