You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Windows: orphaned LISTENING socket after opencode serve termination (EADDRINUSE until reboot) #57723
After opencode serve is terminated abnormally (Ctrl-C in its console window, or killing the parent process), the port stays bound by an orphaned LISTENING socket. Nothing accepts connections (GET /global/health → connection refused), yet a new opencode serve --port 4096 fails with ServeError:
$ node -e "require('net').createServer().listen(4096,'0.0.0.0')"
Error: listen EADDRINUSE: address already in use 0.0.0.0:4096
Only a reboot clears it. Reproduced twice on this machine: first on port 4097 (Oct 19-20), then on port 4096 (Oct 21, socket created at 15:22:17, owning PID 4936).
Get-NetTCPConnection -LocalPort 4096 -State Listen still reports OwningProcess = 4936 (dead PID), CreationTime = <time of the crashed run>
netsh interface portproxy show all → empty (not a portproxy rule)
wsl --shutdown does not clear it
Not caused by a firewall rule or an excluded port range: the socket is visible in the TCP table as LISTENING
Hypothesis
On Windows, socket handles are inheritable across CreateProcess by default (Node/Bun spawn processes with bInheritHandles = TRUE). If opencode serve creates its listening socket before spawning children (plugin/shim/worker processes), every child receives a duplicate of the listening-socket handle.
Sequence that leads to the leak:
opencode serve binds 0.0.0.0:4096 (owner PID 4936) and spawns children.
User presses Ctrl-C / kills only the parent. The parent dies; a surviving child still holds the duplicated handle, so the socket stays bound.
The child later dies abnormally as well; kernel cleanup is deferred and the socket ends up referenced from the System context → a permanent LISTENING entry whose owning PID no longer exists.
Minimal reproduction
Start opencode serve --port 4096 in a console.
Ctrl-C it (or taskkill /PID <pid> on the parent only).
netstat -ano | findstr :4096 → still LISTENING with the dead PID.
Try to start opencode serve --port 4096 again → ServeError / EADDRINUSE.
Reboot to recover.
Suggested fixes
Create the listening socket as non-inheritable: WSA_FLAG_NO_HANDLE_INHERIT in WSASocket, or SetHandleInformation(handle, HANDLE_FLAG_INHERIT, 0) right after bind/socket creation.
Kill the whole process tree on termination: put spawned children in a Job Object with JOB_OBJECT_LIMIT_KILL_ON_JOB_CLOSE, so no child can outlive the server holding the handle.
Startup diagnostics: if the port is bound but /global/health is unreachable, print actionable guidance instead of a bare ServeError (e.g. "port 4096 is held by a dead process; reboot required").
Impact
A single Ctrl-C makes the port unusable machine-wide until reboot. This is especially painful when opencode serve is managed by a service wrapper or a sidecar that restarts it automatically: the restart can never succeed, and the supervisor keeps failing silently.
Thanks for the detailed report and diagnostics, @1648298170!
You're on 1.19.3, which is OpenCode v1 (opencode-ai). v1 now only gets fixes for critical bugs such as data loss, security problems or breakage with no workaround. Starting the server on another port avoids this, so it's unlikely to be fixed in v1.
We'd encourage you to try v2 (@opencode/cli, upgrade with opencode upgrade --major). It's a completely separate implementation. By default it runs the server as a background service, which you can stop with opencode service stop. That command asks the server to exit and force-stops it if it hasn't exited after about 5 seconds.
If you think this is critical, or you see the same orphaned socket on v2, please reply here with your opencode --version and the netstat -ano / Get-NetTCPConnection output taken right after the failure.
Activity
opencode-agent commentedon Oct 21, 2026
Thanks for the detailed report and diagnostics, @1648298170!
You're on
1.19.3, which is OpenCode v1 (opencode-ai). v1 now only gets fixes for critical bugs such as data loss, security problems or breakage with no workaround. Starting the server on another port avoids this, so it's unlikely to be fixed in v1.We'd encourage you to try v2 (
@opencode/cli, upgrade withopencode upgrade --major). It's a completely separate implementation. By default it runs the server as a background service, which you can stop withopencode service stop. That command asks the server to exit and force-stops it if it hasn't exited after about 5 seconds.Related issues, most closely related first:
serveon Windows keeps its port after exit, so the next start fails withServeError(closed as not planned)serveon the same port fails withServeError(closed for v1)If you think this is critical, or you see the same orphaned socket on v2, please reply here with your
opencode --versionand thenetstat -ano/Get-NetTCPConnectionoutput taken right after the failure.