You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

75 lines
1.3 KiB

  1. // Copyright 2015 Daniel Theophanes.
  2. // Use of this source code is governed by a zlib-style
  3. // license that can be found in the LICENSE file.package service
  4. //+build windows
  5. package minwinsvc
  6. import (
  7. "os"
  8. "strconv"
  9. "sync"
  10. "golang.org/x/sys/windows/svc"
  11. )
  12. var (
  13. onExit func()
  14. guard sync.Mutex
  15. skip, _ = strconv.ParseBool(os.Getenv("SKIP_MINWINSVC"))
  16. )
  17. func init() {
  18. if skip {
  19. return
  20. }
  21. interactive, err := svc.IsAnInteractiveSession()
  22. if err != nil {
  23. panic(err)
  24. }
  25. if interactive {
  26. return
  27. }
  28. go func() {
  29. _ = svc.Run("", runner{})
  30. guard.Lock()
  31. f := onExit
  32. guard.Unlock()
  33. // Don't hold this lock in user code.
  34. if f != nil {
  35. f()
  36. }
  37. // Make sure we exit.
  38. os.Exit(0)
  39. }()
  40. }
  41. func setOnExit(f func()) {
  42. guard.Lock()
  43. onExit = f
  44. guard.Unlock()
  45. }
  46. type runner struct{}
  47. func (runner) Execute(args []string, r <-chan svc.ChangeRequest, changes chan<- svc.Status) (bool, uint32) {
  48. const cmdsAccepted = svc.AcceptStop | svc.AcceptShutdown
  49. changes <- svc.Status{State: svc.StartPending}
  50. changes <- svc.Status{State: svc.Running, Accepts: cmdsAccepted}
  51. for {
  52. c := <-r
  53. switch c.Cmd {
  54. case svc.Interrogate:
  55. changes <- c.CurrentStatus
  56. case svc.Stop, svc.Shutdown:
  57. changes <- svc.Status{State: svc.StopPending}
  58. return false, 0
  59. }
  60. }
  61. return false, 0
  62. }