mirror of
https://github.com/foxcpp/maddy.git
synced 2025-04-05 14:07:38 +03:00
96 lines
1.8 KiB
Go
96 lines
1.8 KiB
Go
package maddy
|
|
|
|
import (
|
|
"crypto/tls"
|
|
"fmt"
|
|
"log"
|
|
"net"
|
|
|
|
"github.com/mholt/caddy/caddyfile"
|
|
)
|
|
|
|
type server interface {
|
|
Serve(net.Listener) error
|
|
}
|
|
|
|
var Directives = []string{
|
|
"bind",
|
|
"tls",
|
|
|
|
"log",
|
|
"errors",
|
|
"compress",
|
|
"proxy",
|
|
"pgp",
|
|
}
|
|
|
|
func Start(blocks []caddyfile.ServerBlock) error {
|
|
done := make(chan error, 1)
|
|
|
|
for _, block := range blocks {
|
|
var adresses []Address
|
|
var proto string
|
|
tlsConfig := new(tls.Config)
|
|
for _, k := range block.Keys {
|
|
addr, err := standardizeAddress(k)
|
|
if err != nil {
|
|
return fmt.Errorf("Cannot parse block key %q: %v", k, err)
|
|
}
|
|
|
|
p := addr.Protocol()
|
|
if proto == "" {
|
|
proto = p
|
|
} else if proto != p {
|
|
return fmt.Errorf("Block contains incompatible protocols: %s and %s", proto, p)
|
|
}
|
|
|
|
if addr.IsTLS() && tlsConfig.ServerName == "" {
|
|
tlsConfig.ServerName = addr.Host
|
|
}
|
|
|
|
adresses = append(adresses, addr)
|
|
}
|
|
|
|
var s server
|
|
var err error
|
|
switch proto {
|
|
case "imap":
|
|
s, err = newIMAPServer(block.Tokens)
|
|
case "smtp":
|
|
s, err = newSMTPServer(block.Tokens)
|
|
default:
|
|
return fmt.Errorf("Unsupported protocol %q", proto)
|
|
}
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
if tokens, ok := block.Tokens["tls"]; ok {
|
|
if err := setTLS(caddyfile.NewDispenserTokens("", tokens), &tlsConfig); err != nil {
|
|
return err
|
|
}
|
|
} else {
|
|
tlsConfig = nil
|
|
}
|
|
|
|
for _, addr := range adresses {
|
|
var l net.Listener
|
|
var err error
|
|
l, err = net.Listen("tcp", fmt.Sprintf("%s:%s", addr.Host, addr.Port))
|
|
if err != nil {
|
|
return fmt.Errorf("Cannot listen: %v", err)
|
|
}
|
|
|
|
if addr.IsTLS() {
|
|
l = tls.NewListener(l, tlsConfig)
|
|
}
|
|
|
|
log.Printf("%s server listening on %s\n", addr.Scheme, l.Addr().String())
|
|
go func() {
|
|
done <- s.Serve(l)
|
|
}()
|
|
}
|
|
}
|
|
|
|
return <-done
|
|
}
|