73 lines
1.3 KiB
Go
73 lines
1.3 KiB
Go
package peer
|
|
|
|
type pieceBroker struct {
|
|
stopCh chan struct{}
|
|
publishCh chan *pieceInfo
|
|
subCh chan chan *pieceInfo
|
|
unsubCh chan chan *pieceInfo
|
|
}
|
|
|
|
type pieceInfo struct {
|
|
num int32
|
|
finished bool
|
|
}
|
|
|
|
func newPieceBroker() *pieceBroker {
|
|
return &pieceBroker{
|
|
stopCh: make(chan struct{}),
|
|
publishCh: make(chan *pieceInfo, 10),
|
|
subCh: make(chan chan *pieceInfo),
|
|
unsubCh: make(chan chan *pieceInfo),
|
|
}
|
|
}
|
|
|
|
func (b *pieceBroker) Start() {
|
|
subs := map[chan *pieceInfo]struct{}{}
|
|
for {
|
|
select {
|
|
case <-b.stopCh:
|
|
//for msgCh := range subs {
|
|
// close(msgCh)
|
|
//}
|
|
return
|
|
case msgCh := <-b.subCh:
|
|
subs[msgCh] = struct{}{}
|
|
case msgCh := <-b.unsubCh:
|
|
delete(subs, msgCh)
|
|
case msg := <-b.publishCh:
|
|
for msgCh := range subs {
|
|
// msgCh is buffered, use non-blocking send to protect the broker:
|
|
select {
|
|
case msgCh <- msg:
|
|
default:
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
func (b *pieceBroker) Stop() {
|
|
close(b.stopCh)
|
|
}
|
|
|
|
func (b *pieceBroker) Subscribe() chan *pieceInfo {
|
|
msgCh := make(chan *pieceInfo, 5)
|
|
select {
|
|
case <-b.stopCh:
|
|
case b.subCh <- msgCh:
|
|
}
|
|
|
|
return msgCh
|
|
}
|
|
|
|
func (b *pieceBroker) Unsubscribe(msgCh chan *pieceInfo) {
|
|
b.unsubCh <- msgCh
|
|
}
|
|
|
|
func (b *pieceBroker) Publish(msg *pieceInfo) {
|
|
select {
|
|
case b.publishCh <- msg:
|
|
case <-b.stopCh:
|
|
}
|
|
}
|