@@ -5,14 +5,14 @@ package types
5
5
6
6
import (
7
7
"bytes"
8
- "encoding/binary"
9
8
"sort"
10
9
11
10
fieldparams "github.com/OffchainLabs/prysm/v6/config/fieldparams"
12
11
"github.com/OffchainLabs/prysm/v6/config/params"
12
+ "github.com/OffchainLabs/prysm/v6/encoding/ssz"
13
13
eth "github.com/OffchainLabs/prysm/v6/proto/prysm/v1alpha1"
14
14
"github.com/pkg/errors"
15
- ssz "github.com/prysmaticlabs/fastssz"
15
+ fastssz "github.com/prysmaticlabs/fastssz"
16
16
)
17
17
18
18
const (
@@ -25,11 +25,11 @@ type SSZBytes []byte
25
25
26
26
// HashTreeRoot hashes the uint64 object following the SSZ standard.
27
27
func (b * SSZBytes ) HashTreeRoot () ([32 ]byte , error ) {
28
- return ssz .HashWithDefaultHasher (b )
28
+ return fastssz .HashWithDefaultHasher (b )
29
29
}
30
30
31
31
// HashTreeRootWith hashes the uint64 object with the given hasher.
32
- func (b * SSZBytes ) HashTreeRootWith (hh * ssz .Hasher ) error {
32
+ func (b * SSZBytes ) HashTreeRootWith (hh * fastssz .Hasher ) error {
33
33
indx := hh .Index ()
34
34
hh .PutBytes (* b )
35
35
hh .Merkleize (indx )
@@ -74,7 +74,7 @@ func (r *BeaconBlockByRootsReq) UnmarshalSSZ(buf []byte) error {
74
74
return errors .Errorf ("expected buffer with length of up to %d but received length %d" , maxLength , bufLen )
75
75
}
76
76
if bufLen % fieldparams .RootLength != 0 {
77
- return ssz .ErrIncorrectByteSize
77
+ return fastssz .ErrIncorrectByteSize
78
78
}
79
79
numOfRoots := bufLen / fieldparams .RootLength
80
80
roots := make ([][fieldparams .RootLength ]byte , 0 , numOfRoots )
@@ -131,14 +131,6 @@ func (m *ErrorMessage) UnmarshalSSZ(buf []byte) error {
131
131
// BlobSidecarsByRootReq is used to specify a list of blob targets (root+index) in a BlobSidecarsByRoot RPC request.
132
132
type BlobSidecarsByRootReq []* eth.BlobIdentifier
133
133
134
- // BlobIdentifier is a fixed size value, so we can compute its fixed size at start time (see init below)
135
- var blobIdSize int
136
-
137
- // SizeSSZ returns the size of the serialized representation.
138
- func (b * BlobSidecarsByRootReq ) SizeSSZ () int {
139
- return len (* b ) * blobIdSize
140
- }
141
-
142
134
// MarshalSSZTo appends the serialized BlobSidecarsByRootReq value to the provided byte slice.
143
135
func (b * BlobSidecarsByRootReq ) MarshalSSZTo (dst []byte ) ([]byte , error ) {
144
136
// A List without an enclosing container is marshaled exactly like a vector, no length offset required.
@@ -151,38 +143,22 @@ func (b *BlobSidecarsByRootReq) MarshalSSZTo(dst []byte) ([]byte, error) {
151
143
152
144
// MarshalSSZ serializes the BlobSidecarsByRootReq value to a byte slice.
153
145
func (b * BlobSidecarsByRootReq ) MarshalSSZ () ([]byte , error ) {
154
- buf := make ([]byte , len (* b )* blobIdSize )
155
- for i , id := range * b {
156
- by , err := id .MarshalSSZ ()
157
- if err != nil {
158
- return nil , err
159
- }
160
- copy (buf [i * blobIdSize :(i + 1 )* blobIdSize ], by )
161
- }
162
- return buf , nil
146
+ return ssz.MarshalListFixedElement [* eth.BlobIdentifier ](* b )
163
147
}
164
148
149
+ func newBSBR () * eth.BlobIdentifier { return & eth.BlobIdentifier {} }
150
+
165
151
// UnmarshalSSZ unmarshals the provided bytes buffer into the
166
152
// BlobSidecarsByRootReq value.
167
153
func (b * BlobSidecarsByRootReq ) UnmarshalSSZ (buf []byte ) error {
168
- bufLen := len (buf )
169
- maxLength := int (params .BeaconConfig ().MaxRequestBlobSidecarsElectra ) * blobIdSize
170
- if bufLen > maxLength {
171
- return errors .Wrapf (ssz .ErrIncorrectListSize , "expected buffer with length of up to %d but received length %d" , maxLength , bufLen )
172
- }
173
- if bufLen % blobIdSize != 0 {
174
- return errors .Wrapf (ssz .ErrIncorrectByteSize , "size=%d" , bufLen )
154
+ v , err := ssz .UnmarshalListFixedElement [* eth.BlobIdentifier ](buf , newBSBR )
155
+ if err != nil {
156
+ return errors .Wrapf (err , "failed to unmarshal BlobSidecarsByRootReq" )
175
157
}
176
- count := bufLen / blobIdSize
177
- * b = make ([]* eth.BlobIdentifier , count )
178
- for i := 0 ; i < count ; i ++ {
179
- id := & eth.BlobIdentifier {}
180
- err := id .UnmarshalSSZ (buf [i * blobIdSize : (i + 1 )* blobIdSize ])
181
- if err != nil {
182
- return err
183
- }
184
- (* b )[i ] = id
158
+ if len (v ) > int (params .BeaconConfig ().MaxRequestBlobSidecarsElectra ) {
159
+ return ErrMaxBlobReqExceeded
185
160
}
161
+ * b = v
186
162
return nil
187
163
}
188
164
@@ -213,102 +189,25 @@ func (s BlobSidecarsByRootReq) Len() int {
213
189
// ====================================
214
190
// DataColumnsByRootIdentifiers section
215
191
// ====================================
216
- var _ ssz .Marshaler = DataColumnsByRootIdentifiers {}
217
- var _ ssz .Unmarshaler = ( * DataColumnsByRootIdentifiers )( nil )
192
+ var _ fastssz .Marshaler = & DataColumnsByRootIdentifiers {}
193
+ var _ fastssz .Unmarshaler = & DataColumnsByRootIdentifiers {}
218
194
219
195
// DataColumnsByRootIdentifiers is used to specify a list of data column targets (root+index) in a DataColumnSidecarsByRoot RPC request.
220
196
type DataColumnsByRootIdentifiers []* eth.DataColumnsByRootIdentifier
221
197
222
- // DataColumnIdentifier is a fixed size value, so we can compute its fixed size at start time (see init below)
223
- var dataColumnIdSize int
198
+ func newDCRI () * eth.DataColumnsByRootIdentifier { return & eth.DataColumnsByRootIdentifier {} }
224
199
225
- // UnmarshalSSZ implements ssz.Unmarshaler. It unmarshals the provided bytes buffer into the DataColumnSidecarsByRootReq value.
226
200
func (d * DataColumnsByRootIdentifiers ) UnmarshalSSZ (buf []byte ) error {
227
- // Exit early if the buffer is too small.
228
- if len (buf ) < bytesPerLengthOffset {
229
- return nil
230
- }
231
-
232
- // Get the size of the offsets.
233
- offsetEnd := binary .LittleEndian .Uint32 (buf [:bytesPerLengthOffset ])
234
- if offsetEnd % bytesPerLengthOffset != 0 {
235
- return errors .Errorf ("expected offsets size to be a multiple of %d but got %d" , bytesPerLengthOffset , offsetEnd )
236
- }
237
-
238
- count := offsetEnd / bytesPerLengthOffset
239
- if count < 1 {
240
- return nil
241
- }
242
-
243
- maxSize := params .BeaconConfig ().MaxRequestBlocksDeneb
244
- if uint64 (count ) > maxSize {
245
- return errors .Errorf ("data column identifiers list exceeds max size: %d > %d" , count , maxSize )
246
- }
247
-
248
- if offsetEnd > uint32 (len (buf )) {
249
- return errors .Errorf ("offsets value %d larger than buffer %d" , offsetEnd , len (buf ))
250
- }
251
- valueStart := offsetEnd
252
-
253
- // Decode the identifers.
254
- * d = make ([]* eth.DataColumnsByRootIdentifier , count )
255
- var start uint32
256
- end := uint32 (len (buf ))
257
- for i := count ; i > 0 ; i -- {
258
- offsetEnd -= bytesPerLengthOffset
259
- start = binary .LittleEndian .Uint32 (buf [offsetEnd : offsetEnd + bytesPerLengthOffset ])
260
- if start > end {
261
- return errors .Errorf ("expected offset[%d] %d to be less than %d" , i - 1 , start , end )
262
- }
263
- if start < valueStart {
264
- return errors .Errorf ("offset[%d] %d indexes before value section %d" , i - 1 , start , valueStart )
265
- }
266
- // Decode the identifier.
267
- ident := & eth.DataColumnsByRootIdentifier {}
268
- if err := ident .UnmarshalSSZ (buf [start :end ]); err != nil {
269
- return err
270
- }
271
- (* d )[i - 1 ] = ident
272
- end = start
201
+ v , err := ssz .UnmarshalListVariableElement [* eth.DataColumnsByRootIdentifier ](buf , newDCRI )
202
+ if err != nil {
203
+ return errors .Wrapf (err , "failed to unmarshal DataColumnsByRootIdentifiers" )
273
204
}
274
-
205
+ * d = v
275
206
return nil
276
207
}
277
208
278
- func (d DataColumnsByRootIdentifiers ) MarshalSSZ () ([]byte , error ) {
279
- var err error
280
- count := len (d )
281
- maxSize := params .BeaconConfig ().MaxRequestBlocksDeneb
282
- if uint64 (count ) > maxSize {
283
- return nil , errors .Errorf ("data column identifiers list exceeds max size: %d > %d" , count , maxSize )
284
- }
285
-
286
- if len (d ) == 0 {
287
- return []byte {}, nil
288
- }
289
- sizes := make ([]uint32 , count )
290
- valTotal := uint32 (0 )
291
- for i , elem := range d {
292
- if elem == nil {
293
- return nil , errors .New ("nil item in DataColumnsByRootIdentifiers list" )
294
- }
295
- sizes [i ] = uint32 (elem .SizeSSZ ())
296
- valTotal += sizes [i ]
297
- }
298
- offSize := uint32 (4 * len (d ))
299
- out := make ([]byte , offSize , offSize + valTotal )
300
- for i := range sizes {
301
- binary .LittleEndian .PutUint32 (out [i * 4 :i * 4 + 4 ], offSize )
302
- offSize += sizes [i ]
303
- }
304
- for _ , elem := range d {
305
- out , err = elem .MarshalSSZTo (out )
306
- if err != nil {
307
- return nil , err
308
- }
309
- }
310
-
311
- return out , nil
209
+ func (d * DataColumnsByRootIdentifiers ) MarshalSSZ () ([]byte , error ) {
210
+ return ssz.MarshalListVariableElement [* eth.DataColumnsByRootIdentifier ](* d )
312
211
}
313
212
314
213
// MarshalSSZTo implements ssz.Marshaler. It appends the serialized DataColumnSidecarsByRootReq value to the provided byte slice.
@@ -329,11 +228,3 @@ func (d DataColumnsByRootIdentifiers) SizeSSZ() int {
329
228
}
330
229
return size
331
230
}
332
-
333
- func init () {
334
- blobSizer := & eth.BlobIdentifier {}
335
- blobIdSize = blobSizer .SizeSSZ ()
336
-
337
- dataColumnSizer := & eth.DataColumnSidecarsByRangeRequest {}
338
- dataColumnIdSize = dataColumnSizer .SizeSSZ ()
339
- }
0 commit comments