mirror of
https://github.com/aljazceru/lightning.git
synced 2025-12-19 23:24:27 +01:00
lightningd: expose full onion error when we have it.
Mainly useful for testing. In particular, we don't save it to the db. Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
This commit is contained in:
committed by
Christian Decker
parent
189b2f1313
commit
d943d8abbc
@@ -25,6 +25,8 @@ struct routing_failure {
|
|||||||
struct node_id erring_node;
|
struct node_id erring_node;
|
||||||
struct short_channel_id erring_channel;
|
struct short_channel_id erring_channel;
|
||||||
int channel_dir;
|
int channel_dir;
|
||||||
|
/* If remote sent us a message, this is it. */
|
||||||
|
const u8 *msg;
|
||||||
};
|
};
|
||||||
|
|
||||||
/* sendpay command */
|
/* sendpay command */
|
||||||
@@ -126,7 +128,8 @@ json_add_routefail_info(struct json_stream *js,
|
|||||||
enum onion_type failcode,
|
enum onion_type failcode,
|
||||||
const struct node_id *erring_node,
|
const struct node_id *erring_node,
|
||||||
const struct short_channel_id *erring_channel,
|
const struct short_channel_id *erring_channel,
|
||||||
int channel_dir)
|
int channel_dir,
|
||||||
|
const u8 *msg)
|
||||||
{
|
{
|
||||||
const char *failcodename = onion_type_name(failcode);
|
const char *failcodename = onion_type_name(failcode);
|
||||||
|
|
||||||
@@ -138,6 +141,8 @@ json_add_routefail_info(struct json_stream *js,
|
|||||||
json_add_node_id(js, "erring_node", erring_node);
|
json_add_node_id(js, "erring_node", erring_node);
|
||||||
json_add_short_channel_id(js, "erring_channel", erring_channel);
|
json_add_short_channel_id(js, "erring_channel", erring_channel);
|
||||||
json_add_num(js, "erring_direction", channel_dir);
|
json_add_num(js, "erring_direction", channel_dir);
|
||||||
|
if (msg)
|
||||||
|
json_add_hex_talarr(js, "raw_message", msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* onionreply used if pay_errcode == PAY_UNPARSEABLE_ONION */
|
/* onionreply used if pay_errcode == PAY_UNPARSEABLE_ONION */
|
||||||
@@ -168,7 +173,8 @@ sendpay_fail(struct command *cmd,
|
|||||||
fail->failcode,
|
fail->failcode,
|
||||||
&fail->erring_node,
|
&fail->erring_node,
|
||||||
&fail->erring_channel,
|
&fail->erring_channel,
|
||||||
fail->channel_dir);
|
fail->channel_dir,
|
||||||
|
fail->msg);
|
||||||
json_object_end(data);
|
json_object_end(data);
|
||||||
return command_failed(cmd, data);
|
return command_failed(cmd, data);
|
||||||
}
|
}
|
||||||
@@ -254,6 +260,7 @@ immediate_routing_failure(const tal_t *ctx,
|
|||||||
routing_failure->erring_node = ld->id;
|
routing_failure->erring_node = ld->id;
|
||||||
routing_failure->erring_channel = *channel0;
|
routing_failure->erring_channel = *channel0;
|
||||||
routing_failure->channel_dir = node_id_idx(&ld->id, dstid);
|
routing_failure->channel_dir = node_id_idx(&ld->id, dstid);
|
||||||
|
routing_failure->msg = NULL;
|
||||||
|
|
||||||
return routing_failure;
|
return routing_failure;
|
||||||
}
|
}
|
||||||
@@ -277,6 +284,7 @@ local_routing_failure(const tal_t *ctx,
|
|||||||
routing_failure->erring_channel = payment->route_channels[0];
|
routing_failure->erring_channel = payment->route_channels[0];
|
||||||
routing_failure->channel_dir = node_id_idx(&ld->id,
|
routing_failure->channel_dir = node_id_idx(&ld->id,
|
||||||
&payment->route_nodes[0]);
|
&payment->route_nodes[0]);
|
||||||
|
routing_failure->msg = NULL;
|
||||||
|
|
||||||
log_debug(hout->key.channel->log, "local_routing_failure: %u (%s)",
|
log_debug(hout->key.channel->log, "local_routing_failure: %u (%s)",
|
||||||
hout->failcode, onion_type_name(hout->failcode));
|
hout->failcode, onion_type_name(hout->failcode));
|
||||||
@@ -368,6 +376,8 @@ remote_routing_failure(const tal_t *ctx,
|
|||||||
routing_failure->erring_node = *erring_node;
|
routing_failure->erring_node = *erring_node;
|
||||||
routing_failure->erring_channel = *erring_channel;
|
routing_failure->erring_channel = *erring_channel;
|
||||||
routing_failure->channel_dir = dir;
|
routing_failure->channel_dir = dir;
|
||||||
|
routing_failure->msg = tal_dup_arr(routing_failure, u8, failure->msg,
|
||||||
|
tal_count(failure->msg), 0);
|
||||||
|
|
||||||
return routing_failure;
|
return routing_failure;
|
||||||
}
|
}
|
||||||
@@ -466,6 +476,8 @@ void payment_failed(struct lightningd *ld, const struct htlc_out *hout,
|
|||||||
hout->key.id,
|
hout->key.id,
|
||||||
reply->origin_index,
|
reply->origin_index,
|
||||||
failcode, onion_type_name(failcode));
|
failcode, onion_type_name(failcode));
|
||||||
|
log_debug(hout->key.channel->log, "failmsg: %s",
|
||||||
|
tal_hex(tmpctx, reply->msg));
|
||||||
fail = remote_routing_failure(tmpctx, ld,
|
fail = remote_routing_failure(tmpctx, ld,
|
||||||
payment, reply,
|
payment, reply,
|
||||||
hout->key.channel->log,
|
hout->key.channel->log,
|
||||||
@@ -559,6 +571,8 @@ static struct command_result *wait_payment(struct lightningd *ld,
|
|||||||
fail->erring_node = *failnode;
|
fail->erring_node = *failnode;
|
||||||
fail->erring_channel = *failchannel;
|
fail->erring_channel = *failchannel;
|
||||||
fail->channel_dir = faildirection;
|
fail->channel_dir = faildirection;
|
||||||
|
/* FIXME: We don't store this! */
|
||||||
|
fail->msg = NULL;
|
||||||
return sendpay_fail(cmd,
|
return sendpay_fail(cmd,
|
||||||
faildestperm
|
faildestperm
|
||||||
? PAY_DESTINATION_PERM_FAIL
|
? PAY_DESTINATION_PERM_FAIL
|
||||||
@@ -673,7 +687,8 @@ send_payment(struct lightningd *ld,
|
|||||||
|
|
||||||
json_add_routefail_info(data, 0, WIRE_UNKNOWN_NEXT_PEER,
|
json_add_routefail_info(data, 0, WIRE_UNKNOWN_NEXT_PEER,
|
||||||
&ld->id, &route[0].channel_id,
|
&ld->id, &route[0].channel_id,
|
||||||
node_id_idx(&ld->id, &route[0].nodeid));
|
node_id_idx(&ld->id, &route[0].nodeid),
|
||||||
|
NULL);
|
||||||
json_object_end(data);
|
json_object_end(data);
|
||||||
return command_failed(cmd, data);
|
return command_failed(cmd, data);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2190,3 +2190,25 @@ def test_channel_drainage(node_factory, bitcoind):
|
|||||||
route = l2.rpc.getroute(l1.info['id'], amount, riskfactor=1, fuzzpercent=0)['route']
|
route = l2.rpc.getroute(l1.info['id'], amount, riskfactor=1, fuzzpercent=0)['route']
|
||||||
l2.rpc.sendpay(route, payment_hash)
|
l2.rpc.sendpay(route, payment_hash)
|
||||||
l2.rpc.waitsendpay(payment_hash, TIMEOUT)
|
l2.rpc.waitsendpay(payment_hash, TIMEOUT)
|
||||||
|
|
||||||
|
|
||||||
|
def test_error_returns_blockheight(node_factory, bitcoind):
|
||||||
|
"""Test that incorrect_or_unknown_payment_details returns block height"""
|
||||||
|
l1, l2 = node_factory.line_graph(2)
|
||||||
|
|
||||||
|
l1.rpc.sendpay([{'msatoshi': 100,
|
||||||
|
'id': l2.info['id'],
|
||||||
|
'delay': 10,
|
||||||
|
'channel': l1.get_channel_scid(l2)}],
|
||||||
|
'00' * 32)
|
||||||
|
|
||||||
|
with pytest.raises(RpcError, match=r"INCORRECT_OR_UNKNOWN_PAYMENT_DETAILS.*'erring_index': 1") as err:
|
||||||
|
l1.rpc.waitsendpay('00' * 32, TIMEOUT)
|
||||||
|
|
||||||
|
# BOLT #4:
|
||||||
|
# 1. type: PERM|15 (`incorrect_or_unknown_payment_details`)
|
||||||
|
# 2. data:
|
||||||
|
# * [`u64`:`htlc_msat`]
|
||||||
|
# * [`u32`:`height`]
|
||||||
|
assert (err.value.error['data']['raw_message']
|
||||||
|
== '400f{:016x}{:08x}'.format(100, bitcoind.rpc.getblockcount()))
|
||||||
|
|||||||
Reference in New Issue
Block a user