]> Cypherpunks repositories - gostls13.git/commitdiff
net/textproto: properly write terminating sequence if DotWriter is closed with no...
authorDaniel Cormier <danielc@knowbe4.com>
Fri, 10 Nov 2017 16:50:13 +0000 (11:50 -0500)
committerBrad Fitzpatrick <bradfitz@golang.org>
Thu, 28 Mar 2019 20:27:10 +0000 (20:27 +0000)
Fixed textproto.Writer.DotWriter() to properly write \r\n.\r\n to the buffer
when Close() is called without any bytes written. This properly writes the
terminating sequence outlined in RFC 5321 section 4.1.1.4 and RFC 3977
section 3.1.1, even when no other bytes are written.

Change-Id: I262fd2963ee76fff7ffae8e3cb0e86255694b361
Reviewed-on: https://go-review.googlesource.com/c/go/+/77350
Reviewed-by: Brad Fitzpatrick <bradfitz@golang.org>
src/net/textproto/writer.go
src/net/textproto/writer_test.go

index 1bc5974c6c2f3df3d266d890e3eb505d1307edf8..33c146c02204042402c964e0b9f8d2fe38d513d8 100644 (file)
@@ -58,7 +58,8 @@ type dotWriter struct {
 }
 
 const (
-       wstateBeginLine = iota // beginning of line; initial state; must be zero
+       wstateBegin     = iota // initial state; must be zero
+       wstateBeginLine        // beginning of line
        wstateCR               // wrote \r (possibly at end of line)
        wstateData             // writing data in middle of line
 )
@@ -68,7 +69,7 @@ func (d *dotWriter) Write(b []byte) (n int, err error) {
        for n < len(b) {
                c := b[n]
                switch d.state {
-               case wstateBeginLine:
+               case wstateBegin, wstateBeginLine:
                        d.state = wstateData
                        if c == '.' {
                                // escape leading dot
index ac03669fa2d9fe64308938c16db155778def996f..2afef11b5eeaea35f4a2eb373f40648ed1d2527c 100644 (file)
@@ -33,3 +33,29 @@ func TestDotWriter(t *testing.T) {
                t.Fatalf("wrote %q", s)
        }
 }
+
+func TestDotWriterCloseEmptyWrite(t *testing.T) {
+       var buf bytes.Buffer
+       w := NewWriter(bufio.NewWriter(&buf))
+       d := w.DotWriter()
+       n, err := d.Write([]byte{})
+       if n != 0 || err != nil {
+               t.Fatalf("Write: %d, %s", n, err)
+       }
+       d.Close()
+       want := "\r\n.\r\n"
+       if s := buf.String(); s != want {
+               t.Fatalf("wrote %q; want %q", s, want)
+       }
+}
+
+func TestDotWriterCloseNoWrite(t *testing.T) {
+       var buf bytes.Buffer
+       w := NewWriter(bufio.NewWriter(&buf))
+       d := w.DotWriter()
+       d.Close()
+       want := "\r\n.\r\n"
+       if s := buf.String(); s != want {
+               t.Fatalf("wrote %q; want %q", s, want)
+       }
+}