Lines 26-32
Link Here
|
26 |
#include "yahootypes.h" |
26 |
#include "yahootypes.h" |
27 |
#include "client.h" |
27 |
#include "client.h" |
28 |
#include <qstring.h> |
28 |
#include <qstring.h> |
|
|
29 |
#include <qurl.h> |
29 |
#include <kdebug.h> |
30 |
#include <kdebug.h> |
|
|
31 |
#include <kio/global.h> |
32 |
#include <kio/job.h> |
33 |
#include <kio/jobclasses.h> |
34 |
#include <kurl.h> |
35 |
#include <kmdcodec.h> |
30 |
#include <stdlib.h> |
36 |
#include <stdlib.h> |
31 |
extern "C" |
37 |
extern "C" |
32 |
{ |
38 |
{ |
Lines 67-72
bool LoginTask::take(Transfer* transfer)
Link Here
|
67 |
|
73 |
|
68 |
YMSGTransfer *t = static_cast<YMSGTransfer *>(transfer); |
74 |
YMSGTransfer *t = static_cast<YMSGTransfer *>(transfer); |
69 |
|
75 |
|
|
|
76 |
if( t->service() == Yahoo::ServicePing ) |
77 |
return true; |
78 |
|
70 |
switch (mState) |
79 |
switch (mState) |
71 |
{ |
80 |
{ |
72 |
case (InitialState): |
81 |
case (InitialState): |
Lines 101-106
bool LoginTask::forMe(Transfer* transfer
Link Here
|
101 |
if (!t) |
110 |
if (!t) |
102 |
return false; |
111 |
return false; |
103 |
|
112 |
|
|
|
113 |
if( t->service() == Yahoo::ServicePing ) |
114 |
return true; |
115 |
|
104 |
switch (mState) |
116 |
switch (mState) |
105 |
{ |
117 |
{ |
106 |
case (InitialState): |
118 |
case (InitialState): |
Lines 133-139
void LoginTask::onGo()
Link Here
|
133 |
if (mState == InitialState) |
145 |
if (mState == InitialState) |
134 |
sendVerify(); |
146 |
sendVerify(); |
135 |
else |
147 |
else |
136 |
client()->notifyError( "Error in login procedure.", "take called while not in initial state", Client::Debug ); |
148 |
client()->notifyError( "Error in login procedure.", "onGo called while not in initial state", Client::Debug ); |
137 |
} |
149 |
} |
138 |
|
150 |
|
139 |
void LoginTask::reset() |
151 |
void LoginTask::reset() |
Lines 170-222
void LoginTask::sendAuthResp(YMSGTransfe
Link Here
|
170 |
|
182 |
|
171 |
QString sn = t->firstParam( 1 ); |
183 |
QString sn = t->firstParam( 1 ); |
172 |
QString seed = t->firstParam( 94 ); |
184 |
QString seed = t->firstParam( 94 ); |
|
|
185 |
m_challengeString = seed; |
173 |
QString version_s = t->firstParam( 13 ); |
186 |
QString version_s = t->firstParam( 13 ); |
174 |
uint sessionID = t->id(); |
187 |
m_sessionID = t->id(); |
175 |
int version = version_s.toInt(); |
188 |
int version = version_s.toInt(); |
176 |
|
189 |
|
177 |
switch (version) |
190 |
switch (version) |
178 |
{ |
191 |
{ |
179 |
case 0: |
192 |
case 0: |
180 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " Version pre 0x0b "<< version_s << endl; |
193 |
case 1: |
|
|
194 |
case 2: |
195 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " Using version 16 authorization" << endl; |
196 |
sendAuthSixteenStage1(sn, seed); |
181 |
break; |
197 |
break; |
182 |
default: |
198 |
default: |
183 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " Version 0x0b "<< version_s << endl; |
199 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " Unknown authentication method used !" << endl << " Attempting current authentication anyways" << endl; |
184 |
sendAuthResp_0x0b(sn, seed, sessionID); |
200 |
sendAuthSixteenStage1(sn, seed); |
185 |
break; |
201 |
break; |
186 |
} |
202 |
} |
187 |
mState = SentAuthResp; |
203 |
mState = SentAuthResp; |
188 |
|
204 |
|
189 |
emit haveSessionID( sessionID ); |
205 |
emit haveSessionID( m_sessionID ); |
190 |
} |
206 |
} |
191 |
|
207 |
|
192 |
void LoginTask::sendAuthResp_0x0b(const QString &sn, const QString &seed, uint sessionID) |
208 |
void LoginTask::sendAuthResp_0x0b(const QString &sn, const QString &seed, uint sessionID) |
193 |
{ |
209 |
{ |
|
|
210 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << endl; |
211 |
} |
212 |
|
213 |
void LoginTask::sendAuthSixteenStage1(const QString &sn, const QString &seed) |
214 |
{ |
215 |
const QString YahooTokenUrl = "https://login.yahoo.com/config/pwtoken_get?src=ymsgr&ts=&login=%1&passwd=%2&chal=%3"; |
194 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " with seed " << seed << endl; |
216 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " with seed " << seed << endl; |
195 |
char *resp_6 = (char *) malloc(100); |
217 |
m_stage1Data = QString::null; |
196 |
char *resp_96 = (char *) malloc(100); |
218 |
/* construct a URL from the seed and request tokens */ |
197 |
authresp_0x0b(seed.latin1(), sn.latin1(), (client()->password()).latin1(), resp_6, resp_96); |
219 |
QString urlEncodedPass = client()->password(); |
198 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << "resp_6: " << resp_6 << " resp_69: " << resp_96 << endl; |
220 |
QUrl::encode(urlEncodedPass); |
199 |
YMSGTransfer *t = new YMSGTransfer(Yahoo::ServiceAuthResp, m_stateOnConnect); |
221 |
QString fullUrl = YahooTokenUrl.arg(sn, urlEncodedPass, seed); |
200 |
t->setId( sessionID ); |
222 |
KURL tokenUrl(fullUrl); |
201 |
t->setParam( 0 , sn.local8Bit()); |
223 |
KIO::Job* job = KIO::get(tokenUrl, true, false); |
202 |
t->setParam( 6 , resp_6); |
224 |
connect(job, SIGNAL(data(KIO::Job*, const QByteArray&)), |
203 |
t->setParam( 96 , resp_96); |
225 |
this, SLOT(handleAuthSixteenStage1Data(KIO::Job*, const QByteArray&))); |
204 |
t->setParam( 59 , "B\\tfckeert1kk1nl&b=2" ); // ??? |
226 |
connect(job, SIGNAL(result(KIO::Job*)), |
205 |
t->setParam( 135 , "7,0,0,437" ); // Client version |
227 |
this, SLOT(handleAuthSixteenStage1Result(KIO::Job*))); |
206 |
t->setParam( 148 , -60 ); |
228 |
} |
207 |
t->setParam( 244 , 524223 ); |
229 |
|
208 |
t->setParam( 1 , sn.local8Bit()); |
230 |
void LoginTask::handleAuthSixteenStage1Data(KIO::Job* job, const QByteArray &data) |
|
|
231 |
{ |
232 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " with data " << data << endl; |
233 |
m_stage1Data.append(data); |
234 |
} |
235 |
|
236 |
void LoginTask::handleAuthSixteenStage1Result(KIO::Job* job) |
237 |
{ |
238 |
int responseNumber = -1; |
239 |
QString token; |
240 |
int error = job->error(); |
241 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " error: " << error << endl; |
242 |
if (error == 0) |
243 |
{ |
244 |
QStringList responses = QStringList::split("\r\n", m_stage1Data); |
245 |
responseNumber = responses[0].toInt(); |
246 |
if (responses.count() >= 3) |
247 |
{ |
248 |
token = responses[1]; |
249 |
token.remove("ymsgr="); |
250 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << "response is:" << responseNumber << endl; |
251 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << "token is:" << token << endl; |
252 |
} |
209 |
|
253 |
|
210 |
if( !m_verificationWord.isEmpty() ) |
254 |
if (responseNumber != 0) |
|
|
255 |
{ |
256 |
switch(responseNumber) |
211 |
{ |
257 |
{ |
212 |
t->setParam( 227 , m_verificationWord.local8Bit() ); |
258 |
case -1: |
213 |
m_verificationWord = QString::null; |
259 |
/* error in the received stream */ |
|
|
260 |
emit loginResponse(Yahoo::LoginSock, QString()); |
261 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << "unknown error logging in" << endl; |
262 |
break; |
263 |
case 1212: |
264 |
/* password incorrect */ |
265 |
emit loginResponse(Yahoo::LoginPasswd, QString()); |
266 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << "password incorrect" << endl; |
267 |
break; |
268 |
case 1213: |
269 |
/* security lock */ |
270 |
emit loginResponse(Yahoo::LoginLock, QString()); |
271 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << "user locked" << endl; |
272 |
break; |
273 |
case 1235: |
274 |
/* username does not exist */ |
275 |
emit loginResponse(Yahoo::LoginUname, QString()); |
276 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << "user does not exist" << endl; |
277 |
break; |
278 |
case 1214: |
279 |
case 1236: |
280 |
emit loginResponse(Yahoo::LoginVerify, QString()); |
281 |
break; |
282 |
case 100: /* username or password missing */ |
283 |
/*FIXME handle this */ |
284 |
break; |
285 |
default: |
286 |
/* FIXME unknown error. handle it! */ |
287 |
break; |
288 |
} |
289 |
} |
290 |
else |
291 |
{ |
292 |
/* start stage 2 here */ |
293 |
sendAuthSixteenStage2(token); |
214 |
} |
294 |
} |
|
|
295 |
} |
296 |
} |
215 |
|
297 |
|
216 |
free(resp_6); |
298 |
void LoginTask::sendAuthSixteenStage2(const QString &token) |
217 |
free(resp_96); |
299 |
{ |
218 |
send(t); |
300 |
const QString YahooLoginUrl = "https://login.yahoo.com/config/pwtoken_login?src=ymsgr&ts=&token=%1"; |
|
|
301 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " with token " << token << endl; |
302 |
m_stage2Data = QString::null; |
303 |
QString fullUrl = YahooLoginUrl.arg(token); |
304 |
KURL loginUrl(fullUrl); |
305 |
KIO::Job* job = KIO::get(loginUrl, true, false); |
306 |
connect(job, SIGNAL(data(KIO::Job*, const QByteArray&)), |
307 |
this, SLOT(handleAuthSixteenStage2Data(KIO::Job*, const QByteArray&))); |
308 |
connect(job, SIGNAL(result(KIO::Job*)), |
309 |
this, SLOT(handleAuthSixteenStage2Result(KIO::Job*))); |
310 |
} |
219 |
|
311 |
|
|
|
312 |
void LoginTask::handleAuthSixteenStage2Data(KIO::Job* job, const QByteArray &data) |
313 |
{ |
314 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " with data " << data << endl; |
315 |
m_stage2Data.append(data); |
316 |
} |
317 |
|
318 |
void LoginTask::handleAuthSixteenStage2Result(KIO::Job* job) |
319 |
{ |
320 |
QString crumb; |
321 |
int responseNumber = -1; |
322 |
int error = job->error(); |
323 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << "error:" << error << endl; |
324 |
if (error == 0) |
325 |
{ |
326 |
QStringList responses = QStringList::split("\r\n", m_stage2Data); |
327 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << responses << endl; |
328 |
responseNumber = responses[0].toInt(); |
329 |
if (responseNumber == 0) |
330 |
{ |
331 |
crumb = responses[1]; |
332 |
crumb.remove("crumb="); |
333 |
m_yCookie = responses[2].remove(0,2); /* remove Y= */ |
334 |
m_tCookie = responses[3].remove(0,2); /* remove T= */ |
335 |
} |
336 |
|
337 |
if (responseNumber != 0) |
338 |
{ |
339 |
switch(responseNumber) |
340 |
{ |
341 |
case -1: |
342 |
emit loginResponse(Yahoo::LoginSock, QString()); |
343 |
break; |
344 |
case 100: |
345 |
emit loginResponse(Yahoo::LoginSock, QString()); |
346 |
break; |
347 |
default: /* try to login anyways */ |
348 |
break; |
349 |
} |
350 |
} |
351 |
else |
352 |
{ |
353 |
QString cryptString = crumb; |
354 |
cryptString.append(m_challengeString); |
355 |
sendAuthSixteenStage3(cryptString); |
356 |
} |
357 |
} |
358 |
} |
359 |
|
360 |
void LoginTask::sendAuthSixteenStage3(const QString &cryptString) |
361 |
{ |
362 |
kdDebug(YAHOO_RAW_DEBUG) << k_funcinfo << " with crypt string " << cryptString << endl; |
363 |
|
364 |
KMD5 md5(cryptString.ascii()); |
365 |
QCString cryptStringHash = md5.base64Digest(); |
366 |
cryptStringHash = cryptStringHash.replace('+', '.'); |
367 |
cryptStringHash = cryptStringHash.replace('/', '_'); |
368 |
cryptStringHash = cryptStringHash.replace('=', '-'); |
369 |
|
370 |
YMSGTransfer *t = new YMSGTransfer(Yahoo::ServiceAuthResp, m_stateOnConnect); |
371 |
t->setId( m_sessionID ); |
372 |
t->setParam( 1, client()->userId().local8Bit()); |
373 |
t->setParam( 0 , client()->userId().local8Bit()); |
374 |
t->setParam( 277, m_yCookie.local8Bit() ); |
375 |
t->setParam( 278, m_tCookie.local8Bit() ); |
376 |
t->setParam( 307, cryptStringHash ); |
377 |
t->setParam( 244, 2097087 ); |
378 |
t->setParam( 2 , client()->userId().local8Bit()); |
379 |
t->setParam( 2, 1 ); // Both parameter 2s wind up in the packet |
380 |
t->setParam( 135, YMSG_PROGRAM_VERSION_STRING ); |
381 |
|
382 |
send(t); |
220 |
} |
383 |
} |
221 |
|
384 |
|
222 |
void LoginTask::sendAuthResp_pre_0x0b(const QString &/*sn*/, const QString &/*seed*/) |
385 |
void LoginTask::sendAuthResp_pre_0x0b(const QString &/*sn*/, const QString &/*seed*/) |