func (g *gossip) Start() {
	g.state.Lock()
	defer g.state.Unlock()
	if g.state.running {
		g.logger.Warn("gossip already started")
		return
	}
	g.state.running = true
	g.state.protocolPeriodStop, g.state.protocolPeriodWait = scheduleRepeaditly(g.ProtocolPeriod, g.ComputeProtocolDelay, g.node.clock)
	g.state.protocolRateChannel, _ = scheduleRepeaditly(g.AdjustProtocolRate, func() time.Duration {
		return time.Second
	}, g.node.clock)
	g.logger.Debug("started gossip protocol")
}
start the gossip protocol
package swim
import (
	"math"
	"math/rand"
	"sync"
	"time"
	"github.com/rcrowley/go-metrics"
	log "github.com/uber-common/bark"
	"github.com/uber/ringpop-go/logging"
)
type gossip struct {
	node *Node
	state struct {
		sync.RWMutex
		running bool
		protocolPeriodStop  chan bool
		protocolPeriodWait  <-chan bool
		protocolRateChannel chan bool
	}
	minProtocolPeriod time.Duration
	protocol struct {
		numPeriods int
		lastPeriod time.Time
		lastRate   time.Duration
		timing     metrics.Histogram
		sync.RWMutex
	}
	logger log.Logger
}
func newGossip(node *Node, minProtocolPeriod time.Duration) *gossip {
	gossip := &gossip{
		node:              node,
		minProtocolPeriod: minProtocolPeriod,
		logger:            logging.Logger("gossip").WithField("local", node.Address()),
	}
	gossip.protocol.timing = metrics.NewHistogram(metrics.NewUniformSample(10))
	gossip.protocol.timing.Update(int64(gossip.minProtocolPeriod))
	return gossip
}
func (g *gossip) ComputeProtocolDelay() time.Duration {
	g.protocol.RLock()
	defer g.protocol.RUnlock()
	var delay time.Duration
	if g.protocol.numPeriods != 0 {
		target := g.protocol.lastPeriod.Add(g.protocol.lastRate)
		delay = time.Duration(math.Max(float64(target.Sub(time.Now())), float64(g.minProtocolPeriod)))
	} else {
		delay = time.Duration(rand.Intn(int(g.minProtocolPeriod + 1)))
	}
	g.node.EmitEvent(ProtocolDelayComputeEvent{
		Duration: delay,
	})
	return delay
}
func (g *gossip) ProtocolRate() time.Duration {
	g.protocol.RLock()
	rate := g.protocol.lastRate
	g.protocol.RUnlock()
	return rate
}
func (g *gossip) AdjustProtocolRate() {
	g.protocol.Lock()
	observed := g.protocol.timing.Percentile(0.5) * 2.0
	g.protocol.lastRate = time.Duration(math.Max(observed, float64(g.minProtocolPeriod)))
	g.protocol.Unlock()
}
func (g *gossip) ProtocolTiming() metrics.Histogram {
	g.protocol.RLock()
	histogram := g.protocol.timing
	g.protocol.RUnlock()
	return histogram
}