Browse Source

libplugin: do incremental parsing on lightningd commands.

This doesn't make any difference, since lightningd generally sends us
short commands (command responses are via the rpc loop, which is
already done), but it's harmless.

Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
bump-pyln-proto
Rusty Russell 5 years ago
parent
commit
628ae0a15b
  1. 30
      plugins/libplugin.c

30
plugins/libplugin.c

@ -40,6 +40,8 @@ struct plugin {
/* To read from lightningd */ /* To read from lightningd */
char *buffer; char *buffer;
size_t used, len_read; size_t used, len_read;
jsmn_parser parser;
jsmntok_t *toks;
/* To write to lightningd */ /* To write to lightningd */
struct json_stream **js_arr; struct json_stream **js_arr;
@ -1090,18 +1092,11 @@ static void ld_command_handle(struct plugin *plugin,
static bool ld_read_json_one(struct plugin *plugin) static bool ld_read_json_one(struct plugin *plugin)
{ {
bool complete; bool complete;
jsmntok_t *toks;
struct command *cmd = tal(plugin, struct command); struct command *cmd = tal(plugin, struct command);
jsmn_parser parser;
/* FIXME: This could be done more efficiently by storing the if (!json_parse_input(&plugin->parser, &plugin->toks,
* toks and doing an incremental parse, like lightning-cli plugin->buffer, plugin->used,
* does. */
toks = toks_alloc(NULL);
jsmn_init(&parser);
if (!json_parse_input(&parser, &toks, plugin->buffer, plugin->used,
&complete)) { &complete)) {
tal_free(toks);
plugin_err(plugin, "Failed to parse JSON response '%.*s'", plugin_err(plugin, "Failed to parse JSON response '%.*s'",
(int)plugin->used, plugin->buffer); (int)plugin->used, plugin->buffer);
return false; return false;
@ -1113,20 +1108,23 @@ static bool ld_read_json_one(struct plugin *plugin)
} }
/* Empty buffer? (eg. just whitespace). */ /* Empty buffer? (eg. just whitespace). */
if (tal_count(toks) == 1) { if (tal_count(plugin->toks) == 1) {
toks_reset(plugin->toks);
jsmn_init(&plugin->parser);
plugin->used = 0; plugin->used = 0;
return false; return false;
} }
/* FIXME: Spark doesn't create proper jsonrpc 2.0! So we don't /* FIXME: Spark doesn't create proper jsonrpc 2.0! So we don't
* check for "jsonrpc" here. */ * check for "jsonrpc" here. */
ld_command_handle(plugin, cmd, toks); ld_command_handle(plugin, cmd, plugin->toks);
/* Move this object out of the buffer */ /* Move this object out of the buffer */
memmove(plugin->buffer, plugin->buffer + toks[0].end, memmove(plugin->buffer, plugin->buffer + plugin->toks[0].end,
tal_count(plugin->buffer) - toks[0].end); tal_count(plugin->buffer) - plugin->toks[0].end);
plugin->used -= toks[0].end; plugin->used -= plugin->toks[0].end;
tal_free(toks); toks_reset(plugin->toks);
jsmn_init(&plugin->parser);
return true; return true;
} }
@ -1225,6 +1223,8 @@ static struct plugin *new_plugin(const tal_t *ctx,
p->js_arr = tal_arr(p, struct json_stream *, 0); p->js_arr = tal_arr(p, struct json_stream *, 0);
p->used = 0; p->used = 0;
p->len_read = 0; p->len_read = 0;
jsmn_init(&p->parser);
p->toks = toks_alloc(p);
/* Async RPC */ /* Async RPC */
p->rpc_buffer = tal_arr(p, char, 64); p->rpc_buffer = tal_arr(p, char, 64);
p->rpc_js_arr = tal_arr(p, struct json_stream *, 0); p->rpc_js_arr = tal_arr(p, struct json_stream *, 0);

Loading…
Cancel
Save