subd: hand through fatal messages as well to callback.

This matters in one case: channeld receiving a bad message is a
permenant failure, whereas losing a connection is transient.

Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
This commit is contained in:
Rusty Russell 2017-06-20 15:49:03 +09:30
parent 15405f95e1
commit d95adf7f33
5 changed files with 32 additions and 7 deletions

View File

@ -9,7 +9,10 @@ channel_gossip_bad_message,0x8004
# These are due to peer.
channel_peer_write_failed,0x8010
channel_peer_read_failed,0x8011
channel_peer_bad_message,0x8012
channel_peer_bad_message,,len,u16
channel_peer_bad_message,,msg,len*u8
# Received and sent funding_locked
channel_normal_operation,1001

1 # Shouldn't happen
9 channel_peer_write_failed,0x8010
10 channel_peer_read_failed,0x8011
11 channel_peer_bad_message,0x8012
12 channel_peer_bad_message,,len,u16
13 # Received and sent funding_locked channel_peer_bad_message,,msg,len*u8
14 # Received and sent funding_locked
15 channel_normal_operation,1001
16 channel_normal_operation,1001 #include <lightningd/cryptomsg.h>
17 #include <lightningd/cryptomsg.h> #include <lightningd/channel_config.h>
18 #include <lightningd/channel_config.h> # Begin! (passes gossipd-client fd)

View File

@ -99,13 +99,14 @@ static int gossip_msg(struct subd *gossip, const u8 *msg, const int *fds)
enum gossip_wire_type t = fromwire_peektype(msg);
switch (t) {
/* We don't get told about fatal errors. */
/* subd already logs fatal errors. */
case WIRE_GOSSIPSTATUS_INIT_FAILED:
case WIRE_GOSSIPSTATUS_BAD_NEW_PEER_REQUEST:
case WIRE_GOSSIPSTATUS_BAD_REQUEST:
case WIRE_GOSSIPSTATUS_FDPASS_FAILED:
case WIRE_GOSSIPSTATUS_BAD_RELEASE_REQUEST:
case WIRE_GOSSIPSTATUS_BAD_FAIL_REQUEST:
break;
/* These are messages we send, not them. */
case WIRE_GOSSIPCTL_INIT:
case WIRE_GOSSIPCTL_NEW_PEER:

View File

@ -59,12 +59,13 @@ static int hsm_msg(struct subd *hsm, const u8 *msg, const int *fds)
: "unknown peer",
tal_hex(msg, badmsg));
/* We don't get called for failed status. */
/* subd already logs fatal errors. */
case WIRE_HSMSTATUS_INIT_FAILED:
case WIRE_HSMSTATUS_WRITEMSG_FAILED:
case WIRE_HSMSTATUS_BAD_REQUEST:
case WIRE_HSMSTATUS_FD_FAILED:
case WIRE_HSMSTATUS_KEY_FAILED:
break;
/* HSM doesn't send these */
case WIRE_HSMCTL_INIT:

View File

@ -940,6 +940,20 @@ static int peer_got_funding_locked(struct peer *peer, const u8 *msg)
return 0;
}
static int peer_got_bad_message(struct peer *peer, const u8 *msg)
{
u8 *err;
/* Don't try to fail this (again!) when owner dies. */
peer->owner = NULL;
if (!fromwire_channel_peer_bad_message(peer, NULL, NULL, &err))
err = (u8 *)tal_strdup(peer, "Internal error after bad message");
peer_fail_permanent(peer, take(err));
/* Kill daemon (though it's dying anyway) */
return -1;
}
static int channel_msg(struct subd *sd, const u8 *msg, const int *unused)
{
enum channel_wire_type t = fromwire_peektype(msg);
@ -961,7 +975,7 @@ static int channel_msg(struct subd *sd, const u8 *msg, const int *unused)
case WIRE_CHANNEL_GOT_FUNDING_LOCKED:
return peer_got_funding_locked(sd->peer, msg);
/* We never see fatal ones. */
/* We let peer_owner_finished handle these as transient errors. */
case WIRE_CHANNEL_BAD_COMMAND:
case WIRE_CHANNEL_HSM_FAILED:
case WIRE_CHANNEL_CRYPTO_FAILED:
@ -969,7 +983,12 @@ static int channel_msg(struct subd *sd, const u8 *msg, const int *unused)
case WIRE_CHANNEL_INTERNAL_ERROR:
case WIRE_CHANNEL_PEER_WRITE_FAILED:
case WIRE_CHANNEL_PEER_READ_FAILED:
return -1;
/* This is a permanent error. */
case WIRE_CHANNEL_PEER_BAD_MESSAGE:
return peer_got_bad_message(sd->peer, msg);
/* And we never get these from channeld. */
case WIRE_CHANNEL_INIT:
case WIRE_CHANNEL_FUNDING_LOCKED:

View File

@ -303,11 +303,12 @@ static struct io_plan *sd_msg_read(struct io_conn *conn, struct subd *sd)
if (type == STATUS_TRACE)
log_debug(sd->log, "TRACE: %.*s", str_len, str);
else if (type & STATUS_FAIL)
log_unusual(sd->log, "FAILURE %s: %.*s",
sd->msgname(type), str_len, str);
else {
log_info(sd->log, "UPDATE %s", sd->msgname(type));
if (type & STATUS_FAIL)
log_unusual(sd->log, "FAILURE %s: %.*s",
sd->msgname(type), str_len, str);
else
log_info(sd->log, "UPDATE %s", sd->msgname(type));
if (sd->msgcb) {
int i = sd->msgcb(sd, sd->msg_in, sd->fds_in);