Android C++系列:Linux Socket编程(四)多路IO转接服务器

简介: select能监听的文件描述符个数受限于FD_SETSIZE,一般为1024,单纯改变进程打开 的文件描述符个数并不能改变select监听文件个数

image.png


1. select


1.select能监听的文件描述符个数受限于FD_SETSIZE,一般为1024,单纯改变进程打开 的文件描述符个数并不能改变select监听文件个数


2.解决1024以下客户端时使用select是很合适的,但如果链接客户端过多,select采用 的是轮询模型,会大大降低服务器响应效率,不应在select上投入更多精力


#include <sys/select.h>
/* According to earlier standards */ 
#include <sys/time.h>
#include <sys/types.h>
#include <unistd.h>
int select(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, struct timeval *timeout);
void FD_CLR(int fd, fd_set *set);
把文件描述符集合里fd清0


  • nfds: 监控的文件描述符集里最大文件描述符加1,因为此参数会告诉内核检测前多少个文件描述符的状态
  • readfds:监控有读数据到达文件描述符集合,传入传出参数
  • writefds:监控写数据到达文件描述符集合,传入传出参数
  • exceptfds:监控异常发生达文件描述符集合,如带外数据到达异常,传入传出参数
  • timeout:定时阻塞监控时间,3种情况


  1. NULL,永远等下去
  2. 设置timeval,等待固定时间
  3. 设置timeval里时间均为0,检查描述字后立即返回,轮询


struct timeval {
  long tv_sec;/* seconds */
  long tv_usec;/*microseconds */
};
int FD_ISSET(int fd, fd_set *set); 
void FD_SET(int fd, fd_set *set); 
void FD_ZERO(fd_set *set);
测试文件描述符集合里fd是否置1 把文件描述符集合里fd位置1 把文件描述符集合里所有位清0


2. poll


#include <poll.h>
int poll(struct pollfd *fds, nfds_t nfds, int timeout);
struct pollfd { 
  int fd; /* 文件描述符 */
  short events; /* 监控的事件 */
  short revents;/* 监控事件中满足条件返回的事件 */
};


  • POLLIN普通或带外优先数据可读,即POLLRDNORM | POLLRDBAND
  • POLLRDNORM-数据可读
  • POLLRDBAND-优先级带数据可读
  • POLLPRI 高优先级可读数据
  • POLLOUT普通或带外数据可写
  • POLLWRNORM-数据可写
  • POLLWRBAND-优先级带数据可写
  • POLLERR 发生错误
  • POLLHUP 发生挂起 POLLNVAL 描述字不是一个打开的文件


nfds 监控数组中有多少文件描述符需要被监控 timeout 毫秒级等待


  • -1:阻塞等,#define INFTIM -1 Linux中没有定义此宏


  • 0:立即返回,不阻塞进程


  • 0:等待指定毫秒数,如当前系统时间精度不够毫秒,向上取值


如果不再监控某个文件描述符时,可以把pollfd中,fd设置为-1,poll不再监控此 pollfd,下次返回时,把revents设置为0。


ppoll GNU定义了ppoll(非POSIX标准),可以支持设置信号屏蔽字,可参考poll模型自 行实现C/S


3. epoll


epoll是Linux下多路复用IO接口select/poll的增强版本,它能显著提高程序在大量并 发连接中只有少量活跃的情况下的系统CPU利用率,因为它会复用文件描述符集合来传递结 果而不用迫使开发者每次等待事件之前都必须重新准备要被侦听的文件描述符集合,另一点 原因就是获取事件的时候,它无须遍历整个被侦听的描述符集,只要遍历那些被内核IO事件 异步唤醒而加入Ready队列的描述符集合就行了。


目前epell是linux大规模并发网络程序中的热门首选模型。


epoll除了提供select/poll那种IO事件的电平触发(Level Triggered)外,还提 供了边沿触发(Edge Triggered),这就使得用户空间程序有可能缓存IO状态,减少 epoll_wait/epoll_pwait的调用,提高应用程序效率。


一个进程打开大数目的socket描述符cat /proc/sys/fs/file-max


4. 总结


本文介绍了Linux多路复用的三种技术:select、poll、epoll。

