upgrade deps; rewrite smtp session
This commit is contained in:
19
vendor/github.com/emersion/go-msgauth/dkim/canonical.go
generated
vendored
19
vendor/github.com/emersion/go-msgauth/dkim/canonical.go
generated
vendored
@@ -2,12 +2,9 @@ package dkim
|
||||
|
||||
import (
|
||||
"io"
|
||||
"regexp"
|
||||
"strings"
|
||||
)
|
||||
|
||||
var rxReduceWS = regexp.MustCompile(`[ \t\r\n]+`)
|
||||
|
||||
// Canonicalization is a canonicalization algorithm.
|
||||
type Canonicalization string
|
||||
|
||||
@@ -113,17 +110,15 @@ func (c *simpleCanonicalizer) CanonicalizeBody(w io.Writer) io.WriteCloser {
|
||||
type relaxedCanonicalizer struct{}
|
||||
|
||||
func (c *relaxedCanonicalizer) CanonicalizeHeader(s string) string {
|
||||
kv := strings.SplitN(s, ":", 2)
|
||||
|
||||
k := strings.TrimSpace(strings.ToLower(kv[0]))
|
||||
|
||||
var v string
|
||||
if len(kv) > 1 {
|
||||
v = rxReduceWS.ReplaceAllString(kv[1], " ")
|
||||
v = strings.TrimSpace(v)
|
||||
|
||||
k, v, ok := strings.Cut(s, ":")
|
||||
if !ok {
|
||||
return strings.TrimSpace(strings.ToLower(s)) + ":" + crlf
|
||||
}
|
||||
|
||||
k = strings.TrimSpace(strings.ToLower(k))
|
||||
v = strings.Join(strings.FieldsFunc(v, func(r rune) bool {
|
||||
return r == ' ' || r == '\t' || r == '\n' || r == '\r'
|
||||
}), " ")
|
||||
return k + ":" + v + crlf
|
||||
}
|
||||
|
||||
|
||||
13
vendor/github.com/emersion/go-msgauth/dkim/dkim.go
generated
vendored
13
vendor/github.com/emersion/go-msgauth/dkim/dkim.go
generated
vendored
@@ -1,4 +1,17 @@
|
||||
// Package dkim creates and verifies DKIM signatures, as specified in RFC 6376.
|
||||
//
|
||||
// # FAQ
|
||||
//
|
||||
// Why can't I verify a [net/mail.Message] directly? A [net/mail.Message]
|
||||
// header is already parsed, and whitespace characters (especially continuation
|
||||
// lines) are removed. Thus, the signature computed from the parsed header is
|
||||
// not the same as the one computed from the raw header.
|
||||
//
|
||||
// How can I publish my public key? You have to add a TXT record to your DNS
|
||||
// zone. See [RFC 6376 appendix C]. You can use the dkim-keygen tool included
|
||||
// in go-msgauth to generate the key and the TXT record.
|
||||
//
|
||||
// [RFC 6376 appendix C]: https://tools.ietf.org/html/rfc6376#appendix-C
|
||||
package dkim
|
||||
|
||||
import (
|
||||
|
||||
18
vendor/github.com/emersion/go-msgauth/dkim/header.go
generated
vendored
18
vendor/github.com/emersion/go-msgauth/dkim/header.go
generated
vendored
@@ -66,28 +66,24 @@ func foldHeaderField(kv string) string {
|
||||
return fold.String() + crlf
|
||||
}
|
||||
|
||||
func parseHeaderField(s string) (k string, v string) {
|
||||
kv := strings.SplitN(s, ":", 2)
|
||||
k = strings.TrimSpace(kv[0])
|
||||
if len(kv) > 1 {
|
||||
v = strings.TrimSpace(kv[1])
|
||||
}
|
||||
return
|
||||
func parseHeaderField(s string) (string, string) {
|
||||
key, value, _ := strings.Cut(s, ":")
|
||||
return strings.TrimSpace(key), strings.TrimSpace(value)
|
||||
}
|
||||
|
||||
func parseHeaderParams(s string) (map[string]string, error) {
|
||||
pairs := strings.Split(s, ";")
|
||||
params := make(map[string]string)
|
||||
for _, s := range pairs {
|
||||
kv := strings.SplitN(s, "=", 2)
|
||||
if len(kv) != 2 {
|
||||
key, value, ok := strings.Cut(s, "=")
|
||||
if !ok {
|
||||
if strings.TrimSpace(s) == "" {
|
||||
continue
|
||||
}
|
||||
return params, errors.New("dkim: malformed header params")
|
||||
}
|
||||
|
||||
params[strings.TrimSpace(kv[0])] = strings.TrimSpace(kv[1])
|
||||
params[strings.TrimSpace(key)] = strings.TrimSpace(value)
|
||||
}
|
||||
return params, nil
|
||||
}
|
||||
@@ -149,6 +145,8 @@ func newHeaderPicker(h header) *headerPicker {
|
||||
}
|
||||
|
||||
func (p *headerPicker) Pick(key string) string {
|
||||
key = strings.ToLower(key)
|
||||
|
||||
at := p.picked[key]
|
||||
for i := len(p.h) - 1; i >= 0; i-- {
|
||||
kv := p.h[i]
|
||||
|
||||
27
vendor/github.com/emersion/go-msgauth/dkim/query.go
generated
vendored
27
vendor/github.com/emersion/go-msgauth/dkim/query.go
generated
vendored
@@ -70,24 +70,31 @@ var queryMethods = map[QueryMethod]queryFunc{
|
||||
}
|
||||
|
||||
func queryDNSTXT(domain, selector string, txtLookup txtLookupFunc) (*queryResult, error) {
|
||||
var txts []string
|
||||
var err error
|
||||
if txtLookup != nil {
|
||||
txts, err = txtLookup(selector + "._domainkey." + domain)
|
||||
} else {
|
||||
txts, err = net.LookupTXT(selector + "._domainkey." + domain)
|
||||
if txtLookup == nil {
|
||||
txtLookup = net.LookupTXT
|
||||
}
|
||||
|
||||
txts, err := txtLookup(selector + "._domainkey." + domain)
|
||||
if netErr, ok := err.(net.Error); ok && netErr.Temporary() {
|
||||
return nil, tempFailError("key unavailable: " + err.Error())
|
||||
} else if err != nil {
|
||||
return nil, permFailError("no key for signature: " + err.Error())
|
||||
}
|
||||
|
||||
// Long keys are split in multiple parts
|
||||
txt := strings.Join(txts, "")
|
||||
|
||||
return parsePublicKey(txt)
|
||||
// net.LookupTXT will concatenate strings contained in a single TXT record.
|
||||
// In other words, net.LookupTXT returns one entry per TXT record, even if
|
||||
// a record contains multiple strings.
|
||||
//
|
||||
// RFC 6376 section 3.6.2.2 says multiple TXT records lead to undefined
|
||||
// behavior, so reject that.
|
||||
switch len(txts) {
|
||||
case 0:
|
||||
return nil, permFailError("no valid key found")
|
||||
case 1:
|
||||
return parsePublicKey(txts[0])
|
||||
default:
|
||||
return nil, permFailError("multiple TXT records found for key")
|
||||
}
|
||||
}
|
||||
|
||||
func parsePublicKey(s string) (*queryResult, error) {
|
||||
|
||||
2
vendor/github.com/emersion/go-msgauth/dkim/sign.go
generated
vendored
2
vendor/github.com/emersion/go-msgauth/dkim/sign.go
generated
vendored
@@ -74,7 +74,7 @@ type SignOptions struct {
|
||||
//
|
||||
// The whole message header and body must be written to the Signer. Close should
|
||||
// always be called (either after the whole message has been written, or after
|
||||
// an error occured and the signer won't be used anymore). Close may return an
|
||||
// an error occurred and the signer won't be used anymore). Close may return an
|
||||
// error in case signing fails.
|
||||
//
|
||||
// After a successful Close, Signature can be called to retrieve the
|
||||
|
||||
10
vendor/github.com/emersion/go-msgauth/dkim/verify.go
generated
vendored
10
vendor/github.com/emersion/go-msgauth/dkim/verify.go
generated
vendored
@@ -293,12 +293,10 @@ func verify(h header, r io.Reader, sigField, sigValue string, options *VerifyOpt
|
||||
}
|
||||
|
||||
// Parse algos
|
||||
algos := strings.SplitN(stripWhitespace(params["a"]), "-", 2)
|
||||
if len(algos) != 2 {
|
||||
keyAlgo, hashAlgo, ok := strings.Cut(stripWhitespace(params["a"]), "-")
|
||||
if !ok {
|
||||
return verif, permFailError("malformed algorithm name")
|
||||
}
|
||||
keyAlgo := algos[0]
|
||||
hashAlgo := algos[1]
|
||||
|
||||
// Check hash algo
|
||||
if res.HashAlgos != nil {
|
||||
@@ -457,6 +455,8 @@ func stripWhitespace(s string) string {
|
||||
}, s)
|
||||
}
|
||||
|
||||
var sigRegex = regexp.MustCompile(`(b\s*=)[^;]+`)
|
||||
|
||||
func removeSignature(s string) string {
|
||||
return regexp.MustCompile(`(b\s*=)[^;]+`).ReplaceAllString(s, "$1")
|
||||
return sigRegex.ReplaceAllString(s, "$1")
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user