Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions src/net/mail/message.go
Original file line number Diff line number Diff line change
Expand Up @@ -832,7 +832,7 @@ func (p *addrParser) consumeComment() (string, bool) {
// '(' already consumed.
depth := 1

var comment string
var comment strings.Builder
for {
if p.empty() || depth == 0 {
break
Expand All @@ -846,12 +846,12 @@ func (p *addrParser) consumeComment() (string, bool) {
depth--
}
if depth > 0 {
comment += p.s[:1]
comment.WriteByte(p.s[0])
}
p.s = p.s[1:]
}

return comment, depth == 0
return comment.String(), depth == 0
}

func (p *addrParser) decodeRFC2047Word(s string) (word string, isEncoded bool, err error) {
Expand Down
19 changes: 19 additions & 0 deletions src/net/mail/message_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ package mail

import (
"bytes"
"fmt"
"io"
"mime"
"reflect"
Expand Down Expand Up @@ -1260,3 +1261,21 @@ func TestEmptyAddress(t *testing.T) {
t.Errorf(`ParseAddressList("") = %v, %v, want nil, error`, list, err)
}
}

func BenchmarkConsumeComment(b *testing.B) {
for _, n := range []int{10, 100, 1000, 10000} {
b.Run(fmt.Sprintf("depth-%d", n), func(b *testing.B) {
// Build a deeply nested comment: (((...a...)))
open := strings.Repeat("(", n)
close := strings.Repeat(")", n)
// consumeComment expects the leading '(' already consumed,
// so we start with one fewer opening paren and the parser
// will handle nesting from there.
input := open[:n-1] + "a" + close
for b.Loop() {
p := addrParser{s: input}
p.consumeComment()
}
})
}
}