📄 baseclient.cpp
字号:
DWORD dwEmuleTags = 0;
uint32 tagcount = data->ReadUInt32();
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T(" Tags=%u"), tagcount);
for (uint32 i = 0;i < tagcount; i++){
CTag temptag(data, true);
switch (temptag.GetNameID()){
case CT_NAME:
if (m_pszUsername){
free(m_pszUsername);
m_pszUsername = NULL; // needed, in case 'nstrdup' fires an exception!!
}
m_pszUsername = _tcsdup(temptag.GetStr());
if (bDbgInfo){
if (m_pszUsername){//filter username for bad chars
TCHAR* psz = m_pszUsername;
while (*psz != _T('\0')) {
if (*psz == _T('\n') || *psz == _T('\r'))
*psz = _T(' ');
psz++;
}
}
m_strHelloInfo.AppendFormat(_T("\n Name='%s'"), m_pszUsername);
}
break;
case CT_VERSION:
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n Version=%u"), temptag.GetInt());
m_nClientVersion = temptag.GetInt();
break;
case CT_PORT:
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n Port=%u"), temptag.GetInt());
nUserPort = temptag.GetInt();
break;
case CT_MOD_VERSION:
if (temptag.IsStr())
m_strModVersion = temptag.GetStr();
else if (temptag.IsInt())
m_strModVersion.Format(_T("ModID=%u"), temptag.GetInt());
else
m_strModVersion = _T("ModID=<Unknwon>");
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n ModID=%s"), m_strModVersion);
CheckForGPLEvilDoer();
break;
case CT_EMULE_UDPPORTS:
// 16 KAD Port
// 16 UDP Port
m_nKadPort = (uint16)(temptag.GetInt() >> 16);
m_nUDPPort = (uint16)temptag.GetInt();
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n KadPort=%u UDPPort=%u"), m_nKadPort, m_nUDPPort);
dwEmuleTags |= 1;
break;
case CT_EMULE_BUDDYUDP:
// 16 --Reserved for future use--
// 16 BUDDY Port
m_nBuddyPort = (uint16)temptag.GetInt();
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n BuddyPort=%u"), m_nBuddyPort);
break;
case CT_EMULE_BUDDYIP:
// 32 BUDDY IP
m_nBuddyIP = temptag.GetInt();
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n BuddyIP=%u"), m_nBuddyIP);
break;
case CT_EMULE_MISCOPTIONS1:
// 3 AICH Version (0 = not supported)
// 1 Unicode
// 4 UDP version
// 4 Data compression version
// 4 Secure Ident
// 4 Source Exchange
// 4 Ext. Requests
// 4 Comments
// 1 PeerChache supported
// 1 No 'View Shared Files' supported
// 1 MultiPacket
// 1 Preview
m_fSupportsAICH = (temptag.GetInt() >> 29) & 0x07;
m_bUnicodeSupport = (temptag.GetInt() >> 28) & 0x01;
m_byUDPVer = (temptag.GetInt() >> 24) & 0x0f;
m_byDataCompVer = (temptag.GetInt() >> 20) & 0x0f;
m_bySupportSecIdent = (temptag.GetInt() >> 16) & 0x0f;
m_bySourceExchangeVer = (temptag.GetInt() >> 12) & 0x0f;
m_byExtendedRequestsVer = (temptag.GetInt() >> 8) & 0x0f;
m_byAcceptCommentVer = (temptag.GetInt() >> 4) & 0x0f;
m_fPeerCache = (temptag.GetInt() >> 3) & 0x01;
m_fNoViewSharedFiles = (temptag.GetInt() >> 2) & 0x01;
m_bMultiPacket = (temptag.GetInt() >> 1) & 0x01;
m_fSupportsPreview = (temptag.GetInt() >> 0) & 0x01;
dwEmuleTags |= 2;
if (bDbgInfo){
m_strHelloInfo.AppendFormat(_T("\n PeerCache=%u UDPVer=%u DataComp=%u SecIdent=%u SrcExchg=%u")
_T(" ExtReq=%u Commnt=%u Preview=%u NoViewFiles=%u Unicode=%u"),
m_fPeerCache, m_byUDPVer, m_byDataCompVer, m_bySupportSecIdent, m_bySourceExchangeVer,
m_byExtendedRequestsVer, m_byAcceptCommentVer, m_fSupportsPreview, m_fNoViewSharedFiles, m_bUnicodeSupport);
}
break;
case CT_EMULE_MISCOPTIONS2:
// 28 Reserved
// 4 Kad Version
m_byKadVersion = (temptag.GetInt() >> 0) & 0x0f;
dwEmuleTags |= 8;
if (bDbgInfo){
m_strHelloInfo.AppendFormat(_T("\n KadVersion=%u" ), m_byKadVersion );
}
break;
case CT_EMULE_VERSION:
// 8 Compatible Client ID
// 7 Mjr Version (Doesn't really matter..)
// 7 Min Version (Only need 0-99)
// 3 Upd Version (Only need 0-5)
// 7 Bld Version (Only need 0-99) -- currently not used
m_byCompatibleClient = (temptag.GetInt() >> 24);
m_nClientVersion = temptag.GetInt() & 0x00ffffff;
m_byEmuleVersion = 0x99;
m_fSharedDirectories = 1;
dwEmuleTags |= 4;
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n ClientVer=%u.%u.%u.%u Comptbl=%u"), (m_nClientVersion >> 17) & 0x7f, (m_nClientVersion >> 10) & 0x7f, (m_nClientVersion >> 7) & 0x07, m_nClientVersion & 0x7f, m_byCompatibleClient);
break;
default:
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n ***UnkTag=%s"), temptag.GetFullInfo());
}
}
m_nUserPort = nUserPort;
m_dwServerIP = data->ReadUInt32();
m_nServerPort = data->ReadUInt16();
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n Server=%s:%u"), ipstr(m_dwServerIP), m_nServerPort);
// Hybrid now has an extra uint32.. What is it for?
// Also, many clients seem to send an extra 6? These are not eDonkeys or Hybrids..
if ( data->GetLength() - data->GetPosition() == sizeof(uint32) ){
uint32 test = data->ReadUInt32();
if (test == 'KDLM')
{
m_bIsML = true;
if (bDbgInfo)
m_strHelloInfo += _T("\n ***AddData: \"MLDK\"");
}
else{
m_bIsHybrid = true;
m_fSharedDirectories = 1;
if (bDbgInfo)
m_strHelloInfo.AppendFormat(_T("\n ***AddData: uint32=%u (0x%08x)"), test, test);
}
}
else if (bDbgInfo && data->GetPosition() < data->GetLength()){
UINT uAddHelloDataSize = (UINT)(data->GetLength() - data->GetPosition());
if (uAddHelloDataSize == sizeof(uint32)){
DWORD dwAddHelloInt32 = data->ReadUInt32();
m_strHelloInfo.AppendFormat(_T("\n ***AddData: uint32=%u (0x%08x)"), dwAddHelloInt32, dwAddHelloInt32);
}
else if (uAddHelloDataSize == sizeof(uint32)+sizeof(uint16)){
DWORD dwAddHelloInt32 = data->ReadUInt32();
WORD w = data->ReadUInt16();
m_strHelloInfo.AppendFormat(_T("\n ***AddData: uint32=%u (0x%08x), uint16=%u (0x%04x)"), dwAddHelloInt32, dwAddHelloInt32, w, w);
}
else
m_strHelloInfo.AppendFormat(_T("\n ***AddData: %u bytes"), uAddHelloDataSize);
}
SOCKADDR_IN sockAddr = {0};
int nSockAddrLen = sizeof(sockAddr);
socket->GetPeerName((SOCKADDR*)&sockAddr, &nSockAddrLen);
SetIP(sockAddr.sin_addr.S_un.S_addr);
//EastShare Start - added by AndCycle, IP to Country
if(theApp.ip2country->IsIP2Country()){
// Superlexx
if (m_structUserCountry == theApp.ip2country->GetDefaultIP2Country()){
m_structUserCountry = theApp.ip2country->GetCountryFromIP(m_dwUserIP);
}
}
//EastShare End - added by AndCycle, IP to Country
if (thePrefs.AddServersFromClient() && m_dwServerIP && m_nServerPort){
CServer* addsrv = new CServer(m_nServerPort, ipstr(m_dwServerIP));
addsrv->SetListName(addsrv->GetAddress());
if (!theApp.emuledlg->serverwnd->serverlistctrl.AddServer(addsrv, true))
delete addsrv;
}
//(a)If this is a highID user, store the ID in the Hybrid format.
//(b)Some older clients will not send a ID, these client are HighID users that are not connected to a server.
//(c)Kad users with a *.*.*.0 IPs will look like a lowID user they are actually a highID user.. They can be detected easily
//because they will send a ID that is the same as their IP..
if(!HasLowID() || m_nUserIDHybrid == 0 || m_nUserIDHybrid == m_dwUserIP )
m_nUserIDHybrid = ntohl(m_dwUserIP);
CClientCredits* pFoundCredits = theApp.clientcredits->GetCredit(m_achUserHash);
if (credits == NULL){
credits = pFoundCredits;
if (!theApp.clientlist->ComparePriorUserhash(m_dwUserIP, m_nUserPort, pFoundCredits)){
if (thePrefs.GetLogBannedClients())
AddDebugLogLine(false, _T("Clients: %s (%s), Banreason: Userhash changed (Found in TrackedClientsList)"), GetUserName(), ipstr(GetConnectIP()));
Ban();
}
}
else if (credits != pFoundCredits){
// userhash change ok, however two hours "waittime" before it can be used
credits = pFoundCredits;
if (thePrefs.GetLogBannedClients())
AddDebugLogLine(false, _T("Clients: %s (%s), Banreason: Userhash changed"), GetUserName(), ipstr(GetConnectIP()));
Ban();
}
if ((m_Friend = theApp.friendlist->SearchFriend(m_achUserHash, m_dwUserIP, m_nUserPort)) != NULL){
// Link the friend to that client
m_Friend->SetLinkedClient(this);
}
else{
// avoid that an unwanted client instance keeps a friend slot
SetFriendSlot(false);
}
// check for known major gpl breaker
CString strBuffer = m_pszUsername;
strBuffer.MakeUpper();
strBuffer.Remove(_T(' '));
if (strBuffer.Find(_T("EMULE-CLIENT")) != -1 || strBuffer.Find(_T("POWERMULE")) != -1 || strBuffer.Find(_T("EMULE.COM.CN")) != -1 || strBuffer.Find(_T("MIPHONE")) != -1){ //VeryCD 谁不乖?
m_bGPLEvildoer = true;
}
ReGetClientSoft();
m_byInfopacketsReceived |= IP_EDONKEYPROTPACK;
// check if at least CT_EMULEVERSION was received, all other tags are optional
bool bIsMule = (dwEmuleTags & 0x04) == 0x04;
if (bIsMule){
m_bEmuleProtocol = true;
m_byInfopacketsReceived |= IP_EMULEPROTPACK;
}
if (thePrefs.GetVerbose() && GetServerIP() == INADDR_NONE)
AddDebugLogLine(false, _T("Received invalid server IP %s from %s"), ipstr(GetServerIP()), DbgGetClientInfo());
if( GetKadPort() )
{
Kademlia::CKademlia::bootstrap(ntohl(GetIP()), GetKadPort());
}
return bIsMule;
}
// returns 'false', if client instance was deleted!
bool CUpDownClient::SendHelloPacket(){
if (socket == NULL){
ASSERT(0);
return true;
}
CSafeMemFile data(128);
data.WriteUInt8(16); // size of userhash
SendHelloTypePacket(&data);
Packet* packet = new Packet(&data);
packet->opcode = OP_HELLO;
if (thePrefs.GetDebugClientTCPLevel() > 0)
DebugSend("OP__Hello", this);
theStats.AddUpDataOverheadOther(packet->size);
socket->SendPacket(packet,true);
m_bHelloAnswerPending = true;
return true;
}
void CUpDownClient::SendMuleInfoPacket(bool bAnswer){
if (socket == NULL){
ASSERT(0);
return;
}
CSafeMemFile data(128);
data.WriteUInt8(theApp.m_uCurVersionShort);
data.WriteUInt8(EMULE_PROTOCOL);
data.WriteUInt32(7); // nr. of tags
CTag tag(ET_COMPRESSION,1);
tag.WriteTagToFile(&data);
CTag tag2(ET_UDPVER,4);
tag2.WriteTagToFile(&data);
CTag tag3(ET_UDPPORT,thePrefs.GetUDPPort());
tag3.WriteTagToFile(&data);
CTag tag4(ET_SOURCEEXCHANGE,3);
tag4.WriteTagToFile(&data);
CTag tag5(ET_COMMENTS,1);
tag5.WriteTagToFile(&data);
CTag tag6(ET_EXTENDEDREQUEST,2);
tag6.WriteTagToFile(&data);
uint32 dwTagValue = (theApp.clientcredits->CryptoAvailable() ? 3 : 0);
if (thePrefs.CanSeeShares() != vsfaNobody) // set 'Preview supported' only if 'View Shared Files' allowed
dwTagValue |= 128;
CTag tag7(ET_FEATURES, dwTagValue);
tag7.WriteTagToFile(&data);
Packet* packet = new Packet(&data,OP_EMULEPROT);
if (!bAnswer)
packet->opcode = OP_EMULEINFO;
else
packet->opcode = OP_EMULEINFOANSWER;
if (thePrefs.GetDebugClientTCPLevel() > 0)
DebugSend(!bAnswer ? "OP__EmuleInfo" : "OP__EmuleInfoAnswer", this);
theStats.AddUpDataOverheadOther(packet->size);
socket->SendPacket(packet,true,true);
}
void CUpDownClient::ProcessMuleInfoPacket(char* pachPacket, uint32 nSize)
{
bool bDbgInfo = thePrefs.GetUseDebugDevice();
m_strMuleInfo.Empty();
CSafeMemFile data((BYTE*)pachPacket,nSize);
m_byCompatibleClient = 0;
m_byEmuleVersion = data.ReadUInt8();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T("EmuleVer=0x%x"), (UINT)m_byEmuleVersion);
if( m_byEmuleVersion == 0x2B )
m_byEmuleVersion = 0x22;
uint8 protversion = data.ReadUInt8();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T(" ProtVer=%u"), (UINT)protversion);
//implicitly supported options by older clients
if (protversion == EMULE_PROTOCOL) {
//in the future do not use version to guess about new features
if(m_byEmuleVersion < 0x25 && m_byEmuleVersion > 0x22)
m_byUDPVer = 1;
if(m_byEmuleVersion < 0x25 && m_byEmuleVersion > 0x21)
m_bySourceExchangeVer = 1;
if(m_byEmuleVersion == 0x24)
m_byAcceptCommentVer = 1;
// Shared directories are requested from eMule 0.28+ because eMule 0.27 has a bug in
// the OP_ASKSHAREDFILESDIR handler, which does not return the shared files for a
// directory which has a trailing backslash.
if(m_byEmuleVersion >= 0x28 && !m_bIsML) // MLdonkey currently does not support shared directories
m_fSharedDirectories = 1;
} else {
return;
}
m_bEmuleProtocol = true;
uint32 tagcount = data.ReadUInt32();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T(" Tags=%u"), (UINT)tagcount);
for (uint32 i = 0;i < tagcount; i++){
CTag temptag(&data, false);
switch (temptag.GetNameID()){
case ET_COMPRESSION:
// Bits 31- 8: 0 - reserved
// Bits 7- 0: data compression version
m_byDataCompVer = temptag.GetInt();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T("\n Compr=%u"), (UINT)temptag.GetInt());
break;
case ET_UDPPORT:
// Bits 31-16: 0 - reserved
// Bits 15- 0: UDP port
m_nUDPPort = temptag.GetInt();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T("\n UDPPort=%u"), (UINT)temptag.GetInt());
break;
case ET_UDPVER:
// Bits 31- 8: 0 - reserved
// Bits 7- 0: UDP protocol version
m_byUDPVer = temptag.GetInt();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T("\n UDPVer=%u"), (UINT)temptag.GetInt());
break;
case ET_SOURCEEXCHANGE:
// Bits 31- 8: 0 - reserved
// Bits 7- 0: source exchange protocol version
m_bySourceExchangeVer = temptag.GetInt();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T("\n SrcExch=%u"), (UINT)temptag.GetInt());
break;
case ET_COMMENTS:
// Bits 31- 8: 0 - reserved
// Bits 7- 0: comments version
m_byAcceptCommentVer = temptag.GetInt();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T("\n Commnts=%u"), (UINT)temptag.GetInt());
break;
case ET_EXTENDEDREQUEST:
// Bits 31- 8: 0 - reserved
// Bits 7- 0: extended requests version
m_byExtendedRequestsVer = temptag.GetInt();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T("\n ExtReq=%u"), (UINT)temptag.GetInt());
break;
case ET_COMPATIBLECLIENT:
// Bits 31- 8: 0 - reserved
// Bits 7- 0: compatible client ID
m_byCompatibleClient = temptag.GetInt();
if (bDbgInfo)
m_strMuleInfo.AppendFormat(_T("\n Comptbl=%u"), (UINT)temptag.GetInt());
break;
case ET_FEATURES:
// Bits 31- 8: 0 - reserved
// Bit 7: Preview
// Bit 6- 0: secure identification
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -