Skip to content

Commit

Permalink
channeld: handle more random pre-chatter from peers.
Browse files Browse the repository at this point in the history
Fixes: #2559
Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
  • Loading branch information
rustyrussell committed Apr 12, 2019
1 parent ba41238 commit 9366787
Showing 1 changed file with 33 additions and 15 deletions.
48 changes: 33 additions & 15 deletions channeld/channeld.c
Original file line number Original file line Diff line number Diff line change
Expand Up @@ -2114,6 +2114,24 @@ static void check_current_dataloss_fields(struct peer *peer,
status_trace("option_data_loss_protect: fields are correct"); status_trace("option_data_loss_protect: fields are correct");
} }


/* Older LND sometimes sends funding_locked before reestablish! */
/* ... or announcement_signatures. Sigh, let's handle whatever they send. */
static bool capture_premature_msg(const u8 ***shit_lnd_says, const u8 *msg)
{
if (fromwire_peektype(msg) == WIRE_CHANNEL_REESTABLISH)
return false;

/* Don't allow infinite memory consumption. */
if (tal_count(*shit_lnd_says) > 10)
return false;

status_trace("Stashing early %s msg!",
wire_type_name(fromwire_peektype(msg)));

tal_arr_expand(shit_lnd_says, tal_steal(*shit_lnd_says, msg));
return true;
}

static void peer_reconnect(struct peer *peer, static void peer_reconnect(struct peer *peer,
const struct secret *last_remote_per_commit_secret) const struct secret *last_remote_per_commit_secret)
{ {
Expand All @@ -2128,7 +2146,7 @@ static void peer_reconnect(struct peer *peer,
remote_current_per_commitment_point; remote_current_per_commitment_point;
struct secret last_local_per_commitment_secret; struct secret last_local_per_commitment_secret;
bool dataloss_protect; bool dataloss_protect;
const u8 *premature_funding_locked = NULL; const u8 **premature_msgs = tal_arr(peer, const u8 *, 0);


dataloss_protect = local_feature_negotiated(peer->localfeatures, dataloss_protect = local_feature_negotiated(peer->localfeatures,
LOCAL_DATA_LOSS_PROTECT); LOCAL_DATA_LOSS_PROTECT);
Expand Down Expand Up @@ -2185,16 +2203,9 @@ static void peer_reconnect(struct peer *peer,
do { do {
clean_tmpctx(); clean_tmpctx();
msg = sync_crypto_read(tmpctx, &peer->cs, PEER_FD); msg = sync_crypto_read(tmpctx, &peer->cs, PEER_FD);

} while (handle_peer_gossip_or_error(PEER_FD, GOSSIP_FD, &peer->cs,
/* Older LND sometimes sends funding_locked before reestablish! */ &peer->channel_id, msg)
if (fromwire_peektype(msg) == WIRE_FUNDING_LOCKED || capture_premature_msg(&premature_msgs, msg));
&& !premature_funding_locked) {
status_trace("Stashing early funding_locked msg!");
premature_funding_locked = tal_steal(peer, msg);
msg = NULL;
}
} while (!msg || handle_peer_gossip_or_error(PEER_FD, GOSSIP_FD, &peer->cs,
&peer->channel_id, msg));


if (dataloss_protect) { if (dataloss_protect) {
if (!fromwire_channel_reestablish_option_data_loss_protect(msg, if (!fromwire_channel_reestablish_option_data_loss_protect(msg,
Expand Down Expand Up @@ -2393,10 +2404,17 @@ static void peer_reconnect(struct peer *peer,


peer_billboard(true, "Reconnected, and reestablished."); peer_billboard(true, "Reconnected, and reestablished.");


if (premature_funding_locked) { /* BOLT #2:
handle_peer_funding_locked(peer, premature_funding_locked); * - upon reconnection:
tal_free(premature_funding_locked); *...
} * - MUST transmit `channel_reestablish` for each channel.
* - MUST wait to receive the other node's `channel_reestablish`
* message before sending any other messages for that channel.
*/
/* LND doesn't wait. */
for (size_t i = 0; i < tal_count(premature_msgs); i++)
peer_in(peer, premature_msgs[i]);
tal_free(premature_msgs);
} }


/* ignores the funding_depth unless depth >= minimum_depth /* ignores the funding_depth unless depth >= minimum_depth
Expand Down

0 comments on commit 9366787

Please sign in to comment.