X-Git-Url: https://git.quassel-irc.org/?a=blobdiff_plain;f=src%2Fcore%2Fcorenetwork.cpp;h=51c61888573173f74a739118d14bff21dece0a48;hb=6de2be92eff20e0c3d2e4a6350315b23061f675e;hp=30896aa7d7211b96aaa8a33b3dc39e97f43e4f73;hpb=b5b598dd7fbd64a72ffdeaa6df39a97100dd2810;p=quassel.git diff --git a/src/core/corenetwork.cpp b/src/core/corenetwork.cpp index 30896aa7..51c61888 100644 --- a/src/core/corenetwork.cpp +++ b/src/core/corenetwork.cpp @@ -1,5 +1,5 @@ /*************************************************************************** - * Copyright (C) 2005-2016 by the Quassel Project * + * Copyright (C) 2005-2018 by the Quassel Project * * devel@quassel-irc.org * * * * This program is free software; you can redistribute it and/or modify * @@ -63,6 +63,11 @@ CoreNetwork::CoreNetwork(const NetworkId &networkid, CoreSession *session) _channelKeys[chan.toLower()] = channels[chan]; } + QHash bufferCiphers = coreSession()->bufferCiphers(networkId()); + foreach(QString buffer, bufferCiphers.keys()) { + storeChannelCipherKey(buffer.toLower(), bufferCiphers[buffer]); + } + connect(networkConfig(), SIGNAL(pingTimeoutEnabledSet(bool)), SLOT(enablePingTimeout(bool))); connect(networkConfig(), SIGNAL(pingIntervalSet(int)), SLOT(setPingInterval(int))); connect(networkConfig(), SIGNAL(autoWhoEnabledSet(bool)), SLOT(setAutoWhoEnabled(bool))); @@ -214,12 +219,16 @@ void CoreNetwork::connectToIrc(bool reconnecting) } else if (_previousConnectionAttemptFailed) { // cycle to next server if previous connection attempt failed + _previousConnectionAttemptFailed = false; displayMsg(Message::Server, BufferInfo::StatusBuffer, "", tr("Connection failed. Cycling to next Server")); if (++_lastUsedServerIndex >= serverList().size()) { _lastUsedServerIndex = 0; } } - _previousConnectionAttemptFailed = false; + else { + // Start out with the top server in the list + _lastUsedServerIndex = 0; + } Server server = usedServer(); displayStatusMsg(tr("Connecting to %1:%2...").arg(server.host).arg(server.port)); @@ -237,8 +246,11 @@ void CoreNetwork::connectToIrc(bool reconnecting) // Qt caches DNS entries for a minute, resulting in round-robin (e.g. for chat.freenode.net) not working if several users // connect at a similar time. QHostInfo::fromName(), however, always performs a fresh lookup, overwriting the cache entry. - QHostInfo::fromName(server.host); - + if (! server.useProxy) { + //Avoid hostname lookups when a proxy is specified. The lookups won't use the proxy and may therefore leak the DNS + //hostname of the server. Qt's DNS cache also isn't used by the proxy so we don't need to refresh the entry. + QHostInfo::fromName(server.host); + } #ifdef HAVE_SSL if (server.useSsl) { CoreIdentity *identity = identityPtr(); @@ -435,6 +447,7 @@ void CoreNetwork::setCipherKey(const QString &target, const QByteArray &key) CoreIrcChannel *c = qobject_cast(ircChannel(target)); if (c) { c->setEncrypted(c->cipher()->setKey(key)); + coreSession()->setBufferCipher(networkId(), target, key); return; } @@ -444,6 +457,7 @@ void CoreNetwork::setCipherKey(const QString &target, const QByteArray &key) if (u) { u->setEncrypted(u->cipher()->setKey(key)); + coreSession()->setBufferCipher(networkId(), target, key); return; } } @@ -656,8 +670,11 @@ void CoreNetwork::networkInitialized() // restore away state QString awayMsg = Core::awayMessage(userId(), networkId()); - if (!awayMsg.isEmpty()) - userInputHandler()->handleAway(BufferInfo(), Core::awayMessage(userId(), networkId())); + if (!awayMsg.isEmpty()) { + // Don't re-apply any timestamp formatting in order to preserve escaped percent signs, e.g. + // '%%%%%%%%' -> '%%%%' If processed again, it'd result in '%%'. + userInputHandler()->handleAway(BufferInfo(), awayMsg, true); + } sendPerform(); @@ -891,12 +908,17 @@ void CoreNetwork::doAutoReconnect() void CoreNetwork::sendPing() { - uint now = QDateTime::currentDateTime().toTime_t(); + qint64 now = QDateTime::currentDateTime().toMSecsSinceEpoch(); if (_pingCount != 0) { qDebug() << "UserId:" << userId() << "Network:" << networkName() << "missed" << _pingCount << "pings." << "BA:" << socket.bytesAvailable() << "BTW:" << socket.bytesToWrite(); } - if ((int)_pingCount >= networkConfig()->maxPingCount() && now - _lastPingTime <= (uint)(_pingTimer.interval() / 1000) + 1) { + if ((int)_pingCount >= networkConfig()->maxPingCount() + && (now - _lastPingTime) <= (_pingTimer.interval() + (1 * 1000))) { + // In transitioning to 64-bit time, the interval no longer needs converted down to seconds. + // However, to reduce the risk of breaking things by changing past behavior, we still allow + // up to 1 second missed instead of enforcing a stricter 1 millisecond allowance. + // // the second check compares the actual elapsed time since the last ping and the pingTimer interval // if the interval is shorter then the actual elapsed time it means that this thread was somehow blocked // and unable to even handle a ping answer. So we ignore those misses. @@ -1053,7 +1075,7 @@ void CoreNetwork::serverCapAcknowledged(const QString &capability) // FIXME use event #ifdef HAVE_SSL if (!identityPtr()->sslCert().isNull()) { - if (IrcCap::SaslMech::maybeSupported(capValue(IrcCap::SASL), IrcCap::SaslMech::EXTERNAL)) { + if (saslMaybeSupports(IrcCap::SaslMech::EXTERNAL)) { // EXTERNAL authentication supported, send request putRawLine(serverEncode("AUTHENTICATE EXTERNAL")); } else { @@ -1063,7 +1085,7 @@ void CoreNetwork::serverCapAcknowledged(const QString &capability) } } else { #endif - if (IrcCap::SaslMech::maybeSupported(capValue(IrcCap::SASL), IrcCap::SaslMech::PLAIN)) { + if (saslMaybeSupports(IrcCap::SaslMech::PLAIN)) { // PLAIN authentication supported, send request // Only working with PLAIN atm, blowfish later putRawLine(serverEncode("AUTHENTICATE PLAIN")); @@ -1200,9 +1222,10 @@ void CoreNetwork::beginCapNegotiation() tr("Ready to negotiate (found: %1)").arg(caps().join(", "))); // Build a list of queued capabilities, starting with individual, then bundled, only adding the - // comma separator between the two if needed. + // comma separator between the two if needed (both individual and bundled caps exist). QString queuedCapsDisplay = - (!_capsQueuedIndividual.empty() ? _capsQueuedIndividual.join(", ") + ", " : "") + _capsQueuedIndividual.join(", ") + + ((!_capsQueuedIndividual.empty() && !_capsQueuedBundled.empty()) ? ", " : "") + _capsQueuedBundled.join(", "); displayMsg(Message::Server, BufferInfo::StatusBuffer, "", tr("Negotiating capabilities (requesting: %1)...").arg(queuedCapsDisplay));