我有一个显示日志输出到stdout的程序。
因此,如果我打开一个telnet会话到我的目标linux,然后在这个telnet会话上启动我的程序,那么我将在我的telnet会话上显示日志消息。
在我的程序中,我运行了一个小http服务器。现在,如果我更改目标linux的IP地址,然后我重新启动接口(http服务器将自动重启,因为我通过netlink检测到IP地址的更改)然后我将关闭telnet会话并重定向stdout消息到我的http服务器打开的套接字,我将锁定日志消息的printf。
我尝试使用select检测此锁定但未成功:How to use select with stdout?
在转到prinf(锁定)之前选择返回成功
有任何建议可以避免这个问题吗?
答案 0 :(得分:0)
如果我理解正确的话,由于IP地址的变化,运行HTTP服务器的telnet会话(你为什么不使用SSH?)会被破坏。
如果程序继续将数据写入此会话(这是它的标准输出)之后会发生什么,首先写入将在系统缓冲数据时成功,然后最终写入将阻塞(不是“锁定” “)。最后,TCP连接将超时,写入将返回错误。 TCP会话可能需要或可能不需要很长时间才能超时,但它最终会实现。
如果要避免阻塞,可以使日志输出代码对stdout使用非阻塞写入(例如,如果您的应用程序是事件驱动且不能阻止)。您将需要使用fcntl
将stdout更改为非阻塞,并且您可能需要完全避免使用stdio,因为stdio不适用于非阻塞输出。您必须实现自己的缓冲并直接写入文件描述符1。
您还提到要在stdout日志损坏后登录到HTTP连接。你也可以这样做(一旦你收到写入stdout的错误就触发),但这将是更多的工作。您必须在应用程序内部管理日志缓冲区,直到HTTP客户端连接并请求它。如果没有HTTP客户端连接,您还需要添加一个用于丢弃日志的条款(如果日志太大)。所有这些都是SO问题的范围......