1 /***************************************************************************
2 * Copyright (C) 2005-2010 by the Quassel Project *
3 * devel@quassel-irc.org *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) version 3. *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
21 #include "coresessioneventprocessor.h"
23 #include "corenetwork.h"
24 #include "coresession.h"
27 CoreSessionEventProcessor::CoreSessionEventProcessor(CoreSession *session)
34 bool CoreSessionEventProcessor::checkParamCount(IrcEvent *e, int minParams) {
35 if(e->params().count() < minParams) {
36 if(e->type() == EventManager::IrcEventNumeric) {
37 qWarning() << "Command " << static_cast<IrcEventNumeric *>(e)->number() << " requires " << minParams << "params, got: " << e->params();
39 QString name = coreSession()->eventManager()->enumName(e->type());
40 qWarning() << qPrintable(name) << "requires" << minParams << "params, got:" << e->params();
48 void CoreSessionEventProcessor::processIrcEventNumeric(IrcEventNumeric *e) {
52 case 903: case 904: case 905: case 906: case 907:
53 qobject_cast<CoreNetwork *>(e->network())->putRawLine("CAP END");
61 void CoreSessionEventProcessor::processIrcEventAuthenticate(IrcEvent *e) {
62 if(!checkParamCount(e, 1))
65 if(e->params().at(0) != "+") {
66 qWarning() << "Invalid AUTHENTICATE" << e;
70 CoreNetwork *net = coreNetwork(e);
72 QString construct = net->saslAccount();
73 construct.append(QChar(QChar::Null));
74 construct.append(net->saslAccount());
75 construct.append(QChar(QChar::Null));
76 construct.append(net->saslPassword());
77 QByteArray saslData = QByteArray(construct.toAscii().toBase64());
78 saslData.prepend("AUTHENTICATE ");
79 net->putRawLine(saslData);
82 void CoreSessionEventProcessor::processIrcEventCap(IrcEvent *e) {
83 // for SASL, there will only be a single param of 'sasl', however you can check here for
84 // additional CAP messages (ls, multi-prefix, et cetera).
86 if(e->params().count() == 3) {
87 if(e->params().at(2) == "sasl") {
89 coreNetwork(e)->putRawLine(coreNetwork(e)->serverEncode("AUTHENTICATE PLAIN")); // Only working with PLAIN atm, blowfish later
94 void CoreSessionEventProcessor::processIrcEventInvite(IrcEvent *e) {
95 if(checkParamCount(e, 2)) {
96 e->network()->updateNickFromMask(e->prefix());
100 void CoreSessionEventProcessor::processIrcEventKick(IrcEvent *e) {
101 if(checkParamCount(e, 2)) {
102 e->network()->updateNickFromMask(e->prefix());
103 IrcUser *victim = e->network()->ircUser(e->params().at(1));
105 victim->partChannel(e->params().at(0));
106 //if(e->network()->isMe(victim)) e->network()->setKickedFromChannel(channel);
111 void CoreSessionEventProcessor::processIrcEventNick(IrcEvent *e) {
112 if(checkParamCount(e, 1)) {
113 IrcUser *ircuser = e->network()->updateNickFromMask(e->prefix());
115 qWarning() << Q_FUNC_INFO << "Unknown IrcUser!";
118 QString newnick = e->params().at(0);
119 QString oldnick = ircuser->nick();
121 // the order is cruicial
122 // otherwise the client would rename the buffer, see that the assigned ircuser doesn't match anymore
123 // and remove the ircuser from the querybuffer leading to a wrong on/offline state
124 ircuser->setNick(newnick);
125 coreSession()->renameBuffer(e->networkId(), newnick, oldnick);
129 void CoreSessionEventProcessor::processIrcEventPart(IrcEvent *e) {
130 if(checkParamCount(e, 1)) {
131 IrcUser *ircuser = e->network()->updateNickFromMask(e->prefix());
133 qWarning() << Q_FUNC_INFO<< "Unknown IrcUser!";
136 QString channel = e->params().at(0);
137 ircuser->partChannel(channel);
138 if(e->network()->isMe(ircuser))
139 qobject_cast<CoreNetwork *>(e->network())->setChannelParted(channel);
143 void CoreSessionEventProcessor::processIrcEventPong(IrcEvent *e) {
144 // the server is supposed to send back what we passed as param. and we send a timestamp
145 // but using quote and whatnought one can send arbitrary pings, so we have to do some sanity checks
146 if(checkParamCount(e, 2)) {
147 QString timestamp = e->params().at(1);
148 QTime sendTime = QTime::fromString(timestamp, "hh:mm:ss.zzz");
149 if(sendTime.isValid())
150 e->network()->setLatency(sendTime.msecsTo(QTime::currentTime()) / 2);
154 void CoreSessionEventProcessor::processIrcEventTopic(IrcEvent *e) {
155 if(checkParamCount(e, 2)) {
156 e->network()->updateNickFromMask(e->prefix());
157 IrcChannel *channel = e->network()->ircChannel(e->params().at(0));
159 channel->setTopic(e->params().at(1));
164 void CoreSessionEventProcessor::processIrcEvent001(IrcEvent *e) {
165 if(!checkParamCount(e, 1))
168 QString myhostmask = e->params().at(0).section(' ', -1, -1);
169 e->network()->setCurrentServer(e->prefix());
170 e->network()->setMyNick(nickFromMask(myhostmask));
173 /* RPL_UMODEIS - "<user_modes> [<user_mode_params>]" */
174 void CoreSessionEventProcessor::processIrcEvent221(IrcEvent *) {
175 // TODO: save information in network object
178 /* RPL_STATSCONN - "Highest connection cout: 8000 (7999 clients)" */
179 void CoreSessionEventProcessor::processIrcEvent250(IrcEvent *) {
180 // TODO: save information in network object
183 /* RPL_LOCALUSERS - "Current local user: 5024 Max: 7999 */
184 void CoreSessionEventProcessor::processIrcEvent265(IrcEvent *) {
185 // TODO: save information in network object
188 /* RPL_GLOBALUSERS - "Current global users: 46093 Max: 47650" */
189 void CoreSessionEventProcessor::processIrcEvent266(IrcEvent *) {
190 // TODO: save information in network object
195 Replies 311 - 313, 317 - 319 are all replies generated in response to a WHOIS message.
197 "<nick> :<away message>"
199 Replies 352 and 315 paired are used to answer a WHO message.
202 Replies 314 and 369 are responses to a WHOWAS message.
206 /* RPL_AWAY - "<nick> :<away message>" */
207 void CoreSessionEventProcessor::processIrcEvent301(IrcEvent *e) {
208 if(!checkParamCount(e, 2))
211 IrcUser *ircuser = e->network()->ircUser(e->params().at(0));
213 ircuser->setAway(true);
214 ircuser->setAwayMessage(e->params().at(1));
215 //ircuser->setLastAwayMessage(now);
219 /* RPL_UNAWAY - ":You are no longer marked as being away" */
220 void CoreSessionEventProcessor::processIrcEvent305(IrcEvent *e) {
221 IrcUser *me = e->network()->me();
225 if(e->network()->autoAwayActive())
226 e->network()->setAutoAwayActive(false);
229 /* RPL_NOWAWAY - ":You have been marked as being away" */
230 void CoreSessionEventProcessor::processIrcEvent306(IrcEvent *e) {
231 IrcUser *me = e->network()->me();
237 void CoreSessionEventProcessor::processIrcEvent(IrcEvent *e) {
238 if(!checkParamCount(e, 1))