pytest: make test_no_delay more robust.

Unfortunately the effect of leaving Nagle enabled is subtle.  Here it
is in v25.12:

Normal: 
    tests/test_connection.py::test_no_delay PASSED
    ====================================================================== 1 passed in 13.87s

Nagle enabled:
    tests/test_connection.py::test_no_delay PASSED
    ====================================================================== 1 passed in 21.70s

So it's hard to both catch this issue and not have false positives.  Improve the
test by deliberately running with Nagle enabled, so we can do a direct comparison.

Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
This commit is contained in:
Rusty Russell
2026-02-19 21:27:15 +10:30
parent 10eb2c2ca0
commit d0c158a69d
8 changed files with 49 additions and 10 deletions

View File

@@ -515,9 +515,13 @@ static bool get_remote_address(struct io_conn *conn,
* inserting a delay, creating a trap for every author of network code
* everywhere.
*/
static void set_tcp_no_delay(int fd)
static void set_tcp_no_delay(const struct daemon *daemon, int fd)
{
int val = 1;
if (daemon->dev_keep_nagle)
return;
if (setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &val, sizeof(val)) != 0) {
status_broken("setsockopt TCP_NODELAY=1 fd=%u: %s",
fd, strerror(errno));
@@ -658,7 +662,7 @@ static struct io_plan *connection_in(struct io_conn *conn,
/* Don't try to set TCP options on UNIX socket! */
if (conn_in_arg.addr.itype == ADDR_INTERNAL_WIREADDR)
set_tcp_no_delay(io_conn_fd(conn));
set_tcp_no_delay(daemon, io_conn_fd(conn));
conn_in_arg.daemon = daemon;
conn_in_arg.is_websocket = false;
@@ -1198,7 +1202,7 @@ static void try_connect_one_addr(struct connecting *connect)
/* Don't try to set TCP options on UNIX socket! */
if (addr->itype == ADDR_INTERNAL_WIREADDR)
set_tcp_no_delay(fd);
set_tcp_no_delay(connect->daemon, fd);
connect->connect_attempted = true;
/* This creates the new connection using our fd, with the initialization
@@ -1685,7 +1689,8 @@ static void connect_init(struct daemon *daemon, const u8 *msg)
&dev_throttle_gossip,
&daemon->dev_no_reconnect,
&daemon->dev_fast_reconnect,
&dev_limit_connections_inflight)) {
&dev_limit_connections_inflight,
&daemon->dev_keep_nagle)) {
/* This is a helper which prints the type expected and the actual
* message, then exits (it should never be called!). */
master_badmsg(WIRE_CONNECTD_INIT, msg);
@@ -2555,6 +2560,7 @@ int main(int argc, char *argv[])
daemon->custom_msgs = NULL;
daemon->dev_exhausted_fds = false;
daemon->dev_lightningd_is_slow = false;
daemon->dev_keep_nagle = false;
/* We generally allow 1MB per second per peer, except for dev testing */
daemon->gossip_stream_limit = 1000000;
daemon->scid_htable = new_htable(daemon, scid_htable);

View File

@@ -371,6 +371,8 @@ struct daemon {
bool dev_fast_reconnect;
/* Don't complain about lightningd being unresponsive. */
bool dev_lightningd_is_slow;
/* Don't set TCP_NODELAY */
bool dev_keep_nagle;
};
/* Called by io_tor_connect once it has a connection out. */

View File

@@ -28,6 +28,7 @@ msgdata,connectd_init,dev_throttle_gossip,bool,
msgdata,connectd_init,dev_no_reconnect,bool,
msgdata,connectd_init,dev_fast_reconnect,bool,
msgdata,connectd_init,dev_limit_connections_inflight,bool,
msgdata,connectd_init,dev_keep_nagle,bool,
# Connectd->master, here are the addresses I bound, can announce.
msgtype,connectd_init_reply,2100
1 #include <common/channel_id.h>
28 msgdata,connectd_init,dev_fast_reconnect,bool,
29 msgdata,connectd_init,dev_limit_connections_inflight,bool,
30 # Connectd->master, here are the addresses I bound, can announce. msgdata,connectd_init,dev_keep_nagle,bool,
31 # Connectd->master, here are the addresses I bound, can announce.
32 msgtype,connectd_init_reply,2100
33 msgdata,connectd_init_reply,num_bindings,u16,
34 msgdata,connectd_init_reply,bindings,wireaddr_internal,num_bindings