免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 6529 | 回复: 10
打印 上一主题 下一主题

[技术动态] 讨论:怎样在epoll中实现全工TCP??? [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2013-09-22 12:36 |显示全部楼层 |倒序浏览
问题描述: 怎样在epoll中实现全工TCP???

场景:

epoll一直在用,但是都是在半双工模式。

一般我只把读放进epoll中,我们的应用写很少(大部分都是这种情况吧)就放在队列中等epoll timeout出来转一圈,把该写的数据写出去。

tcp是全双工的,epoll怎么来实现全双工?

思考很久,没有写例子,希望大家帮忙推导一下可能出现的问题,以及解决方案。


思路如下:

1. 启动2线程,一个读(R_EPOLL),一个写(信号量通知,建立一个key是fd的hash表-W_HASH)

2. 每accept一个socket加入R_EPOLL 和 W_HASH

3. 当没错误的时候,一切正常不表。 如果当read出错,或write出错,会发生什么情况?

3-1:read/write出错,write/read也会出错吗?
3-2:当本地或对端shutdown_read,shutdown_write 会导致对方什么情况?
3-3:会发生断开一半,而另外一半正常的情况吗?


各位CUer, 喷我吧~~~

论坛徽章:
0
2 [报告]
发表于 2013-09-22 16:57 |显示全部楼层
回复 2# linux_c_py_php


    和非阻塞读写没关系。呵呵。我的意思是在epoll中怎么来实现读写并发操作,然后出错怎么处理。

不知道大家有想过这些问题了不,我没想明白,拿出来和大家讨论下。大家随意拍。

论坛徽章:
0
3 [报告]
发表于 2013-09-24 13:15 |显示全部楼层
本帖最后由 79hy 于 2013-09-24 13:16 编辑
hanxin83 发表于 2013-09-24 09:16
同没有理解什么叫"同时读写"...


全双工就是 对一个socket同时读写。  比如1个fd,用2个线程,1个线程读,1个线程写,并行。

epoll是单线程的,监听了读写事件后,在同一时间操作fd,要不只能读,要不就只能写。这就是半双工。

我说的你们能理解吗?

论坛徽章:
0
4 [报告]
发表于 2013-09-24 13:18 |显示全部楼层
回复 6# solu


    epoll注册了读写事件后只能在同一事件单一的读或者写。不能同时读写。所以这是半双工。

论坛徽章:
0
5 [报告]
发表于 2013-09-24 13:21 |显示全部楼层
回复 5# egmkang


    同时就是想 如果有个场景是读写都比较频繁的时候,效率高点。让tcp真正的全双工。

论坛徽章:
0
6 [报告]
发表于 2013-09-24 13:23 |显示全部楼层
回复 7# kdkgod


    你的方法还是半双工的。而且频繁的去操作epoll,增加或减少事件,会很降低效率的。

论坛徽章:
0
7 [报告]
发表于 2013-09-25 16:26 |显示全部楼层
回复 22# kdkgod


    也不是一直关心写。有数据写的时候就写。没数据就阻塞休息。 主要是要同一个socket实现同时读写。

论坛徽章:
0
8 [报告]
发表于 2013-09-25 16:28 |显示全部楼层
李营长 发表于 2013-09-24 14:17
回复 17# hellioncu


如果在一个线程池里读写,怎么做到同步? 如果对一个fd进行多线程读、写, 怎么保证读出错,写怎么处理???

论坛徽章:
0
9 [报告]
发表于 2013-09-25 16:34 |显示全部楼层
本帖最后由 79hy 于 2013-09-25 16:34 编辑

回复 26# kdkgod


    谢谢。就是我就是妄想症发了。

其实我现在的处理方式是用ET模式,把IN,OUT都放到epoll里监听。

每个fd上都挂一个sendlist,和recvbuf, 1个SendEnable(SocketMap)

如果有OUT事件,就把SendEnable设置 1. 发送阻塞时设置成0.

每次epoll都0.5s超时出来都遍历一下 SocketMap. 把SendEnable 为1的 sendlist不为空的数据发出去。


我想有没有可能避免掉遍历呢???????

论坛徽章:
0
10 [报告]
发表于 2013-09-25 16:57 |显示全部楼层
kdkgod 发表于 2013-09-25 16:52
sendlist和recvbuff你是怎么实现的?
我当是也是这么干的,sendlist是每一次应用层在调send接口的时候push ...



握爪。  哈哈。


我的recvbuff相当于2块内存,1个固定大小的头,然后一个指针,根据头里的数据大小分配一个内存块。收完后push到业务层去。

sendlist就更简单了,就是个结构体+List,里面存了个已发送字节数和一个要发送的数据块。
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP