// Handles the unwrapping + sending of messages to the right connection. func (s *Swarm) fanOut() { defer s.Children().Done() i := 0 for { select { case <-s.Closing(): return // told to close. case msg, ok := <-s.Outgoing: if !ok { log.Infof("%s outgoing channel closed", s) return } if len(msg.Data()) >= conn.MaxMessageSize { log.Critical("Attempted to send message bigger than max size.") } s.connsLock.RLock() c, found := s.conns[msg.Peer().Key()] s.connsLock.RUnlock() if !found { e := fmt.Errorf("Sent msg to peer without open conn: %v", msg.Peer()) s.errChan <- e log.Error(e) continue } i++ log.Debugf("%s sent message to %s (%d)", s.local, msg.Peer(), i) log.Event(context.TODO(), "sendMessage", s.local, msg) // queue it in the connection's buffer c.Out() <- msg.Data() } } }
func SubtestSwarm(t *testing.T, addrs []string, MsgNum int) { // t.Skip("skipping for another test") ctx := context.Background() swarms, peers := makeSwarms(ctx, t, addrs) // connect everyone { var wg sync.WaitGroup connect := func(s *Swarm, dst peer.Peer) { // copy for other peer cp, err := s.peers.Get(dst.ID()) if err != nil { t.Fatal(err) } cp.AddAddress(dst.Addresses()[0]) log.Info("SWARM TEST: %s dialing %s", s.local, dst) if _, err := s.Dial(cp); err != nil { t.Fatal("error swarm dialing to peer", err) } log.Info("SWARM TEST: %s connected to %s", s.local, dst) wg.Done() } log.Info("Connecting swarms simultaneously.") for _, s := range swarms { for _, p := range peers { if p != s.local { // don't connect to self. wg.Add(1) connect(s, p) } } } wg.Wait() } // ping/pong for _, s1 := range swarms { ctx, cancel := context.WithCancel(ctx) // setup all others to pong for _, s2 := range swarms { if s1 == s2 { continue } go pong(ctx, s2) } peers, err := s1.peers.All() if err != nil { t.Fatal(err) } for k := 0; k < MsgNum; k++ { for _, p := range *peers { log.Debugf("%s ping %s (%d)", s1.local, p, k) s1.Outgoing <- msg.New(p, []byte("ping")) } } got := map[u.Key]int{} for k := 0; k < (MsgNum * len(*peers)); k++ { log.Debugf("%s waiting for pong (%d)", s1.local, k) msg := <-s1.Incoming if string(msg.Data()) != "pong" { t.Error("unexpected conn output", msg.Data) } n, _ := got[msg.Peer().Key()] got[msg.Peer().Key()] = n + 1 } if len(*peers) != len(got) { t.Error("got less messages than sent") } for p, n := range got { if n != MsgNum { t.Error("peer did not get all msgs", p, n, "/", MsgNum) } } cancel() <-time.After(50 * time.Microsecond) } for _, s := range swarms { s.Close() } }