Main Page | Class Hierarchy | Class List | Directories | File List | Class Members | File Members

evaimreceive.cpp

Go to the documentation of this file.
00001 /***************************************************************************
00002  *   Copyright (C) 2004 by yunfan                                          *
00003  *   yunfan_zg@163.com                                                     *
00004  *                                                                         *
00005  *   This program is free software; you can redistribute it and/or modify  *
00006  *   it under the terms of the GNU General Public License as published by  *
00007  *   the Free Software Foundation; either version 2 of the License, or     *
00008  *   (at your option) any later version.                                   *
00009  *                                                                         *
00010  *   This program is distributed in the hope that it will be useful,       *
00011  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
00012  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
00013  *   GNU General Public License for more details.                          *
00014  *                                                                         *
00015  *   You should have received a copy of the GNU General Public License     *
00016  *   along with this program; if not, write to the                         *
00017  *   Free Software Foundation, Inc.,                                       *
00018  *   59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.             *
00019  ***************************************************************************/
00020 #include "evaimreceive.h"
00021 #include "evadefines.h"
00022 #include "evautil.h"
00023 #include <string.h>
00024 #ifdef _WIN32
00025 #include <winsock.h>
00026 #else
00027 #include <arpa/inet.h>
00028 #endif
00029 
00030 
00031 ReceiveIMPacket::ReceiveIMPacket(unsigned char *buf, const int len)
00032         : InPacket(buf, len),
00033         bodyOffset(0)
00034 {
00035 }   
00036 
00037 ReceiveIMPacket::ReceiveIMPacket(const ReceiveIMPacket &rhs)
00038         : InPacket(rhs)
00039 {
00040         memcpy(replyKey, rhs.getReplyKey(), REPLY_KEY_LENGTH);
00041         sender = rhs.getSender();
00042         receiver = rhs.getReceiver();
00043         sequence = rhs.getSequence();
00044         senderIP = rhs.getSenderIP();
00045         senderPort = rhs.getSenderPort();
00046         type = rhs.getIMType();
00047         
00048         bodyOffset = rhs.getLength() - rhs.getBodyLength();
00049 }
00050 
00051 std::string ReceiveIMPacket::convertToShow(const std::string &src, const unsigned char type)
00052 {
00053         std::string converted = "";
00054         unsigned int start = 0;
00055         char *uuid = NULL; // uuid format: {12345678-1234-1234-1234-123456789ABC}
00056         if(type == QQ_IM_IMAGE_REPLY){
00057                 uuid = new char[39]; // 38 + 1
00058                 memcpy(uuid, src.c_str(), 38);
00059                 uuid[38] = 0x00; // just make it as a string
00060                 start+=38;
00061                 start+=2; // 2 unknown bytes: 0x13 0x4c (always)
00062         }
00063         for(uint i=start; i<src.length(); i++){
00064                 if(src[i]==0x14){
00065                         converted+=EvaUtil::smileyToText(src[++i]);
00066                         converted+=' ';
00067                 }else if(src[i]==0x15){
00068                                 int t=0;
00069                                 char *tmp = new char[src.length()+1];
00070                                 strcpy(tmp, src.c_str());
00071                                 converted+=EvaUtil::customSmileyToText(tmp + i, &t, uuid);
00072                                 i+=(t-1); // get rid of 0x15
00073                                 delete tmp;
00074                         } else
00075                                 converted+=src[i];
00076         }
00077         if(uuid) delete []uuid;
00078         return converted;
00079 }
00080 
00081 ReceiveIMPacket &ReceiveIMPacket::operator=(const ReceiveIMPacket &rhs)
00082 {
00083         *((InPacket *)this) = (InPacket)rhs;
00084         memcpy(replyKey, rhs.getReplyKey(), REPLY_KEY_LENGTH);
00085         sender = rhs.getSender();
00086         receiver = rhs.getReceiver();
00087         sequence = rhs.getSequence();
00088         senderIP = rhs.getSenderIP();
00089         senderPort = rhs.getSenderPort();
00090         type = rhs.getIMType();
00091         
00092         bodyOffset = rhs.getLength() - rhs.getBodyLength();
00093         return *this;
00094 }
00095 
00096 void ReceiveIMPacket::parseBody()
00097 {
00098         if(bodyLength < 16){
00099                 printf("message too short, just chuck it\n");  
00100                 bodyOffset = -1; // means error occurred
00101                 return;
00102         }
00103         memcpy(replyKey, decryptedBuf, REPLY_KEY_LENGTH);
00104         bodyOffset = readHeader(decryptedBuf);
00105 }
00106 
00107 int ReceiveIMPacket::readHeader(const unsigned char *buf)
00108 {
00109         int pos=0;      
00110         int tmp4;
00111         memcpy(&tmp4, buf, 4);
00112         sender = ntohl(tmp4);
00113         pos+=4;
00114         
00115         memcpy(&tmp4, buf+pos, 4);
00116         receiver = ntohl(tmp4);
00117         pos+=4;
00118                 
00119         memcpy(&tmp4, buf+pos, 4);
00120         intSequence = ntohl(tmp4);
00121         pos+=4;
00122 
00123         memcpy(&tmp4, buf+pos, 4);
00124         senderIP = ntohl(tmp4);
00125         pos+=4;
00126                 
00127         short tmp2;
00128         memcpy(&tmp2, buf+pos, 2);
00129         senderPort = ntohs(tmp2);
00130         pos+=2;
00131                 
00132         memcpy(&tmp2, buf+pos, 2);
00133         type = ntohs(tmp2);
00134         pos+=2; 
00135         return pos;
00136 }
00137 
00138 /* =========================================================== */
00139 
00140 NormalIMBase::NormalIMBase(const unsigned char *buf, const int len)
00141 {
00142         bodyBuf = (unsigned char *)malloc(len * sizeof(unsigned char));
00143         bodyLength = len;
00144         memcpy(bodyBuf, buf, len);
00145 }
00146 
00147 NormalIMBase::NormalIMBase(const NormalIMBase &rhs)
00148 {
00149         *this = rhs;
00150 }
00151 
00152 NormalIMBase::~NormalIMBase()
00153 {
00154         free(bodyBuf);
00155 }
00156 
00157 void NormalIMBase::setNormalIMBase(const NormalIMBase *base)
00158 {
00159         *this = *base;  
00160 }
00161 
00162 void NormalIMBase::parseData()
00163 {
00164         int len = readHeader(bodyBuf);
00165         parseContents(bodyBuf + len, bodyLength - len);
00166 }
00167 
00168 NormalIMBase &NormalIMBase::operator=(const NormalIMBase &rhs)
00169 {
00170         bodyLength = rhs.getBodyLength();
00171         bodyBuf = (unsigned char *)malloc(bodyLength * sizeof(unsigned char));
00172         memcpy(bodyBuf, rhs.getBodyData(), bodyLength);
00173         
00174         senderVersion = rhs.getSenderVersion();
00175         sender = rhs.getSender();
00176         receiver = rhs.getReceiver();
00177         memcpy(fileSessionKey, rhs.getBuddyFileSessionKey(), 16);
00178         type = rhs.getNormalIMType();
00179         sequence = rhs.getSequence();
00180         sendTime = rhs.getSendTime();
00181         unknown1 = rhs.getUnknown1();
00182         senderFace = rhs.getSenderFace();
00183         return *this;
00184 }
00185 
00186 void NormalIMBase::parseContents(const unsigned char *, const int )
00187 {
00188         //fprintf(stderr, "In NormalIMBase: buf[0]=0x%2x, len=%d\n",buf[0], len); 
00189 }
00190 
00191 int NormalIMBase::readHeader(const unsigned char *buf)
00192 {
00193         int pos=0;
00194         short tmp2;
00195         memcpy(&tmp2, buf, 2);  
00196         senderVersion = ntohs(tmp2);
00197         pos+=2;
00198         
00199         int tmp4;
00200         memcpy(&tmp4, buf+pos, 4);
00201         sender = ntohl(tmp4);
00202         pos+=4;
00203         memcpy(&tmp4, buf+pos, 4);
00204         receiver = ntohl(tmp4);
00205         pos+=4;
00206         
00207         memcpy(fileSessionKey, buf+pos, 16);
00208         pos+=16;
00209         
00210         memcpy(&tmp2, buf+pos, 2);
00211         type = ntohs(tmp2);
00212         pos+=2;
00213         
00214         memcpy(&tmp2, buf+pos, 2);
00215         sequence = ntohs(tmp2);
00216         pos+=2;
00217         
00218         memcpy(&tmp4, buf+pos, 4);
00219         //sendTime = ntohl(tmpTime) * 1000L;
00220         sendTime = ntohl(tmp4);
00221         pos+=4;
00222         
00223         memcpy(&tmp2, buf+pos, 2);
00224         senderFace = ntohs(tmp2);       
00225         pos+=2;
00226         
00227         return pos;
00228 }
00229 
00230 /* =========================================================== */
00231 
00232 ReceivedNormalIM::ReceivedNormalIM(const unsigned char *buf, const int len)
00233         : NormalIMBase(buf, len)
00234 {
00235 }
00236 
00237 ReceivedNormalIM::ReceivedNormalIM(const ReceivedNormalIM &rhs)
00238         : NormalIMBase(rhs)
00239 {
00240         memcpy(unknown2, rhs.getUnknown2(), 3);
00241         memcpy(unknown3, rhs.getUnknown3(), 4);
00242         replyType = rhs.getReplyType();
00243         message = rhs.getMessage();
00244         mHasFontAttribute = rhs.hasFontAttribute();
00245         encoding = rhs.getEncoding();
00246         red = rhs.getRed();
00247         green = rhs.getGreen();
00248         blue = rhs.getBlue();
00249         fontSize = rhs.getFontSize();
00250         fontName = rhs.getFontName();
00251         bold = rhs.isBold();
00252         italic = rhs.isItalic();
00253         underline = rhs.isUnderline();
00254 }
00255 
00256 const bool ReceivedNormalIM::isNormalReply() const
00257 {
00258         return replyType == QQ_IM_NORMAL_REPLY;
00259 }
00260 
00261 ReceivedNormalIM &ReceivedNormalIM::operator=(const ReceivedNormalIM &rhs)
00262 {
00263         *((NormalIMBase *)this) = (NormalIMBase)rhs;
00264         memcpy(unknown2, rhs.getUnknown2(), 3);
00265         memcpy(unknown3, rhs.getUnknown3(), 4);
00266         replyType = rhs.getReplyType();
00267         message = rhs.getMessage();
00268         mHasFontAttribute = rhs.hasFontAttribute();
00269         encoding = rhs.getEncoding();
00270         red = rhs.getRed();
00271         green = rhs.getGreen();
00272         blue = rhs.getBlue();
00273         fontSize = rhs.getFontSize();
00274         fontName = rhs.getFontName();
00275         bold = rhs.isBold();
00276         italic = rhs.isItalic();
00277         underline = rhs.isUnderline();
00278         return *this;
00279 }
00280 
00281 void ReceivedNormalIM::parseContents(const unsigned char *buf, const int len)
00282 {
00283         int pos=0;
00284         memcpy(unknown2, buf, 3);
00285         pos+=3;
00286                 
00287         mHasFontAttribute = (buf[pos++] != 0);
00288         memcpy(unknown3, buf+pos, 4);
00289         pos+=4;
00290 
00291         replyType = buf[pos++];
00292                         
00293         int i=0;
00294         while( (buf[pos++]) != 0x00){
00295                 i++;
00296         }
00297 #ifdef WIN32
00298         char* str; str=(char*)_alloca(i+2);
00299 #else
00300         char str[i+2];
00301 #endif
00302         memcpy(str, buf+(pos-i-1), i+1);
00303         str[i+1]= 0x00;
00304         message = ReceiveIMPacket::convertToShow(str, replyType);
00305         
00306         if(mHasFontAttribute) {
00307                 if(pos<len) {
00308 #ifdef WIN32
00309                         char* fa; fa=(char*)_alloca(len-pos);
00310 #else
00311                         char fa[len-pos];
00312 #endif
00313                         memcpy(fa, buf+pos, len-pos);
00314                         fontSize = fa[0] & 0x1F;
00315                         bold = ((fa[0] & 0x20) != 0);
00316                         italic = ((fa[0] & 0x40) != 0);
00317                         underline = ((fa[0] & 0x80) != 0);
00318                         red = fa[1] & 0xFF;
00319                         green = fa[2] & 0xFF;
00320                         blue = fa[3] & 0xFF;
00321                         short tmp2;
00322                         memcpy(&tmp2, fa+5, 2);
00323                         encoding = ntohs(tmp2);
00324 #ifdef WIN32
00325                         char* fn; fn=(char*)_alloca(len-pos-7);
00326 #else
00327                         char fn[len-pos-7];
00328 #endif
00329                         memcpy(fn, fa+7, len-pos-7-1);
00330                         fn[len-pos-7-1]=0x00;
00331                         //fn[len-pos-7]=0x00;
00332                         fontName.assign(fn);
00333                 } else
00334                         mHasFontAttribute = false;
00335         }
00336 }
00337 
00338 /* =========================================================== */
00339 
00340 ReceivedSystemIM::ReceivedSystemIM(const unsigned char *buf, const int len)
00341 {
00342         parseData(buf, len);
00343 }
00344 
00345 ReceivedSystemIM::ReceivedSystemIM( const ReceivedSystemIM &rhs)
00346 {
00347         *this = rhs;
00348 }
00349 
00350 ReceivedSystemIM &ReceivedSystemIM::operator=(const ReceivedSystemIM &rhs)
00351 {
00352         systemIMType = rhs.getSystemIMType();
00353         message = rhs.getMessage();
00354         return *this;
00355 }
00356 
00357 void ReceivedSystemIM::parseData(const unsigned char *buf, const int len)
00358 {
00359         int pos = 0;
00360         systemIMType = buf[pos++];
00361         
00362         char msgLen = buf[pos++];
00363 #ifdef WIN32
00364         char* msg; msg=(char*)_alloca(msgLen+1);
00365 #else
00366         char msg[msgLen+1];
00367 #endif
00368         memcpy(msg, buf+pos, msgLen);
00369         msg[0xff & msgLen]=0x00;
00370         message.assign(msg);
00371 }
00372 
00373 /* =========================================================== */
00374 
00375 ReceiveIMReplyPacket::ReceiveIMReplyPacket(const char *key) 
00376         : OutPacket(QQ_CMD_RECV_IM, false)
00377 {
00378         memcpy(replyKey, key, 16);
00379 }
00380 
00381 ReceiveIMReplyPacket::ReceiveIMReplyPacket(const ReceiveIMReplyPacket &rhs)
00382         : OutPacket(rhs)
00383 {
00384         memcpy(replyKey, rhs.getReplyKey(), REPLY_KEY_LENGTH);
00385 }
00386 
00387 ReceiveIMReplyPacket &ReceiveIMReplyPacket::operator=(const ReceiveIMReplyPacket &rhs)
00388 {
00389         *((OutPacket *)this) = (OutPacket)rhs;
00390         memcpy(replyKey, rhs.getReplyKey(), REPLY_KEY_LENGTH);
00391         return *this;
00392 }
00393 
00394 int ReceiveIMReplyPacket::putBody(unsigned char *buf) {
00395 
00396         memcpy(buf, replyKey, REPLY_KEY_LENGTH);
00397         return REPLY_KEY_LENGTH;
00398 }
00399 
00400 /* =========================================================== */
00401 
00402 ReceivedQunIM::ReceivedQunIM(const short src,  const unsigned char * buf, const int len )
00403         : source(src)
00404 {
00405         parseData(buf, len);
00406 }
00407 
00408 ReceivedQunIM::ReceivedQunIM( const ReceivedQunIM & rhs )
00409 {
00410         (*this) = rhs;
00411 }
00412 
00413 ReceivedQunIM & ReceivedQunIM::operator =( const ReceivedQunIM & rhs )
00414 {
00415         source = rhs.getSource(); // this is to mention,  permenent, temporary qun 
00416         externalID = rhs.getExtID();
00417         qunID = rhs.getQunID();
00418         type = rhs.getType();
00419         sender = rhs.getSenderQQ();
00420         unknown1 = rhs.getUnknown1();
00421         sequence = rhs.getSequence();
00422         sentTime = rhs.getSentTime();
00423         versionID = rhs.getVersionID();
00424         message = rhs.getMessage();
00425         
00426         mHasFontAttribute = rhs.hasFontAttribute();
00427         encoding = rhs.getEncoding();
00428         red = rhs.getRed();
00429         green = rhs.getGreen();
00430         blue = rhs.getBlue();
00431         fontSize = rhs.getFontSize();
00432         fontName = rhs.getFontName();
00433         bold = rhs.isBold();
00434         italic = rhs.isItalic();
00435         underline = rhs.isUnderline();
00436         return *this;
00437 }
00438 
00439 void ReceivedQunIM::parseData( const unsigned char * buf, const int len )
00440 {
00441         int pos=0;
00442         
00443         int tmp4;
00444         memcpy(&tmp4, buf, 4);
00445         externalID = ntohl(tmp4); // the external Qun ID
00446         pos+=4;
00447         
00448         type = buf[pos++];  // type of the Qun
00449 
00450         if(source == QQ_RECV_IM_TEMP_QUN_IM){ // internal ID of temporary Qun
00451                 memcpy(&tmp4, buf+pos, 4);
00452                 qunID = ntohl(tmp4);
00453                 pos+=4;
00454         }
00455         
00456         memcpy(&tmp4, buf+pos, 4);
00457         sender = ntohl(tmp4);       // the sender
00458         pos+=4;
00459         
00460         short tmp2;
00461         memcpy(&unknown1, buf+pos, 2);
00462         pos+=2;
00463 
00464         memcpy(&tmp2, buf+pos, 2);
00465         sequence = ntohs(tmp2);     // message sequence number
00466         pos+=2;
00467         
00468         memcpy(&tmp4, buf+pos, 4);
00469         sentTime = ntohl(tmp4);    // the sending time
00470         pos+=4;
00471         
00472         memcpy(&tmp4, buf+pos, 4);
00473         versionID = ntohl(tmp4);   // version ID is to tell if something like memebers, or rules of this Qun were changed
00474         pos+=4;
00475 
00476         pos+=2; // ignore 2 bytes;  Luma QQ says it's the length for the following data.
00477 
00478         // 10 unknown bytes
00479         if(source != QQ_RECV_IM_UNKNOWN_QUN_IM) {
00480                 pos+=10;
00481         }
00482         
00483         int i=0;
00484         while( (buf[pos++]) != 0x00){
00485                 i++;
00486         }
00487 #ifdef WIN32
00488         char* str; str=(char*)_alloca(i+2);
00489 #else
00490         char str[i+2];
00491 #endif
00492         memcpy(str, buf+(pos-i-1), i+1);
00493         str[i+1]= 0x00;
00494         message = ReceiveIMPacket::convertToShow(str, QQ_IM_NORMAL_REPLY);
00495         
00496         mHasFontAttribute = (len > pos);
00497         if(mHasFontAttribute) {
00498 #ifdef WIN32
00499                 char* fa; fa=(char*)_alloca(len-pos);
00500 #else
00501                 char fa[len-pos];
00502 #endif
00503                 memcpy(fa, buf+pos, len-pos);
00504                 fontSize = fa[0] & 0x1F;
00505                 bold = ((fa[0] & 0x20) != 0);
00506                 italic = ((fa[0] & 0x40) != 0);
00507                 underline = ((fa[0] & 0x80) != 0);
00508                 red = fa[1] & 0xFF;
00509                 green = fa[2] & 0xFF;
00510                 blue = fa[3] & 0xFF;
00511                 short tmp2;
00512                 memcpy(&tmp2, fa+5, 2);
00513                 encoding = ntohs(tmp2);
00514 #ifdef WIN32
00515                 char* fn; fn=(char*)_alloca(len-pos-7);
00516 #else
00517                 char fn[len-pos-7];
00518 #endif
00519                 memcpy(fn, fa+7, len-pos-7-1);
00520                 fn[len-pos-7-1]=0x00;
00521                 //fn[len-pos-7]=0x00;
00522                 fontName.assign(fn);
00523         } 
00524 }
00525 
00526 
00527 
00528 /* =========================================================== */
00529 
00530 ReceivedQunIMJoinRequest::ReceivedQunIMJoinRequest( const unsigned char * buf, const int len)
00531 {
00532         int pos=0;
00533         int tmp4;
00534         memcpy(&tmp4, buf, 4);
00535         externalID = ntohl(tmp4);
00536         pos+=4;
00537         
00538         type = buf[pos++];
00539 
00540         memcpy(&tmp4, buf + pos, 4);
00541         sender = ntohl(tmp4);
00542         pos+=4;
00543         
00544         if(len == pos) {
00545                 message = "";
00546                 return;
00547         }
00548         unsigned length = (unsigned int)buf[pos++];
00549         char *msg = (char *)malloc((length+1) * sizeof(char));
00550         memcpy(msg, buf + pos, length);
00551         msg[length] = 0x00;
00552         message.assign(msg);
00553         free(msg);
00554 }
00555 
00556 ReceivedQunIMJoinRequest::ReceivedQunIMJoinRequest( const ReceivedQunIMJoinRequest & rhs )
00557 {
00558         *this = rhs;
00559 }
00560 
00561 ReceivedQunIMJoinRequest & ReceivedQunIMJoinRequest::operator =( const ReceivedQunIMJoinRequest & rhs )
00562 {
00563         externalID = rhs.getExtID();
00564         sender = rhs.getSender();
00565         type = rhs.getType();
00566         message = rhs.getMessage();
00567         return *this;
00568 }
00569 
00570 
00571 
00572 /* =========================================================== */
00573 
00574 SignatureChangedPacket::SignatureChangedPacket( const unsigned char * buf, const int len )
00575 {
00576         parseData(buf, len);
00577 }
00578 
00579 SignatureChangedPacket::SignatureChangedPacket( const SignatureChangedPacket & rhs )
00580 {
00581         *this = rhs;
00582 }
00583 
00584 SignatureChangedPacket & SignatureChangedPacket::operator =( const SignatureChangedPacket & rhs )
00585 {
00586         qq = rhs.getQQ();
00587         time = rhs.getTime();
00588         signature = rhs.getSignature();
00589         return *this;
00590 }
00591 
00592 void SignatureChangedPacket::parseData( const unsigned char * buf, const int len )
00593 {
00594         int pos=0;
00595         int tmp4;
00596         memcpy(&tmp4, buf, 4);    // your buddy qq number
00597         qq = ntohl(tmp4); pos+=4;
00598         
00599         memcpy(&tmp4, buf+pos, 4);  // the time he/she changed his/her signature
00600         time = ntohl(tmp4);  pos+=4;
00601         
00602         tmp4 = buf[pos++]; // the length of signature
00603         
00604         char *str = new char[tmp4+1];
00605         memcpy(str, buf+pos, tmp4);   // we get the new signature
00606         str[tmp4] = 0x00;
00607         signature.assign(str);
00608 }
00609 
00610 
00611 
00612 /* =========================================================== */
00613 
00614 
00615 ReceivedFileIM::ReceivedFileIM( const unsigned char * buf, const int len )
00616         : NormalIMBase(buf, len)
00617         , m_FileName("")
00618         , m_FileSize(0)
00619 {
00620 }
00621 
00622 ReceivedFileIM::ReceivedFileIM( const ReceivedFileIM & rhs )
00623         : NormalIMBase(rhs)
00624 {
00625         *this = rhs;
00626 }
00627 
00628 ReceivedFileIM & ReceivedFileIM::operator =( const ReceivedFileIM & rhs )
00629 {
00630         *((NormalIMBase *)this) = (NormalIMBase)rhs;
00631         m_TransferType = rhs.getTransferType();
00632         m_ConnectMode = rhs.getConnectMode();
00633         m_SessionId = getSessionId();
00634         m_WanIp = rhs.getWanIp();
00635         m_WanPort = rhs.getWanPort();
00636         //m_MajorPort = rhs.getMajorPort();
00637         //m_LanIp = rhs.getLanIp();
00638         //m_LanPort = rhs.getLanPort();
00639 
00640         memcpy(m_AgentServerKey, rhs.getAgentServerKey(), 16);
00641         m_FileName = rhs.getFileName();
00642         m_FileSize = rhs.getFileSize();
00643         return *this;
00644 }
00645 
00646 void ReceivedFileIM::parseContents( const unsigned char * buf, const int len )
00647 {
00648         int pos = 19; // ignore 19 bytes
00649         m_TransferType = buf[pos++];
00650         if(m_TransferType != QQ_TRANSFER_FILE && m_TransferType != QQ_TRANSFER_IMAGE) return;
00651         if(getNormalIMType() == QQ_IM_REQUEST_CANCELED) return;
00652 
00653         m_ConnectMode = buf[pos++];
00654         if(getNormalIMType() != QQ_IM_TCP_REQUEST){  
00655                 // this part actually is for UDP only(maybe Request cancellation as well)
00656                 pos++; // unknown bytes, 0x66 or 0x67
00657                 if(getNormalIMType() != QQ_IM_EX_REQUEST_CANCELLED)
00658                         pos+=2; // unknown 2 bytes, 0x0000
00659                 pos+=4; // unknown 4 bytes, 0x00000001
00660 
00661 //              pos+=2; // unknown 2 bytes, 0x0000
00662 //              m_SessionId = EvaUtil::read16(buf+pos); pos+=2;
00663                 m_SessionId = EvaUtil::read32(buf+pos); pos+=4;
00664 
00665                 if(getNormalIMType() == QQ_IM_NOTIFY_FILE_AGENT_INFO)
00666                         pos++; // 0x00, and all above after m_ConnectionMode are 0x00s
00667         }
00668 
00669 
00670         m_WanIp = EvaUtil::read32(buf+pos); pos+=4; // if is cancellation, 0x00000001
00671         m_WanPort = EvaUtil::read16(buf+pos); pos+=2; // if is UDP_EX request, 0x00000000
00672         
00673         if(getNormalIMType() == QQ_IM_NOTIFY_FILE_AGENT_INFO){
00674                 m_SessionId = EvaUtil::read32(buf+pos); pos+=4;
00675                 memcpy(m_AgentServerKey, buf+pos, 16);
00676                 pos++; // last byte always be 0x01
00677                 return;
00678         }
00679         
00680         pos+=2;
00681         // request cancellation finished, actually, there are still 2 bytes(0x0000) afterwards
00682         // we just ignore them :)
00683         if(getNormalIMType() == QQ_IM_EX_REQUEST_CANCELLED) return; 
00684 
00685         // request acceptation finished, actually, there are still 16 bytes afterwards
00686         // they are all unknown, we just ignore them :)
00687         if(getNormalIMType() == QQ_IM_EX_REQUEST_ACCEPTED) return;
00688 
00689         if(getNormalIMType() != QQ_IM_TCP_REQUEST){
00690                 pos+=4; // unknown, 0x00000000
00691                 pos++; // unknown, 0x02 or 0x04
00692         }
00693 
00694         pos+=2; // if UDP request: 0x0000, if TCP request: 0x0102
00695         if(getNormalIMType() != QQ_IM_TCP_REQUEST)
00696                 pos+=4; // unknown, 0x00000000 or 0x00000001
00697 
00698         pos+=2; // unknown 2 bytes, 0x0000
00699 
00700         if(getNormalIMType() != QQ_IM_TCP_REQUEST){
00701                 pos+=2; //FIXME the length of the following part, we should check this
00702                 pos++; // unknown, 0x01
00703                 pos+=2; //FIXME the length of the following part, we should check this, again!
00704         }
00705 
00706         if(getNormalIMType() == QQ_IM_ACCEPT_UDP_REQUEST ||
00707                 getNormalIMType() == QQ_IM_NOTIFY_IP)
00708                 return;
00709 
00710         // now type should be QQ_IM_UDP_REQUEST or QQ_IM_TCP_REQUEST
00711         pos+=2; //FIXME we should check if they space and 0x1F, they should be 0x201f
00712 
00713         int strLen = 0;
00714         while(buf[pos+strLen]!=0x1f)
00715                 strLen++;
00716 #ifdef WIN32
00717         char* strFile; strFile=(char*)_alloca(strLen + 1);
00718 #else
00719         char strFile[strLen + 1];
00720 #endif
00721         memcpy(strFile, buf+pos, strLen);
00722         strFile[strLen] = 0x00;
00723         m_FileName.assign(strFile);
00724         pos+=strLen;
00725         pos++; // the 0x1f
00726         
00727         strLen = len - pos - 5; // ignore last 5 bytes " zijie" in Chinese
00728 #ifdef WIN32
00729         char* strSize; strSize=(char*)_alloca(strLen + 1);
00730 #else
00731         char strSize[strLen + 1];
00732 #endif
00733         memcpy(strSize, buf+pos, strLen);
00734         strSize[strLen] = 0x00;
00735         m_FileSize = atoi(strSize);
00736 }
00737 
00738 
00742 ReceivedFileExIpIM::ReceivedFileExIpIM( const unsigned char * buf, const int len )
00743         : NormalIMBase(buf, len),
00744         m_WanIp1(0), m_WanPort1(0),
00745         m_WanIp2(0), m_WanPort2(0),
00746         m_WanIp3(0), m_WanPort3(0),
00747         m_LanIp1(0), m_LanPort1(0),
00748         m_LanIp2(0), m_LanPort2(0),
00749         m_LanIp3(0), m_LanPort3(0),
00750         m_SyncIp(0), m_SyncPort(0), m_SyncSession(0)
00751 {
00752 }
00753 
00754 ReceivedFileExIpIM::ReceivedFileExIpIM( const ReceivedFileExIpIM & rhs )
00755         : NormalIMBase(rhs)
00756 {
00757         *this = rhs;
00758 }
00759 
00760 ReceivedFileExIpIM & ReceivedFileExIpIM::operator =( const ReceivedFileExIpIM & rhs )
00761 {
00762         *((NormalIMBase *)this) = (NormalIMBase)rhs;
00763         m_TransferType = rhs.getTransferType();
00764         m_ConnectMode = rhs.getConnectMode();
00765         m_SessionId = getSessionId();
00766 
00767         m_WanIp1 = rhs.getWanIp1();
00768         m_WanPort1 = rhs.getWanPort1();
00769         m_WanIp2 = rhs.getWanIp2();
00770         m_WanPort2 = rhs.getWanPort2();
00771         m_WanIp3 = rhs.getWanIp3();
00772         m_WanPort3 = rhs.getWanPort3();
00773 
00774         m_LanIp1 = rhs.getLanIp1();
00775         m_LanPort1 = rhs.getLanPort1();
00776         m_LanIp2 = rhs.getLanIp2();
00777         m_LanPort2 = rhs.getLanPort2();
00778         m_LanIp3 = rhs.getLanIp3();
00779         m_LanPort3 = rhs.getLanPort3();
00780 
00781         return *this;
00782 }
00783 
00784 void ReceivedFileExIpIM::parseContents( const unsigned char * buf, const int len )
00785 {
00786         int pos = 19; // ignore 19 bytes
00787         m_TransferType = buf[pos++];
00788 
00789         m_ConnectMode = buf[pos++];
00790 
00791         // this part actually is for UDP only(maybe Request cancellation as well)
00792         pos++; // unknown bytes, 0x66 or 0x67
00793         pos+=4; // unknown 4 bytes, 0x00000001
00794 
00795         m_SessionId = EvaUtil::read32(buf+pos); pos+=4;
00796 
00797         if(EvaUtil::read16(buf+pos) == 0x0001)
00798                 m_IsSender = true;
00799         else
00800                 m_IsSender = false;
00801         pos+=2;
00802 
00803         int l = EvaUtil::read16(buf+pos); pos+=2;  // following length
00804         if(l!= (len - pos)) return;
00805 
00806         // all ip is in little endian format, whereas port is in big endian
00807         memcpy(&m_WanIp1, buf+pos, 4); pos+=4;
00808         m_WanPort1 = EvaUtil::read16(buf+pos); pos+=2;
00809         memcpy(&m_WanIp2, buf+pos, 4); pos+=4;
00810         m_WanPort2 = EvaUtil::read16(buf+pos); pos+=2;
00811 
00812         memcpy(&m_LanIp1, buf+pos, 4); pos+=4;
00813         m_LanPort1 = EvaUtil::read16(buf+pos); pos+=2;
00814         memcpy(&m_LanIp2, buf+pos, 4); pos+=4;               // always 0?
00815         m_LanPort2 = EvaUtil::read16(buf+pos); pos+=2;       // always 0?
00816         memcpy(&m_LanIp3, buf+pos, 4); pos+=4;
00817         m_LanPort3 = EvaUtil::read16(buf+pos); pos+=2;
00818 
00819         if(m_IsSender){
00820                 memcpy(&m_SyncIp, buf+pos, 4); pos+=4;
00821                 m_SyncPort = EvaUtil::read16(buf+pos); pos+=2;
00822                 m_SyncSession = EvaUtil::read32(buf+pos); pos+=4;
00823         }
00824 
00825         memcpy(&m_WanIp3, buf+pos, 4); pos+=4;
00826         m_WanPort3 = EvaUtil::read16(buf+pos); pos+=2;
00827         
00828         // following are unknown 12 bytes, starting with 0x00 00 14 00 ....
00829         pos+=12;
00830 }
00831 
00832 
00833 
00834 
00835 
00836 
00837 
00838 
00839 

Generated on Mon May 15 20:48:40 2006 for libeva by  doxygen 1.4.4