aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorShulhan <m.shulhan@gmail.com>2023-07-08 14:54:24 +0700
committerShulhan <m.shulhan@gmail.com>2024-01-25 04:01:14 +0700
commit7940d5316aa895ad8da5140bb347f193f795e52f (patch)
treeae9aaf6803e197780e23411adb90aa34f25faeeb
parente7b9ecb7a2ccb9d48da849a37bdb347b7de8f042 (diff)
downloadgo-7940d5316aa895ad8da5140bb347f193f795e52f.tar.xz
mime/quotedprintable: fix encoding where a period alone on a line
Given the following example of message body, A line that precisely have length 75 with . + LF will cause DATA truncation.\n \n Footer.\n The quotedprintable Writer will encode the message into, A line ... truncation=\r\n .\r\n \r\n Footer.\r\n If we pass the Writer output into SMTP DATA command, the server read the "\r\n.\r\n" as the end of DATA which cause the message truncated on the receiver. This changes fix this issue by encode the period at the end with "=2E" based on recommendation in RFC 2049 Section 3, point (8) [1]. [1] https://www.rfc-editor.org/rfc/rfc2049.html#section-3 Fixes #61235 Change-Id: I350387b183ac6b25886f4084a060dcfcb48232a9
-rw-r--r--src/mime/quotedprintable/reader_test.go6
-rw-r--r--src/mime/quotedprintable/writer.go7
-rw-r--r--src/mime/quotedprintable/writer_test.go6
3 files changed, 19 insertions, 0 deletions
diff --git a/src/mime/quotedprintable/reader_test.go b/src/mime/quotedprintable/reader_test.go
index 01647840d4..209d6b0793 100644
--- a/src/mime/quotedprintable/reader_test.go
+++ b/src/mime/quotedprintable/reader_test.go
@@ -66,6 +66,12 @@ func TestReader(t *testing.T) {
want: "Now's the time for all folk to come to the aid of their country."},
{in: "accept UTF-8 right quotation mark: ’",
want: "accept UTF-8 right quotation mark: ’"},
+
+ {
+ // Line break with period at the end.
+ in: strings.Repeat(".", 75) + "=\r\n=2E\r\n=2E\r\nfooter.",
+ want: strings.Repeat(".", 76) + "\r\n.\r\nfooter.",
+ },
}
for _, tt := range tests {
var buf strings.Builder
diff --git a/src/mime/quotedprintable/writer.go b/src/mime/quotedprintable/writer.go
index 16ea0bf7d6..0c49e7a28f 100644
--- a/src/mime/quotedprintable/writer.go
+++ b/src/mime/quotedprintable/writer.go
@@ -133,6 +133,13 @@ func (w *Writer) checkLastByte() error {
}
b := w.line[w.i-1]
+ if w.i == 1 && b == '.' {
+ w.i--
+ if err := w.encode(b); err != nil {
+ return err
+ }
+ return nil
+ }
if isWhitespace(b) {
w.i--
if err := w.encode(b); err != nil {
diff --git a/src/mime/quotedprintable/writer_test.go b/src/mime/quotedprintable/writer_test.go
index 07411fe269..b53bb76d5e 100644
--- a/src/mime/quotedprintable/writer_test.go
+++ b/src/mime/quotedprintable/writer_test.go
@@ -88,6 +88,12 @@ func testWriter(t *testing.T, binary bool) {
in: strings.Repeat(" ", 77),
want: strings.Repeat(" ", 75) + "=\r\n =20",
},
+ {
+ // Line break with period at the end.
+ in: strings.Repeat(".", 76) + "\n.\nfooter.",
+ want: strings.Repeat(".", 75) + "=\r\n=2E\r\n=2E\r\nfooter.",
+ wantB: strings.Repeat(".", 75) + "=\r\n.=0A.=0Afooter.",
+ },
}
for _, tt := range tests {