Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add panic handlers #25

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
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
27 changes: 24 additions & 3 deletions client.go
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@ import (
"fmt"
"math/rand"
"net"
"os"
"runtime/debug"
"strings"
"time"

Expand Down Expand Up @@ -108,7 +110,7 @@ func applyOpts(options ...ClientOption) clientOpts {
return conf
}

func (c *client) run(ctx context.Context, params *lookupParams) error {
func (c *client) run(ctx context.Context, params *lookupParams) (err error) {
ctx, cancel := context.WithCancel(ctx)
done := make(chan struct{})
go func() {
Expand All @@ -118,7 +120,7 @@ func (c *client) run(ctx context.Context, params *lookupParams) error {

// If previous probe was ok, it should be fine now. In case of an error later on,
// the entries' queue is closed.
err := c.periodicQuery(ctx, params)
err = c.periodicQuery(ctx, params)
cancel()
<-done
return err
Expand Down Expand Up @@ -165,6 +167,12 @@ var cleanupFreq = 10 * time.Second

// Start listeners and waits for the shutdown signal from exit channel
func (c *client) mainloop(ctx context.Context, params *lookupParams) {
defer func() {
if rerr := recover(); rerr != nil {
fmt.Fprintf(os.Stderr, "caught panic: %s\n%s\n", rerr, debug.Stack())
}
}()

// start listening for responses
msgCh := make(chan *dns.Msg, 32)
if c.ipv4conn != nil {
Expand Down Expand Up @@ -313,6 +321,12 @@ func (c *client) shutdown() {
// Data receiving routine reads from connection, unpacks packets into dns.Msg
// structures and sends them to a given msgCh channel
func (c *client) recv(ctx context.Context, l interface{}, msgCh chan *dns.Msg) {
defer func() {
if rerr := recover(); rerr != nil {
fmt.Fprintf(os.Stderr, "caught panic: %s\n%s\n", rerr, debug.Stack())
}
}()

var readFrom func([]byte) (n int, src net.Addr, err error)

switch pConn := l.(type) {
Expand Down Expand Up @@ -408,7 +422,14 @@ func (c *client) periodicQuery(ctx context.Context, params *lookupParams) error

// Performs the actual query by service name (browse) or service instance name (lookup),
// start response listeners goroutines and loops over the entries channel.
func (c *client) query(params *lookupParams) error {
func (c *client) query(params *lookupParams) (err error) {
defer func() {
if rerr := recover(); rerr != nil {
fmt.Fprintf(os.Stderr, "caught panic: %s\n%s\n", rerr, debug.Stack())
err = fmt.Errorf("panic in zeroconf query: %s", rerr)
}
}()

var serviceName, serviceInstanceName string
serviceName = fmt.Sprintf("%s.%s.", trimDot(params.Service), trimDot(params.Domain))

Expand Down
18 changes: 16 additions & 2 deletions server.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import (
"math/rand"
"net"
"os"
"runtime/debug"
"strings"
"sync"
"time"
Expand Down Expand Up @@ -309,7 +310,14 @@ func (s *Server) recv6(c *ipv6.PacketConn) {
}

// parsePacket is used to parse an incoming packet
func (s *Server) parsePacket(packet []byte, ifIndex int, from net.Addr) error {
func (s *Server) parsePacket(packet []byte, ifIndex int, from net.Addr) (err error) {
defer func() {
if rerr := recover(); rerr != nil {
fmt.Fprintf(os.Stderr, "caught panic: %s\n%s\n", rerr, debug.Stack())
err = fmt.Errorf("panic in mDNS packet handling: %s", rerr)
}
}()

var msg dns.Msg
if err := msg.Unpack(packet); err != nil {
// log.Printf("[ERR] zeroconf: Failed to unpack packet: %v", err)
Expand Down Expand Up @@ -548,8 +556,14 @@ func (s *Server) serviceTypeName(resp *dns.Msg, ttl uint32) {
}

// Perform probing & announcement
//TODO: implement a proper probing & conflict resolution
// TODO: implement a proper probing & conflict resolution
func (s *Server) probe() {
defer func() {
if rerr := recover(); rerr != nil {
fmt.Fprintf(os.Stderr, "caught panic: %s\n%s\n", rerr, debug.Stack())
}
}()

defer s.refCount.Done()

q := new(dns.Msg)
Expand Down