cmd/syncthing: Always use monitor process (fixes #4774, fixes #5786) (#6278)

This commit is contained in:
Simon Frei 2020-01-20 09:07:46 +01:00 committed by GitHub
parent 879d757850
commit 69da11a263
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 36 additions and 30 deletions

View File

@ -47,6 +47,7 @@ import (
const ( const (
tlsDefaultCommonName = "syncthing" tlsDefaultCommonName = "syncthing"
deviceCertLifetimeDays = 20 * 365 deviceCertLifetimeDays = 20 * 365
sigTerm = syscall.Signal(15)
) )
const ( const (
@ -225,7 +226,7 @@ func parseCommandLineOptions() RuntimeOptions {
flag.BoolVar(&options.Verbose, "verbose", false, "Print verbose log output") flag.BoolVar(&options.Verbose, "verbose", false, "Print verbose log output")
flag.BoolVar(&options.paused, "paused", false, "Start with all devices and folders paused") flag.BoolVar(&options.paused, "paused", false, "Start with all devices and folders paused")
flag.BoolVar(&options.unpaused, "unpaused", false, "Start with all devices and folders unpaused") flag.BoolVar(&options.unpaused, "unpaused", false, "Start with all devices and folders unpaused")
flag.StringVar(&options.logFile, "logfile", options.logFile, "Log file name (still always logs to stdout). Cannot be used together with -no-restart/STNORESTART environment variable.") flag.StringVar(&options.logFile, "logfile", options.logFile, "Log file name (still always logs to stdout).")
flag.IntVar(&options.logMaxSize, "log-max-size", options.logMaxSize, "Maximum size of any file (zero to disable log rotation).") flag.IntVar(&options.logMaxSize, "log-max-size", options.logMaxSize, "Maximum size of any file (zero to disable log rotation).")
flag.IntVar(&options.logMaxFiles, "log-max-old-files", options.logMaxFiles, "Number of old files to keep (zero to keep only current).") flag.IntVar(&options.logMaxFiles, "log-max-old-files", options.logMaxFiles, "Number of old files to keep (zero to keep only current).")
flag.StringVar(&options.auditFile, "auditfile", options.auditFile, "Specify audit file (use \"-\" for stdout, \"--\" for stderr)") flag.StringVar(&options.auditFile, "auditfile", options.auditFile, "Specify audit file (use \"-\" for stdout, \"--\" for stderr)")
@ -260,15 +261,6 @@ func main() {
os.Setenv("STGUIAPIKEY", options.guiAPIKey) os.Setenv("STGUIAPIKEY", options.guiAPIKey)
} }
// Check for options which are not compatible with each other. We have
// to check logfile before it's set to the default below - we only want
// to complain if they set -logfile explicitly, not if it's set to its
// default location
if options.noRestart && (options.logFile != "" && options.logFile != "-") {
l.Warnln("-logfile may not be used with -no-restart or STNORESTART")
os.Exit(syncthing.ExitError.AsInt())
}
if options.hideConsole { if options.hideConsole {
osutil.HideConsole() osutil.HideConsole()
} }
@ -381,7 +373,7 @@ func main() {
return return
} }
if innerProcess || options.noRestart { if innerProcess {
syncthingMain(options) syncthingMain(options)
} else { } else {
monitorMain(options) monitorMain(options)
@ -677,7 +669,6 @@ func setupSignalHandling(app *syncthing.App) {
// Exit with "success" code (no restart) on INT/TERM // Exit with "success" code (no restart) on INT/TERM
stopSign := make(chan os.Signal, 1) stopSign := make(chan os.Signal, 1)
sigTerm := syscall.Signal(15)
signal.Notify(stopSign, os.Interrupt, sigTerm) signal.Notify(stopSign, os.Interrupt, sigTerm)
go func() { go func() {
<-stopSign <-stopSign

View File

@ -21,6 +21,7 @@ import (
"time" "time"
"github.com/syncthing/syncthing/lib/events" "github.com/syncthing/syncthing/lib/events"
"github.com/syncthing/syncthing/lib/fs"
"github.com/syncthing/syncthing/lib/locations" "github.com/syncthing/syncthing/lib/locations"
"github.com/syncthing/syncthing/lib/osutil" "github.com/syncthing/syncthing/lib/osutil"
"github.com/syncthing/syncthing/lib/protocol" "github.com/syncthing/syncthing/lib/protocol"
@ -50,6 +51,9 @@ func monitorMain(runtimeOptions RuntimeOptions) {
logFile := runtimeOptions.logFile logFile := runtimeOptions.logFile
if logFile != "-" { if logFile != "-" {
if expanded, err := fs.ExpandTilde(logFile); err == nil {
logFile = expanded
}
var fileDst io.Writer var fileDst io.Writer
if runtimeOptions.logMaxSize > 0 { if runtimeOptions.logMaxSize > 0 {
open := func(name string) (io.WriteCloser, error) { open := func(name string) (io.WriteCloser, error) {
@ -79,7 +83,6 @@ func monitorMain(runtimeOptions RuntimeOptions) {
var restarts [countRestarts]time.Time var restarts [countRestarts]time.Time
stopSign := make(chan os.Signal, 1) stopSign := make(chan os.Signal, 1)
sigTerm := syscall.Signal(15)
signal.Notify(stopSign, os.Interrupt, sigTerm) signal.Notify(stopSign, os.Interrupt, sigTerm)
restartSign := make(chan os.Signal, 1) restartSign := make(chan os.Signal, 1)
sigHup := syscall.Signal(1) sigHup := syscall.Signal(1)
@ -111,7 +114,7 @@ func monitorMain(runtimeOptions RuntimeOptions) {
panic(err) panic(err)
} }
l.Infoln("Starting syncthing") l.Debugln("Starting syncthing")
err = cmd.Start() err = cmd.Start()
if err != nil { if err != nil {
l.Warnln("Error starting the main Syncthing process:", err) l.Warnln("Error starting the main Syncthing process:", err)
@ -144,12 +147,13 @@ func monitorMain(runtimeOptions RuntimeOptions) {
exit <- cmd.Wait() exit <- cmd.Wait()
}() }()
stopped := false
select { select {
case s := <-stopSign: case s := <-stopSign:
l.Infof("Signal %d received; exiting", s) l.Infof("Signal %d received; exiting", s)
cmd.Process.Signal(sigTerm) cmd.Process.Signal(sigTerm)
<-exit err = <-exit
return stopped = true
case s := <-restartSign: case s := <-restartSign:
l.Infof("Signal %d received; restarting", s) l.Infof("Signal %d received; restarting", s)
@ -157,20 +161,31 @@ func monitorMain(runtimeOptions RuntimeOptions) {
err = <-exit err = <-exit
case err = <-exit: case err = <-exit:
}
if err == nil { if err == nil {
// Successful exit indicates an intentional shutdown // Successful exit indicates an intentional shutdown
return os.Exit(syncthing.ExitSuccess.AsInt())
} else if exiterr, ok := err.(*exec.ExitError); ok { }
if exiterr.ExitCode() == syncthing.ExitUpgrade.AsInt() {
if exiterr, ok := err.(*exec.ExitError); ok {
exitCode := exiterr.ExitCode()
if stopped || runtimeOptions.noRestart {
os.Exit(exitCode)
}
if exitCode == syncthing.ExitUpgrade.AsInt() {
// Restart the monitor process to release the .old // Restart the monitor process to release the .old
// binary as part of the upgrade process. // binary as part of the upgrade process.
l.Infoln("Restarting monitor...") l.Infoln("Restarting monitor...")
if err = restartMonitor(args); err != nil { if err = restartMonitor(args); err != nil {
l.Warnln("Restart:", err) l.Warnln("Restart:", err)
} }
return os.Exit(exitCode)
} }
} }
if runtimeOptions.noRestart {
os.Exit(syncthing.ExitError.AsInt())
} }
l.Infoln("Syncthing exited:", err) l.Infoln("Syncthing exited:", err)

View File

@ -2,7 +2,7 @@
Name=Start Syncthing Name=Start Syncthing
GenericName=File synchronization GenericName=File synchronization
Comment=Starts the main syncthing process in the background. Comment=Starts the main syncthing process in the background.
Exec=/usr/bin/syncthing -no-browser Exec=/usr/bin/syncthing -no-browser -logfile=~/.config/syncthing/syncthing.log
Icon=syncthing Icon=syncthing
Terminal=false Terminal=false
Type=Application Type=Application