From: Manuel Nickschas Date: Wed, 21 Jul 2010 20:43:17 +0000 (+0200) Subject: Clean-up and refactor the blowfish encryption stuff X-Git-Tag: 0.7-beta1~26 X-Git-Url: https://git.quassel-irc.org/?p=quassel.git;a=commitdiff_plain;h=6f0a153a674317d77233139fc50a2985af86e36e Clean-up and refactor the blowfish encryption stuff * Move all QCA2 deps into core only (introduces CoreIrcUser) * Simplify code where appropriate * Handle encodings properly * Whitespace and formatting fixes * Various other bits and pieces --- diff --git a/CMakeLists.txt b/CMakeLists.txt index 494d1ef4..3096bbd9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -9,7 +9,7 @@ # -DWITH_PHONON=OFF : Disable Phonon support (audio notifications) # -DWITH_LIBINDICATE=OFF : Disable libindicate support (Ayatana notifications) # -DWITH_KDE=ON : Enable KDE4 support -# -DWITH_CRYPT=OFF : Disable crypt support +# -DWITH_CRYPT=OFF : Disable encryption support # -DWITH_OXYGEN=(ON|OFF) : Whether to install Oxygen icons (default: yes, unless KDE > 4.3.0 is present and enabled) # # -DEMBED_DATA=ON : Embed all data files in icons the binary, rather than installing them separately @@ -45,7 +45,7 @@ option(WITH_WEBKIT "Enable WebKit support (for link previews)" ON) option(WITH_PHONON "Enable Phonon support (for audio notifications)" ON) option(WITH_LIBINDICATE "Enable Ayatana notification support" ON) option(WITH_KDE "Enable KDE4 integration" OFF) -option(WITH_CRYPT "Enable crypt support if present on system" ON) +option(WITH_CRYPT "Enable encryption support if present on system" ON) # We use icon paths from KDE 4.3.x, which are partially invalid on older and possibly # even on newer KDE versions. Do not disable this unless you are sure that your Quassel will @@ -265,20 +265,20 @@ else(WITH_LIBINDICATE) set(INDICATEQT_LIBRARIES "") endif(WITH_LIBINDICATE) -# Setup QtWebKit support +# Setup encyption support if(WITH_CRYPT) find_package(QCA2) if(QCA2_FOUND) - message(STATUS "Found qca2, enabling crypt support") + message(STATUS "Found QCA2, enabling encryption support") add_definitions(-DHAVE_QCA2) set(LINK_QCA2 QCA2) set(HAVE_QCA2 true) set(MOC_DEFINES ${MOC_DEFINES} -DHAVE_QCA2) else(QCA2_FOUND) - message(STATUS "qca2 not found, disabling crypt support") + message(STATUS "QCA2 not found, disabling encryption support") endif(QCA2_FOUND) else(WITH_CRYPT) - message(STATUS "Not enabling crypt support") + message(STATUS "Not enabling encryption support") endif(WITH_CRYPT) # Now set up install locations; those are set by KDE if integration is enabled diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 240b5407..2c1141ba 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -38,10 +38,6 @@ if(HAVE_INDICATEQT) link_directories(${INDICATEQT_LIBRARY_DIRS}) endif(HAVE_INDICATEQT) -if (QCA2_FOUND) - include_directories(${QCA2_INCLUDE_DIR}) -endif (QCA2_FOUND) - if(WANT_CORE) setup_qt4_variables(NETWORK SCRIPT SQL) add_executable(quasselcore common/main.cpp ${COMMON_DEPS} ${CORE_DEPS}) diff --git a/src/client/CMakeLists.txt b/src/client/CMakeLists.txt index 53fc7612..c8519070 100644 --- a/src/client/CMakeLists.txt +++ b/src/client/CMakeLists.txt @@ -6,10 +6,6 @@ set(QT_USE_QTNETWORK 1) set(QT_USE_QTDBUS 1) include(${QT_USE_FILE}) -if (QCA2_FOUND) - include_directories(${QCA2_INCLUDE_DIR}) -endif (QCA2_FOUND) - set(SOURCES abstractmessageprocessor.cpp backlogrequester.cpp diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt index e2975583..9298b777 100644 --- a/src/common/CMakeLists.txt +++ b/src/common/CMakeLists.txt @@ -1,8 +1,4 @@ # Builds the common module -if (QCA2_FOUND) - include_directories(${QCA2_INCLUDE_DIR}) -endif (QCA2_FOUND) - set(QT_DONT_USE_QTGUI 1) set(QT_USE_QTNETWORK 1) include(${QT_USE_FILE}) @@ -31,18 +27,6 @@ set(SOURCES syncableobject.cpp util.cpp) -if (QCA2_FOUND) - set(SOURCES ${SOURCES} - cipher.cpp) -endif (QCA2_FOUND) - -if(CMAKE_HOST_WIN32) - set(SOURCES ${SOURCES} logbacktrace_win.cpp) -endif(CMAKE_HOST_WIN32) -if(CMAKE_HOST_UNIX) - set(SOURCES ${SOURCES} logbacktrace_unix.cpp) -endif(CMAKE_HOST_UNIX) - set(MOC_HDRS aliasmanager.h backlogmanager.h @@ -71,16 +55,18 @@ set(HEADERS ${MOC_HDRS} types.h util.h) -if (QCA2_FOUND) - set(HEADERS ${HEADERS} - cipher.h) -endif (QCA2_FOUND) - if(APPLE) set(SOURCES ${SOURCES} mac_utils.cpp) set(HEADERS ${HEADERS} mac_utils.h) endif(APPLE) +if(CMAKE_HOST_WIN32) + set(SOURCES ${SOURCES} logbacktrace_win.cpp) +endif(CMAKE_HOST_WIN32) +if(CMAKE_HOST_UNIX) + set(SOURCES ${SOURCES} logbacktrace_unix.cpp) +endif(CMAKE_HOST_UNIX) + qt4_wrap_cpp(MOC ${MOC_HDRS}) include_directories(${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_SOURCE_DIR}) # for version.inc and version.gen @@ -92,10 +78,6 @@ if(APPLE) target_link_libraries(mod_common "-framework CoreServices" "-framework CoreFoundation") endif(APPLE) -if (QCA2_FOUND) - target_link_libraries(mod_common ${QCA2_LIBRARIES}) -endif (QCA2_FOUND) - if(CMAKE_HOST_SYSTEM_NAME STREQUAL "Linux") find_library(libdl dl) if(NOT libdl MATCHES "NOTFOUND") diff --git a/src/common/ircchannel.cpp b/src/common/ircchannel.cpp index d16e42df..3c5d7f9d 100644 --- a/src/common/ircchannel.cpp +++ b/src/common/ircchannel.cpp @@ -36,15 +36,11 @@ IrcChannel::IrcChannel(const QString &channelname, Network *network) _initialized(false), _name(channelname), _topic(QString()), - network(network), + _network(network), _codecForEncoding(0), _codecForDecoding(0) { setObjectName(QString::number(network->networkId().toInt()) + "/" + channelname); - - #ifdef HAVE_QCA2 - _cipher = 0; - #endif } IrcChannel::~IrcChannel() { @@ -58,7 +54,7 @@ bool IrcChannel::isKnownUser(IrcUser *ircuser) const { qWarning() << "Channel" << name() << "received IrcUser Nullpointer!"; return false; } - + if(!_userModes.contains(ircuser)) { qWarning() << "Channel" << name() << "received data for unknown User" << ircuser->nick(); return false; @@ -84,7 +80,7 @@ QString IrcChannel::userModes(IrcUser *ircuser) const { } QString IrcChannel::userModes(const QString &nick) const { - return userModes(network->ircUser(nick)); + return userModes(network()->ircUser(nick)); } void IrcChannel::setCodecForEncoding(const QString &name) { @@ -104,7 +100,7 @@ void IrcChannel::setCodecForDecoding(QTextCodec *codec) { } QString IrcChannel::decodeString(const QByteArray &text) const { - if(!codecForDecoding()) return network->decodeString(text); + if(!codecForDecoding()) return network()->decodeString(text); return ::decodeString(text, _codecForDecoding); } @@ -112,7 +108,7 @@ QByteArray IrcChannel::encodeString(const QString &string) const { if(codecForEncoding()) { return _codecForEncoding->fromUnicode(string); } - return network->encodeString(string); + return network()->encodeString(string); } // ==================== @@ -173,10 +169,10 @@ void IrcChannel::joinIrcUsers(const QList &users, const QStringList & void IrcChannel::joinIrcUsers(const QStringList &nicks, const QStringList &modes) { QList users; foreach(QString nick, nicks) - users << network->newIrcUser(nick); + users << network()->newIrcUser(nick); joinIrcUsers(users, modes); } - + void IrcChannel::joinIrcUser(IrcUser *ircuser) { QList users; users << ircuser; @@ -193,24 +189,24 @@ void IrcChannel::part(IrcUser *ircuser) { // the joines are propagted by the ircuser. the signal ircUserParted is only for convenience disconnect(ircuser, 0, this, 0); emit ircUserParted(ircuser); - - if(network->isMe(ircuser) || _userModes.isEmpty()) { + + if(network()->isMe(ircuser) || _userModes.isEmpty()) { // in either case we're no longer in the channel // -> clean up the channel and destroy it QList users = _userModes.keys(); _userModes.clear(); foreach(IrcUser *user, users) { - disconnect(user, 0, this, 0); - user->partChannel(this); + disconnect(user, 0, this, 0); + user->partChannel(this); } emit parted(); - network->removeIrcChannel(this); + network()->removeIrcChannel(this); } } } void IrcChannel::part(const QString &nick) { - part(network->ircUser(nick)); + part(network()->ircUser(nick)); } // SET USER MODE @@ -224,7 +220,7 @@ void IrcChannel::setUserModes(IrcUser *ircuser, const QString &modes) { } void IrcChannel::setUserModes(const QString &nick, const QString &modes) { - setUserModes(network->ircUser(nick), modes); + setUserModes(network()->ircUser(nick), modes); } // ADD USER MODE @@ -242,7 +238,7 @@ void IrcChannel::addUserMode(IrcUser *ircuser, const QString &mode) { } void IrcChannel::addUserMode(const QString &nick, const QString &mode) { - addUserMode(network->ircUser(nick), mode); + addUserMode(network()->ircUser(nick), mode); } // REMOVE USER MODE @@ -259,7 +255,7 @@ void IrcChannel::removeUserMode(IrcUser *ircuser, const QString &mode) { } void IrcChannel::removeUserMode(const QString &nick, const QString &mode) { - removeUserMode(network->ircUser(nick), mode); + removeUserMode(network()->ircUser(nick), mode); } // INIT SET USER MODES @@ -278,7 +274,7 @@ void IrcChannel::initSetUserModes(const QVariantMap &usermodes) { QStringList modes; QVariantMap::const_iterator iter = usermodes.constBegin(); while(iter != usermodes.constEnd()) { - users << network->newIrcUser(iter.key()); + users << network()->newIrcUser(iter.key()); modes << iter.value().toString(); iter++; } @@ -295,7 +291,7 @@ QVariantMap IrcChannel::initChanModes() const { A_iter++; } channelModes["A"] = A_modes; - + QVariantMap B_modes; QHash::const_iterator B_iter = _B_channelModes.constBegin(); while(B_iter != _B_channelModes.constEnd()) { @@ -303,7 +299,7 @@ QVariantMap IrcChannel::initChanModes() const { B_iter++; } channelModes["B"] = B_modes; - + QVariantMap C_modes; QHash::const_iterator C_iter = _C_channelModes.constBegin(); while(C_iter != _C_channelModes.constEnd()) { @@ -311,7 +307,7 @@ QVariantMap IrcChannel::initChanModes() const { C_iter++; } channelModes["C"] = C_modes; - + QString D_modes; QSet::const_iterator D_iter = _D_channelModes.constBegin(); while(D_iter != _D_channelModes.constEnd()) { @@ -337,7 +333,7 @@ void IrcChannel::initSetChanModes(const QVariantMap &channelModes) { _B_channelModes[iter.key()[0]] = iter.value().toString(); iter++; } - + iter = channelModes["C"].toMap().constBegin(); iterEnd = channelModes["C"].toMap().constEnd(); while(iter != iterEnd) { @@ -369,12 +365,12 @@ void IrcChannel::ircUserNickSet(QString nick) { /******************************************************************************* * * 3.3 CHANMODES - * + * * o CHANMODES=A,B,C,D - * + * * The CHANMODES token specifies the modes that may be set on a channel. * These modes are split into four categories, as follows: - * + * * o Type A: Modes that add or remove an address to or from a list. * These modes always take a parameter when sent by the server to a * client; when sent by a client, they may be specified without a @@ -387,11 +383,11 @@ void IrcChannel::ircUserNickSet(QString nick) { * mode is removed both in the client's and server's MODE command. * o Type D: Modes that change a setting on the channel. These modes * never take a parameter. - * + * * If the server sends any additional types after these 4, the client * MUST ignore them; this is intended to allow future extension of this * token. - * + * * The IRC server MUST NOT list modes in CHANMODES which are also * present in the PREFIX parameter; however, for completeness, modes * described in PREFIX may be treated as type B modes. @@ -413,7 +409,7 @@ void IrcChannel::ircUserNickSet(QString nick) { // NOTE: the behavior of addChannelMode and removeChannelMode depends on the type of mode // see list above for chanmode types void IrcChannel::addChannelMode(const QChar &mode, const QString &value) { - Network::ChannelModeType modeType = network->channelModeType(mode); + Network::ChannelModeType modeType = network()->channelModeType(mode); switch(modeType) { case Network::NOT_A_CHANMODE: @@ -424,7 +420,7 @@ void IrcChannel::addChannelMode(const QChar &mode, const QString &value) { else if(!_A_channelModes[mode].contains(value)) _A_channelModes[mode] << value; break; - + case Network::B_CHANMODE: _B_channelModes[mode] = value; break; @@ -441,7 +437,7 @@ void IrcChannel::addChannelMode(const QChar &mode, const QString &value) { } void IrcChannel::removeChannelMode(const QChar &mode, const QString &value) { - Network::ChannelModeType modeType = network->channelModeType(mode); + Network::ChannelModeType modeType = network()->channelModeType(mode); switch(modeType) { case Network::NOT_A_CHANMODE: @@ -450,7 +446,7 @@ void IrcChannel::removeChannelMode(const QChar &mode, const QString &value) { if(_A_channelModes.contains(mode)) _A_channelModes[mode].removeAll(value); break; - + case Network::B_CHANMODE: _B_channelModes.remove(mode); break; @@ -467,7 +463,7 @@ void IrcChannel::removeChannelMode(const QChar &mode, const QString &value) { } bool IrcChannel::hasMode(const QChar &mode) const { - Network::ChannelModeType modeType = network->channelModeType(mode); + Network::ChannelModeType modeType = network()->channelModeType(mode); switch(modeType) { case Network::NOT_A_CHANMODE: @@ -486,7 +482,7 @@ bool IrcChannel::hasMode(const QChar &mode) const { } QString IrcChannel::modeValue(const QChar &mode) const { - Network::ChannelModeType modeType = network->channelModeType(mode); + Network::ChannelModeType modeType = network()->channelModeType(mode); switch(modeType) { case Network::B_CHANMODE: @@ -502,11 +498,11 @@ QString IrcChannel::modeValue(const QChar &mode) const { default: return QString(); } - + } QStringList IrcChannel::modeValueList(const QChar &mode) const { - Network::ChannelModeType modeType = network->channelModeType(mode); + Network::ChannelModeType modeType = network()->channelModeType(mode); switch(modeType) { case Network::A_CHANMODE: @@ -545,36 +541,3 @@ QString IrcChannel::channelModeString() const { else return QString("+%1 %2").arg(modeString).arg(params.join(" ")); } - -#ifdef HAVE_QCA2 -Cipher* IrcChannel::cipher() { - if(!_cipher) - _cipher = new Cipher(); - return _cipher; -} -#endif - -void IrcChannel::setEncrypted(bool e) { - if(e) { - #ifdef HAVE_QCA2 - if(topic().isEmpty()) - return; - - QByteArray key = network->bufferKey(name()); - if (key.isEmpty()) - return; - - if(!cipher()->setKey(key)) - return; - - //only send encrypted text to decrypter - int index = topic().indexOf(":",topic().indexOf(":")+1); - - QString backup = topic().mid(0,index+1); - QString decrypted = cipher()->decryptTopic(topic().mid(index+1).toAscii());; - decrypted.prepend(backup); - - setTopic(decodeString(decrypted.toAscii())); - #endif - } -} \ No newline at end of file diff --git a/src/common/ircchannel.h b/src/common/ircchannel.h index 0c0f2ed1..564eda89 100644 --- a/src/common/ircchannel.h +++ b/src/common/ircchannel.h @@ -29,10 +29,6 @@ #include "syncableobject.h" -#ifdef HAVE_QCA2 -#include "cipher.h" -#endif - class IrcUser; class Network; @@ -54,6 +50,7 @@ public: inline QString name() const { return _name; } inline QString topic() const { return _topic; } inline QString password() const { return _password; } + inline Network *network() const { return _network; } inline QList ircUsers() const { return _userModes.keys(); } @@ -64,7 +61,7 @@ public: QString modeValue(const QChar &mode) const; QStringList modeValueList(const QChar &mode) const; QString channelModeString() const; - + inline QTextCodec *codecForEncoding() const { return _codecForEncoding; } inline QTextCodec *codecForDecoding() const { return _codecForDecoding; } void setCodecForEncoding(const QString &codecName); @@ -74,12 +71,6 @@ public: QString decodeString(const QByteArray &text) const; QByteArray encodeString(const QString &string) const; - - #ifdef HAVE_QCA2 - Cipher* cipher(); - #endif - - void setEncrypted(bool); public slots: void setTopic(const QString &topic); @@ -103,7 +94,7 @@ public slots: void addChannelMode(const QChar &mode, const QString &value); void removeChannelMode(const QChar &mode, const QString &value); - + // init geters QVariantMap initUserModes() const; QVariantMap initChanModes() const; @@ -111,7 +102,7 @@ public slots: // init seters void initSetUserModes(const QVariantMap &usermodes); void initSetChanModes(const QVariantMap &chanModes); - + signals: void topicSet(const QString &topic); // needed by NetworkModel // void passwordSet(const QString &password); @@ -120,7 +111,7 @@ signals: // void userModeRemoved(QString nick, QString mode); // void channelModeAdded(const QChar &mode, const QString &value); // void channelModeRemoved(const QChar &mode, const QString &value); - + void ircUsersJoined(QList ircusers); // void ircUsersJoined(QStringList nicks, QStringList modes); void ircUserParted(IrcUser *ircuser); @@ -140,10 +131,10 @@ private: QString _name; QString _topic; QString _password; - + QHash _userModes; - Network *network; + Network *_network; QTextCodec *_codecForEncoding; QTextCodec *_codecForDecoding; @@ -152,10 +143,6 @@ private: QHash _B_channelModes; QHash _C_channelModes; QSet _D_channelModes; - - #ifdef HAVE_QCA2 - Cipher *_cipher; - #endif }; #endif diff --git a/src/common/ircuser.cpp b/src/common/ircuser.cpp index 1dbb0f08..95892c49 100644 --- a/src/common/ircuser.cpp +++ b/src/common/ircuser.cpp @@ -47,10 +47,7 @@ IrcUser::IrcUser(const QString &hostmask, Network *network) : SyncableObject(net _codecForDecoding(0) { updateObjectName(); - - #ifdef HAVE_QCA2 - _cipher = 0; - #endif + } IrcUser::~IrcUser() { @@ -314,16 +311,3 @@ void IrcUser::setLastSpokenTo(BufferId buffer, const QDateTime &time) { _lastSpokenTo[buffer] = time; emit lastSpokenToUpdated(buffer, time); } - -#ifdef HAVE_QCA2 -Cipher* IrcUser::cipher() { - if(!_cipher) - _cipher = new Cipher(); - return _cipher; -} -#endif - -void IrcUser::setEncrypted(bool e) { - Q_UNUSED(e); - // TODO -} \ No newline at end of file diff --git a/src/common/ircuser.h b/src/common/ircuser.h index f74c46fd..7ec878e7 100644 --- a/src/common/ircuser.h +++ b/src/common/ircuser.h @@ -30,10 +30,6 @@ #include "syncableobject.h" #include "types.h" -#ifdef HAVE_QCA2 -#include "cipher.h" -#endif - class SignalProxy; class Network; class IrcChannel; @@ -100,12 +96,6 @@ public: inline QDateTime lastSpokenTo(BufferId id) const { return _lastSpokenTo.value(id); } void setLastSpokenTo(BufferId id, const QDateTime &time); - #ifdef HAVE_QCA2 - Cipher* cipher(); - #endif - - void setEncrypted(bool); - public slots: void setUser(const QString &user); void setHost(const QString &host); @@ -132,7 +122,7 @@ public slots: void addUserModes(const QString &modes); void removeUserModes(const QString &modes); - + signals: // void userSet(QString user); // void hostSet(QString host); @@ -200,10 +190,6 @@ private: QHash _lastActivity; QHash _lastSpokenTo; - - #ifdef HAVE_QCA2 - Cipher *_cipher; - #endif }; #endif diff --git a/src/common/network.cpp b/src/common/network.cpp index 5dccc18f..6eccc9bc 100644 --- a/src/common/network.cpp +++ b/src/common/network.cpp @@ -1,5 +1,5 @@ /*************************************************************************** - * Copyright (C) 2005-09 by the Quassel Project * + * Copyright (C) 2005-2010 by the Quassel Project * * devel@quassel-irc.org * * * * This program is free software; you can redistribute it and/or modify * @@ -194,7 +194,7 @@ QString Network::support(const QString ¶m) const { IrcUser *Network::newIrcUser(const QString &hostmask, const QVariantMap &initData) { QString nick(nickFromMask(hostmask).toLower()); if(!_ircUsers.contains(nick)) { - IrcUser *ircuser = new IrcUser(hostmask, this); + IrcUser *ircuser = ircUserFactory(hostmask); if(!initData.isEmpty()) { ircuser->fromVariantMap(initData); ircuser->setInitialized(); @@ -475,14 +475,6 @@ NetworkInfo Network::networkInfoFromPreset(const QString &networkName) { return info; } -QByteArray Network::bufferKey(const QString &recipient) const { - return _keyHash[recipient.toLower()]; -} - -void Network::setBufferKey(const QString &recipient, const QByteArray &key) { - _keyHash[recipient.toLower()] = key; -} - // ==================== // Public Slots: // ==================== @@ -760,8 +752,8 @@ void Network::determinePrefixes() { // we just assume that in PREFIX are only prefix chars stored for(int i = 0; i < defaultPrefixes.size(); i++) { if(prefix.contains(defaultPrefixes[i])) { - _prefixes += defaultPrefixes[i]; - _prefixModes += defaultPrefixModes[i]; + _prefixes += defaultPrefixes[i]; + _prefixModes += defaultPrefixModes[i]; } } // check for success @@ -772,8 +764,8 @@ void Network::determinePrefixes() { // check if it's only prefix modes for(int i = 0; i < defaultPrefixes.size(); i++) { if(prefix.contains(defaultPrefixModes[i])) { - _prefixes += defaultPrefixes[i]; - _prefixModes += defaultPrefixModes[i]; + _prefixes += defaultPrefixes[i]; + _prefixModes += defaultPrefixModes[i]; } } // now we've done all we've could... @@ -882,13 +874,13 @@ QDataStream &operator>>(QDataStream &in, NetworkInfo &info) { QDebug operator<<(QDebug dbg, const NetworkInfo &i) { dbg.nospace() << "(id = " << i.networkId << " name = " << i.networkName << " identity = " << i.identity - << " codecForServer = " << i.codecForServer << " codecForEncoding = " << i.codecForEncoding << " codecForDecoding = " << i.codecForDecoding - << " serverList = " << i.serverList << " useRandomServer = " << i.useRandomServer << " perform = " << i.perform - << " useAutoIdentify = " << i.useAutoIdentify << " autoIdentifyService = " << i.autoIdentifyService << " autoIdentifyPassword = " << i.autoIdentifyPassword + << " codecForServer = " << i.codecForServer << " codecForEncoding = " << i.codecForEncoding << " codecForDecoding = " << i.codecForDecoding + << " serverList = " << i.serverList << " useRandomServer = " << i.useRandomServer << " perform = " << i.perform + << " useAutoIdentify = " << i.useAutoIdentify << " autoIdentifyService = " << i.autoIdentifyService << " autoIdentifyPassword = " << i.autoIdentifyPassword << " useSasl = " << i.useSasl << " saslAccount = " << i.saslAccount << " saslPassword = " << i.saslPassword << " useAutoReconnect = " << i.useAutoReconnect << " autoReconnectInterval = " << i.autoReconnectInterval - << " autoReconnectRetries = " << i.autoReconnectRetries << " unlimitedReconnectRetries = " << i.unlimitedReconnectRetries - << " rejoinChannels = " << i.rejoinChannels << ")"; + << " autoReconnectRetries = " << i.autoReconnectRetries << " unlimitedReconnectRetries = " << i.unlimitedReconnectRetries + << " rejoinChannels = " << i.rejoinChannels << ")"; return dbg.space(); } diff --git a/src/common/network.h b/src/common/network.h index 4e4d60d9..6bce3d91 100644 --- a/src/common/network.h +++ b/src/common/network.h @@ -1,5 +1,5 @@ /*************************************************************************** - * Copyright (C) 2005-09 by the Quassel Project * + * Copyright (C) 2005-2010 by the Quassel Project * * devel@quassel-irc.org * * * * This program is free software; you can redistribute it and/or modify * @@ -112,7 +112,7 @@ public: Server() : port(6667), useSsl(false), sslVersion(0), useProxy(false), proxyType(QNetworkProxy::Socks5Proxy), proxyHost("localhost"), proxyPort(8080) {} Server(const QString &host, uint port, const QString &password, bool useSsl) : host(host), port(port), password(password), useSsl(useSsl), sslVersion(0), - useProxy(false), proxyType(QNetworkProxy::Socks5Proxy), proxyHost("localhost"), proxyPort(8080) {} + useProxy(false), proxyType(QNetworkProxy::Socks5Proxy), proxyHost("localhost"), proxyPort(8080) {} bool operator==(const Server &other) const; bool operator!=(const Server &other) const; }; @@ -215,10 +215,6 @@ public: static QStringList presetDefaultChannels(const QString &networkName); static NetworkInfo networkInfoFromPreset(const QString &networkName); - // Blowfish stuff - QByteArray bufferKey(const QString &recipient) const; - void setBufferKey(const QString &recipient, const QByteArray &key); - public slots: void setNetworkName(const QString &networkName); void setCurrentServer(const QString ¤tServer); @@ -275,10 +271,10 @@ public slots: void emitConnectionError(const QString &); -private slots: - void removeIrcUser(IrcUser *ircuser); - void removeIrcChannel(IrcChannel *ircChannel); - void removeChansAndUsers(); +protected slots: + virtual void removeIrcUser(IrcUser *ircuser); + virtual void removeIrcChannel(IrcChannel *ircChannel); + virtual void removeChansAndUsers(); signals: void aboutToBeDestroyed(); @@ -324,6 +320,7 @@ signals: protected: inline virtual IrcChannel *ircChannelFactory(const QString &channelname) { return new IrcChannel(channelname, this); } + inline virtual IrcUser *ircUserFactory(const QString &hostmask) { return new IrcUser(hostmask, this); } private: QPointer _proxy; @@ -345,9 +342,6 @@ private: QHash _ircChannels; // stores all known channels QHash _supports; // stores results from RPL_ISUPPORT - // Blowfish key map - QHash _keyHash; - ServerList _serverList; bool _useRandomServer; QStringList _perform; diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt index e786dab1..8ac1bddc 100644 --- a/src/core/CMakeLists.txt +++ b/src/core/CMakeLists.txt @@ -6,10 +6,6 @@ set(QT_USE_QTSQL 1) set(QT_USE_QTSCRIPT 1) include(${QT_USE_FILE}) -if (QCA2_FOUND) - include_directories(${QCA2_INCLUDE_DIR}) -endif (QCA2_FOUND) - set(SOURCES abstractsqlstorage.cpp core.cpp @@ -25,6 +21,7 @@ set(SOURCES coreignorelistmanager.cpp coreircchannel.cpp coreirclisthelper.cpp + coreircuser.cpp corenetwork.cpp corenetworkconfig.cpp coresession.cpp @@ -54,6 +51,7 @@ set(MOC_HDRS coreignorelistmanager.h coreircchannel.h coreirclisthelper.h + coreircuser.h corenetwork.h corenetworkconfig.h coresession.h @@ -76,6 +74,12 @@ if(HAVE_SSL) include_directories(${OPENSSL_INCLUDE_DIR}) endif(HAVE_SSL) +if(HAVE_QCA2) + set(SOURCES ${SOURCES} cipher.cpp) + set(HEADERS ${HEADERS} cipher.h) + include_directories(${QCA2_INCLUDE_DIR}) +endif(HAVE_QCA2) + qt4_wrap_cpp(MOC ${MOC_HDRS}) set(CORE_RCS ${CORE_RCS} core/sql.qrc PARENT_SCOPE) @@ -83,3 +87,7 @@ include_directories(${CMAKE_SOURCE_DIR}/src/common) add_library(mod_core STATIC ${SOURCES} ${MOC} ${HEADERS}) add_dependencies(mod_core mod_common) + +if(HAVE_QCA2) + target_link_libraries(mod_core ${QCA2_LIBRARIES}) +endif(HAVE_QCA2) diff --git a/src/common/cipher.cpp b/src/core/cipher.cpp similarity index 100% rename from src/common/cipher.cpp rename to src/core/cipher.cpp diff --git a/src/common/cipher.h b/src/core/cipher.h similarity index 100% rename from src/common/cipher.h rename to src/core/cipher.h diff --git a/src/core/coreircchannel.cpp b/src/core/coreircchannel.cpp index 9db3c1a2..85eb333f 100644 --- a/src/core/coreircchannel.cpp +++ b/src/core/coreircchannel.cpp @@ -1,5 +1,5 @@ /*************************************************************************** - * Copyright (C) 2005-09 by the Quassel Project * + * Copyright (C) 2005-2010 by the Quassel Project * * devel@quassel-irc.org * * * * This program is free software; you can redistribute it and/or modify * @@ -19,10 +19,47 @@ ***************************************************************************/ #include "coreircchannel.h" +#include "corenetwork.h" INIT_SYNCABLE_OBJECT(CoreIrcChannel) CoreIrcChannel::CoreIrcChannel(const QString &channelname, Network *network) : IrcChannel(channelname, network), _receivedWelcomeMsg(false) { +#ifdef HAVE_QCA2 + _cipher = 0; +#endif } + +CoreIrcChannel::~CoreIrcChannel() { +#ifdef HAVE_QCA2 + delete _cipher; +#endif +} + +#ifdef HAVE_QCA2 +Cipher *CoreIrcChannel::cipher() const { + if(!_cipher) + _cipher = new Cipher(); + + return _cipher; +} + +void CoreIrcChannel::setEncrypted(bool e) { + if(e) { + if(topic().isEmpty()) + return; + + QByteArray key = qobject_cast(network())->cipherKey(name()); + if(key.isEmpty()) + return; + + if(!cipher()->setKey(key)) + return; + + QByteArray decrypted = cipher()->decryptTopic(topic().toAscii()); + setTopic(decodeString(decrypted)); + } +} + +#endif diff --git a/src/core/coreircchannel.h b/src/core/coreircchannel.h index 5995165a..450fd58c 100644 --- a/src/core/coreircchannel.h +++ b/src/core/coreircchannel.h @@ -1,5 +1,5 @@ /*************************************************************************** - * Copyright (C) 2005-09 by the Quassel Project * + * Copyright (C) 2005-2010 by the Quassel Project * * devel@quassel-irc.org * * * * This program is free software; you can redistribute it and/or modify * @@ -23,20 +23,34 @@ #include "ircchannel.h" +#ifdef HAVE_QCA2 +# include "cipher.h" +#endif + class CoreIrcChannel : public IrcChannel { SYNCABLE_OBJECT Q_OBJECT public: CoreIrcChannel(const QString &channelname, Network *network); + virtual ~CoreIrcChannel(); inline virtual const QMetaObject *syncMetaObject() const { return &IrcChannel::staticMetaObject; } +#ifdef HAVE_QCA2 + Cipher *cipher() const; + void setEncrypted(bool); +#endif + inline bool receivedWelcomeMsg() const { return _receivedWelcomeMsg; } inline void setReceivedWelcomeMsg() { _receivedWelcomeMsg = true; } private: bool _receivedWelcomeMsg; + +#ifdef HAVE_QCA2 + mutable Cipher *_cipher; +#endif }; #endif //COREIRCCHANNEL_H diff --git a/src/core/coreircuser.cpp b/src/core/coreircuser.cpp new file mode 100644 index 00000000..00b59799 --- /dev/null +++ b/src/core/coreircuser.cpp @@ -0,0 +1,48 @@ +/*************************************************************************** + * Copyright (C) 2005-2010 by the Quassel Project * + * devel@quassel-irc.org * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) version 3. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * + ***************************************************************************/ + +#include "coreircuser.h" + +CoreIrcUser::CoreIrcUser(const QString &hostmask, Network *network) : IrcUser(hostmask, network) { +#ifdef HAVE_QCA2 + _cipher = 0; +#endif +} + +CoreIrcUser::~CoreIrcUser() { +#ifdef HAVE_QCA2 + delete _cipher; +#endif +} + +#ifdef HAVE_QCA2 +Cipher *CoreIrcUser::cipher() const { + if(!_cipher) + _cipher = new Cipher(); + + return _cipher; +} + +void CoreIrcUser::setEncrypted(bool e) { + Q_UNUSED(e); + // TODO +} + +#endif diff --git a/src/core/coreircuser.h b/src/core/coreircuser.h new file mode 100644 index 00000000..b26fed06 --- /dev/null +++ b/src/core/coreircuser.h @@ -0,0 +1,51 @@ +/*************************************************************************** + * Copyright (C) 2005-2010 by the Quassel Project * + * devel@quassel-irc.org * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) version 3. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the * + * Free Software Foundation, Inc., * + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * + ***************************************************************************/ + +#ifndef COREIRCUSER_H_ +#define COREIRCUSER_H_ + +#include "ircuser.h" + +#ifdef HAVE_QCA2 +# include "cipher.h" +#endif + +class CoreIrcUser : public IrcUser { + SYNCABLE_OBJECT + Q_OBJECT + +public: + CoreIrcUser(const QString &hostmask, Network *network); + virtual ~CoreIrcUser(); + + inline virtual const QMetaObject *syncMetaObject() const { return &IrcUser::staticMetaObject; } + +#ifdef HAVE_QCA2 + Cipher *cipher() const; + void setEncrypted(bool); +#endif + +#ifdef HAVE_QCA2 +private: + mutable Cipher *_cipher; +#endif +}; + +#endif diff --git a/src/core/corenetwork.cpp b/src/core/corenetwork.cpp index 76a9d559..ccb5600f 100644 --- a/src/core/corenetwork.cpp +++ b/src/core/corenetwork.cpp @@ -276,6 +276,19 @@ void CoreNetwork::removeChannelKey(const QString &channel) { _channelKeys.remove(channel.toLower()); } +#ifdef HAVE_QCA2 +QByteArray CoreNetwork::cipherKey(const QString &recipient) const { + return _cipherKeys.value(recipient.toLower(), QByteArray()); +} + +void CoreNetwork::setCipherKey(const QString &recipient, const QByteArray &key) { + if(!key.isEmpty()) + _cipherKeys[recipient.toLower()] = key; + else + _cipherKeys.remove(recipient.toLower()); +} +#endif /* HAVE_QCA2 */ + bool CoreNetwork::setAutoWhoDone(const QString &channel) { QString chan = channel.toLower(); if(_autoWhoPending.value(chan, 0) <= 0) @@ -632,7 +645,7 @@ void CoreNetwork::sendPing() { uint now = QDateTime::currentDateTime().toTime_t(); if(_pingCount != 0) { qDebug() << "UserId:" << userId() << "Network:" << networkName() << "missed" << _pingCount << "pings." - << "BA:" << socket.bytesAvailable() << "BTW:" << socket.bytesToWrite(); + << "BA:" << socket.bytesAvailable() << "BTW:" << socket.bytesToWrite(); } if((int)_pingCount >= networkConfig()->maxPingCount() && now - _lastPingTime <= (uint)(_pingTimer.interval() / 1000) + 1) { // the second check compares the actual elapsed time since the last ping and the pingTimer interval diff --git a/src/core/corenetwork.h b/src/core/corenetwork.h index a6d36780..7b458509 100644 --- a/src/core/corenetwork.h +++ b/src/core/corenetwork.h @@ -23,6 +23,7 @@ #include "network.h" #include "coreircchannel.h" +#include "coreircuser.h" #include @@ -33,6 +34,10 @@ # include #endif +#ifdef HAVE_QCA2 +# include "cipher.h" +#endif + #include "coresession.h" class CoreIdentity; @@ -108,6 +113,12 @@ public slots: void addChannelKey(const QString &channel, const QString &key); void removeChannelKey(const QString &channel); + // Blowfish stuff +#ifdef HAVE_QCA2 + QByteArray cipherKey(const QString &recipient) const; + void setCipherKey(const QString &recipient, const QByteArray &key); +#endif + void setAutoWhoEnabled(bool enabled); void setAutoWhoInterval(int interval); void setAutoWhoDelay(int delay); @@ -138,6 +149,13 @@ signals: protected: inline virtual IrcChannel *ircChannelFactory(const QString &channelname) { return new CoreIrcChannel(channelname, this); } + inline virtual IrcUser *ircUserFactory(const QString &hostmask) { return new CoreIrcUser(hostmask, this); } + +protected slots: + // TODO: remove cached cipher keys, when appropriate + //virtual void removeIrcUser(IrcUser *ircuser); + //virtual void removeIrcChannel(IrcChannel *ircChannel); + //virtual void removeChansAndUsers(); private slots: void socketHasData(); @@ -209,6 +227,9 @@ private: QList _msgQueue; QString _requestedUserModes; // 2 strings separated by a '-' character. first part are requested modes to add, the second to remove + + // Blowfish key map + QHash _cipherKeys; }; #endif //CORENETWORK_H diff --git a/src/core/coreuserinputhandler.cpp b/src/core/coreuserinputhandler.cpp index 95605bdb..ecab9e10 100644 --- a/src/core/coreuserinputhandler.cpp +++ b/src/core/coreuserinputhandler.cpp @@ -1,5 +1,5 @@ /*************************************************************************** - * Copyright (C) 2005-10 by the Quassel Project * + * Copyright (C) 2005-2010 by the Quassel Project * * devel@quassel-irc.org * * * * This program is free software; you can redistribute it and/or modify * @@ -22,14 +22,11 @@ #include "util.h" #include "ctcphandler.h" -#include "coreidentity.h" -#include "ircuser.h" -#include #include #ifdef HAVE_QCA2 -#include "cipher.h" +# include "cipher.h" #endif CoreUserInputHandler::CoreUserInputHandler(CoreNetwork *parent) @@ -81,7 +78,7 @@ void CoreUserInputHandler::issueAway(const QString &msg, bool autoCheck) { awayMsg = identity->awayReason(); } if(awayMsg.isEmpty()) { - awayMsg = tr("away"); + awayMsg = tr("away"); } } } @@ -162,57 +159,46 @@ void CoreUserInputHandler::handleCtcp(const BufferInfo &bufferInfo, const QStrin } void CoreUserInputHandler::handleDelkey(const BufferInfo &bufferInfo, const QString &msg) { - #ifdef HAVE_QCA2 - if (!bufferInfo.isValid()) +#ifdef HAVE_QCA2 + if(!bufferInfo.isValid()) return; - + QStringList parms = msg.split(' ', QString::SkipEmptyParts); - + if(parms.isEmpty() && !bufferInfo.bufferName().isEmpty()) parms.prepend(bufferInfo.bufferName()); if(parms.isEmpty()) { - QString message = tr("[usage] /delkey deletes the encryption key for nick or channel or just /delkey when in a channel or query."); - - if(bufferInfo.bufferName().isEmpty()) - emit displayMsg(Message::Info, BufferInfo::StatusBuffer, "", message); - else - emit displayMsg(Message::Info, bufferInfo.bufferName(), message); + emit displayMsg(Message::Info, bufferInfo.bufferName(), "", + tr("[usage] /delkey deletes the encryption key for nick or channel or just /delkey when in a channel or query.")); return; } - if(network()->bufferKey(parms[0]).isEmpty()) { - QString message = tr("No key has been set for %1.").arg(parms[0]); + QString target = parms.at(0); - if(bufferInfo.bufferName().isEmpty()) - emit displayMsg(Message::Info, BufferInfo::StatusBuffer, "", message); - else - emit displayMsg(Message::Info, bufferInfo.bufferName(), message); + if(network()->cipherKey(target).isEmpty()) { + emit displayMsg(Message::Info, bufferInfo.bufferName(), tr("No key has been set for %1.").arg(target)); return; } - network()->setBufferKey(parms[0], ""); + network()->setCipherKey(target, QByteArray()); - if(network()->isChannelName(parms[0]) && network()->channels().contains(parms[0])) { - network()->ircChannel(parms[0])->setEncrypted(false); + if(network()->isChannelName(target) && network()->channels().contains(target)) { + qobject_cast(network()->ircChannel(target))->setEncrypted(false); } - else if(network()->nicks().contains(parms[0])) { - network()->ircUser(parms[0])->setEncrypted(false); + else if(network()->nicks().contains(target)) { + qobject_cast(network()->ircUser(target))->setEncrypted(false); } - QString message = tr("The key for %1 has been deleted.").arg(parms[0]); - - if(bufferInfo.bufferName().isEmpty()) - emit displayMsg(Message::Info, BufferInfo::StatusBuffer, "", message); - else - emit displayMsg(Message::Info, bufferInfo.bufferName(), message); - - #else - emit displayMsg(Message::Error, BufferInfo::StatusBuffer, "", tr("Error: Setting an encryption key requires Quassel to have been built " - "with support for the Qt Cryptographic Architecture (QCA) library. " - "Contact your distributor about a Quassel package with QCA " - "support, or rebuild Quassel with QCA present.")); - #endif + emit displayMsg(Message::Info, bufferInfo.bufferName(), tr("The key for %1 has been deleted.").arg(target)); + +#else + Q_UNUSED(msg) + emit displayMsg(Message::Error, bufferInfo.bufferName(), "", tr("Error: Setting an encryption key requires Quassel to have been built " + "with support for the Qt Cryptographic Architecture (QCA2) library. " + "Contact your distributor about a Quassel package with QCA2 " + "support, or rebuild Quassel with QCA2 present.")); +#endif } void CoreUserInputHandler::handleDeop(const BufferInfo &bufferInfo, const QString &msg) { @@ -354,8 +340,14 @@ void CoreUserInputHandler::handleMsg(const BufferInfo &bufferInfo, const QString if(!msg.contains(' ')) return; - QByteArray target = serverEncode(msg.section(' ', 0, 0)); - putPrivmsg(target, userEncode(target, msg.section(' ', 1)), false); + QString target = msg.section(' ', 0, 0); + QByteArray encMsg = userEncode(target, msg.section(' ', 1)); + +#ifdef HAVE_QCA2 + encMsg = encrypt(target, encMsg); +#endif + + putPrivmsg(serverEncode(target), encMsg, false); } void CoreUserInputHandler::handleNick(const BufferInfo &bufferInfo, const QString &msg) { @@ -445,62 +437,67 @@ void CoreUserInputHandler::handleQuote(const BufferInfo &bufferInfo, const QStri void CoreUserInputHandler::handleSay(const BufferInfo &bufferInfo, const QString &msg) { if(bufferInfo.bufferName().isEmpty()) return; // server buffer - putPrivmsg(serverEncode(bufferInfo.bufferName()), channelEncode(bufferInfo.bufferName(), msg), false); + + QByteArray encMsg = channelEncode(bufferInfo.bufferName(), msg); +#ifdef HAVE_QCA2 + encMsg = encrypt(bufferInfo.bufferName(), encMsg); +#endif + + putPrivmsg(serverEncode(bufferInfo.bufferName()), encMsg, false); emit displayMsg(Message::Plain, bufferInfo.type(), bufferInfo.bufferName(), msg, network()->myNick(), Message::Self); } void CoreUserInputHandler::handleSetkey(const BufferInfo &bufferInfo, const QString &msg) { - #ifdef HAVE_QCA2 +#ifdef HAVE_QCA2 if(!bufferInfo.isValid()) return; - + QStringList parms = msg.split(' ', QString::SkipEmptyParts); - + if(parms.count() == 1 && !bufferInfo.bufferName().isEmpty()) parms.prepend(bufferInfo.bufferName()); else if(parms.count() != 2) { - QString message =tr("[usage] /setkey sets the encryption key for nick or channel. /setkey when in a channel or query buffer sets the key for it."); - - if(bufferInfo.bufferName().isEmpty()) - emit displayMsg(Message::Info, BufferInfo::StatusBuffer, "", message); - else - emit displayMsg(Message::Info, bufferInfo.bufferName(), message); + emit displayMsg(Message::Info, bufferInfo.bufferName(), + tr("[usage] /setkey sets the encryption key for nick or channel. " + "/setkey when in a channel or query buffer sets the key for it.")); return; } - network()->setBufferKey(parms[0], parms[1].toLocal8Bit()); - - if(network()->isChannelName(parms[0]) && network()->channels().contains(parms[0])) - network()->ircChannel(parms[0])->setEncrypted(true); - else if(network()->nicks().contains(parms[0])) - network()->ircUser(parms[0])->setEncrypted(true); - - QString message = tr("The key for %1 has been set.").arg(parms[0]); - if (bufferInfo.bufferName().isEmpty()) - emit displayMsg(Message::Info, BufferInfo::StatusBuffer, "", message); - else - emit displayMsg(Message::Info, bufferInfo.bufferName(), message); - #else - emit displayMsg(Message::Error, BufferInfo::StatusBuffer, "", tr("Error: Setting an encryption key requires Quassel to have been built " - "with support for the Qt Cryptographic Architecture (QCA) library. " - "Contact your distributor about a Quassel package with QCA " - "support, or rebuild Quassel with QCA present.")); - #endif + + QString target = parms.at(0); + QByteArray key = parms.at(1).toLocal8Bit(); + + network()->setCipherKey(target, key); + + if(network()->isChannelName(target) && network()->channels().contains(target)) + qobject_cast(network()->ircChannel(target))->setEncrypted(true); + else if(network()->nicks().contains(target)) + qobject_cast(network()->ircUser(target))->setEncrypted(true); + + emit displayMsg(Message::Info, bufferInfo.bufferName(), tr("The key for %1 has been set.").arg(target)); +#else + Q_UNUSED(msg) + emit displayMsg(Message::Error, bufferInfo.bufferName(), tr("Error: Setting an encryption key requires Quassel to have been built " + "with support for the Qt Cryptographic Architecture (QCA) library. " + "Contact your distributor about a Quassel package with QCA " + "support, or rebuild Quassel with QCA present.")); +#endif } void CoreUserInputHandler::handleTopic(const BufferInfo &bufferInfo, const QString &msg) { - if(bufferInfo.bufferName().isEmpty()) return; + if(bufferInfo.bufferName().isEmpty()) + return; + QList params; params << serverEncode(bufferInfo.bufferName()); + if(!msg.isEmpty()) { - #ifdef HAVE_QCA2 - const QByteArray bufferName = bufferInfo.bufferName().toAscii(); - QByteArray message = channelEncode(bufferInfo.bufferName(), msg); - params << encrypt(bufferName, message); - #else - params << channelEncode(bufferInfo.bufferName(), msg); - #endif +# ifdef HAVE_QCA2 + params << encrypt(bufferInfo.bufferName(), channelEncode(bufferInfo.bufferName(), msg)); +# else + params << channelEncode(bufferInfo.bufferName(), msg); +# endif } - + emit putCmd("TOPIC", params); } @@ -551,16 +548,10 @@ void CoreUserInputHandler::defaultHandler(QString cmd, const BufferInfo &bufferI emit putCmd(serverEncode(cmd.toUpper()), serverEncode(msg.split(" "))); } +// TODO: handle cutoff of encrypted messages void CoreUserInputHandler::putPrivmsg(const QByteArray &target, const QByteArray &message, bool encrypted) { QByteArray temp = message; - - #ifdef HAVE_QCA2 - if(!encrypted) { - temp = encrypt(target, temp); - encrypted = true; - } - #endif static const char *cmd = "PRIVMSG"; int overrun = lastParamOverrun(cmd, QList() << target << temp); @@ -612,24 +603,25 @@ int CoreUserInputHandler::lastParamOverrun(const QString &cmd, const QListbufferKey(target); + QByteArray key = network()->cipherKey(target); if(key.isEmpty()) - return message; - - IrcChannel *channel = network()->ircChannel(target); - IrcUser *user = network()->ircUser(target); - - if(channel && channel->cipher()->setKey(key)) - channel->cipher()->encrypt(message); - else if(user && user->cipher()->setKey(key)) - user->cipher()->encrypt(message); + return message_; + + QByteArray message = message_; + + CoreIrcChannel *channel = qobject_cast(network()->ircChannel(target)); + if(channel) { + if(channel->cipher()->setKey(key)) + channel->cipher()->encrypt(message); + } else { + CoreIrcUser *user = qobject_cast(network()->ircUser(target)); + if(user && user->cipher()->setKey(key)) + user->cipher()->encrypt(message); + } return message; } diff --git a/src/core/coreuserinputhandler.h b/src/core/coreuserinputhandler.h index 4cb2eb84..801024d6 100644 --- a/src/core/coreuserinputhandler.h +++ b/src/core/coreuserinputhandler.h @@ -77,13 +77,13 @@ protected: private: void banOrUnban(const BufferInfo &bufferInfo, const QString &text, bool ban); - void putPrivmsg(const QByteArray &target, const QByteArray &message, bool encrypted); + void putPrivmsg(const QByteArray &target, const QByteArray &message, bool isEncrypted); int lastParamOverrun(const QString &cmd, const QList ¶ms); - #ifdef HAVE_QCA2 - QByteArray encrypt(const QByteArray &target, QByteArray &message); - #endif - +#ifdef HAVE_QCA2 + QByteArray encrypt(const QString &target, const QByteArray &message) const; +#endif + struct Command { BufferInfo bufferInfo; QString command; diff --git a/src/core/ircserverhandler.cpp b/src/core/ircserverhandler.cpp index 655f68a8..b9a2f6c9 100644 --- a/src/core/ircserverhandler.cpp +++ b/src/core/ircserverhandler.cpp @@ -33,7 +33,7 @@ #include #ifdef HAVE_QCA2 -#include "cipher.h" +# include "cipher.h" #endif IrcServerHandler::IrcServerHandler(CoreNetwork *parent) @@ -498,9 +498,9 @@ void IrcServerHandler::handlePrivmsg(const QString &prefix, const QList we let the ctcpHandler do the work network()->ctcpHandler()->parse(Message::Plain, prefix, target, msg); @@ -557,12 +557,13 @@ void IrcServerHandler::handleTopic(const QString &prefix, const QList 1) { - topic = params[1]; - #ifdef HAVE_QCA2 - topic = decryptTopic(channel->name(), topic); - #endif + QByteArray rawTopic = params[1]; +#ifdef HAVE_QCA2 + rawTopic = decrypt(channel->name(), rawTopic, true); +#endif + topic = channelDecode(channel->name(), rawTopic); } - + channel->setTopic(topic); emit displayMsg(Message::Topic, BufferInfo::ChannelBuffer, channel->name(), tr("%1 has changed topic for %2 to: \"%3\"").arg(ircuser->nick()).arg(channel->name()).arg(topic)); @@ -999,12 +1000,12 @@ void IrcServerHandler::handle332(const QString &prefix, const QList return; QString channel = serverDecode(params[0]); - QString topic = channelDecode(channel, params[1]); - - #ifdef HAVE_QCA2 - topic = decryptTopic(channel, topic); - #endif - + QByteArray rawTopic = params[1]; +#ifdef HAVE_QCA2 + rawTopic = decrypt(channel, rawTopic, true); +#endif + QString topic = channelDecode(channel, rawTopic); + IrcChannel *chan = network()->ircChannel(channel); if(chan) chan->setTopic(topic); @@ -1247,71 +1248,26 @@ void IrcServerHandler::destroyNetsplits() { } #ifdef HAVE_QCA2 -QByteArray IrcServerHandler::decrypt(const QString &bufferName, QByteArray &message) { - if(bufferName.isEmpty()) - return message; - - if(message.isEmpty()) - return message; +QByteArray IrcServerHandler::decrypt(const QString &bufferName, const QByteArray &message_, bool isTopic) { + if(bufferName.isEmpty() || message_.isEmpty()) + return message_; - const QByteArray key = network()->bufferKey(bufferName); + const QByteArray key = network()->cipherKey(bufferName); if(key.isEmpty()) - return message; - - IrcChannel *channel = network()->ircChannel(bufferName); - IrcUser *user = network()->ircUser(bufferName); - - //only send encrypted text to decrypter - int index = message.indexOf(":",message.indexOf(":")+1); + return message_; - /* if(this->identifyMsgEnabled()) // Workaround braindead Freenode prefixing messages with + - ++index;*/ - - QByteArray backup = message.mid(0,index+1); + QByteArray message = message_; - if (channel && channel->cipher()->setKey(key)) - message = channel->cipher()->decrypt(message.mid(index+1)); - else if (user && user->cipher()->setKey(key)) - message = user->cipher()->decrypt(message.mid(index+1)); - - message.prepend(backup); + CoreIrcChannel *channel = qobject_cast(network()->ircChannel(bufferName)); + if(channel) { + if(channel->cipher()->setKey(key)) + message = isTopic? channel->cipher()->decryptTopic(message) : channel->cipher()->decrypt(message); + } else { + CoreIrcUser *user = qobject_cast(network()->ircUser(bufferName)); + if(user && user->cipher()->setKey(key)) + message = user->cipher()->decrypt(message); + } - message = channelDecode(bufferName, message).toAscii(); - return message; } - -QString IrcServerHandler::decryptTopic(const QString &bufferName, QString &topic) { - if(bufferName.isEmpty()) - return topic; - - if(topic.isEmpty()) - return topic; - - const QByteArray key = network()->bufferKey(bufferName); - if(key.isEmpty()) - return topic; - - IrcChannel *channel = network()->ircChannel(bufferName); - IrcUser *user = network()->ircUser(bufferName); - - //only send encrypted text to decrypter - int index = topic.indexOf(":",topic.indexOf(":")+1); - - QString backup = topic.mid(0,index+1); - - if (channel && channel->cipher()->setKey(key)) - topic = channel->cipher()->decryptTopic(topic.mid(index+1).toAscii()); - else if (user && user->cipher()->setKey(key)) - topic = user->cipher()->decryptTopic(topic.mid(index+1).toAscii()); - - topic.prepend(backup); - topic = channelDecode(bufferName, topic.toAscii()); - - return topic; -} #endif - -/***********************************************************************************/ - - diff --git a/src/core/ircserverhandler.h b/src/core/ircserverhandler.h index ceb8ef35..df5fcbec 100644 --- a/src/core/ircserverhandler.h +++ b/src/core/ircserverhandler.h @@ -129,12 +129,10 @@ private: // key: quit message // value: the corresponding netsplit object QHash _netsplits; - - #ifdef HAVE_QCA2 - QByteArray decrypt(const QString &bufferName, QByteArray &message); - QString decryptTopic(const QString &bufferName, QString &topic); - #endif -}; +#ifdef HAVE_QCA2 + QByteArray decrypt(const QString &target, const QByteArray &message, bool isTopic = false); +#endif +}; #endif diff --git a/src/qtui/CMakeLists.txt b/src/qtui/CMakeLists.txt index 9a0b1209..aa0496db 100644 --- a/src/qtui/CMakeLists.txt +++ b/src/qtui/CMakeLists.txt @@ -11,14 +11,6 @@ if(HAVE_WEBKIT) endif(HAVE_WEBKIT) include(${QT_USE_FILE}) -if (QCA2_FOUND) - include_directories(${QCA2_INCLUDE_DIR}) -endif (QCA2_FOUND) - -if(INDICATEQT_FOUND) - include_directories(${INDICATEQT_INCLUDE_DIRS}) -endif(INDICATEQT_FOUND) - set(SOURCES aboutdlg.cpp awaylogfilter.cpp @@ -176,6 +168,7 @@ if(INDICATEQT_FOUND) set(SOURCES ${SOURCES} indicatornotificationbackend.cpp) set(MOC_HDRS ${MOC_HDRS} indicatornotificationbackend.h) set(FORMS ${FORMS} indicatornotificationconfigwidget.ui) + include_directories(${INDICATEQT_INCLUDE_DIRS}) endif(INDICATEQT_FOUND) foreach(FORM ${FORMS})