acl -- One advanced C/C++ library for Unix/Windows.
Server framework and network components written by C/C++ for Linux, Mac, FreeBSD, Solaris(x86), Windows, Android, IOS
Under Other
By acl-dev
Server framework and network components written by C/C++ for Linux, Mac, FreeBSD, Solaris(x86), Windows, Android, IOS
Under Other
By acl-dev
acl -- One advanced C/C++ library for Unix/Windows.
English
一、描述
acl 工程是一个跨平台(支持LINUX,WIN32,Solaris,MacOS,FreeBSD)的网络通信库及服务器编程框架,同时提供更多的实用功能库。通过该库,用户可以非常容易地编写支持多种模式(多线程、多进程、非阻塞、触发器、UDP方式、协程方式)的服务器程序,WEB 应用程序,数据库应用程序。此外,该库还提供了常见应用的客户端通信库(如:HTTP、SMTP、ICMP、MQTT、Redis、Memcache、Beanstalk、Handler socket),常见流式编解码库:XML/JSON/MIME/BASE64/UUCODE/QPCODE/RFC2047 etc。
本工程主要包含 4 个库及大量示例。4 个库的说明如下:
1. lib_acl: 该库是最基础的库,其它 3 个库均依赖于该库; 该库以 C 语言实现。
2. lib_protocol: 该库主要实现了 http 协议及 icmp/ping 协议; 该库以 C 语言实现。
3. lib_acl_cpp: 该库用 C++ 语言封装了 lib_acl/lib_protocol 两个库,同时增加了一些其它有价值的功能应用。
4. lib_fiber: 该库为支持协程库,直接 hook 系统 read/write 等 API,与 epoll 配合支持高并发网络编程,有关协程更多内容参考 README.md。
该模块是整个 acl 网络通信最基础的流式通信模块,不仅支持网络流,同时还支持文件流,主要支持:
1. 按行读数据,兼容 win32 下的 \r\n,同时兼容 UNIX 下的 \n 的结束符
2. 按行读数据但要求自动去掉尾部的 \n 或 \r\n
3. 以字符串为分隔符读取数据
4. 读规定长度的数据
5. 尝试性读一行数据或尝试性读规定长度数据
6. 探测网络 IO 状态
7. 写入一行数据
8. 按格式符写入数据,类似于 fprintf
9. 文件流定位操作,类似于 fseek
10. 一次性写入一组数据,类似于 unix 下的 writev
11. 将文件截短,类似于 ftrunk
12. 获取文件大小
13. 获得当前文件流指针位置,类似于 ftell
14. 获得文件尺寸
15. 获得网络流的本地地址及远程地址
该模块主要支持网络服务端监听(支持 TCP/UDP/UNIX 域套接口)、网络客户端连接(支持 TCP/UNIX 域套接口)、DNS 域名查询及结果缓存(支持调用系统 gethostbyname/getaddrinfo 函数和直接发送 DNS 协议两种方式)、套接口(socket)操作及取本机网卡等功能。
支持非阻塞方式连接、读(按行读,规定长度读)、写(写行,写规定长度,写一组数据)等操作。
主要支持常见网络应用协议,诸如:HTTP、SMTP、MQTT、ICMP,其中 HTTP、MQTT、ICMP 两个模块实现了阻塞、非阻塞两种通信方式;此外,HTTP 协议在C++版的 lib_acl_cpp 中还支持服务端、客户端两种通信方式,当作为服务端使用时,支持类似于 JAVA HttpServlet 的接口使用方式,当作为客户端方式使用时,支持连接池与集群管理方式,该模块同时支持 cookie、session、HTTP MIME 文件上传、分块传输、字符集自动转换、自动解压缩、断点续传等丰富的功能。
支持 Redis、Memcached、MQTT、Beanstalk、Handler socket 客户端通信库,该通信库支持连接池方式。
支持 select(UNIX/LINUX/WIN32)、poll(UNIX/LINUX)、epoll(LINUX)、kqueue(BSD)、devpoll(solaris)、iocp(WIN32)、窗口消息(WIN32) 等系统事件引擎,同时支持 Reactor 及 Proactor 两种编程模型。
该模块是 acl 中最为重要的模块,提供了服务器编程中常用的基础设施,该服务器框架来源于著名的 Postfix,在其基础上进行了诸多扩展,有关 acl 服务器编程的更多内容介绍参见:acl服务器编程。
目前已经支持的主要服务模型有:
一个连接一个进程,这种模型的优点是编程简单、安全稳定,缺点是并发度不高;
每个子进程是由线程池中的一组线程处理所有的客户端连接,采用 IO 事件触发方式,只有当连接有数据可读时才会将连接与一个线程进行绑定,线程处理完后立即归还给线程池,这种模型的最大优点是可以用少量的线程便可以处理大量的客户端连接,而且编程比较简单(相对于非阻塞模型);
每个子进程是由一个单独的非阻塞线程组成,该线程采用完全非阻塞 IO 方式处理外来的大量客户端连接(类似于 nginx/squid/ircd),该模型的优点是处理效率高占用资源少,可以处理大量客户端连接,缺点是编程比较复杂;
虽然非阻塞服务模型可以获得大并发处理能力,但编程复杂度较高,协程模型综合了大并发的处理能力和较低的编程复杂度的特点,使编程人员可以顺序 IO 的编程方式简单实现业务逻辑;
该模型主要为了支持 UDP 网络过程而增加的服务模型;
该模型的实例主要用来处理一些定时任务的后台服务过程(类似于系统的 crontab)。
服务器框架中的子进程实用采用半驻留服务模型,支持子进程预启动机制、最大最小进程数控制、子进程异常报警、单一进程监听多个地址(可同时监听TCP/UDP套接字以及 UNIX 域套接字)、子进程安全控制、日志输出至 syslog-ng、多进程TCP连接均匀化;采用配置文件驱动方式,每个服务一个配置文件,方便进程管理及服务进程在线升级。
提供了跨平台的支持 Posix 规范的线程接口(支持WIN32);线程池模块通过多种措施最大程度地减少线程任务分配时的锁冲突(用在 acl 服务器框架中多进程多线程服务模型中)。
提供了完整的 HTTP 协议实现,支持 HTTP/1.0、1.1 版本,更多内容介绍见:Acl HTTP编程。
直接 hook 系统底层 IO API,与 epoll 配合实现网络 IO 的高并发、高性能编程框架,通过该模块可以使一些原生的常见阻塞式网络库(如 mysql/redis/http 等客户端库)直接支持高并发网络操作;通过使用该模块,编程者采用顺序思维编程方式,在协程库内部将阻塞模式转为非阻塞模式,因而大大提高了网络并发能力及处理性能。
设计了统一的数据库操作接口及连接池处理方式,目前支持 sqlite/mysql/postgresql。
采取 KEY/VALUE 分块存储方式,因为 KEY 限定为数字类型,只需内存计算便可算出 KEY 的位置,KEY 中存放了 VALUE 的位置,所以对于任何的数据查询只需两次磁盘定位。(本人在和讯做流量统计存储时,使用该种方式替代了BSD、TC 等采用B树的 K-V 存储)。
该模块提供了常见的哈希表(及多种哈希算法)、动态数组、双向链表、平衡二叉树、队列、二分块查找树、256 叉匹配树等数组结构;提供了统一的数据结构遍历方法(采用 acl_foreach)。
该模块提供三种内存池模型:
1. 基本的内存方式:内部封装了系统的 malloc/free API,提供了内存校验等安全措施;该方式同时提供外部注册接口,允许使用者注册自己的内存分配模型;
2. 内存片(slab) 方式:根据不同的尺寸大小分配多个定长内存链,可以有效地减少内存碎片,大大提升内存分配效率;
3. 内存链方式:将长度不一的小内存分配在一条内存页上,可以非常有效地使用内存,减少内存浪费。
支持字符串匹配查找、前(后)向比较、字符串分割、字符串大小写转换、H2B/B2H 转换、URL 编码/解码等功能。
支持多级目录创建、多级目录扫描、文件句柄缓存等功能,同时在处理多级目录采用循环方式,避免了递归方式时可能的栈溢出的隐患。
支持读 name=value 形式的配置文件,value 较长时可以使用反斜杠()折行,采用配置表方式提取配置文件中的配置项。
支持多组目录队列文件的创建、扫描、删除等操作;常用于临时文件队列调度的服务程序中。
支持流式方式解析 json 数据,同时支持 json 数据包组装。
支持流式方式解析 xml 数据,同时支持 xml 数据包组装。
还包括 rfc2047、url、base64、uucode、qpcode、charset 等编解码库,这些解码库均采用流式解析方式,适合于多种网络 IO 模型(阻塞/非阻塞TCP、UDP)。
整个工程目前支持 Linux(AS4,5,6, CS4,5,6, ubuntu), Windows, MacOS, FreeBSD, Solaris,Android,IOS。
* Linux/UNIX: 编译器为 gcc,直接在终端命令行方式下分别进入 lib_acl/lib_protocol/lib_acl_cpp 目录下,运行 make 命令即可。
* Windows: 可以用 VC2003/VC2008/VC2010/VC2012/vc2013/vc2015/vc2017/vc2019 进行编译。
* MacOS:可使用 xcode 进行编译。
* 同时支持 CMake 跨平台编译方式
当在 WIN32 环境下使用动态库时有几点需要注意:
* 使用 lib_acl 的动态库时,需要在用户的工程预定义: ACL_DLL;
* 使用 lib_protocol 动态库中的 HTTP 库或 ICMP 库时,需要在工程中预定义 HTTP_DLL 或 ICMP_DLL;
* 使用 lib_acl_cpp 的动态库时,需要在工程中预定义 ACL_CPP_DLL,如果您使用用 VC2003 编译环境则还需要预定义 VC2003;
* 详细编译过程,参见:acl 库的编译及使用