From: Ian Lance Taylor Date: Thu, 13 Dec 2018 23:23:35 +0000 (-0800) Subject: mime/multipart: quote boundary in Content-Type if necessary X-Git-Tag: go1.12beta1~57 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=a6293995c55659f51e0662e7656f395633c99b5b;p=gostls13.git mime/multipart: quote boundary in Content-Type if necessary Fixes #26532 Change-Id: Ic086c90503c7b24982f947c828c7ccf016ddbf69 Reviewed-on: https://go-review.googlesource.com/c/154120 Run-TryBot: Ian Lance Taylor Reviewed-by: Brad Fitzpatrick --- diff --git a/src/mime/multipart/writer.go b/src/mime/multipart/writer.go index 3dd0c8fb13..d1ff151a7d 100644 --- a/src/mime/multipart/writer.go +++ b/src/mime/multipart/writer.go @@ -72,7 +72,13 @@ func (w *Writer) SetBoundary(boundary string) error { // FormDataContentType returns the Content-Type for an HTTP // multipart/form-data with this Writer's Boundary. func (w *Writer) FormDataContentType() string { - return "multipart/form-data; boundary=" + w.boundary + b := w.boundary + // We must quote the boundary if it contains any of the + // tspecials characters defined by RFC 2045, or space. + if strings.ContainsAny(b, `()<>@,;:\"/[]?= `) { + b = `"` + b + `"` + } + return "multipart/form-data; boundary=" + b } func randomBoundary() string { diff --git a/src/mime/multipart/writer_test.go b/src/mime/multipart/writer_test.go index 8b1bcd68d8..b89b093fff 100644 --- a/src/mime/multipart/writer_test.go +++ b/src/mime/multipart/writer_test.go @@ -7,6 +7,7 @@ package multipart import ( "bytes" "io/ioutil" + "mime" "net/textproto" "strings" "testing" @@ -94,6 +95,7 @@ func TestWriterSetBoundary(t *testing.T) { {"my-separator", true}, {"with space", true}, {"badspace ", false}, + {"(boundary)", true}, } for i, tt := range tests { var b bytes.Buffer @@ -107,6 +109,17 @@ func TestWriterSetBoundary(t *testing.T) { if got != tt.b { t.Errorf("boundary = %q; want %q", got, tt.b) } + + ct := w.FormDataContentType() + mt, params, err := mime.ParseMediaType(ct) + if err != nil { + t.Errorf("could not parse Content-Type %q: %v", ct, err) + } else if mt != "multipart/form-data" { + t.Errorf("unexpected media type %q; want %q", mt, "multipart/form-data") + } else if b := params["boundary"]; b != tt.b { + t.Errorf("unexpected boundary parameter %q; want %q", b, tt.b) + } + w.Close() wantSub := "\r\n--" + tt.b + "--\r\n" if got := b.String(); !strings.Contains(got, wantSub) {