@@ -16,10 +16,11 @@ use std::marker::PhantomData;
16
16
use std:: sync:: Arc ;
17
17
use tokio_util:: codec:: { Decoder , Encoder } ;
18
18
use types:: {
19
- BlobSidecar , ChainSpec , EthSpec , ForkContext , ForkName , Hash256 , LightClientBootstrap ,
20
- LightClientFinalityUpdate , LightClientOptimisticUpdate , RuntimeVariableList , SignedBeaconBlock ,
21
- SignedBeaconBlockAltair , SignedBeaconBlockBase , SignedBeaconBlockBellatrix ,
22
- SignedBeaconBlockCapella , SignedBeaconBlockDeneb , SignedBeaconBlockElectra ,
19
+ BlobSidecar , ChainSpec , DataColumnSidecar , EthSpec , ForkContext , ForkName , Hash256 ,
20
+ LightClientBootstrap , LightClientFinalityUpdate , LightClientOptimisticUpdate ,
21
+ RuntimeVariableList , SignedBeaconBlock , SignedBeaconBlockAltair , SignedBeaconBlockBase ,
22
+ SignedBeaconBlockBellatrix , SignedBeaconBlockCapella , SignedBeaconBlockDeneb ,
23
+ SignedBeaconBlockElectra ,
23
24
} ;
24
25
use unsigned_varint:: codec:: Uvi ;
25
26
@@ -70,6 +71,8 @@ impl<E: EthSpec> Encoder<RPCCodedResponse<E>> for SSZSnappyInboundCodec<E> {
70
71
RPCResponse :: BlocksByRoot ( res) => res. as_ssz_bytes ( ) ,
71
72
RPCResponse :: BlobsByRange ( res) => res. as_ssz_bytes ( ) ,
72
73
RPCResponse :: BlobsByRoot ( res) => res. as_ssz_bytes ( ) ,
74
+ RPCResponse :: DataColumnsByRoot ( res) => res. as_ssz_bytes ( ) ,
75
+ RPCResponse :: DataColumnsByRange ( res) => res. as_ssz_bytes ( ) ,
73
76
RPCResponse :: LightClientBootstrap ( res) => res. as_ssz_bytes ( ) ,
74
77
RPCResponse :: LightClientOptimisticUpdate ( res) => res. as_ssz_bytes ( ) ,
75
78
RPCResponse :: LightClientFinalityUpdate ( res) => res. as_ssz_bytes ( ) ,
@@ -224,6 +227,8 @@ impl<E: EthSpec> Encoder<OutboundRequest<E>> for SSZSnappyOutboundCodec<E> {
224
227
} ,
225
228
OutboundRequest :: BlobsByRange ( req) => req. as_ssz_bytes ( ) ,
226
229
OutboundRequest :: BlobsByRoot ( req) => req. blob_ids . as_ssz_bytes ( ) ,
230
+ OutboundRequest :: DataColumnsByRange ( req) => req. as_ssz_bytes ( ) ,
231
+ OutboundRequest :: DataColumnsByRoot ( req) => req. data_column_ids . as_ssz_bytes ( ) ,
227
232
OutboundRequest :: Ping ( req) => req. as_ssz_bytes ( ) ,
228
233
OutboundRequest :: MetaData ( _) => return Ok ( ( ) ) , // no metadata to encode
229
234
} ;
@@ -414,7 +419,12 @@ fn context_bytes<E: EthSpec>(
414
419
}
415
420
} ;
416
421
}
417
- RPCResponse :: BlobsByRange ( _) | RPCResponse :: BlobsByRoot ( _) => {
422
+ RPCResponse :: BlobsByRange ( _)
423
+ | RPCResponse :: BlobsByRoot ( _)
424
+ | RPCResponse :: DataColumnsByRoot ( _)
425
+ | RPCResponse :: DataColumnsByRange ( _) => {
426
+ // TODO(das): If DataColumnSidecar is defined as an Electra type, update the
427
+ // context bytes to point to ForkName::Electra
418
428
return fork_context. to_context_bytes ( ForkName :: Deneb ) ;
419
429
}
420
430
RPCResponse :: LightClientBootstrap ( lc_bootstrap) => {
@@ -512,6 +522,17 @@ fn handle_rpc_request<E: EthSpec>(
512
522
) ?,
513
523
} ) ) )
514
524
}
525
+ SupportedProtocol :: DataColumnsByRootV1 => Ok ( Some ( InboundRequest :: DataColumnsByRoot (
526
+ DataColumnsByRootRequest {
527
+ data_column_ids : RuntimeVariableList :: from_ssz_bytes (
528
+ decoded_buffer,
529
+ spec. max_request_data_column_sidecars as usize ,
530
+ ) ?,
531
+ } ,
532
+ ) ) ) ,
533
+ SupportedProtocol :: DataColumnsByRangeV1 => Ok ( Some ( InboundRequest :: DataColumnsByRange (
534
+ DataColumnsByRangeRequest :: from_ssz_bytes ( decoded_buffer) ?,
535
+ ) ) ) ,
515
536
SupportedProtocol :: PingV1 => Ok ( Some ( InboundRequest :: Ping ( Ping {
516
537
data : u64:: from_ssz_bytes ( decoded_buffer) ?,
517
538
} ) ) ) ,
@@ -604,6 +625,51 @@ fn handle_rpc_response<E: EthSpec>(
604
625
) ,
605
626
) ) ,
606
627
} ,
628
+ SupportedProtocol :: DataColumnsByRootV1 => match fork_name {
629
+ Some ( fork_name) => {
630
+ // TODO(das): PeerDAS is currently supported for both deneb and electra. This check
631
+ // does not advertise the topic on deneb, simply allows it to decode it. Advertise
632
+ // logic is in `SupportedTopic::currently_supported`.
633
+ if fork_name. deneb_enabled ( ) {
634
+ Ok ( Some ( RPCResponse :: DataColumnsByRoot ( Arc :: new (
635
+ DataColumnSidecar :: from_ssz_bytes ( decoded_buffer) ?,
636
+ ) ) ) )
637
+ } else {
638
+ Err ( RPCError :: ErrorResponse (
639
+ RPCResponseErrorCode :: InvalidRequest ,
640
+ "Invalid fork name for data columns by root" . to_string ( ) ,
641
+ ) )
642
+ }
643
+ }
644
+ None => Err ( RPCError :: ErrorResponse (
645
+ RPCResponseErrorCode :: InvalidRequest ,
646
+ format ! (
647
+ "No context bytes provided for {:?} response" ,
648
+ versioned_protocol
649
+ ) ,
650
+ ) ) ,
651
+ } ,
652
+ SupportedProtocol :: DataColumnsByRangeV1 => match fork_name {
653
+ Some ( fork_name) => {
654
+ if fork_name. deneb_enabled ( ) {
655
+ Ok ( Some ( RPCResponse :: DataColumnsByRange ( Arc :: new (
656
+ DataColumnSidecar :: from_ssz_bytes ( decoded_buffer) ?,
657
+ ) ) ) )
658
+ } else {
659
+ Err ( RPCError :: ErrorResponse (
660
+ RPCResponseErrorCode :: InvalidRequest ,
661
+ "Invalid fork name for data columns by range" . to_string ( ) ,
662
+ ) )
663
+ }
664
+ }
665
+ None => Err ( RPCError :: ErrorResponse (
666
+ RPCResponseErrorCode :: InvalidRequest ,
667
+ format ! (
668
+ "No context bytes provided for {:?} response" ,
669
+ versioned_protocol
670
+ ) ,
671
+ ) ) ,
672
+ } ,
607
673
SupportedProtocol :: PingV1 => Ok ( Some ( RPCResponse :: Pong ( Ping {
608
674
data : u64:: from_ssz_bytes ( decoded_buffer) ?,
609
675
} ) ) ) ,
@@ -747,7 +813,8 @@ mod tests {
747
813
use crate :: types:: { EnrAttestationBitfield , EnrSyncCommitteeBitfield } ;
748
814
use types:: {
749
815
blob_sidecar:: BlobIdentifier , BeaconBlock , BeaconBlockAltair , BeaconBlockBase ,
750
- BeaconBlockBellatrix , EmptyBlock , Epoch , FullPayload , Signature , Slot ,
816
+ BeaconBlockBellatrix , DataColumnIdentifier , EmptyBlock , Epoch , FullPayload , Signature ,
817
+ Slot ,
751
818
} ;
752
819
753
820
type Spec = types:: MainnetEthSpec ;
@@ -794,6 +861,10 @@ mod tests {
794
861
Arc :: new ( BlobSidecar :: empty ( ) )
795
862
}
796
863
864
+ fn empty_data_column_sidecar ( ) -> Arc < DataColumnSidecar < Spec > > {
865
+ Arc :: new ( DataColumnSidecar :: empty ( ) )
866
+ }
867
+
797
868
/// Bellatrix block with length < max_rpc_size.
798
869
fn bellatrix_block_small (
799
870
fork_context : & ForkContext ,
@@ -855,6 +926,27 @@ mod tests {
855
926
}
856
927
}
857
928
929
+ fn dcbrange_request ( ) -> DataColumnsByRangeRequest {
930
+ DataColumnsByRangeRequest {
931
+ start_slot : 0 ,
932
+ count : 10 ,
933
+ columns : vec ! [ 1 , 2 , 3 ] ,
934
+ }
935
+ }
936
+
937
+ fn dcbroot_request ( spec : & ChainSpec ) -> DataColumnsByRootRequest {
938
+ DataColumnsByRootRequest {
939
+ data_column_ids : RuntimeVariableList :: new (
940
+ vec ! [ DataColumnIdentifier {
941
+ block_root: Hash256 :: zero( ) ,
942
+ index: 0 ,
943
+ } ] ,
944
+ spec. max_request_data_column_sidecars as usize ,
945
+ )
946
+ . unwrap ( ) ,
947
+ }
948
+ }
949
+
858
950
fn bbroot_request_v1 ( spec : & ChainSpec ) -> BlocksByRootRequest {
859
951
BlocksByRootRequest :: new_v1 ( vec ! [ Hash256 :: zero( ) ] , spec)
860
952
}
@@ -1012,6 +1104,12 @@ mod tests {
1012
1104
OutboundRequest :: BlobsByRoot ( bbroot) => {
1013
1105
assert_eq ! ( decoded, InboundRequest :: BlobsByRoot ( bbroot) )
1014
1106
}
1107
+ OutboundRequest :: DataColumnsByRoot ( dcbroot) => {
1108
+ assert_eq ! ( decoded, InboundRequest :: DataColumnsByRoot ( dcbroot) )
1109
+ }
1110
+ OutboundRequest :: DataColumnsByRange ( dcbrange) => {
1111
+ assert_eq ! ( decoded, InboundRequest :: DataColumnsByRange ( dcbrange) )
1112
+ }
1015
1113
OutboundRequest :: Ping ( ping) => {
1016
1114
assert_eq ! ( decoded, InboundRequest :: Ping ( ping) )
1017
1115
}
@@ -1138,6 +1236,34 @@ mod tests {
1138
1236
) ,
1139
1237
Ok ( Some ( RPCResponse :: BlobsByRoot ( empty_blob_sidecar( ) ) ) ) ,
1140
1238
) ;
1239
+
1240
+ assert_eq ! (
1241
+ encode_then_decode_response(
1242
+ SupportedProtocol :: DataColumnsByRangeV1 ,
1243
+ RPCCodedResponse :: Success ( RPCResponse :: DataColumnsByRange (
1244
+ empty_data_column_sidecar( )
1245
+ ) ) ,
1246
+ ForkName :: Deneb ,
1247
+ & chain_spec
1248
+ ) ,
1249
+ Ok ( Some ( RPCResponse :: DataColumnsByRange (
1250
+ empty_data_column_sidecar( )
1251
+ ) ) ) ,
1252
+ ) ;
1253
+
1254
+ assert_eq ! (
1255
+ encode_then_decode_response(
1256
+ SupportedProtocol :: DataColumnsByRootV1 ,
1257
+ RPCCodedResponse :: Success ( RPCResponse :: DataColumnsByRoot (
1258
+ empty_data_column_sidecar( )
1259
+ ) ) ,
1260
+ ForkName :: Deneb ,
1261
+ & chain_spec
1262
+ ) ,
1263
+ Ok ( Some ( RPCResponse :: DataColumnsByRoot (
1264
+ empty_data_column_sidecar( )
1265
+ ) ) ) ,
1266
+ ) ;
1141
1267
}
1142
1268
1143
1269
// Test RPCResponse encoding/decoding for V1 messages
@@ -1491,6 +1617,8 @@ mod tests {
1491
1617
OutboundRequest :: MetaData ( MetadataRequest :: new_v1 ( ) ) ,
1492
1618
OutboundRequest :: BlobsByRange ( blbrange_request ( ) ) ,
1493
1619
OutboundRequest :: BlobsByRoot ( blbroot_request ( & chain_spec) ) ,
1620
+ OutboundRequest :: DataColumnsByRange ( dcbrange_request ( ) ) ,
1621
+ OutboundRequest :: DataColumnsByRoot ( dcbroot_request ( & chain_spec) ) ,
1494
1622
OutboundRequest :: MetaData ( MetadataRequest :: new_v2 ( ) ) ,
1495
1623
] ;
1496
1624
0 commit comments