2013-04-22 61 views
0

我有一个用于交换消息的TCP流连接。这是在Linux内核中。消费者线程不断处理传入的消息。消费一条消息后,我想检查是否有更多待处理消息;在这种情况下,我也会处理它们。我的代码实现这个如下所示。 krecv是sock_recvmsg()的包装,传递标志的值无需修改(krecv从ksocket kernel模块)recv带有标志MSG_DONTWAIT | TCP套接字上的MSG_PEEK

有了MSG_DONTWAIT,我期待它不应该阻塞,但显然它会阻塞。使用MSG_PEEK,如果没有要读取的数据,它应该只返回零。这种理解是否正确?有没有更好的方法来实现我在这里需要的?我猜这应该是一个常见的要求,因为跨节点的消息传递经常使用。

int recvd = 0; 

do { 
      recvd += krecv(*sockp, (uchar*)msg + recvd, sizeof(my_msg) - recvd, 0); 
      printk("recvd = %d/%lu\n", recvd, sizeof(my_msg)); 
} while(recvd < sizeof(my_msg)); 
BUG_ON(recvd != sizeof(my_msg)); 

/* For some reason, below line _blocks_ even with no blocking flags */ 
recvd = krecv(*sockp, (uchar*)tempbuf, sizeof(tempbuf), MSG_PEEK | MSG_DONTWAIT); 
if (recvd) { 
      printk("more data waiting to be read"); 
      more_to_process = true; 
} else { 
      printk("NO more data waiting to be read"); 
} 
+0

哪一个适合我提到的上述情况?如果流中没有任何内容,我不希望我的线程阻塞。 – spa 2013-04-30 14:00:07

+0

MSG_DONTWAIT不应该阻塞。 – EJP 2016-08-31 02:34:36

回答

0

你可能会首先检查缓冲区的长度:

int bytesAv = 0; 
ioctl(m_Socket,FIONREAD,&bytesAv); //m_Socket is the socket client's fd 

如果在它的数据,然后与MSG_PEEK recv的不应该被阻止, 如果没有数据的话,那么没有必要MSG_PEEK, 这可能是你喜欢做的事情。