github.com/turingchain2020/turingchain@v1.1.21/system/p2p/dht/protocol/broadcast/broadcastv2.go (about)

     1  // Copyright Turing Corp. 2018 All Rights Reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package broadcast
     6  
     7  //
     8  //import (
     9  //	prototypes "github.com/turingchain2020/turingchain/system/p2p/dht/protocol/types"
    10  //	core "github.com/libp2p/go-libp2p-core"
    11  //)
    12  //
    13  //// broadcast v2
    14  //type broadcastHandlerV2 struct {
    15  //	prototypes.BaseStreamHandler
    16  //}
    17  //
    18  //// ReuseStream 复用stream, 框架不会进行关闭
    19  //func (b *broadcastHandlerV2) ReuseStream() bool {
    20  //	return true
    21  //}
    22  //
    23  //// Handle 处理广播接收
    24  //func (b *broadcastHandlerV2) Handle(stream core.Stream) {
    25  //	protocol := b.GetProtocol().(*broadcastProtocol)
    26  //	protocol.newStream <- stream
    27  //}
    28  
    29  // 更新广播节点, broadcast v2相关代码, 暂时保留
    30  /*func (protocol *broadcastProtocol) manageBroadcastPeers() {
    31  
    32  	// 节点启动前十分钟,网络还未稳定,每5秒更新一次连接信息, 后续每分钟更新一次
    33  	tick := time.NewTicker(time.Second * 5)
    34  	timer := time.NewTimer(time.Minute * 10)
    35  
    36  	for {
    37  		select {
    38  		//定时获取节点, 加入广播节点列表
    39  		case <-tick.C:
    40  			morePeers := protocol.SubConfig.MaxBroadcastPeers - len(protocol.broadcastPeers)
    41  			peers := protocol.GetConnsManager().FetchConnPeers()
    42  			for i := 0; i < len(peers) && morePeers > 0; i++ {
    43  				pid := peers[i]
    44  				_, ok := protocol.broadcastPeers[pid]
    45  				if !ok {
    46  					protocol.addBroadcastPeer(pid, nil)
    47  					morePeers--
    48  				}
    49  			}
    50  
    51  		case <-timer.C:
    52  			tick.Stop()
    53  			timer.Stop()
    54  			tick = time.NewTicker(time.Minute)
    55  
    56  		//被动接收到节点 加入广播节点列表
    57  		case stream := <-protocol.newStream:
    58  			pid := stream.Conn().RemotePeer()
    59  			//广播节点列表已达上限
    60  			if len(protocol.broadcastPeers) >= protocol.SubConfig.MaxBroadcastPeers {
    61  				_ = stream.Reset()
    62  				break
    63  			}
    64  			pCancel, ok := protocol.broadcastPeers[pid]
    65  			// 该节点已经在广播列表中, 双方同时发起的情况导致双向重复, 这里采用直接比较节点id策略,保留节点id大的的一方主动发起的广播流
    66  			if ok {
    67  
    68  				if strings.Compare(pid.String(), stream.Conn().LocalPeer().String()) > 0 {
    69  					//关闭本地已存在的该节点广播协程
    70  					pCancel()
    71  					//上述操作会将节点从相关结构删除,需要做记录避免误删除
    72  					protocol.simultaneousPeers[pid] = struct{}{}
    73  				} else {
    74  					//保留本地已存在的广播协程, 直接关闭stream并退出
    75  					_ = stream.Reset()
    76  					break
    77  				}
    78  			}
    79  			protocol.addBroadcastPeer(pid, stream)
    80  		case pid := <-protocol.exitPeer:
    81  			protocol.removeBroadcastPeer(pid)
    82  		case pid := <-protocol.errPeer:
    83  			//错误节点减少tag值, 这样在内部连接超额时会优先断开
    84  			protocol.Host.ConnManager().UpsertTag(pid, broadcastTag, func(oldVal int) int { return oldVal - 1 })
    85  		case <-protocol.Ctx.Done():
    86  			tick.Stop()
    87  			timer.Stop()
    88  			return
    89  		}
    90  	}
    91  }*/
    92  
    93  /* broadcast v2 相关代码,暂时保留
    94  func (protocol *broadcastProtocol) broadcastV2(pid peer.ID, stream core.Stream, peerCtx context.Context, peerCancel context.CancelFunc) {
    95  
    96  	sPid := pid.String()
    97  	outgoing := protocol.ps.Sub(bcTopic, sPid)
    98  	peerAddr := stream.Conn().RemoteMultiaddr().String()
    99  	log.Debug("broadcastV2Start", "pid", sPid, "addr", peerAddr)
   100  	errChan := make(chan error, 2)
   101  	defer func() {
   102  		protocol.ps.Unsub(outgoing)
   103  		err := <-errChan
   104  		if err != nil {
   105  			protocol.errPeer <- pid
   106  		}
   107  		protocol.exitPeer <- pid
   108  		_ = stream.Reset()
   109  		log.Debug("broadcastV2End", "pid", sPid, "addr", peerAddr)
   110  	}()
   111  
   112  	// handle broadcast recv
   113  	go func() {
   114  		data := &types.BroadCastData{}
   115  		for {
   116  			//阻塞等待
   117  			err := prototypes.ReadStreamTimeout(data, stream, -1)
   118  			if err != nil {
   119  				log.Error("broadcastV2", "pid", sPid, "addr", peerAddr, "read stream err", err)
   120  				errChan <- err
   121  				peerCancel()
   122  				return
   123  			}
   124  			_ = protocol.handleReceive(data, sPid, peerAddr, broadcastV2)
   125  		}
   126  	}()
   127  
   128  	// handle broadcast send
   129  	for {
   130  		var err error
   131  		select {
   132  		case data := <-outgoing:
   133  			sendData, doSend := protocol.handleSend(data, sPid, peerAddr)
   134  			if !doSend {
   135  				break //ignore send
   136  			}
   137  			err = prototypes.WriteStream(sendData, stream)
   138  			if err != nil {
   139  				errChan <- err
   140  				log.Error("broadcastV2", "pid", sPid, "WriteStream err", err)
   141  				return
   142  			}
   143  
   144  		case <-peerCtx.Done():
   145  			errChan <- nil
   146  			return
   147  		}
   148  	}
   149  }
   150  */