epoll+socket實現 socket併發 linux伺服器
/* 實現功能:通過epoll, 處理多個socket
* 監聽一個埠,監聽到有連結時,新增到epoll_event
* xs
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <poll.h>
#include <sys/epoll.h>
#include <sys/time.h>
#include <netinet/in.h>
#define MYPORT 12345
//最多處理的connect
#define MAX_EVENTS 500
//當前的連線數
int currentClient = 0;
//資料接受 buf
#define REVLEN 10
char recvBuf[REVLEN];
//epoll描述符
int epollfd;
//事件陣列
struct epoll_event eventList[MAX_EVENTS];
void AcceptConn(int srvfd);
void RecvData(int fd);
int main()
{
int i, ret, sinSize;
int recvLen = 0;
fd_set readfds, writefds;
int sockListen, sockSvr, sockMax;
int timeout;
struct sockaddr_in server_addr;
struct sockaddr_in client_addr;
//socket
if((sockListen=socket(AF_INET, SOCK_STREAM, 0)) < 0)
{
printf("socket error\n");
return -1;
}
bzero(&server_addr, sizeof(server_addr));
server_addr.sin_family = AF_INET;
server_addr.sin_port = htons(MYPORT);
server_addr.sin_addr.s_addr = htonl(INADDR_ANY);
//bind
if(bind(sockListen, (struct sockaddr*)&server_addr, sizeof(server_addr)) < 0)
{
printf("bind error\n");
return -1;
}
//listen
if(listen(sockListen, 5) < 0)
{
printf("listen error\n");
return -1;
}
// epoll 初始化
epollfd = epoll_create(MAX_EVENTS);
struct epoll_event event;
event.events = EPOLLIN|EPOLLET;
event.data.fd = sockListen;
//add Event
if(epoll_ctl(epollfd, EPOLL_CTL_ADD, sockListen, &event) < 0)
{
printf("epoll add fail : fd = %d\n", sockListen);
return -1;
}
//epoll
while(1)
{
timeout=3000;
//epoll_wait
int ret = epoll_wait(epollfd, eventList, MAX_EVENTS, timeout);
if(ret < 0)
{
printf("epoll error\n");
break;
}
else if(ret == 0)
{
printf("timeout ...\n");
continue;
}
//直接獲取了事件數量,給出了活動的流,這裡是和poll區別的關鍵
int i = 0;
for(i=0; i<ret; i++)
{
//錯誤退出
if ((eventList[i].events & EPOLLERR) ||
(eventList[i].events & EPOLLHUP) ||
!(eventList[i].events & EPOLLIN))
{
printf ( "epoll error\n");
close (eventList[i].data.fd);
return -1;
}
if (eventList[i].data.fd == sockListen)
{
AcceptConn(sockListen);
}else{
RecvData(eventList[i].data.fd);
}
}
}
close(epollfd);
close(sockListen);
return 0;
}
/**************************************************
函式名:AcceptConn
功能:接受客戶端的連結
引數:srvfd:監聽SOCKET
***************************************************/
void AcceptConn(int srvfd)
{
struct sockaddr_in sin;
socklen_t len = sizeof(struct sockaddr_in);
bzero(&sin, len);
int confd = accept(srvfd, (struct sockaddr*)&sin, &len);
if (confd < 0)
{
printf("bad accept\n");
return;
}else
{
printf("Accept Connection: %d", confd);
}
//將新建立的連線新增到EPOLL的監聽中
struct epoll_event event;
event.data.fd = confd;
event.events = EPOLLIN|EPOLLET;
epoll_ctl(epollfd, EPOLL_CTL_ADD, confd, &event);
}
//讀取資料
void RecvData(int fd)
{
int ret;
int recvLen = 0;
memset(recvBuf, 0, REVLEN);
printf("RecvData function\n");
if(recvLen != REVLEN)
{
while(1)
{
//recv資料
ret = recv(fd, (char *)recvBuf+recvLen, REVLEN-recvLen, 0);
if(ret == 0)
{
recvLen = 0;
break;
}
else if(ret < 0)
{
recvLen = 0;
break;
}
//資料接受正常
recvLen = recvLen+ret;
if(recvLen<REVLEN)
{
continue;
}
else
{
//資料接受完畢
printf("buf = %s\n", recvBuf);
recvLen = 0;
break;
}
}
}
printf("data is %s", recvBuf);
}
相關文章
- 使用socket+gevent實現協程併發
- 用PHP實現高併發伺服器PHP伺服器
- TCP併發伺服器的程式設計實現TCP伺服器程式設計
- C# 實現socket通訊程式(伺服器端)C#伺服器
- socket程式設計實現tcp伺服器_C/C++程式設計TCP伺服器C++
- Netty實現Web SocketNettyWeb
- Tomcat實現Web SocketTomcatWeb
- curl_multi實現併發
- Socket Server 的 N 種併發模型彙總Server模型
- Socket Server的N種併發模型彙總Server模型
- python中socket+threading的自定義併發Pythonthread
- Spring Boot實現Web SocketSpring BootWeb
- socket實現聊天功能(二)
- php原生socket之IO多路複用以及實現web伺服器PHPWeb伺服器
- Linux socket APILinuxAPI
- python——socket實現簡單C/S互動開發Python
- 《初識TCP》iOS、macOS實現socket client與socket serverTCPiOSMacclientServer
- 在Go中如何實現併發Go
- Redis實現併發阻塞鎖方案Redis
- 併發Lock之ReentrantLock實現原理ReentrantLock
- java併發之SynchronousQueue實現原理Java
- Linux 併發與競爭實驗學習Linux
- socket 實現的 web 伺服器在 Windows 下的讀寫問題Web伺服器Windows
- Linux開發板(樹莓派)和伺服器進行雙向通訊(socket)Linux樹莓派伺服器
- Hyperf-Socket.io實現私聊
- Linux 伺服器如何實現資料同步?Linux伺服器
- 實現伺服器和客戶端資料互動,Java Socket有妙招伺服器客戶端Java
- 使用Python語言通過PyQt5和socket實現UDP伺服器PythonQTUDP伺服器
- Nginx 實現高併發的原理分析Nginx
- django框架怎麼實現高併發Django框架
- Golang 併發程式設計(channel實現)Golang程式設計
- 併發機制的底層實現
- 用go實現併發聊天室Go
- Java併發指南9:AQS共享模式與併發工具類的實現JavaAQS模式
- 《java併發程式設計的藝術》併發底層實現原理Java程式設計
- socket實現簡單ssh服務
- UNIX Domain Socket實現簡易聊天AI
- node.js 用socket實現聊天Node.js