From: Shane Synan Date: Wed, 7 Sep 2016 05:35:48 +0000 (-0500) Subject: Skip rate limit for login, capability negotiation X-Git-Tag: travis-deploy-test~388 X-Git-Url: https://git.quassel-irc.org/?p=quassel.git;a=commitdiff_plain;h=d017fec4290f7585427f78371e7851487b9dc2eb;ds=sidebyside Skip rate limit for login, capability negotiation Disable message rate limit during nick registration and capability negotiation (Network::Initializing). Once network initialization is complete (Network::Initialized), re-apply configured rate limits. Helps fix connection timeouts during login on servers with SASL enabled, multiple capabilities negotiated, and a strict 10s login time. Add flag 'forceUnlimited' to updateRateLimiting() which temporarily overrides user preferences to skip all rate limiting. User preferences can be applied afterwards by calling updateRateLimiting() without setting 'forceUnlimited'. Resolves GH-236. --- diff --git a/src/core/corenetwork.cpp b/src/core/corenetwork.cpp index 6f2c285f..383d4c04 100644 --- a/src/core/corenetwork.cpp +++ b/src/core/corenetwork.cpp @@ -542,8 +542,13 @@ void CoreNetwork::socketInitialized() socket.setSocketOption(QAbstractSocket::KeepAliveOption, true); - // Update the TokenBucket with specified rate-limiting settings - updateRateLimiting(); + // Update the TokenBucket, force-enabling unlimited message rates for initial registration and + // capability negotiation. networkInitialized() will call updateRateLimiting() without the + // force flag to apply user preferences. When making changes, ensure that this still happens! + // As Quassel waits for CAP ACK/NAK and AUTHENTICATE replies, this shouldn't ever fill the IRC + // server receive queue and cause a kill. "Shouldn't" being the operative word; the real world + // is a scary place. + updateRateLimiting(true); // Fill up the token bucket as we're connecting from scratch resetTokenBucket(); @@ -640,6 +645,10 @@ void CoreNetwork::networkInitialized() _disconnectExpected = false; _quitRequested = false; + // Update the TokenBucket with specified rate-limiting settings, removing the force-unlimited + // flag used for initial registration and capability negotiation. + updateRateLimiting(); + if (useAutoReconnect()) { // reset counter _autoReconnectCount = unlimitedReconnectRetries() ? -1 : autoReconnectRetries(); @@ -931,12 +940,12 @@ void CoreNetwork::setPingInterval(int interval) /******** Custom Rate Limiting ********/ -void CoreNetwork::updateRateLimiting() +void CoreNetwork::updateRateLimiting(const bool forceUnlimited) { // Always reset the delay and token bucket (safe-guard against accidentally starting the timer) - if (useCustomMessageRate()) { - // Custom message rates enabled. Let's go for it! + if (useCustomMessageRate() || forceUnlimited) { + // Custom message rates enabled, or chosen by means of forcing unlimited. Let's go for it! _messageDelay = messageRateDelay(); @@ -958,8 +967,9 @@ void CoreNetwork::updateRateLimiting() // Toggle the timer according to whether or not rate limiting is enabled // If we're here, useCustomMessageRate is true. Thus, the logic becomes - // _skipMessageRates = (useCustomMessageRate && unlimitedMessageRate) - _skipMessageRates = unlimitedMessageRate(); + // _skipMessageRates = (useCustomMessageRate && (unlimitedMessageRate || forceUnlimited)) + // Override user preferences if called with force unlimited + _skipMessageRates = (unlimitedMessageRate() || forceUnlimited); if (_skipMessageRates) { // If the message queue already contains messages, they need sent before disabling the // timer. Set the timer to a rapid pace and let it disable itself. diff --git a/src/core/corenetwork.h b/src/core/corenetwork.h index 509df19d..8201b437 100644 --- a/src/core/corenetwork.h +++ b/src/core/corenetwork.h @@ -284,8 +284,14 @@ public slots: * @see Network::messageRateBurstSize() * @see Network::messageRateDelay() * @see Network::unlimitedMessageRate() + * + * @param[in] forceUnlimited + * @parmblock + * If true, override user settings to disable message rate limiting, otherwise apply rate limits + * set by the user. Use with caution and remember to re-enable configured limits when done. + * @endparmblock */ - void updateRateLimiting(); + void updateRateLimiting(const bool forceUnlimited = false); /** * Resets the token bucket up to the maximum