Skip to content

Commit

Permalink
when heartbeats were disabled, the event loop refcount would not be r…
Browse files Browse the repository at this point in the history
…estored correctly after the timer expired. This has been fixed (#281)
  • Loading branch information
thijs-blom authored and mvdwerve committed Jan 17, 2019
1 parent 532cc73 commit a18e518
Showing 1 changed file with 21 additions and 9 deletions.
30 changes: 21 additions & 9 deletions include/amqpcpp/libev.h
Original file line number Diff line number Diff line change
Expand Up @@ -221,14 +221,23 @@ class LibEvHandler : public TcpHandler
{
// get the current time
ev_tstamp now = ev_now(_loop);

// if the onNegotiate method was not yet called, and no heartbeat timeout was negotiated
if (_timeout == 0)
{
// there is a theoretical scenario in which the onNegotiate() method
// was overridden, so that the connection-timeout-timer expires, but
// the connection is ready anyway -- in that case we should ignore the timeout
if (_connection->ready()) return;
// the connection is ready anyway -- in that case we should ignore the timeout.
// this also occurs when heartbeats are disabled.
if (_connection->ready())
{
// we send no heartbeats, so the timer will be stopped.
// restore the loop refcount
ev_ref(_loop);

// done
return;
}

// the timer expired because the connection could not be set up in time,
// close the connection with immediate effect
Expand Down Expand Up @@ -314,6 +323,9 @@ class LibEvHandler : public TcpHandler
*/
virtual ~Wrapper()
{
// the timer was already stopped
if (_timeout == 0) return;

// restore loop refcount
ev_ref(_loop);

Expand Down Expand Up @@ -444,15 +456,15 @@ class LibEvHandler : public TcpHandler

protected:
/**
* Method that is called when the heartbeat frequency is negotiated between the server and the client.
* @param connection The connection that suggested a heartbeat interval
* @param interval The suggested interval from the server
* @return uint16_t The interval to use
* Method that is called when the heartbeat timeout is negotiated between the server and the client.
* @param connection The connection that suggested a heartbeat timeout
* @param timeout The suggested timeout from the server
* @return uint16_t The timeout to use
*/
virtual uint16_t onNegotiate(TcpConnection *connection, uint16_t interval) override
virtual uint16_t onNegotiate(TcpConnection *connection, uint16_t timeout) override
{
// lookup the wrapper, and start the timer to check for activity and send heartbeats
return lookup(connection).start(interval);
return lookup(connection).start(timeout);
}

/**
Expand Down

0 comments on commit a18e518

Please sign in to comment.