目录
相关文章
|
Linux API 开发工具
FFmpeg开发笔记(五十九)Linux编译ijkplayer的Android平台so库
ijkplayer是由B站研发的移动端播放器,基于FFmpeg 3.4,支持Android和iOS。其源码托管于GitHub,截至2024年9月15日,获得了3.24万星标和0.81万分支,尽管已停止更新6年。本文档介绍了如何在Linux环境下编译ijkplayer的so库,以便在较新的开发环境中使用。首先需安装编译工具并调整/tmp分区大小,接着下载并安装Android SDK和NDK,最后下载ijkplayer源码并编译。详细步骤包括环境准备、工具安装及库编译等。更多FFmpeg开发知识可参考相关书籍。
625 0
FFmpeg开发笔记(五十九)Linux编译ijkplayer的Android平台so库
|
网络协议 Linux 网络性能优化
Linux基础-socket详解、TCP/UDP
综上所述,Linux下的Socket编程是网络通信的重要组成部分,通过灵活运用TCP和UDP协议,开发者能够构建出满足不同需求的网络应用程序。掌握这些基础知识,是进行更复杂网络编程任务的基石。
538 1
|
Java Android开发 C++
🚀Android NDK开发实战!Java与C++混合编程,打造极致性能体验!📊
在Android应用开发中,追求卓越性能是不变的主题。本文介绍如何利用Android NDK(Native Development Kit)结合Java与C++进行混合编程,提升应用性能。从环境搭建到JNI接口设计,再到实战示例,全面展示NDK的优势与应用技巧,助你打造高性能应用。通过具体案例,如计算斐波那契数列,详细讲解Java与C++的协作流程,帮助开发者掌握NDK开发精髓,实现高效计算与硬件交互。
598 1
|
网络协议 测试技术 网络安全
Python编程-Socket网络编程
Python编程-Socket网络编程
195 0
|
Java Android开发 C++
🚀Android NDK开发实战!Java与C++混合编程,打造极致性能体验!📊
【7月更文挑战第28天】在 Android 开发中, NDK 让 Java 与 C++ 混合编程成为可能, 从而提升应用性能。**为何选 NDK?** C++ 在执行效率与内存管理上优于 Java, 特别适合高性能需求场景。**环境搭建** 需 Android Studio 和 NDK, 工具如 CMake。**JNI** 构建 Java-C++ 交互, 通过声明 `native` 方法并在 C++ 中实现。**实战** 示例: 使用 C++ 计算斐波那契数列以提高效率。**总结** 混合编程增强性能, 但增加复杂性, 使用前需谨慎评估。
518 4
|
网络协议 开发者 Python
深度探索Python Socket编程:从理论到实践,进阶篇带你领略网络编程的魅力!
【7月更文挑战第25天】在网络编程中, Python Socket编程因灵活性强而广受青睐。本文采用问答形式深入探讨其进阶技巧。**问题一**: Socket编程基于TCP/IP,通过创建Socket对象实现通信,支持客户端和服务器间的数据交换。**问题二**: 提升并发处理能力的方法包括多线程(适用于I/O密集型任务)、多进程(绕过GIL限制)和异步IO(asyncio)。**问题三**: 提供了一个使用asyncio库实现的异步Socket服务器示例,展示如何接收及响应客户端消息。通过这些内容,希望能激发读者对网络编程的兴趣并引导进一步探索。
273 4
|
开发者 Python
Python Socket编程:不只是基础,更有进阶秘籍,让你的网络应用飞起来!
【7月更文挑战第25天】在网络应用蓬勃发展的数字时代,Python凭借其简洁的语法和强大的库支持成为开发高效应用的首选。本文通过实时聊天室案例,介绍了Python Socket编程的基础与进阶技巧,包括服务器与客户端的建立、数据交换等基础篇内容,以及使用多线程和异步IO提升性能的进阶篇。基础示例展示了服务器端监听连接请求、接收转发消息,客户端连接服务器并收发消息的过程。进阶部分讨论了如何利用Python的`threading`模块和`asyncio`库来处理多客户端连接,提高应用的并发处理能力和响应速度。掌握这些技能,能使开发者在网络编程领域更加游刃有余,构建出高性能的应用程序。
178 3
|
网络协议 Python
网络世界的建筑师:Python Socket编程基础与进阶,构建你的网络帝国!
【7月更文挑战第26天】在网络的数字宇宙中,Python Socket编程是开启网络世界大门的钥匙。本指南将引领你从基础到实战,成为网络世界的建筑师。
268 2
|
消息中间件 网络协议 网络安全
Python Socket编程:打造你的专属网络通道,基础篇与进阶篇一网打尽!
【7月更文挑战第26天】在网络编程领域,Python以简洁语法和强大库支持成为构建应用的首选。Socket编程为核心,实现计算机间的数据交换。
276 1