summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--core/DHT.c551
-rw-r--r--core/network.c3
-rw-r--r--core/network.h1
3 files changed, 243 insertions, 312 deletions
diff --git a/core/DHT.c b/core/DHT.c
index 9c2245c7..71abea2a 100644
--- a/core/DHT.c
+++ b/core/DHT.c
@@ -23,7 +23,8 @@
23 23
24#include "DHT.h" 24#include "DHT.h"
25 25
26typedef struct { 26typedef struct
27{
27 uint8_t client_id[CLIENT_ID_SIZE]; 28 uint8_t client_id[CLIENT_ID_SIZE];
28 IP_Port ip_port; 29 IP_Port ip_port;
29 uint32_t timestamp; 30 uint32_t timestamp;
@@ -31,12 +32,13 @@ typedef struct {
31 IP_Port ret_ip_port;/* The ip_port returned by this node for the friend 32 IP_Port ret_ip_port;/* The ip_port returned by this node for the friend
32 (for nodes in friends_list) or us (for nodes in close_clientlist) */ 33 (for nodes in friends_list) or us (for nodes in close_clientlist) */
33 uint32_t ret_timestamp; 34 uint32_t ret_timestamp;
34} Client_data; 35}Client_data;
35 36
36/* maximum number of clients stored per friend. */ 37/* maximum number of clients stored per friend. */
37#define MAX_FRIEND_CLIENTS 8 38#define MAX_FRIEND_CLIENTS 8
38 39
39typedef struct { 40typedef struct
41{
40 uint8_t client_id[CLIENT_ID_SIZE]; 42 uint8_t client_id[CLIENT_ID_SIZE];
41 Client_data client_list[MAX_FRIEND_CLIENTS]; 43 Client_data client_list[MAX_FRIEND_CLIENTS];
42 uint32_t lastgetnode; /* time at which the last get_nodes request was sent. */ 44 uint32_t lastgetnode; /* time at which the last get_nodes request was sent. */
@@ -47,19 +49,21 @@ typedef struct {
47 uint32_t punching_timestamp; 49 uint32_t punching_timestamp;
48 uint64_t NATping_id; 50 uint64_t NATping_id;
49 uint32_t NATping_timestamp; 51 uint32_t NATping_timestamp;
50} Friend; 52}Friend;
51 53
52typedef struct { 54typedef struct
55{
53 uint8_t client_id[CLIENT_ID_SIZE]; 56 uint8_t client_id[CLIENT_ID_SIZE];
54 IP_Port ip_port; 57 IP_Port ip_port;
55} Node_format; 58}Node_format;
56 59
57typedef struct { 60typedef struct
61{
58 IP_Port ip_port; 62 IP_Port ip_port;
59 uint64_t ping_id; 63 uint64_t ping_id;
60 uint32_t timestamp; 64 uint32_t timestamp;
61 65
62} Pinged; 66}Pinged;
63 67
64/* Our client id/public key */ 68/* Our client id/public key */
65uint8_t self_public_key[CLIENT_ID_SIZE]; 69uint8_t self_public_key[CLIENT_ID_SIZE];
@@ -70,7 +74,7 @@ uint8_t self_secret_key[crypto_box_SECRETKEYBYTES];
70#define LCLIENT_LIST 32 74#define LCLIENT_LIST 32
71static Client_data close_clientlist[LCLIENT_LIST]; 75static Client_data close_clientlist[LCLIENT_LIST];
72 76
73static Friend *friends_list; 77static Friend * friends_list;
74static uint16_t num_friends; 78static uint16_t num_friends;
75 79
76/* The list of ip ports along with the ping_id of what we sent them and a timestamp */ 80/* The list of ip ports along with the ping_id of what we sent them and a timestamp */
@@ -86,10 +90,10 @@ static Pinged send_nodes[LSEND_NODES_ARRAY];
86 return 0 if both are same distance 90 return 0 if both are same distance
87 return 1 if client_id1 is closer 91 return 1 if client_id1 is closer
88 return 2 if client_id2 is closer */ 92 return 2 if client_id2 is closer */
89int id_closest(uint8_t *client_id, uint8_t *client_id1, uint8_t *client_id2) /* tested */ 93int id_closest(uint8_t * client_id, uint8_t * client_id1, uint8_t * client_id2) /* tested */
90{ 94{
91 uint32_t i; 95 uint32_t i;
92 for (i = 0; i < CLIENT_ID_SIZE; ++i) { 96 for(i = 0; i < CLIENT_ID_SIZE; ++i) {
93 if(abs(client_id[i] ^ client_id1[i]) < abs(client_id[i] ^ client_id2[i])) 97 if(abs(client_id[i] ^ client_id1[i]) < abs(client_id[i] ^ client_id2[i]))
94 return 1; 98 return 1;
95 else if(abs(client_id[i] ^ client_id1[i]) > abs(client_id[i] ^ client_id2[i])) 99 else if(abs(client_id[i] ^ client_id1[i]) > abs(client_id[i] ^ client_id2[i]))
@@ -103,19 +107,18 @@ int id_closest(uint8_t *client_id, uint8_t *client_id1, uint8_t *client_id2) /*
103 if the id is already in the list with a different ip_port, update it. 107 if the id is already in the list with a different ip_port, update it.
104 return True(1) or False(0) 108 return True(1) or False(0)
105 TODO: maybe optimize this. */ 109 TODO: maybe optimize this. */
106int client_in_list(Client_data *list, uint32_t length, uint8_t *client_id, IP_Port ip_port) 110int client_in_list(Client_data * list, uint32_t length, uint8_t * client_id, IP_Port ip_port)
107{ 111{
108 uint32_t i; 112 uint32_t i;
109 uint32_t temp_time = unix_time(); 113 uint32_t temp_time = unix_time();
110 114
111 for (i = 0; i < length; ++i) { 115 for(i = 0; i < length; ++i) {
112 /*If ip_port is assigned to a different client_id replace it*/ 116 /*If ip_port is assigned to a different client_id replace it*/
113 if(list[i].ip_port.ip.i == ip_port.ip.i && 117 if(list[i].ip_port.ip.i == ip_port.ip.i &&
114 list[i].ip_port.port == ip_port.port) 118 list[i].ip_port.port == ip_port.port) {
115 {
116 memcpy(list[i].client_id, client_id, CLIENT_ID_SIZE); 119 memcpy(list[i].client_id, client_id, CLIENT_ID_SIZE);
117 } 120 }
118 121
119 if(memcmp(list[i].client_id, client_id, CLIENT_ID_SIZE) == 0) { 122 if(memcmp(list[i].client_id, client_id, CLIENT_ID_SIZE) == 0) {
120 /* Refresh the client timestamp. */ 123 /* Refresh the client timestamp. */
121 list[i].timestamp = temp_time; 124 list[i].timestamp = temp_time;
@@ -125,31 +128,28 @@ int client_in_list(Client_data *list, uint32_t length, uint8_t *client_id, IP_Po
125 } 128 }
126 } 129 }
127 return 0; 130 return 0;
128 131
129} 132}
130 133
131/* check if client with client_id is already in node format list of length length. 134/* check if client with client_id is already in node format list of length length.
132 return True(1) or False(0) */ 135 return True(1) or False(0) */
133int client_in_nodelist(Node_format *list, uint32_t length, uint8_t *client_id) 136int client_in_nodelist(Node_format * list, uint32_t length, uint8_t * client_id)
134{ 137{
135 uint32_t i; 138 uint32_t i;
136 for (i = 0; i < length; ++i) { 139 for(i = 0; i < length; ++i)
137 if (memcmp(list[i].client_id, client_id, CLIENT_ID_SIZE) == 0) 140 if(memcmp(list[i].client_id, client_id, CLIENT_ID_SIZE) == 0)
138 return 1; 141 return 1;
139 }
140 return 0; 142 return 0;
141
142} 143}
143 144
144/*Return the friend number from the client_id 145/*Return the friend number from the client_id
145 Return -1 if failure, number of friend if success*/ 146 Return -1 if failure, number of friend if success*/
146static int friend_number(uint8_t *client_id) 147static int friend_number(uint8_t * client_id)
147{ 148{
148 uint32_t i; 149 uint32_t i;
149 for (i = 0; i < num_friends; ++i) { 150 for(i = 0; i < num_friends; ++i)
150 if (memcmp(friends_list[i].client_id, client_id, CLIENT_ID_SIZE) == 0) /* Equal */ 151 if(memcmp(friends_list[i].client_id, client_id, CLIENT_ID_SIZE) == 0) /* Equal */
151 return i; 152 return i;
152 }
153 return -1; 153 return -1;
154} 154}
155 155
@@ -161,62 +161,56 @@ static int friend_number(uint8_t *client_id)
161/* Find MAX_SENT_NODES nodes closest to the client_id for the send nodes request: 161/* Find MAX_SENT_NODES nodes closest to the client_id for the send nodes request:
162 put them in the nodes_list and return how many were found. 162 put them in the nodes_list and return how many were found.
163 TODO: Make this function much more efficient. */ 163 TODO: Make this function much more efficient. */
164int get_close_nodes(uint8_t *client_id, Node_format * nodes_list) 164int get_close_nodes(uint8_t * client_id, Node_format * nodes_list)
165{ 165{
166 uint32_t i, j, k; 166 uint32_t i, j, k;
167 int num_nodes=0; 167 int num_nodes=0;
168 uint32_t temp_time = unix_time(); 168 uint32_t temp_time = unix_time();
169 for (i = 0; i < LCLIENT_LIST; ++i) { 169 for(i = 0; i < LCLIENT_LIST; ++i)
170 if (close_clientlist[i].timestamp + BAD_NODE_TIMEOUT > temp_time && 170 if(close_clientlist[i].timestamp + BAD_NODE_TIMEOUT > temp_time &&
171 !client_in_nodelist(nodes_list, MAX_SENT_NODES,close_clientlist[i].client_id)) 171 !client_in_nodelist(nodes_list, MAX_SENT_NODES,close_clientlist[i].client_id)) {
172 {
173 /* if node is good and not already in list. */ 172 /* if node is good and not already in list. */
174 if(num_nodes < MAX_SENT_NODES) { 173 if(num_nodes < MAX_SENT_NODES) {
175 memcpy(nodes_list[num_nodes].client_id, close_clientlist[i].client_id, CLIENT_ID_SIZE); 174 memcpy(nodes_list[num_nodes].client_id, close_clientlist[i].client_id, CLIENT_ID_SIZE);
176 nodes_list[num_nodes].ip_port = close_clientlist[i].ip_port; 175 nodes_list[num_nodes].ip_port = close_clientlist[i].ip_port;
177 num_nodes++; 176 num_nodes++;
178 } 177 }
179 else for(j = 0; j < MAX_SENT_NODES; ++j) { 178 else for(j = 0; j < MAX_SENT_NODES; ++j)
180 if(id_closest(client_id, nodes_list[j].client_id, close_clientlist[i].client_id) == 2) { 179 if(id_closest(client_id, nodes_list[j].client_id, close_clientlist[i].client_id) == 2) {
181 memcpy(nodes_list[j].client_id, close_clientlist[i].client_id, CLIENT_ID_SIZE); 180 memcpy(nodes_list[j].client_id, close_clientlist[i].client_id, CLIENT_ID_SIZE);
182 nodes_list[j].ip_port = close_clientlist[i].ip_port; 181 nodes_list[j].ip_port = close_clientlist[i].ip_port;
183 break; 182 break;
184 } 183 }
185 } 184 }
186 } 185
187 } 186 for(i = 0; i < num_friends; ++i)
188 for (i = 0; i < num_friends; ++i) { 187 for(j = 0; j < MAX_FRIEND_CLIENTS; ++j)
189 for (j = 0; j < MAX_FRIEND_CLIENTS; ++j) { 188 if(friends_list[i].client_list[j].timestamp + BAD_NODE_TIMEOUT > temp_time &&
190 if (friends_list[i].client_list[j].timestamp + BAD_NODE_TIMEOUT > temp_time &&
191 !client_in_nodelist(nodes_list, MAX_SENT_NODES,friends_list[i].client_list[j].client_id)) { 189 !client_in_nodelist(nodes_list, MAX_SENT_NODES,friends_list[i].client_list[j].client_id)) {
192 /* if node is good and not already in list. */ 190 /* if node is good and not already in list. */
193 if (num_nodes < MAX_SENT_NODES) { 191 if(num_nodes < MAX_SENT_NODES) {
194 memcpy(nodes_list[num_nodes].client_id, friends_list[i].client_list[j].client_id, CLIENT_ID_SIZE); 192 memcpy(nodes_list[num_nodes].client_id, friends_list[i].client_list[j].client_id, CLIENT_ID_SIZE);
195 nodes_list[num_nodes].ip_port = friends_list[i].client_list[j].ip_port; 193 nodes_list[num_nodes].ip_port = friends_list[i].client_list[j].ip_port;
196 num_nodes++; 194 num_nodes++;
197 } else for(k = 0; k < MAX_SENT_NODES; ++k) { 195 } else for(k = 0; k < MAX_SENT_NODES; ++k)
198 if(id_closest(client_id, nodes_list[k].client_id, friends_list[i].client_list[j].client_id) == 2) { 196 if(id_closest(client_id, nodes_list[k].client_id, friends_list[i].client_list[j].client_id) == 2) {
199 memcpy(nodes_list[k].client_id, friends_list[i].client_list[j].client_id, CLIENT_ID_SIZE); 197 memcpy(nodes_list[k].client_id, friends_list[i].client_list[j].client_id, CLIENT_ID_SIZE);
200 nodes_list[k].ip_port = friends_list[i].client_list[j].ip_port; 198 nodes_list[k].ip_port = friends_list[i].client_list[j].ip_port;
201 break; 199 break;
202 } 200 }
203 }
204 } 201 }
205 }
206 }
207
208 return num_nodes; 202 return num_nodes;
209} 203}
210 204
211/* replace first bad (or empty) node with this one 205/* replace first bad (or empty) node with this one
212 return 0 if successful 206 return 0 if successful
213 return 1 if not (list contains no bad nodes) */ 207 return 1 if not (list contains no bad nodes) */
214int replace_bad(Client_data *list, uint32_t length, uint8_t *client_id, IP_Port ip_port) /* tested */ 208int replace_bad(Client_data * list, uint32_t length, uint8_t * client_id, IP_Port ip_port) /* tested */
215{ 209{
216 uint32_t i; 210 uint32_t i;
217 uint32_t temp_time = unix_time(); 211 uint32_t temp_time = unix_time();
218 for (i = 0; i < length; ++i) { 212 for(i = 0; i < length; ++i)
219 if (list[i].timestamp + BAD_NODE_TIMEOUT < temp_time) /* if node is bad. */ { 213 if(list[i].timestamp + BAD_NODE_TIMEOUT < temp_time) /* if node is bad. */ {
220 memcpy(list[i].client_id, client_id, CLIENT_ID_SIZE); 214 memcpy(list[i].client_id, client_id, CLIENT_ID_SIZE);
221 list[i].ip_port = ip_port; 215 list[i].ip_port = ip_port;
222 list[i].timestamp = temp_time; 216 list[i].timestamp = temp_time;
@@ -225,19 +219,18 @@ int replace_bad(Client_data *list, uint32_t length, uint8_t *client_id, IP_Port
225 list[i].ret_timestamp = 0; 219 list[i].ret_timestamp = 0;
226 return 0; 220 return 0;
227 } 221 }
228 } 222
229 return 1; 223 return 1;
230
231} 224}
232 225
233/* replace the first good node that is further to the comp_client_id than that of the client_id in the list */ 226/* replace the first good node that is further to the comp_client_id than that of the client_id in the list */
234int replace_good(Client_data *list, uint32_t length, uint8_t *client_id, IP_Port ip_port, uint8_t *comp_client_id) 227int replace_good(Client_data * list, uint32_t length, uint8_t * client_id, IP_Port ip_port, uint8_t * comp_client_id)
235{ 228{
236 uint32_t i; 229 uint32_t i;
237 uint32_t temp_time = unix_time(); 230 uint32_t temp_time = unix_time();
238 231
239 for (i = 0; i < length; ++i) { 232 for(i = 0; i < length; ++i)
240 if (id_closest(comp_client_id, list[i].client_id, client_id) == 2) { 233 if(id_closest(comp_client_id, list[i].client_id, client_id) == 2) {
241 memcpy(list[i].client_id, client_id, CLIENT_ID_SIZE); 234 memcpy(list[i].client_id, client_id, CLIENT_ID_SIZE);
242 list[i].ip_port = ip_port; 235 list[i].ip_port = ip_port;
243 list[i].timestamp = temp_time; 236 list[i].timestamp = temp_time;
@@ -246,59 +239,50 @@ int replace_good(Client_data *list, uint32_t length, uint8_t *client_id, IP_Port
246 list[i].ret_timestamp = 0; 239 list[i].ret_timestamp = 0;
247 return 0; 240 return 0;
248 } 241 }
249 } 242
250 return 1; 243 return 1;
251
252} 244}
253 245
254/* Attempt to add client with ip_port and client_id to the friends client list and close_clientlist */ 246/* Attempt to add client with ip_port and client_id to the friends client list and close_clientlist */
255void addto_lists(IP_Port ip_port, uint8_t *client_id) 247void addto_lists(IP_Port ip_port, uint8_t * client_id)
256{ 248{
257 uint32_t i; 249 uint32_t i;
258 250
259 /* NOTE: current behavior if there are two clients with the same id is to replace the first ip by the second. */ 251 /* NOTE: current behavior if there are two clients with the same id is to replace the first ip by the second. */
260 if (!client_in_list(close_clientlist, LCLIENT_LIST, client_id, ip_port)) { 252 if(!client_in_list(close_clientlist, LCLIENT_LIST, client_id, ip_port))
261 if (replace_bad(close_clientlist, LCLIENT_LIST, client_id, ip_port)) 253 if(replace_bad(close_clientlist, LCLIENT_LIST, client_id, ip_port))
262 replace_good(close_clientlist, LCLIENT_LIST, client_id, ip_port, self_public_key); /* if we can't replace bad nodes we try replacing good ones */ 254 /* if we can't replace bad nodes we try replacing good ones */
263 } 255 replace_good(close_clientlist, LCLIENT_LIST, client_id, ip_port, self_public_key);
264 for(i = 0; i < num_friends; ++i) { 256
265 if(!client_in_list(friends_list[i].client_list, MAX_FRIEND_CLIENTS, client_id, ip_port)) { 257 for(i = 0; i < num_friends; ++i)
266 if(replace_bad(friends_list[i].client_list, MAX_FRIEND_CLIENTS, client_id, ip_port)) { 258 if(!client_in_list(friends_list[i].client_list, MAX_FRIEND_CLIENTS, client_id, ip_port))
259 if(replace_bad(friends_list[i].client_list, MAX_FRIEND_CLIENTS, client_id, ip_port))
267 /* if we can't replace bad nodes we try replacing good ones. */ 260 /* if we can't replace bad nodes we try replacing good ones. */
268 replace_good(friends_list[i].client_list, MAX_FRIEND_CLIENTS, client_id, ip_port, friends_list[i].client_id); 261 replace_good(friends_list[i].client_list, MAX_FRIEND_CLIENTS, client_id, ip_port, friends_list[i].client_id);
269 }
270 }
271 }
272} 262}
273 263
274/* If client_id is a friend or us, update ret_ip_port 264/* If client_id is a friend or us, update ret_ip_port
275 nodeclient_id is the id of the node that sent us this info */ 265 nodeclient_id is the id of the node that sent us this info */
276void returnedip_ports(IP_Port ip_port, uint8_t *client_id, uint8_t *nodeclient_id) 266void returnedip_ports(IP_Port ip_port, uint8_t * client_id, uint8_t * nodeclient_id)
277{ 267{
278 uint32_t i, j; 268 uint32_t i, j;
279 uint32_t temp_time = unix_time(); 269 uint32_t temp_time = unix_time();
280 if (memcmp(client_id, self_public_key, CLIENT_ID_SIZE) == 0) { 270 if(memcmp(client_id, self_public_key, CLIENT_ID_SIZE) == 0) {
281 for (i = 0; i < LCLIENT_LIST; ++i) { 271 for(i = 0; i < LCLIENT_LIST; ++i)
282 if (memcmp(nodeclient_id, close_clientlist[i].client_id, CLIENT_ID_SIZE) == 0) { 272 if(memcmp(nodeclient_id, close_clientlist[i].client_id, CLIENT_ID_SIZE) == 0) {
283 close_clientlist[i].ret_ip_port = ip_port; 273 close_clientlist[i].ret_ip_port = ip_port;
284 close_clientlist[i].ret_timestamp = temp_time; 274 close_clientlist[i].ret_timestamp = temp_time;
285 return; 275 return;
286 } 276 }
287 } 277 } else
288 } 278 for(i = 0; i < num_friends; ++i)
289 else { 279 if(memcmp(client_id, friends_list[i].client_id, CLIENT_ID_SIZE) == 0)
290 for (i = 0; i < num_friends; ++i) { 280 for(j = 0; j < MAX_FRIEND_CLIENTS; ++j)
291 if (memcmp(client_id, friends_list[i].client_id, CLIENT_ID_SIZE) == 0) { 281 if(memcmp(nodeclient_id, friends_list[i].client_list[j].client_id, CLIENT_ID_SIZE) == 0) {
292 for (j = 0; j < MAX_FRIEND_CLIENTS; ++j) { 282 friends_list[i].client_list[j].ret_ip_port = ip_port;
293 if (memcmp(nodeclient_id, friends_list[i].client_list[j].client_id, CLIENT_ID_SIZE) == 0) { 283 friends_list[i].client_list[j].ret_timestamp = temp_time;
294 friends_list[i].client_list[j].ret_ip_port = ip_port; 284 return;
295 friends_list[i].client_list[j].ret_timestamp = temp_time; 285 }
296 return;
297 }
298 }
299 }
300 }
301 }
302} 286}
303 287
304/* ping timeout in seconds */ 288/* ping timeout in seconds */
@@ -315,28 +299,21 @@ int is_pinging(IP_Port ip_port, uint64_t ping_id)
315 uint8_t pinging; 299 uint8_t pinging;
316 uint32_t temp_time = unix_time(); 300 uint32_t temp_time = unix_time();
317 301
318 for (i = 0; i < LPING_ARRAY; ++i ) { 302 for(i = 0; i < LPING_ARRAY; ++i )
319 if ((pings[i].timestamp + PING_TIMEOUT) > temp_time) { 303 if((pings[i].timestamp + PING_TIMEOUT) > temp_time) {
320 pinging = 0; 304 pinging = 0;
321 if (ip_port.ip.i != 0) { 305 if(ip_port.ip.i != 0)
322 if(pings[i].ip_port.ip.i == ip_port.ip.i && 306 if(pings[i].ip_port.ip.i == ip_port.ip.i &&
323 pings[i].ip_port.port == ip_port.port) 307 pings[i].ip_port.port == ip_port.port)
324 {
325 ++pinging; 308 ++pinging;
326 } 309 if(ping_id != 0)
327 }
328 if (ping_id != 0) {
329 if(pings[i].ping_id == ping_id) 310 if(pings[i].ping_id == ping_id)
330 ++pinging; 311 ++pinging;
331
332 }
333 if(pinging == (ping_id != 0) + (ip_port.ip.i != 0)) 312 if(pinging == (ping_id != 0) + (ip_port.ip.i != 0))
334 return 1; 313 return 1;
335 } 314 }
336 }
337 315
338 return 0; 316 return 0;
339
340} 317}
341 318
342/* Same as last function but for get_node requests. */ 319/* Same as last function but for get_node requests. */
@@ -346,26 +323,22 @@ int is_gettingnodes(IP_Port ip_port, uint64_t ping_id)
346 uint8_t pinging; 323 uint8_t pinging;
347 uint32_t temp_time = unix_time(); 324 uint32_t temp_time = unix_time();
348 325
349 for(i = 0; i < LSEND_NODES_ARRAY; ++i) { 326 for(i = 0; i < LSEND_NODES_ARRAY; ++i )
350 if ((send_nodes[i].timestamp + PING_TIMEOUT) > temp_time) { 327 if((send_nodes[i].timestamp + PING_TIMEOUT) > temp_time) {
351 pinging = 0; 328 pinging = 0;
352 if (ip_port.ip.i != 0) { 329 if(ip_port.ip.i != 0)
353 if (send_nodes[i].ip_port.ip.i == ip_port.ip.i && 330 if(send_nodes[i].ip_port.ip.i == ip_port.ip.i &&
354 send_nodes[i].ip_port.port == ip_port.port) { 331 send_nodes[i].ip_port.port == ip_port.port)
355 ++pinging; 332 ++pinging;
356 } 333 if(ping_id != 0)
357 } 334 if(send_nodes[i].ping_id == ping_id)
358 if (ping_id != 0) { 335 ++pinging;
359 if (send_nodes[i].ping_id == ping_id)
360 ++pinging;
361 }
362 if(pinging == (ping_id != 0) + (ip_port.ip.i != 0)) 336 if(pinging == (ping_id != 0) + (ip_port.ip.i != 0))
363 return 1; 337 return 1;
338
364 } 339 }
365 }
366 340
367 return 0; 341 return 0;
368
369} 342}
370 343
371/* Add a new ping request to the list of ping requests 344/* Add a new ping request to the list of ping requests
@@ -377,19 +350,17 @@ uint64_t add_pinging(IP_Port ip_port)
377 uint32_t i, j; 350 uint32_t i, j;
378 uint64_t ping_id = ((uint64_t)random_int() << 32) + random_int(); 351 uint64_t ping_id = ((uint64_t)random_int() << 32) + random_int();
379 uint32_t temp_time = unix_time(); 352 uint32_t temp_time = unix_time();
380 353
381 for (i = 0; i < PING_TIMEOUT; ++i ) { 354 for(i = 0; i < PING_TIMEOUT; ++i )
382 for (j = 0; j < LPING_ARRAY; ++j ) { 355 for(j = 0; j < LPING_ARRAY; ++j )
383 if ((pings[j].timestamp + PING_TIMEOUT - i) < temp_time) { 356 if((pings[j].timestamp + PING_TIMEOUT - i) < temp_time) {
384 pings[j].timestamp = temp_time; 357 pings[j].timestamp = temp_time;
385 pings[j].ip_port = ip_port; 358 pings[j].ip_port = ip_port;
386 pings[j].ping_id = ping_id; 359 pings[j].ping_id = ping_id;
387 return ping_id; 360 return ping_id;
388 } 361 }
389 } 362
390 }
391 return 0; 363 return 0;
392
393} 364}
394 365
395/* Same but for get node requests */ 366/* Same but for get node requests */
@@ -398,40 +369,38 @@ uint64_t add_gettingnodes(IP_Port ip_port)
398 uint32_t i, j; 369 uint32_t i, j;
399 uint64_t ping_id = ((uint64_t)random_int() << 32) + random_int(); 370 uint64_t ping_id = ((uint64_t)random_int() << 32) + random_int();
400 uint32_t temp_time = unix_time(); 371 uint32_t temp_time = unix_time();
401 372
402 for (i = 0; i < PING_TIMEOUT; ++i ) { 373 for(i = 0; i < PING_TIMEOUT; ++i )
403 for (j = 0; j < LSEND_NODES_ARRAY; ++j ) { 374 for(j = 0; j < LSEND_NODES_ARRAY; ++j )
404 if ((send_nodes[j].timestamp + PING_TIMEOUT - i) < temp_time) { 375 if((send_nodes[j].timestamp + PING_TIMEOUT - i) < temp_time) {
405 send_nodes[j].timestamp = temp_time; 376 send_nodes[j].timestamp = temp_time;
406 send_nodes[j].ip_port = ip_port; 377 send_nodes[j].ip_port = ip_port;
407 send_nodes[j].ping_id = ping_id; 378 send_nodes[j].ping_id = ping_id;
408 return ping_id; 379 return ping_id;
409 } 380 }
410 } 381
411 }
412 return 0; 382 return 0;
413
414} 383}
415 384
416/* send a ping request 385/* send a ping request
417 Ping request only works if none has been sent to that ip/port in the last 5 seconds. */ 386 Ping request only works if none has been sent to that ip/port in the last 5 seconds. */
418static int pingreq(IP_Port ip_port, uint8_t *public_key) 387static int pingreq(IP_Port ip_port, uint8_t * public_key)
419{ 388{
420 if (memcmp(public_key, self_public_key, CLIENT_ID_SIZE) == 0) /* check if packet is gonna be sent to ourself */ 389 if(memcmp(public_key, self_public_key, CLIENT_ID_SIZE) == 0) /* check if packet is gonna be sent to ourself */
421 return 1; 390 return 1;
422 391
423 if (is_pinging(ip_port, 0)) 392 if(is_pinging(ip_port, 0))
424 return 1; 393 return 1;
425 394
426 uint64_t ping_id = add_pinging(ip_port); 395 uint64_t ping_id = add_pinging(ip_port);
427 if (ping_id == 0) 396 if(ping_id == 0)
428 return 1; 397 return 1;
429 398
430 uint8_t data[1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + ENCRYPTION_PADDING]; 399 uint8_t data[1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + ENCRYPTION_PADDING];
431 uint8_t encrypt[sizeof(ping_id) + ENCRYPTION_PADDING]; 400 uint8_t encrypt[sizeof(ping_id) + ENCRYPTION_PADDING];
432 uint8_t nonce[crypto_box_NONCEBYTES]; 401 uint8_t nonce[crypto_box_NONCEBYTES];
433 random_nonce(nonce); 402 random_nonce(nonce);
434 403
435 int len = encrypt_data(public_key, self_secret_key, nonce, (uint8_t *)&ping_id, sizeof(ping_id), encrypt); 404 int len = encrypt_data(public_key, self_secret_key, nonce, (uint8_t *)&ping_id, sizeof(ping_id), encrypt);
436 if(len != sizeof(ping_id) + ENCRYPTION_PADDING) 405 if(len != sizeof(ping_id) + ENCRYPTION_PADDING)
437 return -1; 406 return -1;
@@ -439,25 +408,24 @@ static int pingreq(IP_Port ip_port, uint8_t *public_key)
439 memcpy(data + 1, self_public_key, CLIENT_ID_SIZE); 408 memcpy(data + 1, self_public_key, CLIENT_ID_SIZE);
440 memcpy(data + 1 + CLIENT_ID_SIZE, nonce, crypto_box_NONCEBYTES); 409 memcpy(data + 1 + CLIENT_ID_SIZE, nonce, crypto_box_NONCEBYTES);
441 memcpy(data + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, encrypt, len); 410 memcpy(data + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, encrypt, len);
442 411
443 return sendpacket(ip_port, data, sizeof(data)); 412 return sendpacket(ip_port, data, sizeof(data));
444
445} 413}
446 414
447/* send a ping response */ 415/* send a ping response */
448static int pingres(IP_Port ip_port, uint8_t *public_key, uint64_t ping_id) 416static int pingres(IP_Port ip_port, uint8_t * public_key, uint64_t ping_id)
449{ 417{
450 /* check if packet is gonna be sent to ourself */ 418 /* check if packet is gonna be sent to ourself */
451 if (memcmp(public_key, self_public_key, CLIENT_ID_SIZE) == 0) 419 if(memcmp(public_key, self_public_key, CLIENT_ID_SIZE) == 0)
452 return 1; 420 return 1;
453 421
454 uint8_t data[1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + ENCRYPTION_PADDING]; 422 uint8_t data[1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + ENCRYPTION_PADDING];
455 uint8_t encrypt[sizeof(ping_id) + ENCRYPTION_PADDING]; 423 uint8_t encrypt[sizeof(ping_id) + ENCRYPTION_PADDING];
456 uint8_t nonce[crypto_box_NONCEBYTES]; 424 uint8_t nonce[crypto_box_NONCEBYTES];
457 random_nonce(nonce); 425 random_nonce(nonce);
458 426
459 int len = encrypt_data(public_key, self_secret_key, nonce, (uint8_t *)&ping_id, sizeof(ping_id), encrypt); 427 int len = encrypt_data(public_key, self_secret_key, nonce, (uint8_t *)&ping_id, sizeof(ping_id), encrypt);
460 if (len != sizeof(ping_id) + ENCRYPTION_PADDING) 428 if(len != sizeof(ping_id) + ENCRYPTION_PADDING)
461 return -1; 429 return -1;
462 data[0] = 1; 430 data[0] = 1;
463 memcpy(data + 1, self_public_key, CLIENT_ID_SIZE); 431 memcpy(data + 1, self_public_key, CLIENT_ID_SIZE);
@@ -465,21 +433,21 @@ static int pingres(IP_Port ip_port, uint8_t *public_key, uint64_t ping_id)
465 memcpy(data + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, encrypt, len); 433 memcpy(data + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, encrypt, len);
466 434
467 return sendpacket(ip_port, data, sizeof(data)); 435 return sendpacket(ip_port, data, sizeof(data));
468
469} 436}
470 437
471/* send a getnodes request */ 438/* send a getnodes request */
472static int getnodes(IP_Port ip_port, uint8_t *public_key, uint8_t *client_id) 439static int getnodes(IP_Port ip_port, uint8_t * public_key, uint8_t * client_id)
473{ 440{
474 /* check if packet is gonna be sent to ourself */ 441 /* check if packet is gonna be sent to ourself */
475 if (memcmp(public_key, self_public_key, CLIENT_ID_SIZE) == 0) 442 if(memcmp(public_key, self_public_key, CLIENT_ID_SIZE) == 0)
476 return 1; 443 return 1;
477 if (is_gettingnodes(ip_port, 0)) 444
445 if(is_gettingnodes(ip_port, 0))
478 return 1; 446 return 1;
479 447
480 uint64_t ping_id = add_gettingnodes(ip_port); 448 uint64_t ping_id = add_gettingnodes(ip_port);
481 449
482 if (ping_id == 0) 450 if(ping_id == 0)
483 return 1; 451 return 1;
484 452
485 uint8_t data[1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + CLIENT_ID_SIZE + ENCRYPTION_PADDING]; 453 uint8_t data[1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + CLIENT_ID_SIZE + ENCRYPTION_PADDING];
@@ -493,31 +461,30 @@ static int getnodes(IP_Port ip_port, uint8_t *public_key, uint8_t *client_id)
493 461
494 int len = encrypt_data(public_key, self_secret_key, nonce, plain, sizeof(ping_id) + CLIENT_ID_SIZE, encrypt); 462 int len = encrypt_data(public_key, self_secret_key, nonce, plain, sizeof(ping_id) + CLIENT_ID_SIZE, encrypt);
495 463
496 if (len != sizeof(ping_id) + CLIENT_ID_SIZE + ENCRYPTION_PADDING) 464 if(len != sizeof(ping_id) + CLIENT_ID_SIZE + ENCRYPTION_PADDING)
497 return -1; 465 return -1;
498 data[0] = 2; 466 data[0] = 2;
499 memcpy(data + 1, self_public_key, CLIENT_ID_SIZE); 467 memcpy(data + 1, self_public_key, CLIENT_ID_SIZE);
500 memcpy(data + 1 + CLIENT_ID_SIZE, nonce, crypto_box_NONCEBYTES); 468 memcpy(data + 1 + CLIENT_ID_SIZE, nonce, crypto_box_NONCEBYTES);
501 memcpy(data + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, encrypt, len); 469 memcpy(data + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, encrypt, len);
502 return sendpacket(ip_port, data, sizeof(data)); 470 return sendpacket(ip_port, data, sizeof(data));
503
504} 471}
505 472
506/* send a send nodes response */ 473/* send a send nodes response */
507static int sendnodes(IP_Port ip_port, uint8_t *public_key, uint8_t *client_id, uint64_t ping_id) 474static int sendnodes(IP_Port ip_port, uint8_t * public_key, uint8_t * client_id, uint64_t ping_id)
508{ 475{
509 if (memcmp(public_key, self_public_key, CLIENT_ID_SIZE) == 0) /* check if packet is gonna be sent to ourself */ 476 if(memcmp(public_key, self_public_key, CLIENT_ID_SIZE) == 0) /* check if packet is gonna be sent to ourself */
510 return 1; 477 return 1;
511 478
512 uint8_t data[1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) 479 uint8_t data[1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id)
513 + sizeof(Node_format) * MAX_SENT_NODES + ENCRYPTION_PADDING]; 480 + sizeof(Node_format) * MAX_SENT_NODES + ENCRYPTION_PADDING];
514 481
515 Node_format nodes_list[MAX_SENT_NODES]; 482 Node_format nodes_list[MAX_SENT_NODES];
516 int num_nodes = get_close_nodes(client_id, nodes_list); 483 int num_nodes = get_close_nodes(client_id, nodes_list);
517 484
518 if (num_nodes == 0) 485 if(num_nodes == 0)
519 return 0; 486 return 0;
520 487
521 uint8_t plain[sizeof(ping_id) + sizeof(Node_format) * MAX_SENT_NODES]; 488 uint8_t plain[sizeof(ping_id) + sizeof(Node_format) * MAX_SENT_NODES];
522 uint8_t encrypt[sizeof(ping_id) + sizeof(Node_format) * MAX_SENT_NODES + ENCRYPTION_PADDING]; 489 uint8_t encrypt[sizeof(ping_id) + sizeof(Node_format) * MAX_SENT_NODES + ENCRYPTION_PADDING];
523 uint8_t nonce[crypto_box_NONCEBYTES]; 490 uint8_t nonce[crypto_box_NONCEBYTES];
@@ -529,58 +496,57 @@ static int sendnodes(IP_Port ip_port, uint8_t *public_key, uint8_t *client_id, u
529 int len = encrypt_data(public_key, self_secret_key, nonce, plain, 496 int len = encrypt_data(public_key, self_secret_key, nonce, plain,
530 sizeof(ping_id) + num_nodes * sizeof(Node_format), encrypt); 497 sizeof(ping_id) + num_nodes * sizeof(Node_format), encrypt);
531 498
532 if (len != sizeof(ping_id) + num_nodes * sizeof(Node_format) + ENCRYPTION_PADDING) 499 if(len != sizeof(ping_id) + num_nodes * sizeof(Node_format) + ENCRYPTION_PADDING)
533 return -1; 500 return -1;
534 501
535 data[0] = 3; 502 data[0] = 3;
536 memcpy(data + 1, self_public_key, CLIENT_ID_SIZE); 503 memcpy(data + 1, self_public_key, CLIENT_ID_SIZE);
537 memcpy(data + 1 + CLIENT_ID_SIZE, nonce, crypto_box_NONCEBYTES); 504 memcpy(data + 1 + CLIENT_ID_SIZE, nonce, crypto_box_NONCEBYTES);
538 memcpy(data + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, encrypt, len); 505 memcpy(data + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, encrypt, len);
539 506
540 return sendpacket(ip_port, data, 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + len); 507 return sendpacket(ip_port, data, 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + len);
541
542} 508}
543 509
544/* Packet handling functions 510/* Packet handling functions
545 One to handle each types of packets we receive 511 One to handle each types of packets we receive
546 return 0 if handled correctly, 1 if packet is bad. */ 512 return 0 if handled correctly, 1 if packet is bad. */
547int handle_pingreq(uint8_t *packet, uint32_t length, IP_Port source) 513int handle_pingreq(uint8_t * packet, uint32_t length, IP_Port source)
548{ 514{
549 uint64_t ping_id; 515 uint64_t ping_id;
550 if (length != 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + ENCRYPTION_PADDING) 516 if(length != 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + ENCRYPTION_PADDING)
551 return 1; 517 return 1;
552 /* check if packet is from ourself. */ 518 /* check if packet is from ourself. */
553 if (memcmp(packet + 1, self_public_key, CLIENT_ID_SIZE) == 0) 519 if(memcmp(packet + 1, self_public_key, CLIENT_ID_SIZE) == 0)
554 return 1; 520 return 1;
521
555 int len = decrypt_data(packet + 1, self_secret_key, packet + 1 + CLIENT_ID_SIZE, 522 int len = decrypt_data(packet + 1, self_secret_key, packet + 1 + CLIENT_ID_SIZE,
556 packet + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, 523 packet + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES,
557 sizeof(ping_id) + ENCRYPTION_PADDING, (uint8_t *)&ping_id); 524 sizeof(ping_id) + ENCRYPTION_PADDING, (uint8_t *)&ping_id);
558 if (len != sizeof(ping_id)) 525 if(len != sizeof(ping_id))
559 return 1; 526 return 1;
560 527
561 pingres(source, packet + 1, ping_id); 528 pingres(source, packet + 1, ping_id);
562 529
563 pingreq(source, packet + 1); /* TODO: make this smarter? */ 530 pingreq(source, packet + 1); /* TODO: make this smarter? */
564 531
565 return 0; 532 return 0;
566
567} 533}
568 534
569int handle_pingres(uint8_t *packet, uint32_t length, IP_Port source) 535int handle_pingres(uint8_t * packet, uint32_t length, IP_Port source)
570{ 536{
571 uint64_t ping_id; 537 uint64_t ping_id;
572 if (length != 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + ENCRYPTION_PADDING) 538 if(length != 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + ENCRYPTION_PADDING)
573 return 1; 539 return 1;
574 if (memcmp(packet + 1, self_public_key, CLIENT_ID_SIZE) == 0) /* check if packet is from ourself. */ 540 if(memcmp(packet + 1, self_public_key, CLIENT_ID_SIZE) == 0) /* check if packet is from ourself. */
575 return 1; 541 return 1;
576 542
577 int len = decrypt_data(packet + 1, self_secret_key, packet + 1 + CLIENT_ID_SIZE, 543 int len = decrypt_data(packet + 1, self_secret_key, packet + 1 + CLIENT_ID_SIZE,
578 packet + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, 544 packet + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES,
579 sizeof(ping_id) + ENCRYPTION_PADDING, (uint8_t *)&ping_id); 545 sizeof(ping_id) + ENCRYPTION_PADDING, (uint8_t *)&ping_id);
580 if (len != sizeof(ping_id)) 546 if(len != sizeof(ping_id))
581 return 1; 547 return 1;
582 548
583 if (is_pinging(source, ping_id)) { 549 if(is_pinging(source, ping_id)) {
584 addto_lists(source, packet + 1); 550 addto_lists(source, packet + 1);
585 return 0; 551 return 0;
586 } 552 }
@@ -588,29 +554,29 @@ int handle_pingres(uint8_t *packet, uint32_t length, IP_Port source)
588 554
589} 555}
590 556
591int handle_getnodes(uint8_t *packet, uint32_t length, IP_Port source) 557int handle_getnodes(uint8_t * packet, uint32_t length, IP_Port source)
592{ 558{
593 uint64_t ping_id; 559 uint64_t ping_id;
594 if (length != 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + CLIENT_ID_SIZE + ENCRYPTION_PADDING) 560 if(length != 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) + CLIENT_ID_SIZE + ENCRYPTION_PADDING)
595 return 1; 561 return 1;
596 /* check if packet is from ourself. */ 562 /* check if packet is from ourself. */
597 if (memcmp(packet + 1, self_public_key, CLIENT_ID_SIZE) == 0) 563 if(memcmp(packet + 1, self_public_key, CLIENT_ID_SIZE) == 0)
598 return 1; 564 return 1;
599 565
600 uint8_t plain[sizeof(ping_id) + CLIENT_ID_SIZE]; 566 uint8_t plain[sizeof(ping_id) + CLIENT_ID_SIZE];
601 567
602 int len = decrypt_data(packet + 1, self_secret_key, packet + 1 + CLIENT_ID_SIZE, 568 int len = decrypt_data(packet + 1, self_secret_key, packet + 1 + CLIENT_ID_SIZE,
603 packet + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, 569 packet + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES,
604 sizeof(ping_id) + CLIENT_ID_SIZE + ENCRYPTION_PADDING, plain); 570 sizeof(ping_id) + CLIENT_ID_SIZE + ENCRYPTION_PADDING, plain);
605 571
606 if (len != sizeof(ping_id) + CLIENT_ID_SIZE) 572 if(len != sizeof(ping_id) + CLIENT_ID_SIZE)
607 return 1; 573 return 1;
608 574
609 memcpy(&ping_id, plain, sizeof(ping_id)); 575 memcpy(&ping_id, plain, sizeof(ping_id));
610 sendnodes(source, packet + 1, plain + sizeof(ping_id), ping_id); 576 sendnodes(source, packet + 1, plain + sizeof(ping_id), ping_id);
611 577
612 pingreq(source, packet + 1); /* TODO: make this smarter? */ 578 pingreq(source, packet + 1); /* TODO: make this smarter? */
613 579
614 return 0; 580 return 0;
615 581
616} 582}
@@ -618,55 +584,57 @@ int handle_getnodes(uint8_t *packet, uint32_t length, IP_Port source)
618int handle_sendnodes(uint8_t * packet, uint32_t length, IP_Port source) 584int handle_sendnodes(uint8_t * packet, uint32_t length, IP_Port source)
619{ 585{
620 uint64_t ping_id; 586 uint64_t ping_id;
621 if (length > (1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) //TODO: rewrite this monstrosity 587 /* TODO: make this more readable */
588 if(length > (1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id)
622 + sizeof(Node_format) * MAX_SENT_NODES + ENCRYPTION_PADDING) || 589 + sizeof(Node_format) * MAX_SENT_NODES + ENCRYPTION_PADDING) ||
623 (length - (1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) 590 (length - (1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id)
624 + ENCRYPTION_PADDING)) % (sizeof(Node_format)) != 0 || 591 + ENCRYPTION_PADDING)) % (sizeof(Node_format)) != 0 ||
625 length < 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id) 592 length < 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES + sizeof(ping_id)
626 + sizeof(Node_format) + ENCRYPTION_PADDING) { 593 + sizeof(Node_format) + ENCRYPTION_PADDING) {
627 return 1; 594 return 1;
628 } 595 }
629 uint32_t num_nodes = (length - (1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES 596 uint32_t num_nodes = (length - (1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES
630 + sizeof(ping_id) + ENCRYPTION_PADDING)) / sizeof(Node_format); 597 + sizeof(ping_id) + ENCRYPTION_PADDING)) / sizeof(Node_format);
631 598
632 uint8_t plain[sizeof(ping_id) + sizeof(Node_format) * MAX_SENT_NODES]; 599 uint8_t plain[sizeof(ping_id) + sizeof(Node_format) * MAX_SENT_NODES];
633 600
634 int len = decrypt_data(packet + 1, self_secret_key, packet + 1 + CLIENT_ID_SIZE, 601 int len = decrypt_data(packet + 1, self_secret_key, packet + 1 + CLIENT_ID_SIZE,
635 packet + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES, 602 packet + 1 + CLIENT_ID_SIZE + crypto_box_NONCEBYTES,
636 sizeof(ping_id) + num_nodes * sizeof(Node_format) + ENCRYPTION_PADDING, plain); 603 sizeof(ping_id) + num_nodes * sizeof(Node_format) + ENCRYPTION_PADDING, plain);
637 604
638 605 if(len != sizeof(ping_id) + num_nodes * sizeof(Node_format))
639 if (len != sizeof(ping_id) + num_nodes * sizeof(Node_format))
640 return 1; 606 return 1;
607
641 memcpy(&ping_id, plain, sizeof(ping_id)); 608 memcpy(&ping_id, plain, sizeof(ping_id));
642 if(!is_gettingnodes(source, ping_id)) 609 if(!is_gettingnodes(source, ping_id))
643 return 1; 610 return 1;
644 611
645 Node_format nodes_list[MAX_SENT_NODES]; 612 Node_format nodes_list[MAX_SENT_NODES];
646 memcpy(nodes_list, plain + sizeof(ping_id), num_nodes * sizeof(Node_format)); 613 memcpy(nodes_list, plain + sizeof(ping_id), num_nodes * sizeof(Node_format));
647 614
648 addto_lists(source, packet + 1); 615 addto_lists(source, packet + 1);
649 616
650 uint32_t i; 617 uint32_t i;
651 for (i = 0; i < num_nodes; ++i) 618 for(i = 0; i < num_nodes; ++i) {
652 pingreq(nodes_list[i].ip_port, nodes_list[i].client_id); 619 pingreq(nodes_list[i].ip_port, nodes_list[i].client_id);
653 returnedip_ports(nodes_list[i].ip_port, nodes_list[i].client_id, packet + 1); 620 returnedip_ports(nodes_list[i].ip_port, nodes_list[i].client_id, packet + 1);
654 621 }
622
655 return 0; 623 return 0;
656} 624}
657 625
658/* END of packet handling functions */ 626/* END of packet handling functions */
659 627
660int DHT_addfriend(uint8_t *client_id) 628int DHT_addfriend(uint8_t * client_id)
661{ 629{
662 Friend * temp; 630 Friend * temp;
663 if (num_friends == 0) 631 if(num_friends == 0)
664 temp = malloc(sizeof(Friend)); 632 temp = malloc(sizeof(Friend));
665 else 633 else
666 temp = realloc(friends_list, sizeof(Friend) * (num_friends + 1)); 634 temp = realloc(friends_list, sizeof(Friend) * (num_friends + 1));
667 if (temp == NULL) 635 if(temp == NULL)
668 return 1; 636 return 1;
669 637
670 friends_list = temp; 638 friends_list = temp;
671 memset(&friends_list[num_friends], 0, sizeof(Friend)); 639 memset(&friends_list[num_friends], 0, sizeof(Friend));
672 memcpy(friends_list[num_friends].client_id, client_id, CLIENT_ID_SIZE); 640 memcpy(friends_list[num_friends].client_id, client_id, CLIENT_ID_SIZE);
@@ -675,43 +643,41 @@ int DHT_addfriend(uint8_t *client_id)
675 return 0; 643 return 0;
676} 644}
677 645
678int DHT_delfriend(uint8_t *client_id) 646int DHT_delfriend(uint8_t * client_id)
679{ 647{
680 uint32_t i; 648 uint32_t i;
681 Friend * temp; 649 Friend * temp;
682 for (i = 0; i < num_friends; ++i) { 650 for(i = 0; i < num_friends; ++i)
683 /* Equal */ 651 /* Equal */
684 if (memcmp(friends_list[i].client_id, client_id, CLIENT_ID_SIZE) == 0){ 652 if(memcmp(friends_list[i].client_id, client_id, CLIENT_ID_SIZE) == 0) {
685 --num_friends; 653 --num_friends;
686 if (num_friends != i) 654 if(num_friends != i)
687 memcpy(friends_list[i].client_id, friends_list[num_friends].client_id, CLIENT_ID_SIZE); 655 memcpy(friends_list[i].client_id, friends_list[num_friends].client_id, CLIENT_ID_SIZE);
688 temp = realloc(friends_list, sizeof(Friend) * (num_friends)); 656 temp = realloc(friends_list, sizeof(Friend) * (num_friends));
689 if (temp != NULL) 657 if(temp != NULL)
690 friends_list = temp; 658 friends_list = temp;
691 return 0; 659 return 0;
692 } 660 }
693 } 661
694 return 1; 662 return 1;
695} 663}
696 664
697/* TODO: Optimize this. */ 665/* TODO: Optimize this. */
698IP_Port DHT_getfriendip(uint8_t *client_id) 666IP_Port DHT_getfriendip(uint8_t * client_id)
699{ 667{
700 uint32_t i, j; 668 uint32_t i, j;
701 IP_Port empty = {{{0}}, 0}; 669 IP_Port empty = {{{0}}, 0};
702 uint32_t temp_time = unix_time(); 670 uint32_t temp_time = unix_time();
703 for (i = 0; i < num_friends; ++i) { 671 for(i = 0; i < num_friends; ++i)
704 /* Equal */ 672 /* Equal */
705 if(memcmp(friends_list[i].client_id, client_id, CLIENT_ID_SIZE) == 0) { 673 if(memcmp(friends_list[i].client_id, client_id, CLIENT_ID_SIZE) == 0) {
706 for(j = 0; j < MAX_FRIEND_CLIENTS; ++j) { 674 for(j = 0; j < MAX_FRIEND_CLIENTS; ++j)
707 if(memcmp(friends_list[i].client_list[j].client_id, client_id, CLIENT_ID_SIZE) == 0 && 675 if(memcmp(friends_list[i].client_list[j].client_id, client_id, CLIENT_ID_SIZE) == 0 &&
708 friends_list[i].client_list[j].timestamp + BAD_NODE_TIMEOUT > temp_time) { 676 friends_list[i].client_list[j].timestamp + BAD_NODE_TIMEOUT > temp_time)
709 return friends_list[i].client_list[j].ip_port; 677 return friends_list[i].client_list[j].ip_port;
710 } 678
711 }
712 return empty; 679 return empty;
713 } 680 }
714 }
715 empty.ip.i = 1; 681 empty.ip.i = 1;
716 return empty; 682 return empty;
717 683
@@ -735,21 +701,20 @@ void doDHTFriends()
735 uint32_t rand_node; 701 uint32_t rand_node;
736 uint32_t index[MAX_FRIEND_CLIENTS]; 702 uint32_t index[MAX_FRIEND_CLIENTS];
737 703
738 for (i = 0; i < num_friends; ++i) { 704 for(i = 0; i < num_friends; ++i) {
739 uint32_t num_nodes = 0; 705 uint32_t num_nodes = 0;
740 for (j = 0; j < MAX_FRIEND_CLIENTS; ++j) { 706 for(j = 0; j < MAX_FRIEND_CLIENTS; ++j)
741 if (friends_list[i].client_list[j].timestamp + Kill_NODE_TIMEOUT > temp_time) /* if node is not dead. */ { 707 if(friends_list[i].client_list[j].timestamp + Kill_NODE_TIMEOUT > temp_time) /* if node is not dead. */ {
742 if ((friends_list[i].client_list[j].last_pinged + PING_INTERVAL) <= temp_time) { 708 if((friends_list[i].client_list[j].last_pinged + PING_INTERVAL) <= temp_time) {
743 pingreq(friends_list[i].client_list[j].ip_port, friends_list[i].client_list[j].client_id); 709 pingreq(friends_list[i].client_list[j].ip_port, friends_list[i].client_list[j].client_id);
744 friends_list[i].client_list[j].last_pinged = temp_time; 710 friends_list[i].client_list[j].last_pinged = temp_time;
745 } 711 }
746 if (friends_list[i].client_list[j].timestamp + BAD_NODE_TIMEOUT > temp_time) /* if node is good. */ { 712 if(friends_list[i].client_list[j].timestamp + BAD_NODE_TIMEOUT > temp_time) /* if node is good. */ {
747 index[num_nodes] = j; 713 index[num_nodes] = j;
748 ++num_nodes; 714 ++num_nodes;
749 } 715 }
750 } 716 }
751 } 717 if(friends_list[i].lastgetnode + GET_NODE_INTERVAL <= temp_time && num_nodes != 0) {
752 if (friends_list[i].lastgetnode + GET_NODE_INTERVAL <= temp_time && num_nodes != 0) {
753 rand_node = rand() % num_nodes; 718 rand_node = rand() % num_nodes;
754 getnodes(friends_list[i].client_list[index[rand_node]].ip_port, 719 getnodes(friends_list[i].client_list[index[rand_node]].ip_port,
755 friends_list[i].client_list[index[rand_node]].client_id, 720 friends_list[i].client_list[index[rand_node]].client_id,
@@ -771,23 +736,21 @@ void doClose() /* tested */
771 uint32_t rand_node; 736 uint32_t rand_node;
772 uint32_t index[LCLIENT_LIST]; 737 uint32_t index[LCLIENT_LIST];
773 738
774 for (i = 0; i < LCLIENT_LIST; ++i) { 739 for(i = 0; i < LCLIENT_LIST; ++i)
775 /* if node is not dead. */ 740 /* if node is not dead. */
776 if (close_clientlist[i].timestamp + Kill_NODE_TIMEOUT > temp_time) { 741 if(close_clientlist[i].timestamp + Kill_NODE_TIMEOUT > temp_time) {
777 if ((close_clientlist[i].last_pinged + PING_INTERVAL) <= temp_time) 742 if((close_clientlist[i].last_pinged + PING_INTERVAL) <= temp_time) {
778 {
779 pingreq(close_clientlist[i].ip_port, close_clientlist[i].client_id); 743 pingreq(close_clientlist[i].ip_port, close_clientlist[i].client_id);
780 close_clientlist[i].last_pinged = temp_time; 744 close_clientlist[i].last_pinged = temp_time;
781 } 745 }
782 /* if node is good. */ 746 /* if node is good. */
783 if (close_clientlist[i].timestamp + BAD_NODE_TIMEOUT > temp_time) { 747 if(close_clientlist[i].timestamp + BAD_NODE_TIMEOUT > temp_time) {
784 index[num_nodes] = i; 748 index[num_nodes] = i;
785 ++num_nodes; 749 ++num_nodes;
786 } 750 }
787 } 751 }
788 }
789 752
790 if (close_lastgetnodes + GET_NODE_INTERVAL <= temp_time && num_nodes != 0) { 753 if(close_lastgetnodes + GET_NODE_INTERVAL <= temp_time && num_nodes != 0) {
791 rand_node = rand() % num_nodes; 754 rand_node = rand() % num_nodes;
792 getnodes(close_clientlist[index[rand_node]].ip_port, 755 getnodes(close_clientlist[index[rand_node]].ip_port,
793 close_clientlist[index[rand_node]].client_id, 756 close_clientlist[index[rand_node]].client_id,
@@ -796,21 +759,19 @@ void doClose() /* tested */
796 } 759 }
797} 760}
798 761
799void DHT_bootstrap(IP_Port ip_port, uint8_t *public_key) 762void DHT_bootstrap(IP_Port ip_port, uint8_t * public_key)
800{ 763{
801 getnodes(ip_port, public_key, self_public_key); 764 getnodes(ip_port, public_key, self_public_key);
802} 765}
803 766
804/* send the given packet to node with client_id 767/* send the given packet to node with client_id
805 returns -1 if failure */ 768 returns -1 if failure */
806int route_packet(uint8_t *client_id, uint8_t *packet, uint32_t length) 769int route_packet(uint8_t * client_id, uint8_t * packet, uint32_t length)
807{ 770{
808 uint32_t i; 771 uint32_t i;
809 for (i = 0; i < LCLIENT_LIST; ++i) { 772 for(i = 0; i < LCLIENT_LIST; ++i)
810 if (memcmp(client_id, close_clientlist[i].client_id, CLIENT_ID_SIZE) == 0) { 773 if(memcmp(client_id, close_clientlist[i].client_id, CLIENT_ID_SIZE) == 0)
811 return sendpacket(close_clientlist[i].ip_port, packet, length); 774 return sendpacket(close_clientlist[i].ip_port, packet, length);
812 }
813 }
814 return -1; 775 return -1;
815} 776}
816 777
@@ -819,48 +780,43 @@ int route_packet(uint8_t *client_id, uint8_t *packet, uint32_t length)
819 returns the number of ips returned 780 returns the number of ips returned
820 return 0 if we are connected to friend or if no ips were found. 781 return 0 if we are connected to friend or if no ips were found.
821 returns -1 if no such friend*/ 782 returns -1 if no such friend*/
822static int friend_iplist(IP_Port *ip_portlist, uint16_t friend_num) 783static int friend_iplist(IP_Port * ip_portlist, uint16_t friend_num)
823{ 784{
824 int num_ips = 0; 785 int num_ips = 0;
825 uint32_t i; 786 uint32_t i;
826 uint32_t temp_time = unix_time(); 787 uint32_t temp_time = unix_time();
827 if (friend_num >= num_friends) 788 if(friend_num >= num_friends)
828 return -1; 789 return -1;
829 for (i = 0; i < MAX_FRIEND_CLIENTS; ++i) { 790 for(i = 0; i < MAX_FRIEND_CLIENTS; ++i)
830 /*If ip is not zero and node is good */ 791 /*If ip is not zero and node is good */
831 if (friends_list[friend_num].client_list[i].ret_ip_port.ip.i != 0 && 792 if(friends_list[friend_num].client_list[i].ret_ip_port.ip.i != 0 &&
832 friends_list[friend_num].client_list[i].ret_timestamp + BAD_NODE_TIMEOUT > temp_time) 793 friends_list[friend_num].client_list[i].ret_timestamp + BAD_NODE_TIMEOUT > temp_time) {
833 { 794 if(memcmp(friends_list[friend_num].client_list[i].client_id, friends_list[friend_num].client_id, CLIENT_ID_SIZE) == 0 )
834 if (memcmp(friends_list[friend_num].client_list[i].client_id, friends_list[friend_num].client_id, CLIENT_ID_SIZE) == 0)
835 return 0; 795 return 0;
836 ip_portlist[num_ips] = friends_list[friend_num].client_list[i].ret_ip_port; 796 ip_portlist[num_ips] = friends_list[friend_num].client_list[i].ret_ip_port;
837 ++num_ips; 797 ++num_ips;
838 } 798 }
839 }
840 return num_ips; 799 return num_ips;
841} 800}
842 801
843/* Send the following packet to everyone who tells us they are connected to friend_id 802/* Send the following packet to everyone who tells us they are connected to friend_id
844 returns the number of nodes it sent the packet to */ 803 returns the number of nodes it sent the packet to */
845int route_tofriend(uint8_t * friend_id, uint8_t *packet, uint32_t length) 804int route_tofriend(uint8_t * friend_id, uint8_t * packet, uint32_t length)
846{ 805{
847 uint32_t i, j; 806 uint32_t i, j;
848 uint32_t sent = 0; 807 uint32_t sent = 0;
849 uint32_t temp_time = unix_time(); 808 uint32_t temp_time = unix_time();
850 for (i = 0; i < num_friends; ++i) { 809 for(i = 0; i < num_friends; ++i)
851 /* Equal */ 810 /* Equal */
852 if (memcmp(friends_list[i].client_id, friend_id, CLIENT_ID_SIZE) == 0) { 811 if(memcmp(friends_list[i].client_id, friend_id, CLIENT_ID_SIZE) == 0) {
853 for (j = 0; j < MAX_FRIEND_CLIENTS; ++j) { 812 for(j = 0; j < MAX_FRIEND_CLIENTS; ++j)
854 /*If ip is not zero and node is good */ 813 /*If ip is not zero and node is good */
855 if(friends_list[i].client_list[j].ret_ip_port.ip.i != 0 && 814 if(friends_list[i].client_list[j].ret_ip_port.ip.i != 0 &&
856 friends_list[i].client_list[j].ret_timestamp + BAD_NODE_TIMEOUT > temp_time) { 815 friends_list[i].client_list[j].ret_timestamp + BAD_NODE_TIMEOUT > temp_time)
857 if(sendpacket(friends_list[i].client_list[j].ip_port, packet, length) == length) 816 if(sendpacket(friends_list[i].client_list[j].ip_port, packet, length) == length)
858 ++sent; 817 ++sent;
859 }
860 }
861 return sent; 818 return sent;
862 } 819 }
863 }
864 return 0; 820 return 0;
865} 821}
866 822
@@ -869,28 +825,24 @@ int route_tofriend(uint8_t * friend_id, uint8_t *packet, uint32_t length)
869int routeone_tofriend(uint8_t * friend_id, uint8_t * packet, uint32_t length) 825int routeone_tofriend(uint8_t * friend_id, uint8_t * packet, uint32_t length)
870{ 826{
871 int num = friend_number(friend_id); 827 int num = friend_number(friend_id);
872 if(num == -1) { 828 if(num == -1)
873 return 0; 829 return 0;
874 }
875 830
876 IP_Port ip_list[MAX_FRIEND_CLIENTS]; 831 IP_Port ip_list[MAX_FRIEND_CLIENTS];
877 int n = 0; 832 int n = 0;
878 uint32_t i; 833 uint32_t i;
879 uint32_t temp_time = unix_time(); 834 uint32_t temp_time = unix_time();
880 for(i = 0; i < MAX_FRIEND_CLIENTS; ++i) { 835 for(i = 0; i < MAX_FRIEND_CLIENTS; ++i)
881 /*If ip is not zero and node is good */ 836 /*If ip is not zero and node is good */
882 if(friends_list[num].client_list[i].ret_ip_port.ip.i != 0 && 837 if(friends_list[num].client_list[i].ret_ip_port.ip.i != 0 &&
883 friends_list[num].client_list[i].ret_timestamp + BAD_NODE_TIMEOUT > temp_time) { 838 friends_list[num].client_list[i].ret_timestamp + BAD_NODE_TIMEOUT > temp_time) {
884 ip_list[n] = friends_list[num].client_list[i].ip_port; 839 ip_list[n] = friends_list[num].client_list[i].ip_port;
885 ++n; 840 ++n;
886 } 841 }
887 } 842 if(n < 1)
888 if(n < 1) {
889 return 0; 843 return 0;
890 } 844 if(sendpacket(ip_list[rand() % n], packet, length) == length)
891 if(sendpacket(ip_list[rand() % n], packet, length) == length) {
892 return 1; 845 return 1;
893 }
894 return 0; 846 return 0;
895} 847}
896 848
@@ -903,12 +855,10 @@ int friend_ips(IP_Port * ip_portlist, uint8_t * friend_id)
903{ 855{
904 856
905 uint32_t i; 857 uint32_t i;
906 for(i = 0; i < num_friends; ++i) { 858 for(i = 0; i < num_friends; ++i)
907 /* Equal */ 859 /* Equal */
908 if(memcmp(friends_list[i].client_id, friend_id, CLIENT_ID_SIZE) == 0) { 860 if(memcmp(friends_list[i].client_id, friend_id, CLIENT_ID_SIZE) == 0)
909 return friend_iplist(ip_portlist, i); 861 return friend_iplist(ip_portlist, i);
910 }
911 }
912 return -1; 862 return -1;
913} 863}
914 864
@@ -922,19 +872,17 @@ int send_NATping(uint8_t * public_key, uint64_t ping_id, uint8_t type)
922 872
923 uint8_t packet[MAX_DATA_SIZE]; 873 uint8_t packet[MAX_DATA_SIZE];
924 int len = create_request(packet, public_key, data, sizeof(uint64_t) + 1, 254); /* 254 is NAT ping request packet id */ 874 int len = create_request(packet, public_key, data, sizeof(uint64_t) + 1, 254); /* 254 is NAT ping request packet id */
925 if(len == -1) { 875 if(len == -1)
926 return -1; 876 return -1;
927 } 877
928 int num = 0; 878 int num = 0;
929 if(type == 0) { 879
880 if(type == 0)
930 num = route_tofriend(public_key, packet, len);/*If packet is request use many people to route it*/ 881 num = route_tofriend(public_key, packet, len);/*If packet is request use many people to route it*/
931 } 882 else if(type == 1)
932 else if(type == 1) {
933 num = routeone_tofriend(public_key, packet, len);/*If packet is response use only one person to route it*/ 883 num = routeone_tofriend(public_key, packet, len);/*If packet is response use only one person to route it*/
934 } 884 if(num == 0)
935 if(num == 0) {
936 return -1; 885 return -1;
937 }
938 return num; 886 return num;
939} 887}
940 888
@@ -942,44 +890,37 @@ int send_NATping(uint8_t * public_key, uint64_t ping_id, uint8_t type)
942int handle_NATping(uint8_t * packet, uint32_t length, IP_Port source) 890int handle_NATping(uint8_t * packet, uint32_t length, IP_Port source)
943{ 891{
944 if(length <= crypto_box_PUBLICKEYBYTES * 2 + crypto_box_NONCEBYTES + 1 + ENCRYPTION_PADDING && 892 if(length <= crypto_box_PUBLICKEYBYTES * 2 + crypto_box_NONCEBYTES + 1 + ENCRYPTION_PADDING &&
945 length > MAX_DATA_SIZE + ENCRYPTION_PADDING) { 893 length > MAX_DATA_SIZE + ENCRYPTION_PADDING)
946 return 1; 894 return 1;
947 }
948 /* check if request is for us. */ 895 /* check if request is for us. */
949 if(memcmp(packet + 1, self_public_key, crypto_box_PUBLICKEYBYTES) == 0) { 896 if(memcmp(packet + 1, self_public_key, crypto_box_PUBLICKEYBYTES) == 0) {
950 uint8_t public_key[crypto_box_PUBLICKEYBYTES]; 897 uint8_t public_key[crypto_box_PUBLICKEYBYTES];
951 uint8_t data[MAX_DATA_SIZE]; 898 uint8_t data[MAX_DATA_SIZE];
952 int len = handle_request(public_key, data, packet, length); 899 int len = handle_request(public_key, data, packet, length);
953 if(len != sizeof(uint64_t) + 1) { 900 if(len != sizeof(uint64_t) + 1)
954 return 1; 901 return 1;
955 }
956 uint64_t ping_id; 902 uint64_t ping_id;
957 memcpy(&ping_id, data + 1, sizeof(uint64_t)); 903 memcpy(&ping_id, data + 1, sizeof(uint64_t));
958 904
959 int friendnumber = friend_number(public_key); 905 int friendnumber = friend_number(public_key);
960 if(friendnumber == -1) { 906 if(friendnumber == -1)
961 return 1; 907 return 1;
962 }
963 908
964 if(data[0] == 0) { 909 if(data[0] == 0) {
965 send_NATping(public_key, ping_id, 1);/*1 is reply*/ 910 send_NATping(public_key, ping_id, 1); /*1 is reply*/
966 return 0; 911 return 0;
967 } else if (data[0] == 1) { 912 } else if (data[0] == 1)
968 if(friends_list[friendnumber].NATping_id == ping_id) 913 if(friends_list[friendnumber].NATping_id == ping_id) {
969 {
970 friends_list[friendnumber].NATping_id = ((uint64_t)random_int() << 32) + random_int(); 914 friends_list[friendnumber].NATping_id = ((uint64_t)random_int() << 32) + random_int();
971 friends_list[friendnumber].hole_punching = 1; 915 friends_list[friendnumber].hole_punching = 1;
972 return 0; 916 return 0;
973 } 917 }
974 }
975 return 1; 918 return 1;
976 } 919 }
977 /* if request is not for us, try routing it. */ 920 /* if request is not for us, try routing it. */
978 else { 921 else
979 if(route_packet(packet + 1, packet, length) == length) { 922 if(route_packet(packet + 1, packet, length) == length)
980 return 0; 923 return 0;
981 }
982 }
983 return 0; 924 return 0;
984} 925}
985 926
@@ -990,21 +931,17 @@ int handle_NATping(uint8_t * packet, uint32_t length, IP_Port source)
990static IP NAT_commonip(IP_Port * ip_portlist, uint16_t len, uint16_t min_num) 931static IP NAT_commonip(IP_Port * ip_portlist, uint16_t len, uint16_t min_num)
991{ 932{
992 IP zero = {{0}}; 933 IP zero = {{0}};
993 if(len > MAX_FRIEND_CLIENTS) { 934 if(len > MAX_FRIEND_CLIENTS)
994 return zero; 935 return zero;
995 }
996 936
997 uint32_t i, j; 937 uint32_t i, j;
998 uint16_t numbers[MAX_FRIEND_CLIENTS] = {0}; 938 uint16_t numbers[MAX_FRIEND_CLIENTS] = {0};
999 for(i = 0; i < len; ++i) { 939 for(i = 0; i < len; ++i) {
1000 for(j = 0; j < len; ++j) { 940 for(j = 0; j < len; ++j)
1001 if(ip_portlist[i].ip.i == ip_portlist[j].ip.i) { 941 if(ip_portlist[i].ip.i == ip_portlist[j].ip.i)
1002 ++numbers[i]; 942 ++numbers[i];
1003 } 943 if(numbers[i] >= min_num)
1004 }
1005 if(numbers[i] >= min_num) {
1006 return ip_portlist[i].ip; 944 return ip_portlist[i].ip;
1007 }
1008 } 945 }
1009 return zero; 946 return zero;
1010} 947}
@@ -1017,12 +954,11 @@ static uint16_t NAT_getports(uint16_t * portlist, IP_Port * ip_portlist, uint16_
1017{ 954{
1018 uint32_t i; 955 uint32_t i;
1019 uint16_t num = 0; 956 uint16_t num = 0;
1020 for(i = 0; i < len; ++i) { 957 for(i = 0; i < len; ++i)
1021 if(ip_portlist[i].ip.i == ip.i) { 958 if(ip_portlist[i].ip.i == ip.i) {
1022 portlist[num] = ntohs(ip_portlist[i].port); 959 portlist[num] = ntohs(ip_portlist[i].port);
1023 ++num; 960 ++num;
1024 } 961 }
1025 }
1026 return num; 962 return num;
1027} 963}
1028 964
@@ -1030,9 +966,8 @@ static uint16_t NAT_getports(uint16_t * portlist, IP_Port * ip_portlist, uint16_
1030 966
1031static void punch_holes(IP ip, uint16_t * port_list, uint16_t numports, uint16_t friend_num) 967static void punch_holes(IP ip, uint16_t * port_list, uint16_t numports, uint16_t friend_num)
1032{ 968{
1033 if(numports > MAX_FRIEND_CLIENTS || numports == 0) { 969 if(numports > MAX_FRIEND_CLIENTS || numports == 0)
1034 return; 970 return;
1035 }
1036 uint32_t i; 971 uint32_t i;
1037 uint32_t top = friends_list[friend_num].punching_index + MAX_PUNCHING_PORTS; 972 uint32_t top = friends_list[friend_num].punching_index + MAX_PUNCHING_PORTS;
1038 for(i = friends_list[friend_num].punching_index; i != top; i++) { 973 for(i = friends_list[friend_num].punching_index; i != top; i++) {
@@ -1055,9 +990,9 @@ static void doNAT()
1055 IP_Port ip_list[MAX_FRIEND_CLIENTS]; 990 IP_Port ip_list[MAX_FRIEND_CLIENTS];
1056 int num = friend_iplist(ip_list, i); 991 int num = friend_iplist(ip_list, i);
1057 /*If we are connected to friend or if friend is not online don't try to hole punch with him*/ 992 /*If we are connected to friend or if friend is not online don't try to hole punch with him*/
1058 if(num < MAX_FRIEND_CLIENTS/2) { 993 if(num < MAX_FRIEND_CLIENTS/2)
1059 continue; 994 continue;
1060 } 995
1061 if(friends_list[i].hole_punching != 1) { 996 if(friends_list[i].hole_punching != 1) {
1062 if(friends_list[i].NATping_timestamp + PUNCH_INTERVAL < temp_time) { 997 if(friends_list[i].NATping_timestamp + PUNCH_INTERVAL < temp_time) {
1063 send_NATping(friends_list[i].client_id, friends_list[i].NATping_id, 0); /*0 is request*/ 998 send_NATping(friends_list[i].client_id, friends_list[i].NATping_id, 0); /*0 is request*/
@@ -1066,9 +1001,9 @@ static void doNAT()
1066 } 1001 }
1067 else if(friends_list[i].punching_timestamp + PUNCH_INTERVAL < temp_time) { 1002 else if(friends_list[i].punching_timestamp + PUNCH_INTERVAL < temp_time) {
1068 IP ip = NAT_commonip(ip_list, num, MAX_FRIEND_CLIENTS/2); 1003 IP ip = NAT_commonip(ip_list, num, MAX_FRIEND_CLIENTS/2);
1069 if(ip.i == 0) { 1004 if(ip.i == 0)
1070 continue; 1005 continue;
1071 } 1006
1072 uint16_t port_list[MAX_FRIEND_CLIENTS]; 1007 uint16_t port_list[MAX_FRIEND_CLIENTS];
1073 uint16_t numports = NAT_getports(port_list, ip_list, num, ip); 1008 uint16_t numports = NAT_getports(port_list, ip_list, num, ip);
1074 punch_holes(ip, port_list, numports, i); 1009 punch_holes(ip, port_list, numports, i);
@@ -1105,7 +1040,6 @@ int DHT_handlepacket(uint8_t * packet, uint32_t length, IP_Port source)
1105 } 1040 }
1106 1041
1107 return 0; 1042 return 0;
1108
1109} 1043}
1110 1044
1111void doDHT() 1045void doDHT()
@@ -1133,12 +1067,10 @@ void DHT_save(uint8_t * data)
1133 return 0 if success */ 1067 return 0 if success */
1134int DHT_load(uint8_t * data, uint32_t size) 1068int DHT_load(uint8_t * data, uint32_t size)
1135{ 1069{
1136 if(size < sizeof(close_clientlist)) { 1070 if(size < sizeof(close_clientlist))
1137 return -1; 1071 return -1;
1138 } 1072 if((size - sizeof(close_clientlist)) % sizeof(Friend) != 0)
1139 if((size - sizeof(close_clientlist)) % sizeof(Friend) != 0) {
1140 return -1; 1073 return -1;
1141 }
1142 uint32_t i, j; 1074 uint32_t i, j;
1143 /* uint32_t temp_time = unix_time(); */ 1075 /* uint32_t temp_time = unix_time(); */
1144 uint16_t temp; 1076 uint16_t temp;
@@ -1150,21 +1082,18 @@ int DHT_load(uint8_t * data, uint32_t size)
1150 1082
1151 for(i = 0; i < temp; ++i) { 1083 for(i = 0; i < temp; ++i) {
1152 DHT_addfriend(tempfriends_list[i].client_id); 1084 DHT_addfriend(tempfriends_list[i].client_id);
1153 for(j = 0; j < MAX_FRIEND_CLIENTS; ++j) { 1085 for(j = 0; j < MAX_FRIEND_CLIENTS; ++j)
1154 if(tempfriends_list[i].client_list[j].timestamp != 0) { 1086 if(tempfriends_list[i].client_list[j].timestamp != 0) {
1155 getnodes(tempfriends_list[i].client_list[j].ip_port, 1087 getnodes(tempfriends_list[i].client_list[j].ip_port,
1156 tempfriends_list[i].client_list[j].client_id, tempfriends_list[i].client_id); 1088 tempfriends_list[i].client_list[j].client_id, tempfriends_list[i].client_id);
1157 } 1089 }
1158 }
1159 } 1090 }
1160 } 1091 }
1161 Client_data * tempclose_clientlist = (Client_data *)data; 1092 Client_data * tempclose_clientlist = (Client_data *)data;
1162 1093
1163 for(i = 0; i < LCLIENT_LIST; ++i) { 1094 for(i = 0; i < LCLIENT_LIST; ++i)
1164 if(tempclose_clientlist[i].timestamp != 0) { 1095 if(tempclose_clientlist[i].timestamp != 0)
1165 DHT_bootstrap(tempclose_clientlist[i].ip_port, tempclose_clientlist[i].client_id); 1096 DHT_bootstrap(tempclose_clientlist[i].ip_port, tempclose_clientlist[i].client_id);
1166 }
1167 }
1168 return 0; 1097 return 0;
1169} 1098}
1170 1099
@@ -1174,10 +1103,8 @@ int DHT_isconnected()
1174{ 1103{
1175 uint32_t i; 1104 uint32_t i;
1176 uint32_t temp_time = unix_time(); 1105 uint32_t temp_time = unix_time();
1177 for(i = 0; i < LCLIENT_LIST; ++i) { 1106 for(i = 0; i < LCLIENT_LIST; ++i)
1178 if(close_clientlist[i].timestamp + BAD_NODE_TIMEOUT > temp_time) { 1107 if(close_clientlist[i].timestamp + BAD_NODE_TIMEOUT > temp_time)
1179 return 1; 1108 return 1;
1180 }
1181 }
1182 return 0; 1109 return 0;
1183} \ No newline at end of file 1110}
diff --git a/core/network.c b/core/network.c
index 160db880..8804ab4e 100644
--- a/core/network.c
+++ b/core/network.c
@@ -156,7 +156,10 @@ int init_networking(IP ip, uint16_t port)
156void shutdown_networking() 156void shutdown_networking()
157{ 157{
158 #ifdef WIN32 158 #ifdef WIN32
159 closesocket(sock);
159 WSACleanup(); 160 WSACleanup();
161 #else
162 close(sock);
160 #endif 163 #endif
161 return; 164 return;
162} 165}
diff --git a/core/network.h b/core/network.h
index 8b22a09c..a59d7c38 100644
--- a/core/network.h
+++ b/core/network.h
@@ -48,6 +48,7 @@
48#include <sys/time.h> 48#include <sys/time.h>
49#include <sys/types.h> 49#include <sys/types.h>
50#include <netdb.h> 50#include <netdb.h>
51#include <unistd.h>
51 52
52#endif 53#endif
53 54