现在的位置: 首页 > 综合 > 正文

UNIX域套接字

2013年10月12日 ⁄ 综合 ⁄ 共 2516字 ⁄ 字号 评论关闭

记在此处,怕给忘记了

#include <iostream>
#include <vector>
#include <sys/types.h>
#include <sys/un.h>   // struct sockaddr_un
#include <sys/stat.h>
#include <sys/socket.h>
#include <sys/epoll.h>
#include <sys/time.h>  // gettimeofday()
#include <netinet/in.h>  // struct in_addr
#include <arpa/inet.h> // inet_aton()
#include <unistd.h>  // getpid()
#include <signal.h>
#include <fcntl.h>
#include <cerrno>
using namespace std;
#define MAX_CONNECT 10
void nothing(int i)
{
	cerr << "signal: " << i << endl;
}
void rmsocket(int)
{
	unlink("/home/whh/fym/gcc/c"); //bind(): Address already in use
}
int main()
{
	int nconn = 0;
	int nacc = 0;
	bool maxconn = false;  

	signal(SIGINT,rmsocket);
	int n;
	cout << getpid() << endl;
	char buf[BUFSIZ];
	struct sockaddr_un addr;
	struct sockaddr_un cli_addr;
	socklen_t cli_len = sizeof cli_addr;
	memset(&addr,0,sizeof addr);

	short port;
	int fd = socket(PF_UNIX,SOCK_STREAM,0);
	if(fd < 0)
	{
		perror("socket()");
		return 1;
	}

	int flags = fcntl(fd,F_GETFL,0);
	flags |= O_NONBLOCK;
	//fcntl(fd,F_SETFL,flags);
	
	addr.sun_family = AF_UNIX;
        unlink("/home/whh/fym/gcc/c");
        strcpy(addr.sun_path,"/home/whh/fym/gcc/c");

	n = bind(fd,(struct sockaddr*) &addr,sizeof(addr));
	if(n < 0)
	{  //如果addr.sun_path所指的路径已经存在,则出错
		perror("bind()");  //Address already in use.
		return 2;
	}

	n = listen(fd,2);
	if(n < 0)
	{
		perror("listen()");
		return 3;
	}

	vector<int> fdvec;
	fdvec.push_back(fd);

	struct epoll_event ev = {0};
	int kfd = epoll_create(MAX_CONNECT+1);
	if(kfd < 0)
	{
		perror("epoll_create");
		return 4;
	}
	ev.data.fd = fd;
	ev.events = EPOLLIN | EPOLLET;
	n = epoll_ctl(kfd,EPOLL_CTL_ADD,fd,&ev);
	if(n < 0)
	{
		perror("epoll_ctl()");
		return 5;
	}

	while(1)
	{
		struct epoll_event events[20];
		memset(events,0,sizeof events);
		cerr << "epoll_wait..." << "total:" << nconn;
		n = epoll_wait(kfd,events,MAX_CONNECT+1,-1);
		cerr << " Done. "<<n<<endl;
		if(n < 0)
		{
			perror("epoll_wait");
			return 6;
		}
		else if(0 == n)
		{
			cout << "Timeout." << endl;
			continue;
		}
		else
		{
			for(int i=0; i<n; ++i)
			{
				if(events[i].data.fd == fd)
				{ // accept
					int newfd = accept(fd,(struct sockaddr*)&cli_addr,&cli_len);
					cerr << "accept:" << newfd << endl;
					if(newfd < 0)
					{
						perror("accept()");
						return 5;
					}
					ev.data.fd = newfd;
					ev.events = EPOLLIN | EPOLLET;
					epoll_ctl(kfd,EPOLL_CTL_ADD,newfd,&ev);
					if(++nconn >= MAX_CONNECT)
					{
						ev.data.fd = fd;
						epoll_ctl(kfd,EPOLL_CTL_DEL,fd,&ev);
						maxconn = true;
					}

				}
				else if(events[i].events & EPOLLIN)
				{ // read
					char buf[BUFSIZ] = {0};
					int n = read(events[i].data.fd,buf,sizeof(buf));
					cerr << "read " <<n<<"bytes"<<endl;
					if(n < 0)
					{
						perror("read()");
						if(EINTR == errno)
						{
							continue;
						}
						return 6;
					}
					if(0 == n)
					{ // client closed or network down.
						close(events[i].data.fd);
						--nconn;
						if(maxconn)
						{
							maxconn = false;
							ev.data.fd = fd;
							ev.events = EPOLLIN | EPOLLET;
							epoll_ctl(kfd,EPOLL_CTL_ADD,fd,&ev);
						}
						continue;
					}
					int m = write(events[i].data.fd,buf,n);
					if(m < 0)
					{
						perror("write()");
						return 7;
					}
				}
			} // for.
		}

	} //while(1)

	return 0;
}

抱歉!评论已关闭.