MSG_READALL is to recv() as ?? is to send()
From the recv(2)
man page:
MSG_WAITALL
This flag requests that the operation block until the full request is satisfied. However, the call may still return less data than requested if a signal is caught, an error or disconnect occurs, or the next data to be receiv开发者_开发百科ed is of a different type than that returned.
It doesn't look like there's an equivalent flag for send(2)
, which strikes me as strange. Maybe send()
s are guaranteed to always accept the whole buffer, but I don't see that written anywhere (and anyway, that seems unlikely to me).
Is there a way to tell send()
to wait until it's sent the whole buffer before returning, equivalently to recv()
's MSG_WAITALL
?
Edit: I understand that send() just copies data into a buffer in the operating system and that I can't force send() to put data onto the wire. My question is: Can I force send() to block until all the data I gave it has been copied into the OS's buffer?
You can't. send
just offloads the buffer to the kernel, then returns.
To quote from the Unix standard:
The
send()
function shall initiate transmission of a message from the specified socket to its peer (...) Successful completion of a call to send() does not guarantee delivery of the message.
Note the word "initiate". It doesn't actually send anything, rather tells the OS to send the message when it's ready for it (when its buffers are full or after some time has passed).
send(2)
for TCP does not actually "send" anything on the wire, but places your bytes into the socket send buffer. It tells you how many bytes it was able to copy there in the return value.
Make the send buffer bigger (see setsockopt(2)
and tcp(7)
), pay attention to the syscall return value. In any case, TCP is a stream. You need to manage application-level protocol yourself.
精彩评论