mirror of
https://github.com/ElementsProject/lightning.git
synced 2025-02-22 14:42:40 +01:00
lightningd: refactor to extract getmanifest paths.
This will allow the dynamic starting code to use them too. Also lets us move dev_debug_subprocess under #if DEVELOPER. Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
This commit is contained in:
parent
6441233d2b
commit
1e4f85a539
5 changed files with 87 additions and 52 deletions
|
@ -123,8 +123,8 @@ static struct lightningd *new_lightningd(const tal_t *ctx)
|
|||
* is a nod to keeping it minimal and explicit: we need this code for
|
||||
* testing, but its existence means we're not actually testing the
|
||||
* same exact code users will be running. */
|
||||
ld->dev_debug_subprocess = NULL;
|
||||
#if DEVELOPER
|
||||
ld->dev_debug_subprocess = NULL;
|
||||
ld->dev_disconnect_fd = -1;
|
||||
ld->dev_subdaemon_fail = false;
|
||||
ld->dev_allow_localhost = false;
|
||||
|
@ -808,7 +808,7 @@ int main(int argc, char *argv[])
|
|||
/*~ Initialize all the plugins we just registered, so they can
|
||||
* do their thing and tell us about themselves (including
|
||||
* options registration). */
|
||||
plugins_init(ld->plugins, ld->dev_debug_subprocess);
|
||||
plugins_init(ld->plugins);
|
||||
|
||||
/*~ Handle options and config. */
|
||||
handle_opts(ld, argc, argv);
|
||||
|
|
|
@ -200,15 +200,15 @@ struct lightningd {
|
|||
* if we are the fundee. */
|
||||
u32 max_funding_unconfirmed;
|
||||
|
||||
/* If we want to debug a subdaemon/plugin. */
|
||||
const char *dev_debug_subprocess;
|
||||
|
||||
/* RPC which asked us to shutdown, if non-NULL */
|
||||
struct io_conn *stop_conn;
|
||||
/* RPC response to send once we've shut down. */
|
||||
const char *stop_response;
|
||||
|
||||
#if DEVELOPER
|
||||
/* If we want to debug a subdaemon/plugin. */
|
||||
const char *dev_debug_subprocess;
|
||||
|
||||
/* If we have a --dev-disconnect file */
|
||||
int dev_disconnect_fd;
|
||||
|
||||
|
|
|
@ -1188,60 +1188,85 @@ void plugins_add_default_dir(struct plugins *plugins)
|
|||
}
|
||||
}
|
||||
|
||||
void plugins_init(struct plugins *plugins, const char *dev_plugin_debug)
|
||||
bool plugin_send_getmanifest(struct plugin *p)
|
||||
{
|
||||
struct plugin *p;
|
||||
char **cmd;
|
||||
int stdin, stdout;
|
||||
struct jsonrpc_request *req;
|
||||
bool debug = false;
|
||||
|
||||
#if DEVELOPER
|
||||
if (p->plugins->ld->dev_debug_subprocess
|
||||
&& strends(p->cmd, p->plugins->ld->dev_debug_subprocess))
|
||||
debug = true;
|
||||
#endif
|
||||
cmd = tal_arrz(tmpctx, char *, 2 + debug);
|
||||
cmd[0] = p->cmd;
|
||||
if (debug)
|
||||
cmd[1] = "--debugger";
|
||||
p->pid = pipecmdarr(&stdin, &stdout, &pipecmd_preserve, cmd);
|
||||
if (p->pid == -1)
|
||||
return false;
|
||||
|
||||
log_debug(p->plugins->log, "started(%u) %s", p->pid, p->cmd);
|
||||
p->buffer = tal_arr(p, char, 64);
|
||||
p->stop = false;
|
||||
|
||||
/* Create two connections, one read-only on top of p->stdout, and one
|
||||
* write-only on p->stdin */
|
||||
io_new_conn(p, stdout, plugin_stdout_conn_init, p);
|
||||
io_new_conn(p, stdin, plugin_stdin_conn_init, p);
|
||||
req = jsonrpc_request_start(p, "getmanifest", p->log,
|
||||
plugin_manifest_cb, p);
|
||||
jsonrpc_request_end(req);
|
||||
plugin_request_send(p, req);
|
||||
p->plugin_state = AWAITING_GETMANIFEST_RESPONSE;
|
||||
|
||||
/* Don't timeout if they're running a debugger. */
|
||||
if (debug)
|
||||
p->timeout_timer = NULL;
|
||||
else {
|
||||
p->timeout_timer
|
||||
= new_reltimer(p->plugins->ld->timers, p,
|
||||
time_from_sec(PLUGIN_MANIFEST_TIMEOUT),
|
||||
plugin_manifest_timeout, p);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool plugins_send_getmanifest(struct plugins *plugins)
|
||||
{
|
||||
struct plugin *p, *next;
|
||||
bool sent = false;
|
||||
|
||||
/* Spawn the plugin processes before entering the io_loop */
|
||||
list_for_each_safe(&plugins->plugins, p, next, list) {
|
||||
if (p->plugin_state != UNCONFIGURED)
|
||||
continue;
|
||||
if (plugin_send_getmanifest(p)) {
|
||||
sent = true;
|
||||
continue;
|
||||
}
|
||||
if (plugins->startup)
|
||||
fatal("error starting plugin '%s': %s", p->cmd,
|
||||
strerror(errno));
|
||||
plugin_kill(p, "error starting: %s", strerror(errno));
|
||||
tal_free(p);
|
||||
}
|
||||
|
||||
return sent;
|
||||
}
|
||||
|
||||
void plugins_init(struct plugins *plugins)
|
||||
{
|
||||
plugins->default_dir = path_join(plugins, plugins->ld->config_basedir, "plugins");
|
||||
plugins_add_default_dir(plugins);
|
||||
|
||||
setenv("LIGHTNINGD_PLUGIN", "1", 1);
|
||||
setenv("LIGHTNINGD_VERSION", version(), 1);
|
||||
/* Spawn the plugin processes before entering the io_loop */
|
||||
list_for_each(&plugins->plugins, p, list) {
|
||||
bool debug;
|
||||
|
||||
debug = dev_plugin_debug && strends(p->cmd, dev_plugin_debug);
|
||||
cmd = tal_arrz(p, char *, 2 + debug);
|
||||
cmd[0] = p->cmd;
|
||||
if (debug)
|
||||
cmd[1] = "--debugger";
|
||||
p->pid = pipecmdarr(&stdin, &stdout, &pipecmd_preserve, cmd);
|
||||
|
||||
if (p->pid == -1)
|
||||
fatal("error starting plugin '%s': %s", p->cmd,
|
||||
strerror(errno));
|
||||
else
|
||||
log_debug(plugins->log, "started(%u) %s", p->pid, p->cmd);
|
||||
p->buffer = tal_arr(p, char, 64);
|
||||
p->stop = false;
|
||||
|
||||
/* Create two connections, one read-only on top of p->stdout, and one
|
||||
* write-only on p->stdin */
|
||||
io_new_conn(p, stdout, plugin_stdout_conn_init, p);
|
||||
io_new_conn(p, stdin, plugin_stdin_conn_init, p);
|
||||
req = jsonrpc_request_start(p, "getmanifest", p->log,
|
||||
plugin_manifest_cb, p);
|
||||
jsonrpc_request_end(req);
|
||||
plugin_request_send(p, req);
|
||||
p->plugin_state = AWAITING_GETMANIFEST_RESPONSE;
|
||||
|
||||
/* Don't timeout if they're running a debugger. */
|
||||
if (debug)
|
||||
p->timeout_timer = NULL;
|
||||
else {
|
||||
p->timeout_timer
|
||||
= new_reltimer(plugins->ld->timers, p,
|
||||
time_from_sec(PLUGIN_MANIFEST_TIMEOUT),
|
||||
plugin_manifest_timeout, p);
|
||||
}
|
||||
tal_free(cmd);
|
||||
}
|
||||
|
||||
if (plugins_any_in_state(plugins, AWAITING_GETMANIFEST_RESPONSE))
|
||||
if (plugins_send_getmanifest(plugins))
|
||||
io_loop_with_timers(plugins->ld);
|
||||
}
|
||||
|
||||
|
|
|
@ -144,10 +144,8 @@ void plugins_add_default_dir(struct plugins *plugins);
|
|||
* arguments. In order to read the getmanifest reply from the plugins
|
||||
* we spin up our own io_loop that exits once all plugins have
|
||||
* responded.
|
||||
*
|
||||
* The dev_plugin_debug arg comes from --dev-debugger if DEVELOPER.
|
||||
*/
|
||||
void plugins_init(struct plugins *plugins, const char *dev_plugin_debug);
|
||||
void plugins_init(struct plugins *plugins);
|
||||
|
||||
/**
|
||||
* Free all resources that are held by plugins in the correct order.
|
||||
|
@ -196,6 +194,18 @@ bool plugin_paths_match(const char *cmd, const char *name);
|
|||
*/
|
||||
bool plugin_remove(struct plugins *plugins, const char *name);
|
||||
|
||||
/**
|
||||
* Kick of initialization of a plugin.
|
||||
*/
|
||||
bool plugin_send_getmanifest(struct plugin *p);
|
||||
|
||||
/**
|
||||
* Kick of initialization of all plugins which need it/
|
||||
*
|
||||
* Return true if any were started.
|
||||
*/
|
||||
bool plugins_send_getmanifest(struct plugins *plugins);
|
||||
|
||||
/**
|
||||
* Kill a plugin process, with an error message.
|
||||
*/
|
||||
|
|
|
@ -194,7 +194,7 @@ void plugins_config(struct plugins *plugins UNNEEDED)
|
|||
void plugins_free(struct plugins *plugins UNNEEDED)
|
||||
{ fprintf(stderr, "plugins_free called!\n"); abort(); }
|
||||
/* Generated stub for plugins_init */
|
||||
void plugins_init(struct plugins *plugins UNNEEDED, const char *dev_plugin_debug UNNEEDED)
|
||||
void plugins_init(struct plugins *plugins UNNEEDED)
|
||||
{ fprintf(stderr, "plugins_init called!\n"); abort(); }
|
||||
/* Generated stub for plugins_new */
|
||||
struct plugins *plugins_new(const tal_t *ctx UNNEEDED, struct log_book *log_book UNNEEDED,
|
||||
|
|
Loading…
Add table
Reference in a new issue