1//
2// This file is part of the aMule Project.
3//
4// Copyright (c) 2008-2011 D��vai Tam��s ( gonosztopi@amule.org )
5// Copyright (c) 2004-2011 aMule Team ( admin@amule.org / http://www.amule.org )
6//
7// Any parts of this program derived from the xMule, lMule or eMule project,
8// or contributed by third-party developers are copyrighted by their
9// respective authors.
10//
11// This program is free software; you can redistribute it and/or modify
12// it under the terms of the GNU General Public License as published by
13// the Free Software Foundation; either version 2 of the License, or
14// (at your option) any later version.
15//
16// This program is distributed in the hope that it will be useful,
17// but WITHOUT ANY WARRANTY; without even the implied warranty of
18// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19// GNU General Public License for more details.
20//
21// You should have received a copy of the GNU General Public License
22// along with this program; if not, write to the Free Software
23// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301, USA
24//
25
26#include "KadFiles.h"
27#include "Print.h"
28#include "../../SafeFile.h"
29#include "../../kademlia/kademlia/SearchManager.h"	// for CSearchManager::GetInvalidKeywordChars()
30#include <wx/tokenzr.h>
31
32void DecodePreferencesKadDat(const CFileDataIO& file)
33{
34	cout << "IP      : " << CKadIP(file.ReadUInt32()) << '\n';
35	cout << "(unused): " << file.ReadUInt16() << '\n';
36	cout << "ClientID: " << file.ReadUInt128() << '\n';
37}
38
39void DecodeLoadIndexDat(const CFileDataIO& file)
40{
41	cout << "Version   : " << file.ReadUInt32();
42	cout << "\n(savetime): " << CTimeT(file.ReadUInt32());
43	uint32_t numLoad = file.ReadUInt32();
44	cout << "\nnumLoad   : " << numLoad << '\n';
45	for (uint32_t i = 0; i < numLoad; i++) {
46		cout << "\t{ " << file.ReadUInt128();
47		cout << ", " << CTimeT(file.ReadUInt32()) << " }\n";
48	}
49}
50
51// from Kademlia.cpp
52#include "../../CryptoPP_Inc.h"
53void KadGetKeywordHash(const wxString& rstrKeyword, Kademlia::CUInt128* pKadID)
54{
55	byte Output[16];
56#ifdef CRYPTOPP_ENABLE_NAMESPACE_WEAK
57	CryptoPP::Weak::MD4 md4_hasher;
58#else
59	CryptoPP::MD4 md4_hasher;
60#endif
61
62	// This should be safe - we assume rstrKeyword is ANSI anyway.
63	Unicode2CharBuf ansi_buffer(unicode2UTF8(rstrKeyword));
64
65	md4_hasher.CalculateDigest(Output, (const byte *) (const char *) ansi_buffer, strlen(ansi_buffer));
66
67	pKadID->SetValueBE(Output);
68}
69
70// code from CSearchManager::GetWords(const wxString& str, WordList *words)
71bool IdentifyKeyword(const Kademlia::CUInt128& keyID, const wxString& str, wxString& keyword)
72{
73	wxStringTokenizer tkz(str, Kademlia::CSearchManager::GetInvalidKeywordChars());
74	while (tkz.HasMoreTokens()) {
75		wxString current_word = tkz.GetNextToken();
76
77		if (current_word.Length() > 2) {
78			current_word.MakeLower();
79			Kademlia::CUInt128 currentID;
80			KadGetKeywordHash(current_word, &currentID);
81			if (currentID == keyID) {
82				keyword = current_word;
83				return true;
84			}
85		}
86	}
87	return false;
88}
89
90void DecodeKeyIndexDat(const CFileDataIO& file)
91{
92	uint32_t version;
93	uint32_t numKeys;
94	uint32_t numSource;
95	uint32_t numName;
96	uint8_t tagCount;
97
98	cout << "Version : " << (version = file.ReadUInt32());
99	cout << "\nSaveTime: " << CTimeT(file.ReadUInt32());
100	cout << "\nID      : " << file.ReadUInt128();
101	cout << "\nnumKeys : " << (numKeys = file.ReadUInt32()) << '\n';
102	for (uint32_t ik = 0; ik < numKeys; ik++) {
103		Kademlia::CUInt128 keyID = file.ReadUInt128();
104		bool identified = false;
105		cout << "\tKeyID    : " << keyID;
106		cout << "\n\tnumSource: " << (numSource = file.ReadUInt32()) << '\n';
107		for (uint32_t is = 0; is < numSource; is++) {
108			cout << "\t\tSourceID: " << file.ReadUInt128();
109			cout << "\n\t\tnumName : " << (numName = file.ReadUInt32()) << '\n';
110			for (uint32_t iN = 0; iN < numName; iN++) {
111				cout << "\t\t\tLifeTime : " <<  CTimeT(file.ReadUInt32()) << '\n';
112				if (version >= 3) {
113					uint32_t count;
114					cout << "\t\t\tnameCount: " << (count = file.ReadUInt32()) << '\n';
115					for (uint32_t i = 0; i < count; i++) {
116						wxString name = file.ReadString(true, 2);
117						cout << "\t\t\t\t{ " << MakePrintableString(name);
118						cout << ", " << file.ReadUInt32() << " }\n";
119						wxString keyword;
120						if (!identified && IdentifyKeyword(keyID, name, keyword)) {
121							cout << "\tKeyword: " << MakePrintableString(keyword) << '\n';
122							identified = true;
123						}
124					}
125					cout << "\t\t\tipCount  : " << (count = file.ReadUInt32()) << '\n';
126					for (uint32_t i = 0; i < count; i++) {
127						cout << "\t\t\t\t{ " << CKadIP(file.ReadUInt32());
128						cout << ", " << CTimeT(file.ReadUInt32()) << " }\n";
129					}
130				}
131				cout << "\t\t\ttagCount : " << (uint32)(tagCount = file.ReadUInt8()) << '\n';
132				for (uint32_t it = 0; it < tagCount; it++) {
133					CTag *tag = file.ReadTag();
134					cout << "\t\t\t\t" << *tag << '\n';
135					delete tag;
136				}
137			}
138		}
139	}
140}
141
142void DecodeSourceIndexDat(const CFileDataIO& file)
143{
144	uint32_t numKeys;
145	uint32_t numSource;
146	uint32_t numName;
147	uint8_t tagCount;
148
149	cout << "Version : " << file.ReadUInt32();
150	cout << "\nSaveTime: " << CTimeT(file.ReadUInt32());
151	cout << "\nnumKeys : " << (numKeys = file.ReadUInt32()) << '\n';
152	for (uint32_t ik = 0; ik < numKeys; ik++) {
153		cout << "\tKeyID    : " << file.ReadUInt128();
154		cout << "\n\tnumSource: " << (numSource = file.ReadUInt32()) << '\n';
155		for (uint32_t is = 0; is < numSource; is++) {
156			cout << "\t\tSourceID: " << file.ReadUInt128();
157			cout << "\n\t\tnumName : " << (numName = file.ReadUInt32()) << '\n';
158			for (uint32_t iN = 0; iN < numName; iN++) {
159				cout << "\t\t\tLifeTime: " << CTimeT(file.ReadUInt32());
160				cout << "\n\t\t\ttagCount: " << (tagCount = file.ReadUInt8()) << '\n';
161				for (uint32_t it = 0; it < tagCount; it++) {
162					CTag *tag = file.ReadTag();
163					cout << "\t\t\t\t" << *tag << '\n';
164					delete tag;
165				}
166			}
167		}
168	}
169}
170
171void DecodeNodesDat(const CFileDataIO& file)
172{
173	uint32_t numContacts = file.ReadUInt32();
174	uint32_t fileVersion = 0;
175
176	cout << "NumContacts #1  : " << numContacts << '\n';
177	if (numContacts == 0) {
178		cout << "FileVersion     : " << (fileVersion = file.ReadUInt32()) << '\n';
179		if (fileVersion == 3) {
180			cout << "BootstrapEdition: " << file.ReadUInt32() << '\n';
181		}
182		if (fileVersion >= 1 && fileVersion <= 3) {
183			cout << "NumContacts #2  : " << (numContacts = file.ReadUInt32()) << '\n';
184		}
185	}
186	for (uint32_t i = 0; i < numContacts; i++) {
187		cout << wxString::Format(wxT("#%u\tID       : "), i) << file.ReadUInt128();
188		cout << "\n\tIP       : " << CKadIP(file.ReadUInt32());
189		cout << "\n\tUDP Port : " << file.ReadUInt16();
190		cout << "\n\tTCP Port : " << file.ReadUInt16();
191		if (fileVersion >= 1) {
192			cout << "\n\tVersion  : ";
193		} else {
194			cout << "\n\tType     : ";
195		}
196		cout << (unsigned)file.ReadUInt8();
197		if (fileVersion >= 2) {
198			cout << "\n\tUDP Key  : { " << hex(file.ReadUInt32());
199			cout << ", " << CKadIP(file.ReadUInt32());
200			cout << " }\n\tVerified : " << (file.ReadUInt8() != 0 ? "true" : "false");
201		}
202		cout << '\n';
203	}
204}
205