func (ml *multiListener) listen(l net.Listener) {
	defer ml.wg.Done()
	for {
		c, err := l.Accept()
		if err != nil {
			select {
			case ml.errCh <- err:
			case <-ml.closeCh:
				return
			}
			return
		}
		select {
		case ml.ch <- c:
		case <-ml.closeCh:
			c.Close()
			return
		}
	}
}
listen waits for and returns the next connection for the listener.
package app
import (
	"context"
	"net"
	"sync"
	"github.com/pkg/errors"
	"github.com/target/goalert/util/log"
)
type multiListener struct {
	listeners []net.Listener
	ch      chan net.Conn
	errCh   chan error
	closeCh chan struct{}
	closed  bool
	wg      sync.WaitGroup
}
func newMultiListener(ln ...net.Listener) *multiListener {
	ml := multiListener{
		listeners: ln,
		ch:        make(chan net.Conn),
		errCh:     make(chan error),
		closeCh:   make(chan struct{}),
	}
	for _, l := range ln {
		ml.wg.Add(1)
		go ml.listen(l)
	}
	return &ml
}