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

evaonlinestatus.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  
00021 #include "evaonlinestatus.h"
00022 #include "evadefines.h"
00023 #include <string.h>
00024 #ifdef _WIN32
00025 #include <winsock.h>
00026 #else
00027 #include <arpa/inet.h>
00028 #endif
00029 
00030 // class FriendStatus for private use
00031 class FriendStatus {
00032 public:
00033         FriendStatus() : numOfBytes(0) {};
00034         FriendStatus(unsigned char * buf);
00035         ~FriendStatus() {};
00036         
00037         int qqNum;
00038         char unknown4;
00039         int ip;  // 4 bytes
00040         short port;
00041         char unknown11;
00042         char status;
00043         short unknown13_14;
00044         unsigned char unknownKey[QQ_KEY_LENGTH];
00045         
00046         int numOfBytes;
00047         
00048         FriendStatus & operator=(const FriendStatus& other);
00049         
00050         int readData(unsigned char * buf);
00051 }; 
00052 
00053 FriendStatus::FriendStatus(unsigned char * buf)
00054 {
00055         numOfBytes = readData(buf);
00056 }
00057         
00058 FriendStatus &FriendStatus::operator= (const FriendStatus& other)
00059 {
00060         qqNum = other.qqNum;
00061         unknown4 = other.unknown4;
00062         ip = other.ip;  // 4 bytes
00063         port = other.port;
00064         unknown11 = other.unknown11;
00065         status = other.status;
00066         unknown13_14 = other.unknown13_14;
00067         memcpy(unknownKey, other.unknownKey, QQ_KEY_LENGTH);
00068         
00069         numOfBytes = other.numOfBytes;
00070         return *this;
00071 }
00072 
00073 int FriendStatus::readData(unsigned char * buf)
00074 {
00075         int tmp4;
00076         memcpy(&tmp4,buf,4);
00077         // 000-003:  qq id 
00078         qqNum = ntohl(tmp4);
00079         unknown4 = buf[4];
00080         // 005-008: IP  
00081         memcpy(&tmp4, buf+5, 4);
00082         ip = ntohl(tmp4);
00083         // 009-010: port
00084         short tmp2;
00085         memcpy(&tmp2, buf+9, 2);
00086         port = ntohs(tmp2);
00087         unknown11 = buf[11];
00088         // 012: status
00089         status = buf[12];
00090         memcpy(&tmp2, buf+13, 2);
00091         unknown13_14 = ntohs(tmp2);
00092         memcpy(unknownKey, buf+15, QQ_KEY_LENGTH);
00093         numOfBytes = 31; // always 31 bytes31
00094         return numOfBytes;
00095 }
00096 
00097 /*  ======================================================= */
00098 
00099 FriendOnlineEntry::FriendOnlineEntry()
00100         :numOfBytes(0)
00101 {
00102 }
00103 
00104 FriendOnlineEntry::FriendOnlineEntry(const FriendOnlineEntry &rhs)
00105 {
00106         status = new FriendStatus();
00107         status->qqNum = rhs.getQQ();
00108         status->unknown4 = rhs.getUnknown1_4();
00109         status->ip = rhs.getIP();  // 4 bytes
00110         status->port = rhs.getPort();
00111         status->unknown11 = rhs.getUnknown2_11();
00112         status->status = rhs.getStatus();
00113         status->unknown13_14 = rhs.getUnknown3_13_14();
00114         memcpy(status->unknownKey, rhs.getUnknownKey(), QQ_KEY_LENGTH);
00115         
00116         unknown31_32 = rhs.getUnknown4_31_32();
00117         extFlag = rhs.getExtFlag();
00118         commFlag = rhs.getCommFlag();
00119         unknown35_36 = rhs.getUnknown5_35_36();
00120         ending = rhs.getEnd();
00121                 
00122         numOfBytes = rhs.numOfBytes;
00123 }
00124 
00125 FriendOnlineEntry::~FriendOnlineEntry()
00126 { 
00127         delete status; 
00128 }
00129 
00130 const int FriendOnlineEntry::getQQ() const  { return status->qqNum;}
00131 const int FriendOnlineEntry::getIP() const  { return status->ip;}
00132 const short FriendOnlineEntry::getPort() const  { return status->port;}
00133 const char FriendOnlineEntry::getStatus() const  { return status->status;}
00134 const char FriendOnlineEntry::getUnknown1_4() const  { return status->unknown4;}
00135 const char FriendOnlineEntry::getUnknown2_11() const  { return status->unknown11;}
00136 const short FriendOnlineEntry::getUnknown3_13_14() const  { return status->unknown13_14;}
00137 const unsigned char * FriendOnlineEntry::getUnknownKey() const  { return status->unknownKey;}
00138 
00139 
00140 int FriendOnlineEntry::readData(unsigned char * buf)
00141 {
00142         status = new FriendStatus();
00143         status->readData(buf);
00144         unknown31_32 = (short)(buf[31])<<8 + buf[32];
00145         extFlag = buf[33];
00146         commFlag = buf[34];
00147         unknown35_36 = (short)(buf[35])<<8 + buf[36];
00148         ending = buf[37];
00149         numOfBytes = 38;
00150         return numOfBytes;
00151 }
00152 
00153 FriendOnlineEntry & FriendOnlineEntry::operator=(const FriendOnlineEntry &rhs)
00154 {
00155         status = new FriendStatus();
00156         status->qqNum = rhs.getQQ();
00157         status->unknown4 = rhs.getUnknown1_4();
00158         status->ip = rhs.getIP();  // 4 bytes
00159         status->port = rhs.getPort();
00160         status->unknown11 = rhs.getUnknown2_11();
00161         status->status = rhs.getStatus();
00162         status->unknown13_14 = rhs.getUnknown3_13_14();
00163         memcpy(status->unknownKey, rhs.getUnknownKey(), QQ_KEY_LENGTH);
00164         
00165         unknown31_32 = rhs.getUnknown4_31_32();
00166         extFlag = rhs.getExtFlag();
00167         commFlag = rhs.getCommFlag();
00168         unknown35_36 = rhs.getUnknown5_35_36();
00169         ending = rhs.getEnd();
00170                 
00171         numOfBytes = rhs.numOfBytes;
00172         return *this;
00173 }
00174 
00175 /*  ======================================================= */
00176 
00177 GetOnlineFriendsPacket::GetOnlineFriendsPacket()
00178         : OutPacket(QQ_CMD_GET_FRIEND_ONLINE, true),
00179           startPosition (QQ_FRIEND_ONLINE_LIST_POSITION_START)
00180 {
00181 }
00182 
00183 GetOnlineFriendsPacket::GetOnlineFriendsPacket(const char position)
00184         : OutPacket(QQ_CMD_GET_FRIEND_ONLINE, true),
00185           startPosition (position)
00186 {
00187 }
00188          
00189 GetOnlineFriendsPacket::GetOnlineFriendsPacket(const GetOnlineFriendsPacket &rhs)
00190         : OutPacket(rhs)
00191 {
00192         startPosition = rhs.getStartPosition();
00193 }
00194 
00195 GetOnlineFriendsPacket &GetOnlineFriendsPacket::operator=(const GetOnlineFriendsPacket &rhs)
00196 {
00197         *((OutPacket *)this) = (OutPacket)rhs;
00198         startPosition = rhs.getStartPosition(); 
00199         return *this;
00200 }
00201 
00202 int GetOnlineFriendsPacket::putBody(unsigned char *buf) 
00203 {
00204         buf[0] = 0x02;
00205         buf[1]=startPosition;
00206         memset(buf+2, 0, 3);
00207         return 5;
00208 }
00209 
00210 /*  ======================================================= */
00211 
00212 GetOnlineFriendReplyPacket::GetOnlineFriendReplyPacket(unsigned char *buf, int len) 
00213         : InPacket(buf, len)
00214 {
00215 }
00216 
00217 GetOnlineFriendReplyPacket::GetOnlineFriendReplyPacket(const GetOnlineFriendReplyPacket &rhs)
00218         : InPacket(rhs)
00219 {
00220         position = rhs.getPosition();
00221         onlineFriends = rhs.getOnlineFriendList();
00222 }
00223 
00224 GetOnlineFriendReplyPacket &GetOnlineFriendReplyPacket::operator=(const GetOnlineFriendReplyPacket &rhs)
00225 {
00226         *((InPacket *)this) = (InPacket)rhs;
00227         position = rhs.getPosition();
00228         onlineFriends = rhs.getOnlineFriendList();
00229         return *this;
00230 }
00231 
00232 void GetOnlineFriendReplyPacket::parseBody()
00233 {
00234         position = decryptedBuf[0];
00235         int offset = 1;
00236         while(bodyLength>offset) {
00237                 FriendOnlineEntry entry;
00238                 offset+= entry.readData(decryptedBuf+offset);    
00239                 onlineFriends.push_back(entry);
00240         }
00241 }
00242 
00243 /*  ======================================================= */
00244 
00245 FriendChangeStatusPacket::FriendChangeStatusPacket(unsigned char* buf, int len)
00246         : InPacket(buf, len), status(NULL)
00247 {
00248 }
00249 
00250 FriendChangeStatusPacket::FriendChangeStatusPacket(const FriendChangeStatusPacket &rhs)
00251         : InPacket(rhs), status(NULL)
00252 {
00253         status = new FriendStatus();
00254         status->qqNum = rhs.getQQ();
00255         status->unknown4 = rhs.getUnknown1_4();
00256         status->ip = rhs.getIP();  // 4 bytes
00257         status->port = rhs.getPort();
00258         status->unknown11 = rhs.getUnknown2_11();
00259         status->status = rhs.getStatus();
00260         status->unknown13_14 = rhs.getUnknown3_13_14();
00261         memcpy(status->unknownKey, rhs.getUnknownKey(), QQ_KEY_LENGTH);
00262         
00263         myQQNum = rhs.getMyQQ();
00264 }
00265 
00266 FriendChangeStatusPacket::~FriendChangeStatusPacket()
00267 {
00268         if(status)
00269                 delete status;
00270 }
00271 
00272 FriendChangeStatusPacket &FriendChangeStatusPacket::operator=(const FriendChangeStatusPacket &rhs)
00273 {
00274         *((InPacket *)this) = (InPacket)rhs;
00275         status = new FriendStatus();
00276         status->qqNum = rhs.getQQ();
00277         status->unknown4 = rhs.getUnknown1_4();
00278         status->ip = rhs.getIP();  // 4 bytes
00279         status->port = rhs.getPort();
00280         status->unknown11 = rhs.getUnknown2_11();
00281         status->status = rhs.getStatus();
00282         status->unknown13_14 = rhs.getUnknown3_13_14();
00283         memcpy(status->unknownKey, rhs.getUnknownKey(), QQ_KEY_LENGTH);
00284         
00285         myQQNum = rhs.getMyQQ();
00286         return *this;
00287 }
00288 
00289 void FriendChangeStatusPacket::parseBody()
00290 {
00291         status = new FriendStatus();
00292         status->readData(decryptedBuf);
00293         
00294         // friendStatus read 31 bytes, but there still 4 bytes unknown, ignore them
00295         memcpy(&myQQNum,decryptedBuf + 4 + 31, 4);
00296         // this is not that useful, just means the message's receiver should hold this account
00297         myQQNum = ntohl(myQQNum);
00298 }
00299 
00300 const int FriendChangeStatusPacket::getQQ() const  { return status->qqNum;}
00301 const int FriendChangeStatusPacket::getIP() const  { return status->ip;}
00302 const short FriendChangeStatusPacket::getPort() const  { return status->port;}
00303 const char FriendChangeStatusPacket::getStatus() const  { return status->status;}
00304 const char FriendChangeStatusPacket::getUnknown1_4() const  { return status->unknown4;}
00305 const char FriendChangeStatusPacket::getUnknown2_11() const  { return status->unknown11;}
00306 const short FriendChangeStatusPacket::getUnknown3_13_14() const  { return status->unknown13_14;}
00307 const unsigned char * FriendChangeStatusPacket::getUnknownKey() const  { return status->unknownKey;}
00308 
00309 
00310 /*  ======================================================= */
00311 
00312 ChangeStatusPacket::ChangeStatusPacket() 
00313         : OutPacket(QQ_CMD_CHANGE_STATUS, true) 
00314 {
00315         myStatus = QQ_FRIEND_STATUS_INVISIBLE;
00316         miscStatus=0;
00317 }
00318 
00319 ChangeStatusPacket::ChangeStatusPacket(char status) 
00320         : OutPacket(QQ_CMD_CHANGE_STATUS, true) 
00321 {
00322         myStatus = status;
00323 }
00324 
00325 ChangeStatusPacket::ChangeStatusPacket(const ChangeStatusPacket &rhs)
00326         : OutPacket(rhs)
00327 {
00328         myStatus = rhs.getOnlineStatus();
00329 }
00330 
00331 ChangeStatusPacket &ChangeStatusPacket::operator=(const ChangeStatusPacket &rhs)
00332 {
00333         *((OutPacket *)this) = (OutPacket)rhs;
00334         myStatus = rhs.getOnlineStatus();
00335         return *this;
00336 }
00337 
00338 int ChangeStatusPacket::putBody(unsigned char *buf) 
00339 {
00340         buf[0]=myStatus;
00341         // show fake video
00342         //memset(buf+1, 0, 4);
00343         *((unsigned int*)buf+1)=miscStatus;
00344         //memmove(buf+1,&miscStatus,sizeof(unsigned int));
00345         
00346         return 5;
00347 }
00348 
00349 /*  ======================================================= */
00350 
00351 ChangeStatusReplyPacket::ChangeStatusReplyPacket(unsigned char *buf, int len) 
00352         : InPacket(buf, len)
00353 { 
00354 }
00355 
00356 ChangeStatusReplyPacket::ChangeStatusReplyPacket(const ChangeStatusReplyPacket &rhs)
00357         : InPacket(rhs)
00358 {
00359         replyCode = rhs.getReplyCode(); 
00360 }        
00361     
00362 void ChangeStatusReplyPacket::parseBody()
00363 {
00364     replyCode = decryptedBuf[0];
00365 }
00366 
00367 const bool ChangeStatusReplyPacket::isAccepted() const
00368 {
00369         return ( replyCode == QQ_CHANGE_STATUS_REPLY_OK);
00370 }
00371 
00372 ChangeStatusReplyPacket &ChangeStatusReplyPacket::operator=(const ChangeStatusReplyPacket &rhs)
00373 {
00374         *((InPacket *)this) = (InPacket)rhs;
00375         replyCode = rhs.getReplyCode();
00376         return *this;
00377 }

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