github.com/onflow/flow-go@v0.33.17/network/underlay/network.go (about)

     1  package underlay
     2  
     3  import (
     4  	"bufio"
     5  	"context"
     6  	"errors"
     7  	"fmt"
     8  	"io"
     9  	"sync"
    10  	"time"
    11  
    12  	ggio "github.com/gogo/protobuf/io"
    13  	"github.com/ipfs/go-datastore"
    14  	libp2pnet "github.com/libp2p/go-libp2p/core/network"
    15  	"github.com/libp2p/go-libp2p/core/peer"
    16  	"github.com/libp2p/go-libp2p/core/peerstore"
    17  	"github.com/libp2p/go-libp2p/core/protocol"
    18  	"github.com/rs/zerolog"
    19  
    20  	"github.com/onflow/flow-go/model/flow"
    21  	"github.com/onflow/flow-go/model/flow/filter"
    22  	"github.com/onflow/flow-go/module"
    23  	"github.com/onflow/flow-go/module/component"
    24  	"github.com/onflow/flow-go/module/irrecoverable"
    25  	"github.com/onflow/flow-go/network"
    26  	alspmgr "github.com/onflow/flow-go/network/alsp/manager"
    27  	netcache "github.com/onflow/flow-go/network/cache"
    28  	"github.com/onflow/flow-go/network/channels"
    29  	"github.com/onflow/flow-go/network/codec"
    30  	"github.com/onflow/flow-go/network/internal/p2putils"
    31  	"github.com/onflow/flow-go/network/message"
    32  	"github.com/onflow/flow-go/network/p2p"
    33  	"github.com/onflow/flow-go/network/p2p/blob"
    34  	p2plogging "github.com/onflow/flow-go/network/p2p/logging"
    35  	"github.com/onflow/flow-go/network/p2p/ping"
    36  	"github.com/onflow/flow-go/network/p2p/subscription"
    37  	"github.com/onflow/flow-go/network/p2p/unicast/protocols"
    38  	"github.com/onflow/flow-go/network/p2p/unicast/ratelimit"
    39  	"github.com/onflow/flow-go/network/p2p/utils"
    40  	"github.com/onflow/flow-go/network/queue"
    41  	"github.com/onflow/flow-go/network/underlay/internal"
    42  	"github.com/onflow/flow-go/network/validator"
    43  	flowpubsub "github.com/onflow/flow-go/network/validator/pubsub"
    44  	_ "github.com/onflow/flow-go/utils/binstat"
    45  	"github.com/onflow/flow-go/utils/logging"
    46  )
    47  
    48  const (
    49  	_ = iota
    50  	_ = 1 << (10 * iota)
    51  	mb
    52  	gb
    53  )
    54  
    55  const (
    56  	// DefaultMaxUnicastMsgSize defines maximum message size in unicast mode for most messages
    57  	DefaultMaxUnicastMsgSize = 10 * mb // 10 mb
    58  
    59  	// LargeMsgMaxUnicastMsgSize defines maximum message size in unicast mode for large messages
    60  	LargeMsgMaxUnicastMsgSize = gb // 1 gb
    61  
    62  	// DefaultUnicastTimeout is the default maximum time to wait for a default unicast request to complete
    63  	// assuming at least a 1mb/sec connection
    64  	DefaultUnicastTimeout = 5 * time.Second
    65  
    66  	// LargeMsgUnicastTimeout is the maximum time to wait for a unicast request to complete for large message size
    67  	LargeMsgUnicastTimeout = 1000 * time.Second
    68  )
    69  
    70  var (
    71  	// ErrUnicastMsgWithoutSub error is provided to the slashing violations consumer in the case where
    72  	// the network receives a message via unicast but does not have a corresponding subscription for
    73  	// the channel in that message.
    74  	ErrUnicastMsgWithoutSub = errors.New("networking layer does not have subscription for the channel ID indicated in the unicast message received")
    75  )
    76  
    77  // NotEjectedFilter is an identity filter that, when applied to the identity
    78  // table at a given snapshot, returns all nodes that we should communicate with
    79  // over the networking layer.
    80  //
    81  // NOTE: The protocol state includes nodes from the previous/next epoch that should
    82  // be included in network communication. We omit any nodes that have been ejected.
    83  var NotEjectedFilter = filter.Not(filter.Ejected)
    84  
    85  // Network serves as the comprehensive networking layer that integrates three interfaces within Flow; Underlay, EngineRegistry, and ConduitAdapter.
    86  // It is responsible for creating conduits through which engines can send and receive messages to and from other engines on the network, as well as registering other services
    87  // such as BlobService and PingService. It also provides a set of APIs that can be used to send messages to other nodes on the network.
    88  // Network is also responsible for managing the topology of the network, i.e., the set of nodes that are connected to each other.
    89  // It is also responsible for managing the set of nodes that are connected to each other.
    90  type Network struct {
    91  	// TODO: using a waitgroup here doesn't actually guarantee that we'll wait for all
    92  	// goroutines to exit, because new goroutines could be started after we've already
    93  	// returned from wg.Wait(). We need to solve this the right way using ComponentManager
    94  	// and worker routines.
    95  	wg sync.WaitGroup
    96  	*component.ComponentManager
    97  	ctx                         context.Context
    98  	sporkId                     flow.Identifier
    99  	identityProvider            module.IdentityProvider
   100  	identityTranslator          p2p.IDTranslator
   101  	logger                      zerolog.Logger
   102  	codec                       network.Codec
   103  	me                          module.Local
   104  	metrics                     module.NetworkCoreMetrics
   105  	receiveCache                *netcache.ReceiveCache // used to deduplicate incoming messages
   106  	queue                       network.MessageQueue
   107  	subscriptionManager         network.SubscriptionManager // used to keep track of subscribed channels
   108  	conduitFactory              network.ConduitFactory
   109  	topology                    network.Topology
   110  	registerEngineRequests      chan *registerEngineRequest
   111  	registerBlobServiceRequests chan *registerBlobServiceRequest
   112  	misbehaviorReportManager    network.MisbehaviorReportManager
   113  	unicastMessageTimeout       time.Duration
   114  	libP2PNode                  p2p.LibP2PNode
   115  	bitswapMetrics              module.BitswapMetrics
   116  	peerUpdateLock              sync.Mutex // protects the peer update process
   117  	previousProtocolStatePeers  []peer.AddrInfo
   118  	slashingViolationsConsumer  network.ViolationsConsumer
   119  	peerManagerFilters          []p2p.PeerFilter
   120  	unicastRateLimiters         *ratelimit.RateLimiters
   121  	validators                  []network.MessageValidator
   122  	authorizedSenderValidator   *validator.AuthorizedSenderValidator
   123  	preferredUnicasts           []protocols.ProtocolName
   124  }
   125  
   126  var _ network.EngineRegistry = &Network{}
   127  var _ network.Underlay = &Network{}
   128  var _ network.ConduitAdapter = &Network{}
   129  
   130  type registerEngineRequest struct {
   131  	channel          channels.Channel
   132  	messageProcessor network.MessageProcessor
   133  	respChan         chan *registerEngineResp
   134  }
   135  
   136  type registerEngineResp struct {
   137  	conduit network.Conduit
   138  	err     error
   139  }
   140  
   141  type registerBlobServiceRequest struct {
   142  	channel  channels.Channel
   143  	ds       datastore.Batching
   144  	opts     []network.BlobServiceOption
   145  	respChan chan *registerBlobServiceResp
   146  }
   147  
   148  type registerBlobServiceResp struct {
   149  	blobService network.BlobService
   150  	err         error
   151  }
   152  
   153  var ErrNetworkShutdown = errors.New("network has already shutdown")
   154  
   155  // NetworkConfig is a configuration struct for the network. It contains all the
   156  // necessary components to create a new network.
   157  type NetworkConfig struct {
   158  	Logger                           zerolog.Logger
   159  	Codec                            network.Codec
   160  	Me                               module.Local
   161  	Topology                         network.Topology
   162  	Metrics                          module.NetworkCoreMetrics
   163  	IdentityProvider                 module.IdentityProvider
   164  	IdentityTranslator               p2p.IDTranslator
   165  	ReceiveCache                     *netcache.ReceiveCache
   166  	ConduitFactory                   network.ConduitFactory
   167  	AlspCfg                          *alspmgr.MisbehaviorReportManagerConfig
   168  	SporkId                          flow.Identifier
   169  	UnicastMessageTimeout            time.Duration
   170  	Libp2pNode                       p2p.LibP2PNode
   171  	BitSwapMetrics                   module.BitswapMetrics
   172  	SlashingViolationConsumerFactory func(network.ConduitAdapter) network.ViolationsConsumer
   173  }
   174  
   175  // Validate validates the configuration, and sets default values for any missing fields.
   176  func (cfg *NetworkConfig) Validate() {
   177  	if cfg.UnicastMessageTimeout <= 0 {
   178  		cfg.UnicastMessageTimeout = DefaultUnicastTimeout
   179  	}
   180  }
   181  
   182  // NetworkConfigOption is a function that can be used to override network config parmeters.
   183  type NetworkConfigOption func(*NetworkConfig)
   184  
   185  // WithAlspConfig overrides the default misbehavior report manager config. It is mostly used for testing purposes.
   186  // Note: do not override the default misbehavior report manager config in production unless you know what you are doing.
   187  // Args:
   188  // cfg: misbehavior report manager config
   189  // Returns:
   190  // NetworkConfigOption: network param option
   191  func WithAlspConfig(cfg *alspmgr.MisbehaviorReportManagerConfig) NetworkConfigOption {
   192  	return func(params *NetworkConfig) {
   193  		params.AlspCfg = cfg
   194  	}
   195  }
   196  
   197  // WithCodec overrides the default codec (i.e., encoder and decoder). It is mostly used for testing purposes.
   198  // Note: do not override the default codec in production unless you know what you are doing.
   199  func WithCodec(codec network.Codec) NetworkConfigOption {
   200  	return func(params *NetworkConfig) {
   201  		params.Codec = codec
   202  	}
   203  }
   204  
   205  func WithSlashingViolationConsumerFactory(factory func(adapter network.ConduitAdapter) network.ViolationsConsumer) NetworkConfigOption {
   206  	return func(params *NetworkConfig) {
   207  		params.SlashingViolationConsumerFactory = factory
   208  	}
   209  }
   210  
   211  // NetworkOption is a function that can be used to override network attributes.
   212  // It is mostly used for testing purposes.
   213  // Note: do not override network attributes in production unless you know what you are doing.
   214  type NetworkOption func(*Network)
   215  
   216  // WithAlspManager sets the misbehavior report manager for the network. It overrides the default
   217  // misbehavior report manager that is created from the config.
   218  // Note that this option is mostly used for testing purposes, do not use it in production unless you
   219  // know what you are doing.
   220  //
   221  // Args:
   222  //
   223  //	mgr: misbehavior report manager
   224  //
   225  // Returns:
   226  //
   227  //	NetworkOption: network option
   228  func WithAlspManager(mgr network.MisbehaviorReportManager) NetworkOption {
   229  	return func(n *Network) {
   230  		n.misbehaviorReportManager = mgr
   231  	}
   232  }
   233  
   234  // WithPeerManagerFilters sets the peer manager filters for the network. It overrides the default
   235  // peer manager filters that are created from the config.
   236  func WithPeerManagerFilters(filters ...p2p.PeerFilter) NetworkOption {
   237  	return func(n *Network) {
   238  		n.peerManagerFilters = filters
   239  	}
   240  }
   241  
   242  // WithUnicastRateLimiters sets the unicast rate limiters for the network. It overrides the default
   243  // unicast rate limiters that are created from the config.
   244  func WithUnicastRateLimiters(limiters *ratelimit.RateLimiters) NetworkOption {
   245  	return func(n *Network) {
   246  		n.unicastRateLimiters = limiters
   247  	}
   248  }
   249  
   250  // WithPreferredUnicastProtocols sets the preferred unicast protocols for the network. It overrides the default
   251  // preferred unicast.
   252  func WithPreferredUnicastProtocols(protocols ...protocols.ProtocolName) NetworkOption {
   253  	return func(n *Network) {
   254  		n.preferredUnicasts = protocols
   255  	}
   256  }
   257  
   258  // WithMessageValidators sets the message validators for the network. It overrides the default
   259  // message validators.
   260  func WithMessageValidators(validators ...network.MessageValidator) NetworkOption {
   261  	return func(n *Network) {
   262  		n.validators = validators
   263  	}
   264  }
   265  
   266  // NewNetwork creates a new network with the given configuration.
   267  // Args:
   268  // param: network configuration
   269  // opts: network options
   270  // Returns:
   271  // Network: a new network
   272  func NewNetwork(param *NetworkConfig, opts ...NetworkOption) (*Network, error) {
   273  	param.Validate()
   274  
   275  	n := &Network{
   276  		logger:                      param.Logger.With().Str("component", "network").Logger(),
   277  		codec:                       param.Codec,
   278  		me:                          param.Me,
   279  		receiveCache:                param.ReceiveCache,
   280  		topology:                    param.Topology,
   281  		metrics:                     param.Metrics,
   282  		bitswapMetrics:              param.BitSwapMetrics,
   283  		identityProvider:            param.IdentityProvider,
   284  		conduitFactory:              param.ConduitFactory,
   285  		registerEngineRequests:      make(chan *registerEngineRequest),
   286  		registerBlobServiceRequests: make(chan *registerBlobServiceRequest),
   287  		sporkId:                     param.SporkId,
   288  		identityTranslator:          param.IdentityTranslator,
   289  		unicastMessageTimeout:       param.UnicastMessageTimeout,
   290  		libP2PNode:                  param.Libp2pNode,
   291  		unicastRateLimiters:         ratelimit.NoopRateLimiters(),
   292  		validators:                  DefaultValidators(param.Logger.With().Str("component", "network-validators").Logger(), param.Me.NodeID()),
   293  	}
   294  
   295  	n.subscriptionManager = subscription.NewChannelSubscriptionManager(n)
   296  
   297  	misbehaviorMngr, err := alspmgr.NewMisbehaviorReportManager(param.AlspCfg, n)
   298  	if err != nil {
   299  		return nil, fmt.Errorf("could not create misbehavior report manager: %w", err)
   300  	}
   301  	n.misbehaviorReportManager = misbehaviorMngr
   302  
   303  	for _, opt := range opts {
   304  		opt(n)
   305  	}
   306  
   307  	if err := n.conduitFactory.RegisterAdapter(n); err != nil {
   308  		return nil, fmt.Errorf("could not register network adapter: %w", err)
   309  	}
   310  
   311  	builder := component.NewComponentManagerBuilder()
   312  	builder.AddWorker(func(ctx irrecoverable.SignalerContext, ready component.ReadyFunc) {
   313  		n.logger.Debug().Msg("starting misbehavior manager")
   314  		n.misbehaviorReportManager.Start(ctx)
   315  
   316  		select {
   317  		case <-n.misbehaviorReportManager.Ready():
   318  			n.logger.Debug().Msg("misbehavior manager is ready")
   319  			ready()
   320  		case <-ctx.Done():
   321  			// jumps to the end of the select statement to let a graceful shutdown.
   322  		}
   323  
   324  		<-ctx.Done()
   325  		n.logger.Debug().Msg("stopping misbehavior manager")
   326  		<-n.misbehaviorReportManager.Done()
   327  		n.logger.Debug().Msg("misbehavior manager stopped")
   328  	})
   329  	builder.AddWorker(func(ctx irrecoverable.SignalerContext, ready component.ReadyFunc) {
   330  		n.logger.Debug().Msg("setting up network context")
   331  		n.ctx = ctx
   332  
   333  		ready()
   334  
   335  		<-ctx.Done()
   336  		n.logger.Debug().Msg("network context is done")
   337  	})
   338  
   339  	for _, limiter := range n.unicastRateLimiters.Limiters() {
   340  		rateLimiter := limiter
   341  		builder.AddWorker(func(ctx irrecoverable.SignalerContext, ready component.ReadyFunc) {
   342  			ready()
   343  			rateLimiter.Start(ctx)
   344  			<-rateLimiter.Ready()
   345  			ready()
   346  			<-rateLimiter.Done()
   347  		})
   348  	}
   349  
   350  	builder.AddWorker(func(ctx irrecoverable.SignalerContext, ready component.ReadyFunc) {
   351  		// creation of slashing violations consumer should be postponed till here where the network
   352  		// is start and the overlay is set.
   353  		n.slashingViolationsConsumer = param.SlashingViolationConsumerFactory(n)
   354  
   355  		n.authorizedSenderValidator = validator.NewAuthorizedSenderValidator(
   356  			n.logger,
   357  			n.slashingViolationsConsumer,
   358  			n.Identity)
   359  
   360  		err := n.libP2PNode.WithDefaultUnicastProtocol(n.handleIncomingStream, n.preferredUnicasts)
   361  		if err != nil {
   362  			ctx.Throw(fmt.Errorf("could not register preferred unicast protocols on libp2p node: %w", err))
   363  		}
   364  
   365  		n.UpdateNodeAddresses()
   366  		n.libP2PNode.WithPeersProvider(n.authorizedPeers)
   367  
   368  		ready()
   369  
   370  		<-ctx.Done()
   371  		n.logger.Info().Str("component", "network").Msg("stopping subroutines, blocking on read connection loops to end")
   372  
   373  		// wait for the readConnection and readSubscription routines to stop
   374  		n.wg.Wait()
   375  		n.logger.Info().Str("component", "network").Msg("stopped subroutines")
   376  	})
   377  
   378  	builder.AddWorker(n.createInboundMessageQueue)
   379  	builder.AddWorker(n.processRegisterEngineRequests)
   380  	builder.AddWorker(n.processRegisterBlobServiceRequests)
   381  
   382  	n.ComponentManager = builder.Build()
   383  	return n, nil
   384  }
   385  
   386  func (n *Network) processRegisterEngineRequests(parent irrecoverable.SignalerContext, ready component.ReadyFunc) {
   387  	ready()
   388  
   389  	// we need to wait for the libp2p node to be ready before we can register engines
   390  	n.logger.Debug().Msg("waiting for libp2p node to be ready")
   391  	<-n.libP2PNode.Ready()
   392  	n.logger.Debug().Msg("libp2p node is ready")
   393  
   394  	for {
   395  		select {
   396  		case req := <-n.registerEngineRequests:
   397  			conduit, err := n.handleRegisterEngineRequest(parent, req.channel, req.messageProcessor)
   398  			resp := &registerEngineResp{
   399  				conduit: conduit,
   400  				err:     err,
   401  			}
   402  
   403  			select {
   404  			case <-parent.Done():
   405  				return
   406  			case req.respChan <- resp:
   407  			}
   408  		case <-parent.Done():
   409  			return
   410  		}
   411  	}
   412  }
   413  
   414  func (n *Network) processRegisterBlobServiceRequests(parent irrecoverable.SignalerContext, ready component.ReadyFunc) {
   415  	ready()
   416  
   417  	n.logger.Debug().Msg("waiting for libp2p node to be ready")
   418  	<-n.libP2PNode.Ready()
   419  	n.logger.Debug().Msg("libp2p node is ready")
   420  
   421  	for {
   422  		select {
   423  		case req := <-n.registerBlobServiceRequests:
   424  			blobService, err := n.handleRegisterBlobServiceRequest(parent, req.channel, req.ds, req.opts)
   425  			resp := &registerBlobServiceResp{
   426  				blobService: blobService,
   427  				err:         err,
   428  			}
   429  
   430  			select {
   431  			case <-parent.Done():
   432  				return
   433  			case req.respChan <- resp:
   434  			}
   435  		case <-parent.Done():
   436  			return
   437  		}
   438  	}
   439  }
   440  
   441  // createInboundMessageQueue creates the queue that will be used to process incoming messages.
   442  func (n *Network) createInboundMessageQueue(ctx irrecoverable.SignalerContext, ready component.ReadyFunc) {
   443  	n.queue = queue.NewMessageQueue(ctx, queue.GetEventPriority, n.metrics)
   444  	queue.CreateQueueWorkers(ctx, queue.DefaultNumWorkers, n.queue, n.queueSubmitFunc)
   445  
   446  	ready()
   447  }
   448  
   449  func (n *Network) handleRegisterEngineRequest(parent irrecoverable.SignalerContext, channel channels.Channel, engine network.MessageProcessor) (network.Conduit, error) {
   450  	if !channels.ChannelExists(channel) {
   451  		return nil, fmt.Errorf("unknown channel: %s, should be registered in topic map", channel)
   452  	}
   453  
   454  	err := n.subscriptionManager.Register(channel, engine)
   455  	if err != nil {
   456  		return nil, fmt.Errorf("failed to register engine for channel %s: %w", channel, err)
   457  	}
   458  
   459  	n.logger.Info().
   460  		Str("channel_id", channel.String()).
   461  		Msg("channel successfully registered")
   462  
   463  	// create the conduit
   464  	newConduit, err := n.conduitFactory.NewConduit(parent, channel)
   465  	if err != nil {
   466  		return nil, fmt.Errorf("could not create conduit using factory: %w", err)
   467  	}
   468  
   469  	return newConduit, nil
   470  }
   471  
   472  func (n *Network) handleRegisterBlobServiceRequest(parent irrecoverable.SignalerContext, channel channels.Channel, ds datastore.Batching, opts []network.BlobServiceOption) (network.BlobService,
   473  	error) {
   474  	bs := blob.NewBlobService(n.libP2PNode.Host(), n.libP2PNode.Routing(), channel.String(), ds, n.bitswapMetrics, n.logger, opts...)
   475  
   476  	// start the blob service using the network's context
   477  	bs.Start(parent)
   478  
   479  	return bs, nil
   480  }
   481  
   482  // Register will register the given engine with the given unique engine engineID,
   483  // returning a conduit to directly submit messages to the message bus of the
   484  // engine.
   485  func (n *Network) Register(channel channels.Channel, messageProcessor network.MessageProcessor) (network.Conduit, error) {
   486  	respChan := make(chan *registerEngineResp)
   487  
   488  	select {
   489  	case <-n.ComponentManager.ShutdownSignal():
   490  		return nil, ErrNetworkShutdown
   491  	case n.registerEngineRequests <- &registerEngineRequest{
   492  		channel:          channel,
   493  		messageProcessor: messageProcessor,
   494  		respChan:         respChan,
   495  	}:
   496  		select {
   497  		case <-n.ComponentManager.ShutdownSignal():
   498  			return nil, ErrNetworkShutdown
   499  		case resp := <-respChan:
   500  			return resp.conduit, resp.err
   501  		}
   502  	}
   503  }
   504  
   505  func (n *Network) RegisterPingService(pingProtocol protocol.ID, provider network.PingInfoProvider) (network.PingService, error) {
   506  	select {
   507  	case <-n.ComponentManager.ShutdownSignal():
   508  		return nil, ErrNetworkShutdown
   509  	default:
   510  		return ping.NewPingService(n.libP2PNode.Host(), pingProtocol, n.logger, provider), nil
   511  	}
   512  }
   513  
   514  // RegisterBlobService registers a BlobService on the given channel.
   515  // The returned BlobService can be used to request blobs from the network.
   516  func (n *Network) RegisterBlobService(channel channels.Channel, ds datastore.Batching, opts ...network.BlobServiceOption) (network.BlobService, error) {
   517  	respChan := make(chan *registerBlobServiceResp)
   518  
   519  	select {
   520  	case <-n.ComponentManager.ShutdownSignal():
   521  		return nil, ErrNetworkShutdown
   522  	case n.registerBlobServiceRequests <- &registerBlobServiceRequest{
   523  		channel:  channel,
   524  		ds:       ds,
   525  		opts:     opts,
   526  		respChan: respChan,
   527  	}:
   528  		select {
   529  		case <-n.ComponentManager.ShutdownSignal():
   530  			return nil, ErrNetworkShutdown
   531  		case resp := <-respChan:
   532  			return resp.blobService, resp.err
   533  		}
   534  	}
   535  }
   536  
   537  // UnRegisterChannel unregisters the engine for the specified channel. The engine will no longer be able to send or
   538  // receive messages from that channel.
   539  func (n *Network) UnRegisterChannel(channel channels.Channel) error {
   540  	err := n.subscriptionManager.Unregister(channel)
   541  	if err != nil {
   542  		return fmt.Errorf("failed to unregister engine for channel %s: %w", channel, err)
   543  	}
   544  	return nil
   545  }
   546  
   547  func (n *Network) Identities() flow.IdentityList {
   548  	return n.identityProvider.Identities(NotEjectedFilter)
   549  }
   550  
   551  func (n *Network) Identity(pid peer.ID) (*flow.Identity, bool) {
   552  	return n.identityProvider.ByPeerID(pid)
   553  }
   554  
   555  func (n *Network) Receive(msg network.IncomingMessageScope) error {
   556  	n.metrics.InboundMessageReceived(msg.Size(), msg.Channel().String(), msg.Protocol().String(), msg.PayloadType())
   557  
   558  	err := n.processNetworkMessage(msg)
   559  	if err != nil {
   560  		return fmt.Errorf("could not process message: %w", err)
   561  	}
   562  	return nil
   563  }
   564  
   565  func (n *Network) processNetworkMessage(msg network.IncomingMessageScope) error {
   566  	// checks the cache for deduplication and adds the message if not already present
   567  	if !n.receiveCache.Add(msg.EventID()) {
   568  		// drops duplicate message
   569  		n.logger.Debug().
   570  			Hex("sender_id", logging.ID(msg.OriginId())).
   571  			Hex("event_id", msg.EventID()).
   572  			Str("channel", msg.Channel().String()).
   573  			Msg("dropping message due to duplication")
   574  
   575  		n.metrics.DuplicateInboundMessagesDropped(msg.Channel().String(), msg.Protocol().String(), msg.PayloadType())
   576  
   577  		return nil
   578  	}
   579  
   580  	// create queue message
   581  	qm := queue.QMessage{
   582  		Payload:  msg.DecodedPayload(),
   583  		Size:     msg.Size(),
   584  		Target:   msg.Channel(),
   585  		SenderID: msg.OriginId(),
   586  	}
   587  
   588  	// insert the message in the queue
   589  	err := n.queue.Insert(qm)
   590  	if err != nil {
   591  		return fmt.Errorf("failed to insert message in queue: %w", err)
   592  	}
   593  
   594  	return nil
   595  }
   596  
   597  // UnicastOnChannel sends the message in a reliable way to the given recipient.
   598  // It uses 1-1 direct messaging over the underlying network to deliver the message.
   599  // It returns an error if unicasting fails.
   600  func (n *Network) UnicastOnChannel(channel channels.Channel, payload interface{}, targetID flow.Identifier) error {
   601  	if targetID == n.me.NodeID() {
   602  		n.logger.Debug().Msg("network skips self unicasting")
   603  		return nil
   604  	}
   605  
   606  	msg, err := message.NewOutgoingScope(
   607  		flow.IdentifierList{targetID},
   608  		channels.TopicFromChannel(channel, n.sporkId),
   609  		payload,
   610  		n.codec.Encode,
   611  		message.ProtocolTypeUnicast)
   612  	if err != nil {
   613  		return fmt.Errorf("could not generate outgoing message scope for unicast: %w", err)
   614  	}
   615  
   616  	n.metrics.UnicastMessageSendingStarted(channel.String())
   617  	defer n.metrics.UnicastMessageSendingCompleted(channel.String())
   618  
   619  	// since it is a unicast, we only need to get the first peer ID.
   620  	peerID, err := n.identityTranslator.GetPeerID(msg.TargetIds()[0])
   621  	if err != nil {
   622  		return fmt.Errorf("could not find peer id for target id: %w", err)
   623  	}
   624  
   625  	maxMsgSize := unicastMaxMsgSize(msg.PayloadType())
   626  	if msg.Size() > maxMsgSize {
   627  		// message size goes beyond maximum size that the serializer can handle.
   628  		// proceeding with this message results in closing the connection by the target side, and
   629  		// delivery failure.
   630  		return fmt.Errorf("message size %d exceeds configured max message size %d", msg.Size(), maxMsgSize)
   631  	}
   632  
   633  	maxTimeout := n.unicastMaxMsgDuration(msg.PayloadType())
   634  
   635  	// pass in a context with timeout to make the unicast call fail fast
   636  	ctx, cancel := context.WithTimeout(n.ctx, maxTimeout)
   637  	defer cancel()
   638  
   639  	// protect the underlying connection from being inadvertently pruned by the peer manager while the stream and
   640  	// connection creation is being attempted, and remove it from protected list once stream created.
   641  	channel, ok := channels.ChannelFromTopic(msg.Topic())
   642  	if !ok {
   643  		return fmt.Errorf("could not find channel for topic %s", msg.Topic())
   644  	}
   645  	streamProtectionTag := fmt.Sprintf("%v:%v", channel, msg.PayloadType())
   646  
   647  	err = n.libP2PNode.OpenAndWriteOnStream(ctx, peerID, streamProtectionTag, func(stream libp2pnet.Stream) error {
   648  		bufw := bufio.NewWriter(stream)
   649  		writer := ggio.NewDelimitedWriter(bufw)
   650  
   651  		err = writer.WriteMsg(msg.Proto())
   652  		if err != nil {
   653  			return fmt.Errorf("failed to send message to target id %x with peer id %s: %w", msg.TargetIds()[0], peerID, err)
   654  		}
   655  
   656  		// flush the stream
   657  		err = bufw.Flush()
   658  		if err != nil {
   659  			return fmt.Errorf("failed to flush stream for target id %x with peer id %s: %w", msg.TargetIds()[0], peerID, err)
   660  		}
   661  
   662  		return nil
   663  	})
   664  	if err != nil {
   665  		return fmt.Errorf("failed to send message to %x: %w", targetID, err)
   666  	}
   667  
   668  	n.metrics.OutboundMessageSent(msg.Size(), channel.String(), message.ProtocolTypeUnicast.String(), msg.PayloadType())
   669  	return nil
   670  }
   671  
   672  // PublishOnChannel sends the message in an unreliable way to the given recipients.
   673  // In this context, unreliable means that the message is published over a libp2p pub-sub
   674  // channel and can be read by any node subscribed to that channel.
   675  // The selector could be used to optimize or restrict delivery.
   676  func (n *Network) PublishOnChannel(channel channels.Channel, message interface{}, targetIDs ...flow.Identifier) error {
   677  	filteredIDs := flow.IdentifierList(targetIDs).Filter(n.removeSelfFilter())
   678  
   679  	if len(filteredIDs) == 0 {
   680  		return fmt.Errorf("targetIDs %v: %w", len(targetIDs), network.EmptyTargetList)
   681  	}
   682  
   683  	err := n.sendOnChannel(channel, message, filteredIDs)
   684  
   685  	if err != nil {
   686  		return fmt.Errorf("failed to publish on channel %s: %w", channel, err)
   687  	}
   688  
   689  	return nil
   690  }
   691  
   692  // MulticastOnChannel unreliably sends the specified event over the channel to randomly selected 'num' number of recipients
   693  // selected from the specified targetIDs.
   694  func (n *Network) MulticastOnChannel(channel channels.Channel, message interface{}, num uint, targetIDs ...flow.Identifier) error {
   695  	selectedIDs, err := flow.IdentifierList(targetIDs).Filter(n.removeSelfFilter()).Sample(num)
   696  	if err != nil {
   697  		return fmt.Errorf("sampling failed: %w", err)
   698  	}
   699  
   700  	if len(selectedIDs) == 0 {
   701  		return fmt.Errorf("targetIDs %v: %w", len(targetIDs), network.EmptyTargetList)
   702  	}
   703  
   704  	err = n.sendOnChannel(channel, message, selectedIDs)
   705  
   706  	// publishes the message to the selected targets
   707  	if err != nil {
   708  		return fmt.Errorf("failed to multicast on channel %s: %w", channel, err)
   709  	}
   710  
   711  	return nil
   712  }
   713  
   714  // removeSelfFilter removes the flow.Identifier of this node if present, from the list of nodes
   715  func (n *Network) removeSelfFilter() flow.IdentifierFilter {
   716  	return func(id flow.Identifier) bool {
   717  		return id != n.me.NodeID()
   718  	}
   719  }
   720  
   721  // sendOnChannel sends the message on channel to targets.
   722  func (n *Network) sendOnChannel(channel channels.Channel, msg interface{}, targetIDs []flow.Identifier) error {
   723  	n.logger.Debug().
   724  		Interface("message", msg).
   725  		Str("channel", channel.String()).
   726  		Str("target_ids", fmt.Sprintf("%v", targetIDs)).
   727  		Msg("sending new message on channel")
   728  
   729  	// generate network message (encoding) based on list of recipients
   730  	scope, err := message.NewOutgoingScope(
   731  		targetIDs,
   732  		channels.TopicFromChannel(channel, n.sporkId),
   733  		msg,
   734  		n.codec.Encode,
   735  		message.ProtocolTypePubSub)
   736  	if err != nil {
   737  		return fmt.Errorf("failed to generate outgoing message scope %s: %w", channel, err)
   738  	}
   739  
   740  	// publish the message through the channel, however, the message
   741  	// is only restricted to targetIDs (if they subscribed to channel).
   742  	err = n.libP2PNode.Publish(n.ctx, scope)
   743  	if err != nil {
   744  		return fmt.Errorf("failed to send message on channel %s: %w", channel, err)
   745  	}
   746  
   747  	n.metrics.OutboundMessageSent(scope.Size(), channel.String(), message.ProtocolTypePubSub.String(), scope.PayloadType())
   748  
   749  	return nil
   750  }
   751  
   752  // queueSubmitFunc submits the message to the engine synchronously. It is the callback for the queue worker
   753  // when it gets a message from the queue
   754  func (n *Network) queueSubmitFunc(message interface{}) {
   755  	qm := message.(queue.QMessage)
   756  
   757  	logger := n.logger.With().
   758  		Str("channel_id", qm.Target.String()).
   759  		Str("sender_id", qm.SenderID.String()).
   760  		Logger()
   761  
   762  	eng, err := n.subscriptionManager.GetEngine(qm.Target)
   763  	if err != nil {
   764  		// This means the message was received on a channel that the node has not registered an
   765  		// engine for. This may be because the message was received during startup and the node
   766  		// hasn't subscribed to the channel yet, or there is a bug.
   767  		logger.Err(err).Msg("failed to submit message")
   768  		return
   769  	}
   770  
   771  	logger.Debug().Msg("submitting message to engine")
   772  
   773  	n.metrics.MessageProcessingStarted(qm.Target.String())
   774  
   775  	// submits the message to the engine synchronously and
   776  	// tracks its processing time.
   777  	startTimestamp := time.Now()
   778  
   779  	err = eng.Process(qm.Target, qm.SenderID, qm.Payload)
   780  	if err != nil {
   781  		logger.Err(err).Msg("failed to process message")
   782  	}
   783  
   784  	n.metrics.MessageProcessingFinished(qm.Target.String(), time.Since(startTimestamp))
   785  }
   786  
   787  func (n *Network) Topology() flow.IdentityList {
   788  	return n.topology.Fanout(n.Identities())
   789  }
   790  
   791  // ReportMisbehaviorOnChannel reports the misbehavior of a node on sending a message to the current node that appears
   792  // valid based on the networking layer but is considered invalid by the current node based on the Flow protocol.
   793  // The misbehavior report is sent to the current node's networking layer on the given channel to be processed.
   794  // Args:
   795  // - channel: The channel on which the misbehavior report is sent.
   796  // - report: The misbehavior report to be sent.
   797  // Returns:
   798  // none
   799  func (n *Network) ReportMisbehaviorOnChannel(channel channels.Channel, report network.MisbehaviorReport) {
   800  	n.misbehaviorReportManager.HandleMisbehaviorReport(channel, report)
   801  }
   802  
   803  func DefaultValidators(log zerolog.Logger, flowID flow.Identifier) []network.MessageValidator {
   804  	return []network.MessageValidator{
   805  		validator.ValidateNotSender(flowID),   // validator to filter out messages sent by this node itself
   806  		validator.ValidateTarget(log, flowID), // validator to filter out messages not intended for this node
   807  	}
   808  }
   809  
   810  // isProtocolParticipant returns a PeerFilter that returns true if a peer is a staked (i.e., authorized) node.
   811  func (n *Network) isProtocolParticipant() p2p.PeerFilter {
   812  	return func(p peer.ID) error {
   813  		if _, ok := n.Identity(p); !ok {
   814  			return fmt.Errorf("failed to get identity of unknown peer with peer id %s", p2plogging.PeerId(p))
   815  		}
   816  		return nil
   817  	}
   818  }
   819  
   820  func (n *Network) peerIDs(flowIDs flow.IdentifierList) peer.IDSlice {
   821  	result := make([]peer.ID, 0, len(flowIDs))
   822  
   823  	for _, fid := range flowIDs {
   824  		pid, err := n.identityTranslator.GetPeerID(fid)
   825  		if err != nil {
   826  			// We probably don't need to fail the entire function here, since the other
   827  			// translations may still succeed
   828  			n.logger.
   829  				Err(err).
   830  				Str(logging.KeySuspicious, "true").
   831  				Hex("node_id", logging.ID(fid)).
   832  				Msg("failed to translate to peer ID")
   833  			continue
   834  		}
   835  
   836  		result = append(result, pid)
   837  	}
   838  
   839  	return result
   840  }
   841  
   842  func (n *Network) UpdateNodeAddresses() {
   843  	n.logger.Info().Msg("updating protocol state node addresses")
   844  
   845  	ids := n.Identities()
   846  	newInfos, invalid := utils.PeerInfosFromIDs(ids)
   847  
   848  	for id, err := range invalid {
   849  		n.logger.
   850  			Err(err).
   851  			Bool(logging.KeySuspicious, true).
   852  			Hex("node_id", logging.ID(id)).
   853  			Msg("failed to extract peer info from identity")
   854  	}
   855  
   856  	n.peerUpdateLock.Lock()
   857  	defer n.peerUpdateLock.Unlock()
   858  
   859  	// set old addresses to expire
   860  	for _, oldInfo := range n.previousProtocolStatePeers {
   861  		n.libP2PNode.Host().Peerstore().SetAddrs(oldInfo.ID, oldInfo.Addrs, peerstore.TempAddrTTL)
   862  	}
   863  
   864  	for _, info := range newInfos {
   865  		n.libP2PNode.Host().Peerstore().SetAddrs(info.ID, info.Addrs, peerstore.PermanentAddrTTL)
   866  	}
   867  
   868  	n.previousProtocolStatePeers = newInfos
   869  }
   870  
   871  // authorizedPeers is a peer manager callback used by the underlying libp2p node that updates who can connect to this node (as
   872  // well as who this node can connect to).
   873  // and who is not allowed to connect to this node. This function is called by the peer manager and connection gater components
   874  // of libp2p.
   875  //
   876  // Args:
   877  // none
   878  // Returns:
   879  // - peer.IDSlice: a list of peer IDs that are allowed to connect to this node (and that this node can connect to). Any peer
   880  // not in this list is assumed to be disconnected from this node (if connected) and not allowed to connect to this node.
   881  // This is the guarantee that the underlying libp2p node implementation makes.
   882  func (n *Network) authorizedPeers() peer.IDSlice {
   883  	peerIDs := make([]peer.ID, 0)
   884  	for _, id := range n.peerIDs(n.Topology().NodeIDs()) {
   885  		peerAllowed := true
   886  		for _, filter := range n.peerManagerFilters {
   887  			if err := filter(id); err != nil {
   888  				n.logger.Debug().
   889  					Err(err).
   890  					Str("peer_id", p2plogging.PeerId(id)).
   891  					Msg("filtering topology peer")
   892  
   893  				peerAllowed = false
   894  				break
   895  			}
   896  		}
   897  
   898  		if peerAllowed {
   899  			peerIDs = append(peerIDs, id)
   900  		}
   901  	}
   902  
   903  	return peerIDs
   904  }
   905  
   906  func (n *Network) OnDisallowListNotification(notification *network.DisallowListingUpdate) {
   907  	for _, pid := range n.peerIDs(notification.FlowIds) {
   908  		n.libP2PNode.OnDisallowListNotification(pid, notification.Cause)
   909  	}
   910  }
   911  
   912  func (n *Network) OnAllowListNotification(notification *network.AllowListingUpdate) {
   913  	for _, pid := range n.peerIDs(notification.FlowIds) {
   914  		n.libP2PNode.OnAllowListNotification(pid, notification.Cause)
   915  	}
   916  }
   917  
   918  // handleIncomingStream handles an incoming stream from a remote peer
   919  // it is a callback that gets called for each incoming stream by libp2p with a new stream object.
   920  // TODO: this should be eventually moved to libp2p node.
   921  func (n *Network) handleIncomingStream(s libp2pnet.Stream) {
   922  	// qualify the logger with local and remote address
   923  	log := p2putils.StreamLogger(n.logger, s)
   924  
   925  	log.Info().Msg("incoming stream received")
   926  
   927  	success := false
   928  
   929  	remotePeer := s.Conn().RemotePeer()
   930  
   931  	defer func() {
   932  		if success {
   933  			err := s.Close()
   934  			if err != nil {
   935  				log.Err(err).Msg("failed to close stream")
   936  			}
   937  		} else {
   938  			err := s.Reset()
   939  			if err != nil {
   940  				log.Err(err).Msg("failed to reset stream")
   941  			}
   942  		}
   943  	}()
   944  
   945  	// check if peer is currently rate limited before continuing to process stream.
   946  	if n.unicastRateLimiters.MessageRateLimiter.IsRateLimited(remotePeer) || n.unicastRateLimiters.BandWidthRateLimiter.IsRateLimited(remotePeer) {
   947  		log.Debug().
   948  			Bool(logging.KeySuspicious, true).
   949  			Msg("dropping unicast stream from rate limited peer")
   950  		return
   951  	}
   952  
   953  	// TODO: We need to allow per-topic timeouts and message size limits.
   954  	// This allows us to configure higher limits for topics on which we expect
   955  	// to receive large messages (e.g. Chunk Data Packs), and use the normal
   956  	// limits for other topics. In order to enable this, we will need to register
   957  	// a separate stream handler for each topic.
   958  	ctx, cancel := context.WithTimeout(n.ctx, LargeMsgUnicastTimeout)
   959  	defer cancel()
   960  
   961  	deadline, _ := ctx.Deadline()
   962  
   963  	err := s.SetReadDeadline(deadline)
   964  	if err != nil {
   965  		log.Err(err).Msg("failed to set read deadline for stream")
   966  		return
   967  	}
   968  
   969  	// create the reader
   970  	r := ggio.NewDelimitedReader(s, LargeMsgMaxUnicastMsgSize)
   971  	for {
   972  		if ctx.Err() != nil {
   973  			return
   974  		}
   975  
   976  		// Note: message fields must not be trusted until explicitly validated
   977  		var msg message.Message
   978  		// read the next message (blocking call)
   979  		err = r.ReadMsg(&msg)
   980  		if err != nil {
   981  			if err == io.EOF {
   982  				break
   983  			}
   984  
   985  			n.logger.Err(err).Msg("failed to read message")
   986  			return
   987  		}
   988  
   989  		channel := channels.Channel(msg.ChannelID)
   990  		topic := channels.TopicFromChannel(channel, n.sporkId)
   991  
   992  		// ignore messages if node does not have subscription to topic
   993  		if !n.libP2PNode.HasSubscription(topic) {
   994  			violation := &network.Violation{
   995  				Identity: nil, PeerID: p2plogging.PeerId(remotePeer), Channel: channel, Protocol: message.ProtocolTypeUnicast,
   996  			}
   997  
   998  			msgCode, err := codec.MessageCodeFromPayload(msg.Payload)
   999  			if err != nil {
  1000  				violation.Err = err
  1001  				n.slashingViolationsConsumer.OnUnknownMsgTypeError(violation)
  1002  				return
  1003  			}
  1004  
  1005  			// msg type is not guaranteed to be correct since it is set by the client
  1006  			_, what, err := codec.InterfaceFromMessageCode(msgCode)
  1007  			if err != nil {
  1008  				violation.Err = err
  1009  				n.slashingViolationsConsumer.OnUnknownMsgTypeError(violation)
  1010  				return
  1011  			}
  1012  
  1013  			violation.MsgType = what
  1014  			violation.Err = ErrUnicastMsgWithoutSub
  1015  			n.slashingViolationsConsumer.OnUnauthorizedUnicastOnChannel(violation)
  1016  			return
  1017  		}
  1018  
  1019  		// check if unicast messages have reached rate limit before processing next message
  1020  		if !n.unicastRateLimiters.MessageAllowed(remotePeer) {
  1021  			return
  1022  		}
  1023  
  1024  		// check if we can get a role for logging and metrics label if this is not a public channel
  1025  		role := ""
  1026  		if !channels.IsPublicChannel(channels.Channel(msg.ChannelID)) {
  1027  			if identity, ok := n.Identity(remotePeer); ok {
  1028  				role = identity.Role.String()
  1029  			}
  1030  		}
  1031  
  1032  		// check unicast bandwidth rate limiter for peer
  1033  		if !n.unicastRateLimiters.BandwidthAllowed(
  1034  			remotePeer,
  1035  			role,
  1036  			msg.Size(),
  1037  			message.MessageType(msg.Payload),
  1038  			channels.Topic(msg.ChannelID)) {
  1039  			return
  1040  		}
  1041  
  1042  		n.wg.Add(1)
  1043  		go func() {
  1044  			defer n.wg.Done()
  1045  			n.processUnicastStreamMessage(remotePeer, &msg)
  1046  		}()
  1047  	}
  1048  
  1049  	success = true
  1050  }
  1051  
  1052  // Subscribe subscribes the network to a channel.
  1053  // No errors are expected during normal operation.
  1054  func (n *Network) Subscribe(channel channels.Channel) error {
  1055  	topic := channels.TopicFromChannel(channel, n.sporkId)
  1056  
  1057  	var peerFilter p2p.PeerFilter
  1058  	var validators []validator.PubSubMessageValidator
  1059  	if channels.IsPublicChannel(channel) {
  1060  		// NOTE: for public channels the callback used to check if a node is staked will
  1061  		// return true for every node.
  1062  		peerFilter = p2p.AllowAllPeerFilter()
  1063  	} else {
  1064  		// for channels used by the staked nodes, add the topic validator to filter out messages from non-staked nodes
  1065  		validators = append(validators, n.authorizedSenderValidator.PubSubMessageValidator(channel))
  1066  
  1067  		// NOTE: For non-public channels the libP2P node topic validator will reject
  1068  		// messages from unstaked nodes.
  1069  		peerFilter = n.isProtocolParticipant()
  1070  	}
  1071  
  1072  	topicValidator := flowpubsub.TopicValidator(n.logger, peerFilter, validators...)
  1073  	s, err := n.libP2PNode.Subscribe(topic, topicValidator)
  1074  	if err != nil {
  1075  		return fmt.Errorf("could not subscribe to topic (%s): %w", topic, err)
  1076  	}
  1077  
  1078  	// create a new readSubscription with the context of the network
  1079  	rs := internal.NewReadSubscription(s, n.processPubSubMessages, n.logger)
  1080  	n.wg.Add(1)
  1081  
  1082  	// kick off the receive loop to continuously receive messages
  1083  	go func() {
  1084  		defer n.wg.Done()
  1085  		rs.ReceiveLoop(n.ctx)
  1086  	}()
  1087  
  1088  	// update peers to add some nodes interested in the same topic as direct peers
  1089  	n.libP2PNode.RequestPeerUpdate()
  1090  
  1091  	return nil
  1092  }
  1093  
  1094  // processPubSubMessages processes messages received from the pubsub subscription.
  1095  func (n *Network) processPubSubMessages(msg *message.Message, peerID peer.ID) {
  1096  	n.processAuthenticatedMessage(msg, peerID, message.ProtocolTypePubSub)
  1097  }
  1098  
  1099  // Unsubscribe unsubscribes the network from a channel.
  1100  // The following benign errors are expected during normal operations from libP2P:
  1101  // - the libP2P node fails to unsubscribe to the topic created from the provided channel.
  1102  //
  1103  // All errors returned from this function can be considered benign.
  1104  func (n *Network) Unsubscribe(channel channels.Channel) error {
  1105  	topic := channels.TopicFromChannel(channel, n.sporkId)
  1106  	return n.libP2PNode.Unsubscribe(topic)
  1107  }
  1108  
  1109  // processUnicastStreamMessage will decode, perform authorized sender validation and process a message
  1110  // sent via unicast stream. This func should be invoked in a separate goroutine to avoid creating a message decoding bottleneck.
  1111  func (n *Network) processUnicastStreamMessage(remotePeer peer.ID, msg *message.Message) {
  1112  	channel := channels.Channel(msg.ChannelID)
  1113  
  1114  	// TODO: once we've implemented per topic message size limits per the TODO above,
  1115  	// we can remove this check
  1116  	maxSize, err := UnicastMaxMsgSizeByCode(msg.Payload)
  1117  	if err != nil {
  1118  		n.slashingViolationsConsumer.OnUnknownMsgTypeError(&network.Violation{
  1119  			Identity: nil, PeerID: p2plogging.PeerId(remotePeer), MsgType: "", Channel: channel, Protocol: message.ProtocolTypeUnicast, Err: err,
  1120  		})
  1121  		return
  1122  	}
  1123  	if msg.Size() > maxSize {
  1124  		// message size exceeded
  1125  		n.logger.Error().
  1126  			Str("peer_id", p2plogging.PeerId(remotePeer)).
  1127  			Str("channel", msg.ChannelID).
  1128  			Int("max_size", maxSize).
  1129  			Int("size", msg.Size()).
  1130  			Bool(logging.KeySuspicious, true).
  1131  			Msg("received message exceeded permissible message maxSize")
  1132  		return
  1133  	}
  1134  
  1135  	// if message channel is not public perform authorized sender validation
  1136  	if !channels.IsPublicChannel(channel) {
  1137  		messageType, err := n.authorizedSenderValidator.Validate(remotePeer, msg.Payload, channel, message.ProtocolTypeUnicast)
  1138  		if err != nil {
  1139  			n.logger.
  1140  				Error().
  1141  				Err(err).
  1142  				Str("peer_id", p2plogging.PeerId(remotePeer)).
  1143  				Str("type", messageType).
  1144  				Str("channel", msg.ChannelID).
  1145  				Msg("unicast authorized sender validation failed")
  1146  			return
  1147  		}
  1148  	}
  1149  	n.processAuthenticatedMessage(msg, remotePeer, message.ProtocolTypeUnicast)
  1150  }
  1151  
  1152  // processAuthenticatedMessage processes a message and a source (indicated by its peer ID) and eventually passes it to the overlay
  1153  // In particular, it populates the `OriginID` field of the message with a Flow ID translated from this source.
  1154  func (n *Network) processAuthenticatedMessage(msg *message.Message, peerID peer.ID, protocol message.ProtocolType) {
  1155  	originId, err := n.identityTranslator.GetFlowID(peerID)
  1156  	if err != nil {
  1157  		// this error should never happen. by the time the message gets here, the peer should be
  1158  		// authenticated which means it must be known
  1159  		n.logger.Error().
  1160  			Err(err).
  1161  			Str("peer_id", p2plogging.PeerId(peerID)).
  1162  			Bool(logging.KeySuspicious, true).
  1163  			Msg("dropped message from unknown peer")
  1164  		return
  1165  	}
  1166  
  1167  	channel := channels.Channel(msg.ChannelID)
  1168  	decodedMsgPayload, err := n.codec.Decode(msg.Payload)
  1169  	switch {
  1170  	case codec.IsErrUnknownMsgCode(err):
  1171  		// slash peer if message contains unknown message code byte
  1172  		violation := &network.Violation{
  1173  			PeerID: p2plogging.PeerId(peerID), OriginID: originId, Channel: channel, Protocol: protocol, Err: err,
  1174  		}
  1175  		n.slashingViolationsConsumer.OnUnknownMsgTypeError(violation)
  1176  		return
  1177  	case codec.IsErrMsgUnmarshal(err) || codec.IsErrInvalidEncoding(err):
  1178  		// slash if peer sent a message that could not be marshalled into the message type denoted by the message code byte
  1179  		violation := &network.Violation{
  1180  			PeerID: p2plogging.PeerId(peerID), OriginID: originId, Channel: channel, Protocol: protocol, Err: err,
  1181  		}
  1182  		n.slashingViolationsConsumer.OnInvalidMsgError(violation)
  1183  		return
  1184  	case err != nil:
  1185  		// this condition should never happen and indicates there's a bug
  1186  		// don't crash as a result of external inputs since that creates a DoS vector
  1187  		// collect slashing data because this could potentially lead to slashing
  1188  		err = fmt.Errorf("unexpected error during message validation: %w", err)
  1189  		violation := &network.Violation{
  1190  			PeerID: p2plogging.PeerId(peerID), OriginID: originId, Channel: channel, Protocol: protocol, Err: err,
  1191  		}
  1192  		n.slashingViolationsConsumer.OnUnexpectedError(violation)
  1193  		return
  1194  	}
  1195  
  1196  	scope, err := message.NewIncomingScope(originId, protocol, msg, decodedMsgPayload)
  1197  	if err != nil {
  1198  		n.logger.Error().
  1199  			Err(err).
  1200  			Str("peer_id", p2plogging.PeerId(peerID)).
  1201  			Str("origin_id", originId.String()).
  1202  			Msg("could not create incoming message scope")
  1203  		return
  1204  	}
  1205  
  1206  	n.processMessage(scope)
  1207  }
  1208  
  1209  // processMessage processes a message and eventually passes it to the overlay
  1210  func (n *Network) processMessage(scope network.IncomingMessageScope) {
  1211  	logger := n.logger.With().
  1212  		Str("channel", scope.Channel().String()).
  1213  		Str("type", scope.Protocol().String()).
  1214  		Int("msg_size", scope.Size()).
  1215  		Hex("origin_id", logging.ID(scope.OriginId())).
  1216  		Logger()
  1217  
  1218  	// run through all the message validators
  1219  	for _, v := range n.validators {
  1220  		// if any one fails, stop message propagation
  1221  		if !v.Validate(scope) {
  1222  			logger.Debug().Msg("new message filtered by message validators")
  1223  			return
  1224  		}
  1225  	}
  1226  
  1227  	logger.Debug().Msg("processing new message")
  1228  
  1229  	// if validation passed, send the message to the overlay
  1230  	err := n.Receive(scope)
  1231  	if err != nil {
  1232  		n.logger.Error().Err(err).Msg("could not deliver payload")
  1233  	}
  1234  }
  1235  
  1236  // UnicastMaxMsgSizeByCode returns the max permissible size for a unicast message code
  1237  func UnicastMaxMsgSizeByCode(payload []byte) (int, error) {
  1238  	msgCode, err := codec.MessageCodeFromPayload(payload)
  1239  	if err != nil {
  1240  		return 0, err
  1241  	}
  1242  	_, messageType, err := codec.InterfaceFromMessageCode(msgCode)
  1243  	if err != nil {
  1244  		return 0, err
  1245  	}
  1246  
  1247  	maxSize := unicastMaxMsgSize(messageType)
  1248  	return maxSize, nil
  1249  }
  1250  
  1251  // unicastMaxMsgSize returns the max permissible size for a unicast message
  1252  func unicastMaxMsgSize(messageType string) int {
  1253  	switch messageType {
  1254  	case "*messages.ChunkDataResponse", "messages.ChunkDataResponse":
  1255  		return LargeMsgMaxUnicastMsgSize
  1256  	default:
  1257  		return DefaultMaxUnicastMsgSize
  1258  	}
  1259  }
  1260  
  1261  // unicastMaxMsgDuration returns the max duration to allow for a unicast send to complete
  1262  func (n *Network) unicastMaxMsgDuration(messageType string) time.Duration {
  1263  	switch messageType {
  1264  	case "*messages.ChunkDataResponse", "messages.ChunkDataResponse":
  1265  		if LargeMsgUnicastTimeout > n.unicastMessageTimeout {
  1266  			return LargeMsgUnicastTimeout
  1267  		}
  1268  		return n.unicastMessageTimeout
  1269  	default:
  1270  		return n.unicastMessageTimeout
  1271  	}
  1272  }