Skip to content

Commit 49ccb0e

Browse files
committed
chanbackup: don't send our backups to peers if they would be overlength.
They will in fact get truncated, and never restore. Large nodes should be using some real backup strategy! For this reason, we split "peer_backup" support into send vs store support, so we can turn off send of our own without disabling storing/sending theirs. Signed-off-by: Rusty Russell <[email protected]>
1 parent c5cde13 commit 49ccb0e

File tree

1 file changed

+45
-19
lines changed

1 file changed

+45
-19
lines changed

plugins/chanbackup.c

Lines changed: 45 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,10 @@ HTABLE_DEFINE_NODUPS_TYPE(struct node_id,
6161
peer_map);
6262

6363
struct chanbackup {
64-
bool peer_backup;
64+
/* Do we send/acccept peer backups? */
65+
bool send_our_peer_backup;
66+
bool handle_their_peer_backup;
67+
6568
/* Global secret object to keep the derived encryption key for the SCB */
6669
struct secret secret;
6770

@@ -449,18 +452,16 @@ static struct command_result
449452
return command_hook_success(cmd);
450453
}
451454

452-
static struct command_result *peer_after_send_scb(struct command *cmd,
453-
const char *method,
454-
const char *buf,
455-
const jsmntok_t *params,
456-
struct node_id *nodeid)
455+
static struct command_result *send_peers_scb(struct command *cmd,
456+
struct node_id *nodeid)
457457
{
458458
const struct chanbackup *cb = chanbackup(cmd->plugin);
459459
struct peer_backup *pb;
460460
struct out_req *req;
461461
const u8 *msg;
462462

463-
plugin_log(cmd->plugin, LOG_DBG, "Peer storage sent!");
463+
if (!cb->handle_their_peer_backup)
464+
return command_hook_success(cmd);
464465

465466
/* Now send their backup, if any. */
466467
pb = backup_map_get(cb->backups, nodeid);
@@ -484,6 +485,17 @@ static struct command_result *peer_after_send_scb(struct command *cmd,
484485
return send_outreq(req);
485486
}
486487

488+
static struct command_result *peer_after_send_scb(struct command *cmd,
489+
const char *method,
490+
const char *buf,
491+
const jsmntok_t *params,
492+
struct node_id *nodeid)
493+
{
494+
plugin_log(cmd->plugin, LOG_DBG, "Peer storage sent!");
495+
496+
return send_peers_scb(cmd, nodeid);
497+
}
498+
487499
static struct command_result *peer_after_send_scb_failed(struct command *cmd,
488500
const char *method,
489501
const char *buf,
@@ -543,12 +555,12 @@ static struct command_result *send_to_peers(struct command *cmd)
543555
{
544556
struct out_req *req;
545557
size_t *idx = tal(cmd, size_t);
546-
u8 *serialise_scb;
558+
u8 *serialise_scb, *data;
547559
struct peer_map_iter it;
548560
const struct node_id *peer;
549561
struct chanbackup *cb = chanbackup(cmd->plugin);
550562

551-
if (!cb->peer_backup)
563+
if (!cb->send_our_peer_backup)
552564
return notification_or_hook_done(cmd);
553565

554566
/* BOLT #1:
@@ -560,8 +572,15 @@ static struct command_result *send_to_peers(struct command *cmd)
560572
* - SHOULD pad the `blob` to ensure its length is always exactly 65531 bytes.
561573
*/
562574
/* FIXME: We do not pad! But this is because LDK doesn't store > 1k anyway */
563-
serialise_scb = towire_peer_storage(cmd,
564-
get_file_data(tmpctx, cmd->plugin));
575+
data = get_file_data(tmpctx, cmd->plugin);
576+
if (tal_bytelen(data) > 65531) {
577+
plugin_log(cmd->plugin, LOG_UNUSUAL,
578+
"Peer backup would be %zu bytes. That is too large: disabling peer backups!",
579+
tal_bytelen(data));
580+
cb->send_our_peer_backup = false;
581+
return notification_or_hook_done(cmd);
582+
}
583+
serialise_scb = towire_peer_storage(cmd, data);
565584

566585
*idx = 0;
567586
for (peer = peer_map_pick(cb->peers, pseudorand_u64(), &it);
@@ -684,9 +703,6 @@ static struct command_result *peer_connected(struct command *cmd,
684703
u8 *features;
685704
struct chanbackup *cb = chanbackup(cmd->plugin);
686705

687-
if (!cb->peer_backup)
688-
return command_hook_success(cmd);
689-
690706
serialise_scb = towire_peer_storage(cmd,
691707
get_file_data(tmpctx, cmd->plugin));
692708
node_id = tal(cmd, struct node_id);
@@ -710,6 +726,9 @@ static struct command_result *peer_connected(struct command *cmd,
710726
if (!peer_map_get(cb->peers, node_id))
711727
peer_map_add(cb->peers, tal_dup(cb->peers, struct node_id, node_id));
712728

729+
if (!cb->send_our_peer_backup)
730+
return send_peers_scb(cmd, node_id);
731+
713732
req = jsonrpc_request_start(cmd,
714733
"sendcustommsg",
715734
peer_after_send_scb,
@@ -769,9 +788,6 @@ static struct command_result *handle_your_peer_storage(struct command *cmd,
769788
const char *err;
770789
const struct chanbackup *cb = chanbackup(cmd->plugin);
771790

772-
if (!cb->peer_backup)
773-
return command_hook_success(cmd);
774-
775791
err = json_scan(cmd, buf, params,
776792
"{payload:%,peer_id:%}",
777793
JSON_SCAN_TAL(cmd, json_tok_bin_from_hex, &payload),
@@ -786,6 +802,9 @@ static struct command_result *handle_your_peer_storage(struct command *cmd,
786802
if (fromwire_peer_storage(cmd, payload, &payload_deserialise)) {
787803
struct peer_backup *pb;
788804

805+
if (!cb->handle_their_peer_backup)
806+
return command_hook_success(cmd);
807+
789808
/* BOLT #1:
790809
* The receiver of `peer_storage`:
791810
* - If it offered `option_provide_storage`:
@@ -812,10 +831,13 @@ static struct command_result *handle_your_peer_storage(struct command *cmd,
812831
pb->data = tal_steal(pb, payload_deserialise);
813832
return commit_peer_backup(cmd, pb);
814833
} else if (fromwire_peer_storage_retrieval(cmd, payload, &payload_deserialise)) {
834+
crypto_secretstream_xchacha20poly1305_state crypto_state;
835+
815836
plugin_log(cmd->plugin, LOG_DBG,
816837
"Received peer_storage from peer.");
817838

818-
crypto_secretstream_xchacha20poly1305_state crypto_state;
839+
if (!cb->send_our_peer_backup)
840+
return command_hook_success(cmd);
819841

820842
if (tal_bytelen(payload_deserialise) < ABYTES +
821843
HEADER_LEN)
@@ -1056,7 +1078,11 @@ static const char *init(struct command *init_cmd,
10561078
take(json_out_obj(NULL, NULL, NULL)),
10571079
"{our_features:{init:%}}",
10581080
JSON_SCAN_TAL(tmpctx, json_tok_bin_from_hex, &features));
1059-
cb->peer_backup = feature_offered(features, OPT_PROVIDE_STORAGE);
1081+
1082+
/* If we unset this feature, we don't even *send* peer backups */
1083+
cb->handle_their_peer_backup
1084+
= cb->send_our_peer_backup
1085+
= feature_offered(features, OPT_PROVIDE_STORAGE);
10601086

10611087
rpc_scan(init_cmd, "staticbackup",
10621088
take(json_out_obj(NULL, NULL, NULL)),

0 commit comments

Comments
 (0)