github.com/prysmaticlabs/prysm@v1.4.4/beacon-chain/sync/rpc_beacon_blocks_by_root.go (about) 1 package sync 2 3 import ( 4 "context" 5 6 libp2pcore "github.com/libp2p/go-libp2p-core" 7 "github.com/libp2p/go-libp2p-core/peer" 8 "github.com/pkg/errors" 9 "github.com/prysmaticlabs/prysm/beacon-chain/p2p/types" 10 "github.com/prysmaticlabs/prysm/proto/interfaces" 11 "github.com/prysmaticlabs/prysm/shared/params" 12 ) 13 14 // sendRecentBeaconBlocksRequest sends a recent beacon blocks request to a peer to get 15 // those corresponding blocks from that peer. 16 func (s *Service) sendRecentBeaconBlocksRequest(ctx context.Context, blockRoots *types.BeaconBlockByRootsReq, id peer.ID) error { 17 ctx, cancel := context.WithTimeout(ctx, respTimeout) 18 defer cancel() 19 20 _, err := SendBeaconBlocksByRootRequest(ctx, s.cfg.Chain, s.cfg.P2P, id, blockRoots, func(blk interfaces.SignedBeaconBlock) error { 21 blkRoot, err := blk.Block().HashTreeRoot() 22 if err != nil { 23 return err 24 } 25 s.pendingQueueLock.Lock() 26 if err := s.insertBlockToPendingQueue(blk.Block().Slot(), blk, blkRoot); err != nil { 27 return err 28 } 29 s.pendingQueueLock.Unlock() 30 return nil 31 }) 32 return err 33 } 34 35 // beaconBlocksRootRPCHandler looks up the request blocks from the database from the given block roots. 36 func (s *Service) beaconBlocksRootRPCHandler(ctx context.Context, msg interface{}, stream libp2pcore.Stream) error { 37 ctx, cancel := context.WithTimeout(ctx, ttfbTimeout) 38 defer cancel() 39 SetRPCStreamDeadlines(stream) 40 log := log.WithField("handler", "beacon_blocks_by_root") 41 42 rawMsg, ok := msg.(*types.BeaconBlockByRootsReq) 43 if !ok { 44 return errors.New("message is not type BeaconBlockByRootsReq") 45 } 46 blockRoots := *rawMsg 47 if err := s.rateLimiter.validateRequest(stream, uint64(len(blockRoots))); err != nil { 48 return err 49 } 50 if len(blockRoots) == 0 { 51 // Add to rate limiter in the event no 52 // roots are requested. 53 s.rateLimiter.add(stream, 1) 54 s.writeErrorResponseToStream(responseCodeInvalidRequest, "no block roots provided in request", stream) 55 return errors.New("no block roots provided") 56 } 57 58 if uint64(len(blockRoots)) > params.BeaconNetworkConfig().MaxRequestBlocks { 59 s.writeErrorResponseToStream(responseCodeInvalidRequest, "requested more than the max block limit", stream) 60 return errors.New("requested more than the max block limit") 61 } 62 s.rateLimiter.add(stream, int64(len(blockRoots))) 63 64 for _, root := range blockRoots { 65 blk, err := s.cfg.DB.Block(ctx, root) 66 if err != nil { 67 log.WithError(err).Debug("Could not fetch block") 68 s.writeErrorResponseToStream(responseCodeServerError, types.ErrGeneric.Error(), stream) 69 return err 70 } 71 if blk == nil || blk.IsNil() { 72 continue 73 } 74 if err := s.chunkWriter(stream, blk.Proto()); err != nil { 75 return err 76 } 77 } 78 closeStream(stream, log) 79 return nil 80 }