Skip to content

Instantly share code, notes, and snippets.

@yifan-gu
Created August 23, 2014 21:23
Show Gist options
  • Save yifan-gu/529f305dd89685fda299 to your computer and use it in GitHub Desktop.
Save yifan-gu/529f305dd89685fda299 to your computer and use it in GitHub Desktop.
simulator for HyParView protocol bootstraping
package main
import (
"fmt"
"math/rand"
"sync/atomic"
"time"
)
var makeup int32
var breakup int32
var messageSent int32
type member struct {
fanout int
totalPool []*member
id int
friends []int
makeup chan int
breakup chan int
needNewFriend chan bool
}
func (m *member) run() {
for {
select {
case id := <-m.makeup:
atomic.AddInt32(&makeup, 1)
if len(m.friends) < m.fanout+2 {
m.friends = append(m.friends, id)
} else {
vindex := rand.Intn(len(m.friends))
victim := m.friends[vindex]
m.totalPool[victim].breakup <- m.id
m.friends[vindex] = id
}
case id := <-m.breakup:
atomic.AddInt32(&breakup, 1)
index := -1
for i := range m.friends {
if m.friends[i] == id {
index = i
break
}
}
if index >= 0 {
// Slot found for making new friends
newFriend := rand.Intn(len(m.totalPool))
m.friends[index] = newFriend
m.totalPool[newFriend].makeup <- m.id
}
case <-m.needNewFriend:
if len(m.friends) < m.fanout {
newFriend := rand.Intn(len(m.totalPool))
m.friends = append(m.friends, newFriend)
m.totalPool[newFriend].makeup <- m.id
}
if len(m.friends) < m.fanout {
m.needNewFriend <- true
}
}
atomic.AddInt32(&messageSent, 1)
}
}
func main() {
n := 10000
fan := 5
m := make([]*member, n)
for i := range m {
m[i] = &member{
totalPool: m,
fanout: fan,
id: i,
friends: make([]int, 0, fan),
makeup: make(chan int, 1024),
breakup: make(chan int, 1024),
needNewFriend: make(chan bool, 1024),
}
}
for i := range m {
m[i].needNewFriend <- true
go m[i].run()
}
for j := 0; ; j++ {
select {
case <-time.After(time.Millisecond):
fmt.Println("round ", j)
for i := range m {
fmt.Println(i, ": ", m[i].friends)
}
fmt.Println("makeup: ", makeup, "breakup: ", breakup)
atomic.StoreInt32(&makeup, 0)
atomic.StoreInt32(&breakup, 0)
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment