I have multiple Goroutines sharing a net.Conn object. Can they issue a Write calls simultaneously?
My main concern is that of Write calls which are partially done. Say I intend to wrote 100 bytes, but only 30 were sent, so I need to send 70 more. For this I will typically write a loop:
count := 0
for count < len(buf) {
byteSent, err := conn.Write(buf[count:])
//check error
count += byteSent
}
But I see that Go implements this loop in net.Conn.Write line number 318 and it does so by taking a lock.
However, on Windows implementation there is no such loop except that there is a call to WSASend. I do not know how WSASend behaves and could not get much from the MSDN docs
Hence the questions are:
[edit] Added 4th question
Yes, you can make many calls to a net.Conn
's write method in parallel.
Part of net.Conn
's contract is that it can be used from multiple Goroutines concurrently. This is explicitly called out in its documentation:
Conn is a generic stream-oriented network connection.
Multiple goroutines may invoke methods on a Conn simultaneously.
Though I can't speak to the Windows implementation in particular, this statement holds true for all platforms. Since there is no loop in the Windows implementation then WSASend
calls must make guarantees that the Unix API does not.
The io.Write says that in case of partial write, err will be != nil
Found here on StackOverflow that WSASend need not have a loop around it.
From #1 & #2, it implies that I need not acquire lock before calling net.Conn.Write.
So my question stands answered.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With