Deliver loopback UDP datagrams across processes on the same machine#855
Open
brandonpayton wants to merge 1 commit into
Open
Deliver loopback UDP datagrams across processes on the same machine#855brandonpayton wants to merge 1 commit into
brandonpayton wants to merge 1 commit into
Conversation
POSIX loopback is machine-scoped: `sendto(127.0.0.1:port)` from one process must reach a socket bound to that port in another process on the same machine. Kandelo delivered loopback datagrams only within the sender's own process (`udp_send_datagram` holds a single `&mut Process` and skipped every endpoint whose `pid != proc.pid`), so cross-process loopback UDP was silently dropped — unconnected `sendto` returned success with the datagram lost, and connected sockets got a spurious `ECONNREFUSED`. TCP already handled the analogous case via `cross_process_loopback_connect`; UDP had no equivalent. Add `deliver_cross_process_loopback_udp`, invoked from the `kernel_sendto`, `kernel_send`, and `kernel_sendmsg` dispatch entry points after the same-process attempt (the dispatch layer owns the global process table, mirroring `cross_process_loopback_connect`). A loopback UDP port binds in exactly one process, and endpoints owned by the sender are skipped, so this never double-delivers a datagram already queued same-process. No ABI change: no new kernel exports/imports or repr(C) types; snapshot unchanged. Validation: `cargo test -p kandelo --lib` (964 pass, incl. new `test_udp_loopback_cross_process` exercising bind/deliver/recvfrom across two processes); `scripts/check-abi-version.sh` reports snapshot in sync. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Contract: POSIX loopback is machine-scoped, not process-scoped
sendto(127.0.0.1:port)from one process must reach a socket bound to that port in another process on the same machine. Kandelo delivered loopback datagrams only within the sender's own process —udp_send_datagramholds a single&mut Processand skipped every endpoint whosepid != proc.pid. So cross-process loopback UDP was silently dropped: unconnectedsendtoreturned success with the datagram lost, and connected sockets got a spuriousECONNREFUSED.TCP already handled the analogous case (
cross_process_loopback_connect, invoked fromkernel_connect— this is how nginx→PHP-FPM works over loopback). UDP had no equivalent.Fix
Add
deliver_cross_process_loopback_udp(insyscalls.rs, table-agnostic and unit-testable), invoked from thekernel_sendto/kernel_send/kernel_sendmsgdispatch entry points after the same-process attempt. The dispatch layer owns the global process table, mirroring the existing TCP cross-process pattern;syscalls.rsstays table-agnostic.127.x. Non-loopback (virtual-network10.88.x) and same-process delivery are untouched.INADDR_ANY; its source is reported as127.0.0.1so the receiver'srecvfromsees a loopback source, matching real semantics.ABI
No change — no new kernel exports/imports or
repr(C)types.scripts/check-abi-version.shreports the snapshot in sync andABI_VERSION/snapshot consistent.Validation
cargo test -p kandelo --target aarch64-apple-darwin --lib— 964 pass, including newtest_udp_loopback_cross_process, which binds a UDP socket in process B, delivers from process A, and reads it back via realsys_socket/sys_bind/sys_recvfromacross twoProcesses (asserting payload + loopback source addr/port).scripts/check-abi-version.sh— snapshot in sync.test_udp_loopback) and non-loopback paths unchanged (helper is a no-op for them).Follow-up (not in this PR): a host-level two-process integration test would exercise the guest
sendto()syscall end-to-end; the dispatch wiring here mirrors the already-proven TCPcross_process_loopback_connect.🤖 Generated with Claude Code