老师交给小明一个开发任务,实现一个TCP网络迭代并发服务器,用于回射任何接收到的通讯数据。小明很懒,他在开源中国项目库里搜到了开源库tcpdaemon来帮助他快速完成任务。首先他安装好tcpdaemon,然后写了一个C程序文件test_callback_echo.c
$ vi test_callback_echo.c
_WINDLL_FUNC int tcpmain( struct TcpdaemonServerEnvirment p_env , int sock , void p_addr ) { char buffer[ 4096 ] ; long len ;
len = recv( sock , buffer , sizeof(buffer) , 0 ) ; if( len <= 0 ) return len;
len = send( sock , buffer , len , 0 ) ; if( len < 0 ) return len;
return 0; }
他编译链接成动态库test_callback_echo.so,最后用tcpdaemon直接挂接执行
$ tcpdaemon -m IF -l 0:9527 -s test_callback_echo.so -c 10 –tcp-nodelay –logfile $HOME/log/test_callback_echo.log
OK,总共花了五分钟,圆满完成老师作业。老师说这个太简单了,小明你给我改成像Apache经典的Leader- Follow服务端模型,小明说没问题,他把启动命令参数-m IF改成了-m LF,再次执行,完成老师要求,总共花了五秒钟。老师问你怎么这么快就改好了,小明说全靠开源项目tcpdaemon帮了大忙啊 ^_^
-m IF
-m LF
tcpdaemon是一个TCP通讯服务端平台/库,它封装了众多常见服务端进程/线程管理和TCP连接管理模型(Forking、Leader- Follow、IO-Multiplex、WindowsThreads Leader- Follow),使用者只需加入TCP通讯数据收发和应用逻辑代码就能快速构建出完整的TCP应用服务器。
服务模型模型说明 Forking : 单进程主守护,每当一条TCP新连接进来后,接受之,创建子进程进入回调函数tcpmain处理之。一条连接对应一个子进程(短生命周期) Leader-Follow : 单进程管理进程,预先创建一组子进程(长生命周期)并监控其异常重启。子进程等待循环争抢TCP新连接调用回调函数tcpmain处理之 IO-Multiplex : 单进程主守护,IO多路复用等待TCP新连接进来事件、TCP数据到来事件,TCP数据可写事件,调用回调函数tcpmain处理之 WindowsThreads Leader-Follow : 同Leader-Follow,区别在于预先创建一组子线程而非子进程
tcpdaemon提供了三种与使用者代码对接方式:(注意:.exe只是为了说明自己是可执行文件,在UNIX/Linux中可执行文件一般没有扩展名) 回调模式 : tcpdaemon.exe+user.so(tcpmain) | 可执行程序tcpdaemon通过启动命令行参数挂接用户动态库,获得动态库中函数tcpmain指针。当建立TCP连接后 或 IO多路复用模式下当可读可写事件发生时 调用回调函数tcpmain 主调模式 : user.exe(main,tcpmain)+libtcpdaemon.a(tcpdaemon) | 用户可执行程序user.exe隐式链接库libtcpdaemon.a。用户函数main(user.exe)初始化tcpdaemon参数结构体,并设置回调函数tcpmain,调用函数tcpdaemon(libtcpdaemon.so)。当建立TCP连接后 或 IO多路复用模式下当可读可写事件发生时 调用回调函数tcpmain 主调+回调模式 : user.exe(main)+libtcpdaemon.a(tcpdaemon) + user.so(tcpmain) | 同上,区别在于用户函数main不直接设置回调函数tcpmain而设置user.so文件名。函数tcpdaemon负责挂接动态库user.so并获得函数tcpmain指针
一般简单情况下,使用者采用回调模式即可,只要编写一个动态库user.so(内含回调函数tcpmain)被可执行程序tcpdaemon挂接上去运行。如果使用者想订制一些自定义处理,如初始化环境,可以采用主调模式,实现函数main里把自定义参数传递给tcpdaemon穿透给tcpmain。如果想实现运行时选择回调函数tcpmain则可以采用主调+回调模式。