diff --git a/common/signals.go b/common/signals.go new file mode 100644 index 00000000..067bf340 --- /dev/null +++ b/common/signals.go @@ -0,0 +1,38 @@ +package common + +import ( + "os" + "os/signal" + "runtime" + "syscall" +) + +// A subsystem/server/... that can be stopped or queried about the status with a signal +type SignalsReceiver interface { + Status() string + Stop() error +} + +func SignalHandlerLoop(ss ...SignalsReceiver) { + sigs := make(chan os.Signal, 1) + signal.Notify(sigs, syscall.SIGINT, syscall.SIGQUIT, syscall.SIGUSR1) + buf := make([]byte, 1<<20) + for { + sig := <-sigs + switch sig { + case syscall.SIGINT: + Info.Printf("=== received SIGINT ===\n*** exiting\n") + for _, subsystem := range ss { + subsystem.Stop() + } + os.Exit(0) + case syscall.SIGQUIT: + stacklen := runtime.Stack(buf, true) + Info.Printf("=== received SIGQUIT ===\n*** goroutine dump...\n%s\n*** end\n", buf[:stacklen]) + case syscall.SIGUSR1: + for _, subsystem := range ss { + Info.Printf("=== received SIGUSR1 ===\n*** status...\n%s\n*** end\n", subsystem.Status()) + } + } + } +} diff --git a/weavedns/main.go b/weavedns/main.go index ae1e06e8..6a888896 100644 --- a/weavedns/main.go +++ b/weavedns/main.go @@ -9,9 +9,6 @@ import ( weavenet "github.com/weaveworks/weave/net" "net" "os" - "os/signal" - "runtime" - "syscall" ) var version = "(unreleased version)" @@ -90,30 +87,11 @@ func main() { } Info.Println("Upstream", srv.Upstream) - Debug.Printf("Starting the signals handler") - go handleSignals(srv) - + go SignalHandlerLoop(srv) go weavedns.ListenHTTP(version, srv, domain, zone, httpPort) + err = srv.Start() if err != nil { - Error.Fatal("Failed to start the WeaveDNS server", err) - } -} - -func handleSignals(s *weavedns.DNSServer) { - sigs := make(chan os.Signal, 1) - signal.Notify(sigs, syscall.SIGINT, syscall.SIGQUIT) - buf := make([]byte, 1<<20) - for { - sig := <-sigs - switch sig { - case syscall.SIGINT: - Info.Printf("=== received SIGINT ===\n*** exiting\n") - s.Stop() - os.Exit(0) - case syscall.SIGQUIT: - stacklen := runtime.Stack(buf, true) - Info.Printf("=== received SIGQUIT ===\n*** goroutine dump...\n%s\n*** end\n", buf[:stacklen]) - } + Error.Fatal("[main] Failed to start the WeaveDNS server: ", err) } }