@@ -33,6 +33,14 @@ mod sealed { // You should just use the type aliases instead.
33
33
pub trait VariableLengthOnion : Context { }
34
34
impl VariableLengthOnion for InitContext { }
35
35
impl VariableLengthOnion for NodeContext { }
36
+
37
+ pub trait PaymentSecret : Context { }
38
+ impl PaymentSecret for InitContext { }
39
+ impl PaymentSecret for NodeContext { }
40
+
41
+ pub trait BasicMPP : Context { }
42
+ impl BasicMPP for InitContext { }
43
+ impl BasicMPP for NodeContext { }
36
44
}
37
45
38
46
/// Tracks the set of features which a node implements, templated by the context in which it
@@ -73,7 +81,7 @@ impl InitFeatures {
73
81
/// Create a Features with the features we support
74
82
pub fn supported ( ) -> InitFeatures {
75
83
InitFeatures {
76
- flags : vec ! [ 2 | 1 << 5 , 1 << ( 9 -8 ) ] ,
84
+ flags : vec ! [ 2 | 1 << 5 , 1 << ( 9 -8 ) | 1 << ( 15 - 8 ) , 1 << ( 17 - 8 * 2 ) ] ,
77
85
mark : PhantomData ,
78
86
}
79
87
}
@@ -136,14 +144,14 @@ impl NodeFeatures {
136
144
#[ cfg( not( feature = "fuzztarget" ) ) ]
137
145
pub ( crate ) fn supported ( ) -> NodeFeatures {
138
146
NodeFeatures {
139
- flags : vec ! [ 2 | 1 << 5 , 1 << ( 9 -8 ) ] ,
147
+ flags : vec ! [ 2 | 1 << 5 , 1 << ( 9 -8 ) | 1 << ( 15 - 8 ) , 1 << ( 17 - 8 * 2 ) ] ,
140
148
mark : PhantomData ,
141
149
}
142
150
}
143
151
#[ cfg( feature = "fuzztarget" ) ]
144
152
pub fn supported ( ) -> NodeFeatures {
145
153
NodeFeatures {
146
- flags : vec ! [ 2 | 1 << 5 , 1 << ( 9 -8 ) ] ,
154
+ flags : vec ! [ 2 | 1 << 5 , 1 << ( 9 -8 ) | 1 << ( 15 - 8 ) , 1 << ( 17 - 8 * 2 ) ] ,
147
155
mark : PhantomData ,
148
156
}
149
157
}
@@ -199,8 +207,10 @@ impl<T: sealed::Context> Features<T> {
199
207
// unknown, upfront_shutdown_script, unknown (actually initial_routing_sync, but it
200
208
// is only valid as an optional feature), and data_loss_protect:
201
209
0 => ( byte & 0b01000100 ) ,
202
- // unknown, unknown, unknown, var_onion_optin:
203
- 1 => ( byte & 0b01010100 ) ,
210
+ // payment_secret, unknown, unknown, var_onion_optin:
211
+ 1 => ( byte & 0b00010100 ) ,
212
+ // unknown, unknown, unknown, basic_mpp:
213
+ 2 => ( byte & 0b01010100 ) ,
204
214
// fallback, all even bits set:
205
215
_ => ( byte & 0b01010101 ) ,
206
216
} ) != 0
@@ -213,8 +223,10 @@ impl<T: sealed::Context> Features<T> {
213
223
// unknown, upfront_shutdown_script, initial_routing_sync (is only valid as an
214
224
// optional feature), and data_loss_protect:
215
225
0 => ( byte & 0b11000100 ) ,
216
- // unknown, unknown, unknown, var_onion_optin:
217
- 1 => ( byte & 0b11111100 ) ,
226
+ // payment_secret, unknown, unknown, var_onion_optin:
227
+ 1 => ( byte & 0b00111100 ) ,
228
+ // unknown, unknown, unknown, basic_mpp:
229
+ 2 => ( byte & 0b11111100 ) ,
218
230
_ => byte,
219
231
} ) != 0
220
232
} )
@@ -228,16 +240,19 @@ impl<T: sealed::Context> Features<T> {
228
240
229
241
#[ cfg( test) ]
230
242
pub ( crate ) fn set_require_unknown_bits ( & mut self ) {
231
- let newlen = cmp:: max ( 2 , self . flags . len ( ) ) ;
243
+ let newlen = cmp:: max ( 3 , self . flags . len ( ) ) ;
232
244
self . flags . resize ( newlen, 0u8 ) ;
233
- self . flags [ 1 ] |= 0x40 ;
245
+ self . flags [ 2 ] |= 0x40 ;
234
246
}
235
247
236
248
#[ cfg( test) ]
237
249
pub ( crate ) fn clear_require_unknown_bits ( & mut self ) {
238
- let newlen = cmp:: max ( 2 , self . flags . len ( ) ) ;
250
+ let newlen = cmp:: max ( 3 , self . flags . len ( ) ) ;
239
251
self . flags . resize ( newlen, 0u8 ) ;
240
- self . flags [ 1 ] &= !0x40 ;
252
+ self . flags [ 2 ] &= !0x40 ;
253
+ if self . flags . len ( ) == 3 && self . flags [ 2 ] == 0 {
254
+ self . flags . resize ( 2 , 0u8 ) ;
255
+ }
241
256
if self . flags . len ( ) == 2 && self . flags [ 1 ] == 0 {
242
257
self . flags . resize ( 1 , 0u8 ) ;
243
258
}
@@ -279,6 +294,23 @@ impl<T: sealed::InitialRoutingSync> Features<T> {
279
294
}
280
295
}
281
296
297
+ impl < T : sealed:: PaymentSecret > Features < T > {
298
+ #[ allow( dead_code) ]
299
+ // Note that we never need to test this since what really matters is the invoice - iff the
300
+ // invoice provides a payment_secret, we assume all the way through that we can do MPP.
301
+ pub ( crate ) fn payment_secret ( & self ) -> bool {
302
+ self . flags . len ( ) > 1 && ( self . flags [ 1 ] & ( 3 << ( 12 -8 ) ) ) != 0
303
+ }
304
+ }
305
+
306
+ impl < T : sealed:: BasicMPP > Features < T > {
307
+ // We currently never test for this since we don't actually *generate* multipath routes.
308
+ #[ allow( dead_code) ]
309
+ pub ( crate ) fn basic_mpp ( & self ) -> bool {
310
+ self . flags . len ( ) > 2 && ( self . flags [ 2 ] & ( 3 << ( 16 -8 * 2 ) ) ) != 0
311
+ }
312
+ }
313
+
282
314
impl < T : sealed:: Context > Writeable for Features < T > {
283
315
fn write < W : Writer > ( & self , w : & mut W ) -> Result < ( ) , :: std:: io:: Error > {
284
316
w. size_hint ( self . flags . len ( ) + 2 ) ;
0 commit comments