Skip to content

Commit 55c1e31

Browse files
rustyrussellShahanaFarooqui
authored andcommitted
subds: fix case where we keep retrying on EOF.
Our low-level ccan/io IO routines return three values: -1: error. 0: call me again, I'm not finished. 1: I'm done, go onto the next thing. In the last release, we tweaked the sematics of "-1": we now opportunistically call a routine which returns 0 once more, in case there's more data. We use errno to distinguish between "EAGAIN" which means there wasn't any data, and real errors. However, if the underlying read() returns 0 (which it does when the peer has closed the other end) the value of errno is UNDEFINED. If it happens to be EAGAIN, we will call it again, rather than closing. This causes us to spin: in particular people reported hsmd consuming 100% of CPU. The ccan/io read code handled this by setting errno to 0 in this case, but our own wire low-level routines *did not*. Fixes: #7655 Changelog-Fixed: Fixed intermittant bug where hsmd (particularly, but also lightningd) could use 100% CPU. Signed-off-by: Rusty Russell <[email protected]>
1 parent 99962f9 commit 55c1e31

File tree

1 file changed

+10
-2
lines changed

1 file changed

+10
-2
lines changed

wire/wire_io.c

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -27,8 +27,12 @@ static int do_read_wire_header(int fd, struct io_plan_arg *arg)
2727
u8 *p = *(u8 **)arg->u1.vp;
2828

2929
ret = read(fd, p + len, HEADER_LEN - len);
30-
if (ret <= 0)
30+
if (ret <= 0) {
31+
/* Errno isn't set if we hit EOF, so set it to distinct value */
32+
if (ret == 0)
33+
errno = 0;
3134
return -1;
35+
}
3236
arg->u2.s += ret;
3337

3438
/* Length bytes read? Set up for normal read of data. */
@@ -61,8 +65,12 @@ static int do_read_wire(int fd, struct io_plan_arg *arg)
6165

6266
/* Normal read */
6367
ret = read(fd, arg->u1.cp, arg->u2.s);
64-
if (ret <= 0)
68+
if (ret <= 0) {
69+
/* Errno isn't set if we hit EOF, so set it to distinct value */
70+
if (ret == 0)
71+
errno = 0;
6572
return -1;
73+
}
6674

6775
arg->u1.cp += ret;
6876
arg->u2.s -= ret;

0 commit comments

Comments
 (0)