aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorOphestra <cat@gensokyo.uk>2025-12-08 22:56:13 +0900
committerOphestra <cat@gensokyo.uk>2025-12-08 22:56:13 +0900
commitdafe9f8efc46bbd0fb391d1f7a93f05ee9751250 (patch)
tree60408f6f5ddc4c5939346c017da879ea5ffbbc7f
parent96dd7abd806f6639703968a7f8267901d5955dad (diff)
container: spin instead of block on wait4 ECHILD
Blocking prevents further wait4 processing causing ops to never receive their signals. Signed-off-by: Ophestra <cat@gensokyo.uk>
-rw-r--r--container/init.go12
1 files changed, 6 insertions, 6 deletions
diff --git a/container/init.go b/container/init.go
index 923feb49..04c643d9 100644
--- a/container/init.go
+++ b/container/init.go
@@ -11,6 +11,7 @@ import (
"slices"
"strconv"
"sync"
+ "sync/atomic"
. "syscall"
"time"
@@ -368,8 +369,8 @@ func initEntrypoint(k syscallDispatcher, msg message.Msg) {
// when there are no longer any processes left to reap
info := make(chan winfo, 1)
- // closed when the initial process has started
- initialProcessStarted := make(chan struct{})
+ // whether initial process has started
+ var initialProcessStarted atomic.Bool
k.new(func(k syscallDispatcher) {
k.lockOSThread()
@@ -413,11 +414,10 @@ func initEntrypoint(k syscallDispatcher, msg message.Msg) {
if !errors.Is(err, ECHILD) {
k.printf(msg, "unexpected wait4 response: %v", err)
- } else if initialProcessStarted != nil {
+ } else if !initialProcessStarted.Load() {
// initial process has not yet been reached and all daemons
// terminated or none were started in the first place
- <-initialProcessStarted
- initialProcessStarted = nil
+ time.Sleep(500 * time.Microsecond)
goto wait4
}
@@ -458,7 +458,7 @@ func initEntrypoint(k syscallDispatcher, msg message.Msg) {
if err := k.start(cmd); err != nil {
k.fatalf(msg, "%v", err)
}
- close(initialProcessStarted)
+ initialProcessStarted.Store(true)
// handle signals to dump withheld messages
sig := make(chan os.Signal, 2)