0

我想写一个服务器程序,支持一个客户端,直到现在和几天我试图发展它,我总结我需要线程。这样做的原因是因为我从wifi套接字输入并稍后处理它并最终写入文件,处理时间很慢,因此我需要一个输入线程 - >循环缓冲区 - >生产者消费者的输出线程模式这在网络编程中很常见。多线程Linux套接字编程设计

现在,情况变得复杂了,因为我需要管理客户端断开连接和重新连接。我想过使用pthread_exit()并清理所有信号量,然后在每次重新连接单个客户端时重新初始化它们。

我的问题是,这是一种有效的方法,即每次杀死线程和信号量并重新创建它们。有没有更好的解决方案。

谢谢。

回答

-1

一些意见和建议。

1-In TCP检测到对方已悄悄断开连接,如果不是不可能,则非常困难。客户端可以断开向服务器发送RST TCP消息或发送FIN消息,这是很好的例子。有时客户端可能会在没有通知的情况下断开连接(崩溃,电缆断开等)。

  • 这里的一个建议是,您考虑客户端和服务器的通信方式。例如,您可以使用函数“select”设置从客户端接收消息的超时时间并检测静默客户端。此外,根据编程语言和操作系统的不同,您可能需要处理断开的管道(SIGPIPE)信号(在Linux中,使用C/C++),对于尝试通过连接关闭的连接发送消息的服务器客户。

2-关于信号量,当客户端断开连接时,您不需要以任何特殊方式清理信号量。通过应用锁定和解锁互斥锁的常见良好做法应该足够了。同样对于像文件描述符这样的资源,您需要在通过从线程启动函数或pthread_exit返回来结束线程之前释放它们。也许我不明白这个问题的这一部分。

3 - 关于线程:如果您使用多个线程来优化工作,则需要有一个预先创建的使用者/工作线程池,它将检查循环缓冲区以使用下一个可用连接。创建和销毁线程对于操作系统来说代价很高。

  • 线程耗费资源,如果您需要创建1,000个线程,则可能会耗尽操作系统资源。

  • 另一种选择是,只有一个消费者线程异步管理所有连接(套接字):a)每个连接都有自己的状态。 b)主线程遍历所有连接并使用函数“select”来检测连接读取或写入准备就绪。 3)使用非阻塞套接字,但这不是必需的,因为从选择你知道哪些套接字已准备好并且不会阻塞。

  • 您可以使用函数select,poll,epoll。Using select() for non-blocking sockets 用一个例子其它链接:关于选择和非阻塞套接字

一个链接http://linux.die.net/man/2/select

+0

作为编辑我使用简单的标志来表示线程停止并最终加入。它适用于两个连接,第三个连接面临问题。我应该在关闭前一个套接字和新套接字时放一些延迟。 – Haswell 2014-09-02 07:40:41

+0

在为新连接创建任何新套接字fd之前,我正在关闭所有描述符。 – Haswell 2014-09-02 08:53:49

+0

你不是在使用像bind,listen,accept等标准套接字函数吗?你粘贴的代码对我来说没有多大意义。 – rodolk 2014-09-03 02:45:49

0

我的问题是,这是一个有效的方法,即每次杀死线程和信号量和重创造它们。有没有更好的解决方案。

  1. 了解如何使用非阻塞套接字和事件循环。或者使用一个为您提供TCP会话的库,使用非阻塞套接字。如boost::asio
  2. 了解如何使用多线程而不会通过使用消息传递在线程之间进行通信而不是共享状态与任何同步原语污染代码。用于非阻塞I/O的事件循环库还应提供用于跨线程消息传递的手段。