2026-10-08 16:09:04 +08:00
|
|
|
//go:build !android
|
2026-09-05 20:09:28 +08:00
|
|
|
|
2026-10-08 16:09:04 +08:00
|
|
|
package core
|
2026-09-05 20:09:28 +08:00
|
|
|
|
|
|
|
|
import (
|
|
|
|
|
"fmt"
|
|
|
|
|
"os"
|
|
|
|
|
"os/signal"
|
|
|
|
|
"syscall"
|
|
|
|
|
"time"
|
|
|
|
|
)
|
|
|
|
|
|
|
|
|
|
const exitCleanupTimeout = 3 * time.Second // sing-tun's Linux policy routes outlive the process; only a shutdown removes them
|
|
|
|
|
|
|
|
|
|
func releaseOnExit() {
|
|
|
|
|
if !isInit.Load() {
|
|
|
|
|
return
|
|
|
|
|
}
|
|
|
|
|
done := make(chan struct{})
|
|
|
|
|
go func() {
|
|
|
|
|
defer close(done)
|
|
|
|
|
handleShutdown()
|
|
|
|
|
}()
|
|
|
|
|
select {
|
|
|
|
|
case <-done:
|
|
|
|
|
case <-time.After(exitCleanupTimeout):
|
|
|
|
|
fmt.Fprintln(os.Stderr, "[ERROR] core cleanup did not finish before exit")
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2026-10-08 16:09:04 +08:00
|
|
|
func ExitOnTermination() {
|
2026-09-05 20:09:28 +08:00
|
|
|
signals := make(chan os.Signal, 1)
|
|
|
|
|
signal.Notify(signals, os.Interrupt, syscall.SIGTERM)
|
|
|
|
|
<-signals
|
|
|
|
|
releaseOnExit()
|
|
|
|
|
os.Exit(0)
|
|
|
|
|
}
|