Do iov_len and iov_base have to be reset after EAGAIN on kernel_recvmsg?

From: Steve French
Date: Mon Nov 03 2008 - 14:47:25 EST


In cifs_demultiplex_thread Shirish suggested changing the following to
handle the case in which EAGAIN is returned from kernel_recvmsg and
has corrupted the value of iov_len and iov_base

--- a/fs/cifs/connect.c
+++ b/fs/cifs/connect.c
@@ -417,10 +417,16 @@ incomplete_rcv:
msleep(1); /* minimum sleep to prevent looping
allowing socket to clear and app threads to set
tcpStatus CifsNeedReconnect if server hung */
- if (pdu_length < 4)
+ if (pdu_length < 4) {
+ iov.iov_base = (4 - pdu_length) +
+ (char *)smb_buffer;
+ iov.iov_len = pdu_length;
+ smb_msg.msg_control = NULL;
+ smb_msg.msg_controllen = 0;
goto incomplete_rcv;

based on Sridhar's comment:

"i think you are running into a case where kernel_recvmsg() is called
via 'goto incomplete_rcv'
It happens if the previous call fails with EAGAIN. If you want to
call recvmsg() after EAGAIN failure, you need to reset iov."

It sounds strange to reset iov_len and iov_base on EAGAIN or ENOSPACE
from the socket, but seems harmless ... but what about resetting
msg_control and msg_controllen ... is that ever necessary? Is that
safe?

--
Thanks,

Steve
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/