@@ -3020,6 +3020,61 @@ where
3020
3020
}
3021
3021
}
3022
3022
3023
+ fn process_failed_accept_err(
3024
+ &self, msg: &msgs::UpdateAddHTLC, counterparty_node_id: &PublicKey, err_msg: &'static str,
3025
+ mut err_code: u16, chan_update: Option<msgs::ChannelUpdate>, is_intro_node_forward: bool,
3026
+ shared_secret: &[u8; 32]
3027
+ ) -> HTLCFailureMsg {
3028
+ let mut res = VecWriter(Vec::with_capacity(chan_update.serialized_length() + 2 + 8 + 2));
3029
+ if let Some(chan_update) = chan_update {
3030
+ if err_code == 0x1000 | 11 || err_code == 0x1000 | 12 {
3031
+ msg.amount_msat.write(&mut res).expect("Writes cannot fail");
3032
+ }
3033
+ else if err_code == 0x1000 | 13 {
3034
+ msg.cltv_expiry.write(&mut res).expect("Writes cannot fail");
3035
+ }
3036
+ else if err_code == 0x1000 | 20 {
3037
+ // TODO: underspecified, follow https://github.com/lightning/bolts/issues/791
3038
+ 0u16.write(&mut res).expect("Writes cannot fail");
3039
+ }
3040
+ (chan_update.serialized_length() as u16 + 2).write(&mut res).expect("Writes cannot fail");
3041
+ msgs::ChannelUpdate::TYPE.write(&mut res).expect("Writes cannot fail");
3042
+ chan_update.write(&mut res).expect("Writes cannot fail");
3043
+ } else if err_code & 0x1000 == 0x1000 {
3044
+ // If we're trying to return an error that requires a `channel_update` but
3045
+ // we're forwarding to a phantom or intercept "channel" (i.e. cannot
3046
+ // generate an update), just use the generic "temporary_node_failure"
3047
+ // instead.
3048
+ err_code = 0x2000 | 2;
3049
+ }
3050
+
3051
+ log_info!(
3052
+ WithContext::from(&self.logger, Some(*counterparty_node_id), Some(msg.channel_id)),
3053
+ "Failed to accept/forward incoming HTLC: {}", err_msg
3054
+ );
3055
+ // If `msg.blinding_point` is set, we must always fail with malformed.
3056
+ if msg.blinding_point.is_some() {
3057
+ return HTLCFailureMsg::Malformed(msgs::UpdateFailMalformedHTLC {
3058
+ channel_id: msg.channel_id,
3059
+ htlc_id: msg.htlc_id,
3060
+ sha256_of_onion: [0; 32],
3061
+ failure_code: INVALID_ONION_BLINDING,
3062
+ });
3063
+ }
3064
+
3065
+ let (err_code, err_data) = if is_intro_node_forward {
3066
+ (INVALID_ONION_BLINDING, &[0; 32][..])
3067
+ } else {
3068
+ (err_code, &res.0[..])
3069
+ };
3070
+ HTLCFailureMsg::Relay(msgs::UpdateFailHTLC {
3071
+ channel_id: msg.channel_id,
3072
+ htlc_id: msg.htlc_id,
3073
+ reason: HTLCFailReason::reason(err_code, err_data.to_vec())
3074
+ .get_encrypted_failure_packet(shared_secret, &None),
3075
+ })
3076
+ }
3077
+
3023
3078
fn decode_update_add_htlc_onion(
3024
3079
&self, msg: &msgs::UpdateAddHTLC, counterparty_node_id: &PublicKey,
3025
3080
) -> Result<
@@ -3038,36 +3093,6 @@ where
3038
3093
_ => false,
3039
3094
};
3040
3095
3041
- macro_rules! return_err {
3042
- ($msg: expr, $err_code: expr, $data: expr) => {
3043
- {
3044
- log_info!(
3045
- WithContext::from(&self.logger, Some(*counterparty_node_id), Some(msg.channel_id)),
3046
- "Failed to accept/forward incoming HTLC: {}", $msg
3047
- );
3048
- // If `msg.blinding_point` is set, we must always fail with malformed.
3049
- if msg.blinding_point.is_some() {
3050
- return Err(HTLCFailureMsg::Malformed(msgs::UpdateFailMalformedHTLC {
3051
- channel_id: msg.channel_id,
3052
- htlc_id: msg.htlc_id,
3053
- sha256_of_onion: [0; 32],
3054
- failure_code: INVALID_ONION_BLINDING,
3055
- }));
3056
- }
3057
-
3058
- let (err_code, err_data) = if is_intro_node_forward {
3059
- (INVALID_ONION_BLINDING, &[0; 32][..])
3060
- } else { ($err_code, $data) };
3061
- return Err(HTLCFailureMsg::Relay(msgs::UpdateFailHTLC {
3062
- channel_id: msg.channel_id,
3063
- htlc_id: msg.htlc_id,
3064
- reason: HTLCFailReason::reason(err_code, err_data.to_vec())
3065
- .get_encrypted_failure_packet(&shared_secret, &None),
3066
- }));
3067
- }
3068
- }
3069
- }
3070
-
3071
3096
let NextPacketDetails {
3072
3097
next_packet_pubkey, outgoing_amt_msat, outgoing_scid, outgoing_cltv_value
3073
3098
} = match next_packet_details_opt {
@@ -3078,7 +3103,7 @@ where
3078
3103
3079
3104
// Perform outbound checks here instead of in [`Self::construct_pending_htlc_info`] because we
3080
3105
// can't hold the outbound peer state lock at the same time as the inbound peer state lock.
3081
- if let Some((err, mut code, chan_update)) = loop {
3106
+ if let Some((err, code, chan_update)) = loop {
3082
3107
let id_option = self.short_to_chan_info.read().unwrap().get(&outgoing_scid).cloned();
3083
3108
let forwarding_chan_info_opt = match id_option {
3084
3109
None => { // unknown_next_peer
@@ -3171,29 +3196,9 @@ where
3171
3196
break None;
3172
3197
}
3173
3198
{
3174
- let mut res = VecWriter(Vec::with_capacity(chan_update.serialized_length() + 2 + 8 + 2));
3175
- if let Some(chan_update) = chan_update {
3176
- if code == 0x1000 | 11 || code == 0x1000 | 12 {
3177
- msg.amount_msat.write(&mut res).expect("Writes cannot fail");
3178
- }
3179
- else if code == 0x1000 | 13 {
3180
- msg.cltv_expiry.write(&mut res).expect("Writes cannot fail");
3181
- }
3182
- else if code == 0x1000 | 20 {
3183
- // TODO: underspecified, follow https://github.com/lightning/bolts/issues/791
3184
- 0u16.write(&mut res).expect("Writes cannot fail");
3185
- }
3186
- (chan_update.serialized_length() as u16 + 2).write(&mut res).expect("Writes cannot fail");
3187
- msgs::ChannelUpdate::TYPE.write(&mut res).expect("Writes cannot fail");
3188
- chan_update.write(&mut res).expect("Writes cannot fail");
3189
- } else if code & 0x1000 == 0x1000 {
3190
- // If we're trying to return an error that requires a `channel_update` but
3191
- // we're forwarding to a phantom or intercept "channel" (i.e. cannot
3192
- // generate an update), just use the generic "temporary_node_failure"
3193
- // instead.
3194
- code = 0x2000 | 2;
3195
- }
3196
- return_err!(err, code, &res.0[..]);
3199
+ return Err(self.process_failed_accept_err(
3200
+ msg, counterparty_node_id, err, code, chan_update, is_intro_node_forward, &shared_secret
3201
+ ));
3197
3202
}
3198
3203
Ok((next_hop, shared_secret, Some(next_packet_pubkey)))
3199
3204
}
0 commit comments