Code in question:
// Flush writes any buffered data to the underlying io.Writer.
func (b *Writer) Flush() error {
if b.err != nil {
return b.err
}
if b.n == 0 {
return nil
}
n, err := b.wr.Write(b.buf[0:b.n])
if n < b.n && err == nil {
err = io.ErrShortWrite
}
if err != nil {
if n > 0 && n < b.n {
copy(b.buf[0:b.n-n], b.buf[n:b.n])
}
b.n -= n
b.err = err
return err
}
b.n = 0
return nil
}
Consider that underlying io.Writer is a TCP socket. Under system load,
partial write can occur and write() system call does not consider partial
write as an error (see man 2 write). In other words, if n < b.n, only some
data got written to the underlying io.Writer and this in itself is not an
erro. bufio is expected to handle this by keep the bytes not yet written
in the buffer so that those bytes will get written in future (code above
does this: copy(b.buf[0:b.n-n], b.buf[n:b.n]). However, the Flush() code
is buggy (unless I am missing something). It sets b.err to
io.ErrShortWrite if n < b.n and any further Flush() call by client to
continue to write to the underlying io.Writer bails out as the first line
of this function checks for b.err. b.err never gets cleared, and as a
result no further writes can occur.
I don't see anything else in bufio that would clear b.err. How is this
supposed to work when underlying io.Writer only write partial data.
Regards,
Bhupesh
--
You received this message because you are subscribed to the Google Groups
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/d/optout.