应用层poll使用例子
时间: 2023-07-11 17:52:00 浏览: 50
下面是一个简单的应用层poll使用例子:
```c
#include <stdio.h>
#include <stdlib.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <poll.h>
#define MAX_CLIENTS 10
#define BUFFER_SIZE 1024
int main(int argc, char* argv[]) {
// 创建socket
int server_fd = socket(AF_INET, SOCK_STREAM, 0);
if (server_fd < 0) {
perror("socket");
return -1;
}
// 绑定地址和端口
struct sockaddr_in addr;
addr.sin_family = AF_INET;
addr.sin_port = htons(8888);
addr.sin_addr.s_addr = INADDR_ANY;
if (bind(server_fd, (struct sockaddr*)&addr, sizeof(addr)) < 0) {
perror("bind");
return -1;
}
// 监听端口
if (listen(server_fd, 5) < 0) {
perror("listen");
return -1;
}
// 创建pollfd数组
struct pollfd fds[MAX_CLIENTS + 1];
for (int i = 0; i < MAX_CLIENTS + 1; i++) {
fds[i].fd = -1;
fds[i].events = POLLIN;
}
fds[0].fd = server_fd;
while (1) {
// 使用poll等待读取事件
int ret = poll(fds, MAX_CLIENTS + 1, -1);
if (ret < 0) {
perror("poll");
break;
}
// 处理服务器socket的读取事件
if (fds[0].revents & POLLIN) {
int client_fd = accept(server_fd, NULL, NULL);
if (client_fd < 0) {
perror("accept");
continue;
}
// 将新客户端加入pollfd数组
int i;
for (i = 1; i < MAX_CLIENTS + 1; i++) {
if (fds[i].fd == -1) {
fds[i].fd = client_fd;
break;
}
}
if (i == MAX_CLIENTS + 1) {
close(client_fd);
printf("Too many clients, connection rejected.\n");
} else {
printf("New client connected: %d\n", client_fd);
}
}
// 处理客户端socket的读取事件
for (int i = 1; i < MAX_CLIENTS + 1; i++) {
if (fds[i].fd == -1) {
continue;
}
if (fds[i].revents & POLLIN) {
char buffer[BUFFER_SIZE];
int n = recv(fds[i].fd, buffer, BUFFER_SIZE - 1, 0);
if (n < 0) {
perror("recv");
close(fds[i].fd);
fds[i].fd = -1;
} else if (n == 0) {
printf("Client disconnected: %d\n", fds[i].fd);
close(fds[i].fd);
fds[i].fd = -1;
} else {
buffer[n] = '\0';
printf("Received from client %d: %s", fds[i].fd, buffer);
}
}
}
}
// 关闭socket
close(server_fd);
return 0;
}
```
这个例子使用了poll来同时处理多个客户端的socket读取事件。在主循环中,poll等待读取事件,然后处理服务器socket的读取事件和客户端socket的读取事件。如果有新客户端连接,将其加入pollfd数组中。如果客户端断开连接或者出现错误,将其从pollfd数组中删除。