A more idiomatic way of trying a non-blocking send on a buffered channel
and falling back to a blocking send inside a goroutine. This really needs to be fixed. The situation only arises when events are sent and aren't pulled off the channel using {Wait,Poll}ForEvent. Namely, if the event send blocks, the entire program will deadlock. Using a goroutine is not ideal because we lose a guarantee of order: that events are processed in the order of their arrival. However, it seems OK as a temporary band-aide for a situation that probably doesn't arise too often. What I need to do is implement a dynamic queue. Here is a reference implementation: http://play.golang.org/p/AiHBsxTFpj
This commit is contained in:
parent
7abc9c6455
commit
6bdfd1d1b1
|
@ -379,12 +379,14 @@ func (c *Conn) readResponses() {
|
||||||
// FIXME: I'm not sure if using a goroutine here to guarantee
|
// FIXME: I'm not sure if using a goroutine here to guarantee
|
||||||
// a non-blocking send is the right way to go. I should implement
|
// a non-blocking send is the right way to go. I should implement
|
||||||
// a proper dynamic queue.
|
// a proper dynamic queue.
|
||||||
if cap(c.eventChan) == len(c.eventChan) {
|
// I am pretty sure this also loses a guarantee of events being
|
||||||
|
// processed in order of being received.
|
||||||
|
select {
|
||||||
|
case c.eventChan <- event:
|
||||||
|
default:
|
||||||
go func() {
|
go func() {
|
||||||
c.eventChan <- event
|
c.eventChan <- event
|
||||||
}()
|
}()
|
||||||
} else {
|
|
||||||
c.eventChan <- event
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// No more processing for events.
|
// No more processing for events.
|
||||||
|
|
Loading…
Reference in New Issue