ccan: update to get ccan/io shutdown fix.
What changed, and why it matters
This commit updates an internal networking helper library (CCAN) to fix a bug where a Lightning node might not send its final message—often a warning or error—before closing a connection. The fix prevents the node from accidentally trying to write again after it has already initiated a socket shutdown, which could cause the final packet to be dropped. It is a protocol reliability fix rather than a clear-cut security vulnerability, but lost error/warning messages could theoretically hide important protocol state from a peer.
Treat as a reliability fix worth including in release notes, but do not assign a CVE or issue a security advisory solely on this diff. Monitor for follow-up vendor or researcher analysis that demonstrates exploitable consequences (e.g., funds at risk, state desynchronization attacks, or denial-of-service).
Security signals we found
Fixes a protocol-level message-delivery failure (final packet loss)
Changes socket shutdown behavior to prevent premature close
Changelog labels it as a protocol fix for lost final packets
No explicit security framing by the vendor
Evidence from the diff
The patch changes io_sock_shutdown() in ccan/ccan/io/io.c. Previously, after calling shutdown(fd, SHUT_WR), the function returned the IO_IN plan, leaving the IO_OUT plan unset. The new behavior returns io_wait_dir(conn, io_sock_shutdown, IO_OUT, io_never, NULL), which parks the outbound direction on a waiter that never fires. This stops the IO loop from attempting another write on a half-shutdown socket, failing, and immediately closing the connection before queued outbound data (final warnings/errors) is flushed. The CCAN import is bumped from init-2595-ge43c61c4 to init-2597-gc4760b30.
Changed components
ccan/ccan/io/io.cio_sock_shutdown()Connection teardown / final packet flushingInspect captured patch +5 / −3
diff --git a/ccan/README b/ccan/README
index 5aee7108..8dbc5520 100644
--- a/ccan/README
+++ b/ccan/README
@@ -1,3 +1,3 @@
CCAN imported from http://ccodearchive.net.
-CCAN version: init-2595-ge43c61c4
+CCAN version: init-2597-gc4760b30
diff --git a/ccan/ccan/io/io.c b/ccan/ccan/io/io.c
index 58ae19bd..baa9a497 100644
--- a/ccan/ccan/io/io.c
+++ b/ccan/ccan/io/io.c
@@ -583,8 +583,10 @@ struct io_plan *io_sock_shutdown(struct io_conn *conn)
if (shutdown(io_conn_fd(conn), SHUT_WR) != 0)
return io_close(conn);
- /* And leave unset .*/
- return &conn->plan[IO_IN];
+ /* We need to make sure we don't try to write again, so
+ * "wait" on something which will never be woken: otherwise
+ * we will try to write, fail, and immediately close. */
+ return io_wait_dir(conn, io_sock_shutdown, IO_OUT, io_never, NULL);
}
bool io_flush_sync(struct io_conn *conn)
Why this scored 44/100
Community notes
Notes can correct, qualify, or add evidence to the AI analysis. Every note shown here has been validated by a human moderator.
The AI analysis stands alone for now. Submit a note if you can add evidence or important context.