sipeed/picoclaw · critical
error in syscall.Dup2: %v
Error message
error in syscall.Dup2: %v
What it means
Startup panic in the unix build: after successfully creating the panic log file, unix.Dup2(file.Fd(), os.Stderr.Fd()) failed while redirecting stderr onto the panic file so runtime panics are captured there. Dup2 of fd 2 essentially only fails when fd 2 is not an open descriptor (process launched with stderr closed, e.g. 2>&-) or the syscall is blocked by a sandbox/seccomp policy.
Source
Thrown at pkg/logger/panic_unix.go:19
//go:build !windows
package logger
import (
"fmt"
"io"
"os"
"golang.org/x/sys/unix"
)
func initPanicFile(panicFile string) io.WriteCloser {
file, err := os.OpenFile(panicFile, os.O_WRONLY|os.O_CREATE|os.O_APPEND|os.O_SYNC, 0o600)
if err != nil {
panic(fmt.Sprintf("error in open panic: %v", err))
}
if err = unix.Dup2(int(file.Fd()), int(os.Stderr.Fd())); err != nil {
panic(fmt.Sprintf("error in syscall.Dup2: %v", err))
}
return file
}
View on GitHub (pinned to 49183d7e8d)
Solutions
- Change the launch configuration: redirect stderr to a file or /dev/null (2>/dev/null) instead of closing it (2>&-)
- If sandboxed, permit dup2 in the seccomp/AppArmor profile
- Verify fd 2 exists before launch: ls -l /proc/<pid>/fd/2
Example fix
# before ./launcher 2>&- # after ./launcher 2>/dev/null
Defensive patterns
Strategy: validation
Validate before calling
if _, err := unix.FcntlInt(uintptr(os.Stderr.Fd()), unix.F_GETFD, 0); err != nil {
return errors.New("fd 2 closed; redirect stderr to /dev/null instead of closing it")
} Try / catch
Pre-main crash: handle at the supervisor level. Treat an immediate exit with this message as a launcher-configuration bug (closed stderr) and fix the launch line, not the code.
Prevention
- Never launch services with 2>&-; use 2>/dev/null
- Keep standard fds open (even to /dev/null) in unit files and containers
- Smoke-test startup once under the exact production launcher configuration
When it happens
Trigger: Service launched with stderr closed (2>&- in shell/supervisor configs, or an exec harness that closes all standard fds); seccomp/container profiles denying dup2; os.Stderr.Fd() not a valid open descriptor in the runtime environment.
Common situations: 'Clean' daemonizer scripts and minimal containers that close std fds instead of redirecting to /dev/null; hardened sandboxes; init templates using 2>&-.
Related errors
- error in open panic: %v
- Failed to redirect stderr to file: %v
- error in open panic: %v
- error initializing panic log: %v
- error enabling file logging: %v
AI-assisted analysis of sipeed/picoclaw@49183d7e8d (2026-08-15).
Data as JSON: /api/errors/4c8b9000246653bf.
Report an issue: GitHub.