📄 kademliaudplistener.cpp
字号:
pEntry->m_listTag.push_back(pTag);
}
else
{
//More then one size tag found
delete pTag;
}
}
else
{
//TODO: Filter tags
pEntry->m_listTag.push_back(pTag);
}
}
uTags--;
}
if (bDbgInfo && !sInfo.IsEmpty())
Debug(_T("%s\n"), sInfo);
}
catch(...)
{
delete pEntry;
throw;
}
if( !pIndexed->AddKeyword(uFile, uTarget, pEntry, uLoad) )
{
//We already indexed the maximum number of keywords.
//We do not index anymore but we still send a success..
//Reason: Because if a VERY busy node tells the publisher it failed,
//this busy node will spread to all the surrounding nodes causing popular
//keywords to be stored on MANY nodes..
//So, once we are full, we will periodically clean our list until we can
//begin storing again..
delete pEntry;
pEntry = NULL;
}
uCount--;
}
CSafeMemFile fileIO2(17);
fileIO2.WriteUInt128(&uFile);
fileIO2.WriteUInt8(uLoad);
if (thePrefs.GetDebugClientKadUDPLevel() > 0)
DebugSend("KADEMLIA2_PUBLISH_RES", uIP, uUDPPort);
SendPacket( &fileIO2, KADEMLIA2_PUBLISH_RES, uIP, uUDPPort);
}
// Used in Kad2.0 only
void CKademliaUDPListener::Process_KADEMLIA2_PUBLISH_SOURCE_REQ (const byte *pbyPacketData, uint32 uLenPacket, uint32 uIP, uint16 uUDPPort)
{
//Used Pointers
CIndexed *pIndexed = CKademlia::GetIndexed();
if( CKademlia::GetPrefs()->GetFirewalled() )
//We are firewalled. We should not index this entry and give publisher a false report.
return;
CByteIO byteIO(pbyPacketData, uLenPacket);
CUInt128 uFile;
byteIO.ReadUInt128(&uFile);
CUInt128 uDistance(CKademlia::GetPrefs()->GetKadID());
uDistance.Xor(uFile);
if( thePrefs.FilterLANIPs() && uDistance.Get32BitChunk(0) > SEARCHTOLERANCE)
return;
bool bDbgInfo = (thePrefs.GetDebugClientKadUDPLevel() > 0);
CString sInfo;
sInfo.Empty();
uint8 uLoad = 0;
bool bFlag = false;
CUInt128 uTarget;
byteIO.ReadUInt128(&uTarget);
CEntry* pEntry = new Kademlia::CEntry();
try
{
pEntry->m_uIP = uIP;
pEntry->m_uUDPPort = uUDPPort;
pEntry->m_uKeyID.SetValue(uFile);
pEntry->m_uSourceID.SetValue(uTarget);
pEntry->m_bSource = false;
pEntry->m_tLifetime = (uint32)time(NULL)+KADEMLIAREPUBLISHTIMES;
uint32 uTags = byteIO.ReadByte();
while(uTags > 0)
{
CKadTag* pTag = byteIO.ReadTag();
if(pTag)
{
if (!pTag->m_name.Compare(TAG_SOURCETYPE))
{
if( pEntry->m_bSource == false )
{
pEntry->m_listTag.push_back(new CKadTagUInt(TAG_SOURCEIP, pEntry->m_uIP));
pEntry->m_listTag.push_back(new CKadTagUInt(TAG_SOURCEUPORT, pEntry->m_uUDPPort));
pEntry->m_listTag.push_back(pTag);
pEntry->m_bSource = true;
}
else
{
//More then one sourcetype tag found.
delete pTag;
}
}
else if (!pTag->m_name.Compare(TAG_FILESIZE))
{
if( pEntry->m_uSize == 0 )
{
pEntry->m_uSize = pTag->GetInt();
if (bDbgInfo)
sInfo.AppendFormat(_T(" Size=%u"), pEntry->m_uSize);
// NOTE: always add the 'size' tag, even if it's stored separately in 'size'. the tag is still needed for answering search request
pEntry->m_listTag.push_back(pTag);
}
else
{
//More then one size tag found
delete pTag;
}
}
else if (!pTag->m_name.Compare(TAG_SOURCEPORT))
{
if( pEntry->m_uTCPPort == 0 )
{
pEntry->m_uTCPPort = (uint16)pTag->GetInt();
pEntry->m_listTag.push_back(pTag);
}
else
{
//More then one port tag found
delete pTag;
}
}
else
{
//TODO: Filter tags
pEntry->m_listTag.push_back(pTag);
}
}
uTags--;
}
if (bDbgInfo && !sInfo.IsEmpty())
Debug(_T("%s\n"), sInfo);
}
catch(...)
{
delete pEntry;
throw;
}
if( pEntry->m_bSource == true )
{
if( pIndexed->AddSources(uFile, uTarget, pEntry, uLoad ) )
bFlag = true;
else
{
delete pEntry;
pEntry = NULL;
}
}
else
{
delete pEntry;
pEntry = NULL;
}
if( bFlag )
{
CSafeMemFile fileIO2(17);
fileIO2.WriteUInt128(&uFile);
fileIO2.WriteUInt8(uLoad);
if (thePrefs.GetDebugClientKadUDPLevel() > 0)
DebugSend("KADEMLIA2_PUBLISH_RES", uIP, uUDPPort);
SendPacket( &fileIO2, KADEMLIA2_PUBLISH_RES, uIP, uUDPPort);
}
}
// Used only by Kad1.0
void CKademliaUDPListener::Process_KADEMLIA_PUBLISH_RES (const byte *pbyPacketData, uint32 uLenPacket, uint32 uIP)
{
// Verify packet is expected size
if (uLenPacket < 16)
{
CString strError;
strError.Format(_T("***NOTE: Received wrong size (%u) packet in %hs"), uLenPacket, __FUNCTION__);
throw strError;
}
else if (!IsOnTrackList(uIP, KADEMLIA_PUBLISH_REQ)){
CString strError;
strError.Format(_T("***NOTE: Received unrequested repsonse packet, size (%u) in %hs"), uLenPacket, __FUNCTION__);
throw strError;
}
CSafeMemFile fileIO(pbyPacketData, uLenPacket);
CUInt128 uFile;
fileIO.ReadUInt128(&uFile);
bool bLoadResponse = false;
uint8 uLoad = 0;
if( fileIO.GetLength() > fileIO.GetPosition() )
{
bLoadResponse = true;
uLoad = fileIO.ReadUInt8();
}
CSearchManager::ProcessPublishResult(uFile, uLoad, bLoadResponse);
}
// Used only by Kad2.0
void CKademliaUDPListener::Process_KADEMLIA2_PUBLISH_RES (const byte *pbyPacketData, uint32 uLenPacket, uint32 uIP)
{
if (!IsOnTrackList(uIP, KADEMLIA2_PUBLISH_KEY_REQ) && !IsOnTrackList(uIP, KADEMLIA2_PUBLISH_SOURCE_REQ) && !IsOnTrackList(uIP, KADEMLIA2_PUBLISH_NOTES_REQ)){
CString strError;
strError.Format(_T("***NOTE: Received unrequested repsonse packet, size (%u) in %hs"), uLenPacket, __FUNCTION__);
throw strError;
}
CSafeMemFile fileIO(pbyPacketData, uLenPacket);
CUInt128 uFile;
fileIO.ReadUInt128(&uFile);
uint8 uLoad = fileIO.ReadUInt8();
CSearchManager::ProcessPublishResult(uFile, uLoad, true);
}
// Used only by Kad1.0
void CKademliaUDPListener::Process_KADEMLIA_SEARCH_NOTES_REQ (const byte *pbyPacketData, uint32 uLenPacket, uint32 uIP, uint16 uUDPPort)
{
// Verify packet is expected size
if (uLenPacket < 32)
{
CString strError;
strError.Format(_T("***NOTE: Received wrong size (%u) packet in %hs"), uLenPacket, __FUNCTION__);
throw strError;
}
CSafeMemFile fileIO( pbyPacketData, uLenPacket);
CUInt128 uTarget;
fileIO.ReadUInt128(&uTarget);
// This info is currently not used.
// CUInt128 uSource;
// fileIO.ReadUInt128(&uSource);
CKademlia::GetIndexed()->SendValidNoteResult(uTarget, uIP, uUDPPort, false, 0);
}
// Used only by Kad2.0
void CKademliaUDPListener::Process_KADEMLIA2_SEARCH_NOTES_REQ (const byte *pbyPacketData, uint32 uLenPacket, uint32 uIP, uint16 uUDPPort)
{
CSafeMemFile fileIO(pbyPacketData, uLenPacket);
CUInt128 uTarget;
fileIO.ReadUInt128(&uTarget);
uint64 uFileSize = fileIO.ReadUInt64();
CKademlia::GetIndexed()->SendValidNoteResult(uTarget, uIP, uUDPPort, true, uFileSize);
}
// Used only by Kad1.0
void CKademliaUDPListener::Process_KADEMLIA_SEARCH_NOTES_RES (const byte *pbyPacketData, uint32 uLenPacket, uint32 uIP)
{
// Verify packet is expected size
if (uLenPacket < 37)
{
CString strError;
strError.Format(_T("***NOTE: Received wrong size (%u) packet in %hs"), uLenPacket, __FUNCTION__);
throw strError;
}
else if (!IsOnTrackList(uIP, KADEMLIA_SEARCH_NOTES_REQ, true)){
CString strError;
strError.Format(_T("***NOTE: Received unrequested repsonse packet, size (%u) in %hs"), uLenPacket, __FUNCTION__);
throw strError;
}
// What search does this relate to
CByteIO byteIO(pbyPacketData, uLenPacket);
CUInt128 uTarget;
byteIO.ReadUInt128(&uTarget);
uint16 uCount = byteIO.ReadUInt16();
CUInt128 uAnswer;
while( uCount > 0 )
{
// What is the answer
byteIO.ReadUInt128(&uAnswer);
// Get info about answer
// NOTE: this is the one and only place in Kad where we allow string conversion to local code page in
// case we did not receive an UTF8 string. this is for backward compatibility for search results which are
// supposed to be 'viewed' by user only and not feed into the Kad engine again!
// If that tag list is once used for something else than for viewing, special care has to be taken for any
// string conversion!
TagList* pTags = new TagList;
try
{
byteIO.ReadTagList(pTags, true);
}
catch(...)
{
deleteTagListEntries(pTags);
delete pTags;
pTags = NULL;
throw;
}
CSearchManager::ProcessResult(uTarget, uAnswer, pTags);
uCount--;
}
}
// Used only by Kad1.0
void CKademliaUDPListener::Process_KADEMLIA_PUBLISH_NOTES_REQ (const byte *pbyPacketData, uint32 uLenPacket, uint32 uIP, uint16 uUDPPort)
{
// Verify packet is expected size
if (uLenPacket < 37)
{
CString strError;
strError.Format(_T("***NOTE: Received wrong size (%u) packet in %hs"), uLenPacket, __FUNCTION__);
throw strError;
}
if( CKademlia::GetPrefs()->GetFirewalled() )
//We are firewalled. We should not index this entry and give publisher a false report.
return;
CByteIO byteIO(pbyPacketData, uLenPacket);
CUInt128 uTarget;
byteIO.ReadUInt128(&uTarget);
CUInt128 uDistance(CKademlia::GetPrefs()->GetKadID());
uDistance.Xor(uTarget);
// Shouldn't LAN IPs already be filtered?
if( thePrefs.FilterLANIPs() && uDistance.Get32BitChunk(0) > SEARCHTOLERANCE)
return;
CUInt128 uSource;
byteIO.ReadUInt128(&uSource);
Kademlia::CEntry* pEntry = new Kademlia::CEntry();
try
{
pEntry->m_uIP = uIP;
pEntry->m_uUDPPort = uUDPPort;
pEntry->m_uKeyID.SetValue(uTarget);
pEntry->m_uSourceID.SetValue(uSource);
byteIO.ReadTagList(&pEntry->m_listTag);
pEntry->m_bSource = false;
}
catch(...)
{
delete pEntry;
pEntry = NULL;
throw;
}
if( pEntry == NULL )
{
throw CString(_T("CKademliaUDPListener::Process_KADEMLIA_PUBLISH_NOTES_REQ: pEntry == NULL"));
}
else if( pEntry->m_listTag.size() == 0 || pEntry->m_listTag.size() > 5)
{
delete pEntry;
throw CString(_T("CKademliaUDPListener::Process_KADEMLIA_PUBLISH_NOTES_REQ: pEntry->m_listTag.size() == 0 || pEntry->m_listTag.size() > 5"));
}
uint8 uLoad = 0;
if( CKademlia::GetIndexed()->AddNotes(uTarget, uSource, pEntry, uLoad ) )
{
CSafeMemFile fileIO2(17);
fileIO2.WriteUInt128(&uTarget);
fileIO2.WriteUInt8(uLoad);
if (thePrefs.GetDebugClientKadUDPLevel() > 0)
DebugSend("KADEMLIA_PUBLISH_NOTES_RES", uIP, uUDPPort);
SendPacket( &fileIO2, KADEMLIA_PUBLISH_NOTES_RES, uIP, uUDPPort);
}
else
delete pEntry;
}
// Used only by Kad2.0
void CKademliaUDPListener::Process_KADEMLIA2_PUBLISH_NOTES_REQ (const byte *pbyPacketData, uint32 uLenPacket, uint32 uIP, uint16 uUDPPort)
{
if( CKademlia::GetPrefs()->GetFirewalled() )
//We are firewalled. We should not index this entry and give publisher a false report.
return;
CByteIO byteIO(pbyPacketData, uLenPacket);
CUInt128 uTarget;
byteIO.ReadUInt128(&uTarget);
CUInt128 uDistance(CKademlia::GetPrefs()->GetKadID());
uDistance.Xor(uTarget);
// Shouldn't LAN IPs already be filtered?
if( thePrefs.FilterLANIPs() && uDistance.Get32BitChunk(0) > SEARCHTOLERANCE)
return;
CUInt128 uSource;
byteIO.ReadUInt128(&uSource);
Kademlia::CEntry* pEntry = new Kademlia::CEntry();
try
{
pEntry->m_uIP = uIP;
pEntry->m_uUDPPort = uUDPPort;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -