mirror of https://github.com/tailscale/tailscale/
parent
7529b74018
commit
6099ecf7f4
@ -0,0 +1,13 @@
|
|||||||
|
// Copyright (c) 2021 Tailscale Inc & AUTHORS All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
// +build !windows
|
||||||
|
|
||||||
|
package main // import "tailscale.com/cmd/tailscaled"
|
||||||
|
|
||||||
|
import "tailscale.com/logpolicy"
|
||||||
|
|
||||||
|
func isWindowsService() bool { return false }
|
||||||
|
|
||||||
|
func runWindowsService(pol *logpolicy.Policy) error { panic("unreachable") }
|
@ -0,0 +1,64 @@
|
|||||||
|
// Copyright (c) 2021 Tailscale Inc & AUTHORS All rights reserved.
|
||||||
|
// Use of this source code is governed by a BSD-style
|
||||||
|
// license that can be found in the LICENSE file.
|
||||||
|
|
||||||
|
package main // import "tailscale.com/cmd/tailscaled"
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"log"
|
||||||
|
|
||||||
|
"golang.org/x/sys/windows"
|
||||||
|
"golang.org/x/sys/windows/svc"
|
||||||
|
"tailscale.com/ipn/ipnserver"
|
||||||
|
"tailscale.com/logpolicy"
|
||||||
|
)
|
||||||
|
|
||||||
|
const serviceName = "Tailscale IPN"
|
||||||
|
|
||||||
|
func isWindowsService() bool {
|
||||||
|
v, err := svc.IsWindowsService()
|
||||||
|
if err != nil {
|
||||||
|
log.Fatalf("svc.IsWindowsService failed: %v", err)
|
||||||
|
}
|
||||||
|
return v
|
||||||
|
}
|
||||||
|
|
||||||
|
func runWindowsService(pol *logpolicy.Policy) error {
|
||||||
|
return svc.Run(serviceName, &ipnService{Policy: pol})
|
||||||
|
}
|
||||||
|
|
||||||
|
type ipnService struct {
|
||||||
|
Policy *logpolicy.Policy
|
||||||
|
}
|
||||||
|
|
||||||
|
// Called by Windows to execute the windows service.
|
||||||
|
func (service *ipnService) Execute(args []string, r <-chan svc.ChangeRequest, changes chan<- svc.Status) (bool, uint32) {
|
||||||
|
changes <- svc.Status{State: svc.StartPending}
|
||||||
|
|
||||||
|
ctx, cancel := context.WithCancel(context.Background())
|
||||||
|
doneCh := make(chan struct{})
|
||||||
|
go func() {
|
||||||
|
defer close(doneCh)
|
||||||
|
args := []string{"/subproc", service.Policy.PublicID.String()}
|
||||||
|
ipnserver.BabysitProc(ctx, args, log.Printf)
|
||||||
|
}()
|
||||||
|
|
||||||
|
changes <- svc.Status{State: svc.Running, Accepts: svc.AcceptStop}
|
||||||
|
|
||||||
|
for ctx.Err() == nil {
|
||||||
|
select {
|
||||||
|
case <-doneCh:
|
||||||
|
case cmd := <-r:
|
||||||
|
switch cmd.Cmd {
|
||||||
|
case svc.Stop:
|
||||||
|
cancel()
|
||||||
|
case svc.Interrogate:
|
||||||
|
changes <- cmd.CurrentStatus
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
changes <- svc.Status{State: svc.StopPending}
|
||||||
|
return false, windows.NO_ERROR
|
||||||
|
}
|
Loading…
Reference in New Issue