@@ -174,8 +174,13 @@ macro_rules! decode_tlv {
174174 } } ;
175175}
176176
177+ // `$decode_custom_tlv` is a closure that may be optionally provided to handle custom message types.
178+ // If it is provided, it will be called with the custom type and the `FixedLengthReader` containing
179+ // the message contents. It should return `Ok(true)` if the custom message is successfully parsed,
180+ // `Ok(false)` if the message type is unknown, and `Err(DecodeError)` if parsing fails.
177181macro_rules! decode_tlv_stream {
178- ( $stream: expr, { $( ( $type: expr, $field: ident, $fieldty: tt) ) ,* $( , ) * } ) => { {
182+ ( $stream: expr, { $( ( $type: expr, $field: ident, $fieldty: tt) ) ,* $( , ) * }
183+ $( , $decode_custom_tlv: expr) ?) => { {
179184 use ln:: msgs:: DecodeError ;
180185 let mut last_seen_type: Option <u64 > = None ;
181186 let mut stream_ref = $stream;
@@ -226,10 +231,19 @@ macro_rules! decode_tlv_stream {
226231 return Err ( DecodeError :: InvalidValue ) ;
227232 }
228233 } , ) *
229- x if x % 2 == 0 => {
230- return Err ( DecodeError :: UnknownRequiredFeature ) ;
231- } ,
232- _ => { } ,
234+ t => {
235+ $(
236+ if $decode_custom_tlv( t, & mut s) ? {
237+ // If a custom TLV was successfully read (i.e. decode_custom_tlv returns true),
238+ // continue to the next TLV read.
239+ s. eat_remaining( ) ?;
240+ continue ' tlv_read;
241+ }
242+ ) ?
243+ if t % 2 == 0 {
244+ return Err ( DecodeError :: UnknownRequiredFeature ) ;
245+ }
246+ }
233247 }
234248 s. eat_remaining( ) ?;
235249 }
0 commit comments