lightningd/io_loop_with_timers.c: Move mainloop to its own source file, have chaintopology use it.

Fixes: #2687
This commit is contained in:
ZmnSCPxj
2019-05-30 02:30:10 +00:00
committed by Christian Decker
parent 883d4b4e6e
commit 48df6c8566
7 changed files with 57 additions and 26 deletions

View File

@@ -69,6 +69,7 @@ LIGHTNINGD_SRC := \
lightningd/hsm_control.c \ lightningd/hsm_control.c \
lightningd/htlc_end.c \ lightningd/htlc_end.c \
lightningd/invoice.c \ lightningd/invoice.c \
lightningd/io_loop_with_timers.c \
lightningd/json.c \ lightningd/json.c \
lightningd/json_stream.c \ lightningd/json_stream.c \
lightningd/jsonrpc.c \ lightningd/jsonrpc.c \

View File

@@ -22,6 +22,7 @@
#include <inttypes.h> #include <inttypes.h>
#include <lightningd/channel_control.h> #include <lightningd/channel_control.h>
#include <lightningd/gossip_control.h> #include <lightningd/gossip_control.h>
#include <lightningd/io_loop_with_timers.h>
/* Mutual recursion via timer. */ /* Mutual recursion via timer. */
static void try_extend_tip(struct chain_topology *topo); static void try_extend_tip(struct chain_topology *topo);
@@ -894,7 +895,7 @@ void setup_topology(struct chain_topology *topo,
start_fee_estimate(topo); start_fee_estimate(topo);
/* Once it gets initial block, it calls io_break() and we return. */ /* Once it gets initial block, it calls io_break() and we return. */
io_loop(NULL, NULL); io_loop_with_timers(topo->ld);
} }
void begin_topology(struct chain_topology *topo) void begin_topology(struct chain_topology *topo)

View File

@@ -0,0 +1,36 @@
#include "lightningd/io_loop_with_timers.h"
#include <ccan/io/io.h>
#include <ccan/timer/timer.h>
#include <common/timeout.h>
#include <lightningd/lightningd.h>
#include <wallet/db.h>
#include <wallet/wallet.h>
void *io_loop_with_timers(struct lightningd *ld)
{
void *retval = NULL;
struct timer *expired;
while (!retval) {
/* ~ccan/io's io_loop() continuously calls
* io_poll_lightningd() for all file descriptors registered
* with it, then calls their callbacks or closes them if they
* fail, as appropriate.
*
* It will only exit if there's an expired timer, *or* someone
* calls io_break, or if there are no more file descriptors
* (which never happens in our code). */
retval = io_loop(&ld->timers, &expired);
/*~ Notice that timers are called here in the event loop like
* anything else, so there are no weird concurrency issues. */
if (expired) {
db_begin_transaction(ld->wallet->db);
timer_expired(ld, expired);
db_commit_transaction(ld->wallet->db);
}
}
return retval;
}

View File

@@ -0,0 +1,10 @@
#ifndef LIGHTNING_LIGHTNINGD_IO_LOOP_WITH_TIMERS_H
#define LIGHTNING_LIGHTNINGD_IO_LOOP_WITH_TIMERS_H
#include "config.h"
struct lightningd;
void *io_loop_with_timers(struct lightningd *ld);
#endif /* LIGHTNING_LIGHTNINGD_IO_LOOP_WITH_TIMERS_H */

View File

@@ -70,6 +70,7 @@
#include <lightningd/channel_control.h> #include <lightningd/channel_control.h>
#include <lightningd/connect_control.h> #include <lightningd/connect_control.h>
#include <lightningd/invoice.h> #include <lightningd/invoice.h>
#include <lightningd/io_loop_with_timers.h>
#include <lightningd/jsonrpc.h> #include <lightningd/jsonrpc.h>
#include <lightningd/log.h> #include <lightningd/log.h>
#include <lightningd/onchain_control.h> #include <lightningd/onchain_control.h>
@@ -810,30 +811,12 @@ int main(int argc, char *argv[])
/*~ The root of every backtrace (almost). This is our main event /*~ The root of every backtrace (almost). This is our main event
* loop. */ * loop. */
for (;;) { void *io_loop_ret = io_loop_with_timers(ld);
/* ~ccan/io's io_loop() continuously calls /*~ io_loop_with_timers will only exit if we call io_break.
* io_poll_lightningd() for all file descriptors registered * At this point in code, we should use io_break(ld) to
* with it, then calls their callbacks or closes them if they * shut down.
* fail, as appropriate. */
* assert(io_loop_ret == ld);
* It will only exit if there's an expired timer, *or* someone
* calls io_break, or if there are no more file descriptors
* (which never happens in our code). */
struct timer *expired;
void *v = io_loop(&ld->timers, &expired);
/*~ We use io_break(ld) to shut down. */
if (v == ld)
break;
/*~ Notice that timers are called here in the event loop like
* anything else, so there are no weird concurrency issues. */
if (expired) {
db_begin_transaction(ld->wallet->db);
timer_expired(ld, expired);
db_commit_transaction(ld->wallet->db);
}
}
shutdown_subdaemons(ld); shutdown_subdaemons(ld);

View File

@@ -2,6 +2,7 @@
int unused_main(int argc, char *argv[]); int unused_main(int argc, char *argv[]);
#include "../../common/base32.c" #include "../../common/base32.c"
#include "../../common/wireaddr.c" #include "../../common/wireaddr.c"
#include "../io_loop_with_timers.c"
#include "../lightningd.c" #include "../lightningd.c"
#include "../subd.c" #include "../subd.c"
#include <common/amount.h> #include <common/amount.h>

View File

@@ -1401,7 +1401,6 @@ def test_newaddr(node_factory):
assert both['bech32'].startswith('bcrt1') assert both['bech32'].startswith('bcrt1')
@pytest.mark.xfail(strict=True)
def test_bitcoind_fail_first(node_factory, bitcoind, executor): def test_bitcoind_fail_first(node_factory, bitcoind, executor):
"""Make sure we handle spurious bitcoin-cli failures during startup """Make sure we handle spurious bitcoin-cli failures during startup