summaryrefslogtreecommitdiff
path: root/toxcore/onion_announce.c
diff options
context:
space:
mode:
Diffstat (limited to 'toxcore/onion_announce.c')
-rw-r--r--toxcore/onion_announce.c63
1 files changed, 39 insertions, 24 deletions
diff --git a/toxcore/onion_announce.c b/toxcore/onion_announce.c
index 3e4f7e0a..8150974b 100644
--- a/toxcore/onion_announce.c
+++ b/toxcore/onion_announce.c
@@ -29,7 +29,7 @@
29 29
30#define PING_ID_TIMEOUT 20 30#define PING_ID_TIMEOUT 20
31 31
32#define ANNOUNCE_REQUEST_SIZE (1 + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES + ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH + crypto_box_MACBYTES) 32#define ANNOUNCE_REQUEST_SIZE (1 + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES + ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + crypto_box_PUBLICKEYBYTES + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH + crypto_box_MACBYTES)
33#define ANNOUNCE_REQUEST_SIZE_RECV (ANNOUNCE_REQUEST_SIZE + ONION_RETURN_3) 33#define ANNOUNCE_REQUEST_SIZE_RECV (ANNOUNCE_REQUEST_SIZE + ONION_RETURN_3)
34 34
35#define DATA_REQUEST_MIN_SIZE (1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES + crypto_box_MACBYTES) 35#define DATA_REQUEST_MIN_SIZE (1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES + crypto_box_MACBYTES)
@@ -43,6 +43,7 @@
43 * public_key and secret_key is the kepair which will be used to encrypt the request. 43 * public_key and secret_key is the kepair which will be used to encrypt the request.
44 * ping_id is the ping id that will be sent in the request. 44 * ping_id is the ping id that will be sent in the request.
45 * client_id is the client id of the node we are searching for. 45 * client_id is the client id of the node we are searching for.
46 * data_public_key is the public key we want others to encrypt their data packets with.
46 * sendback_data is the data of ONION_ANNOUNCE_SENDBACK_DATA_LENGTH length that we expect to 47 * sendback_data is the data of ONION_ANNOUNCE_SENDBACK_DATA_LENGTH length that we expect to
47 * receive back in the response. 48 * receive back in the response.
48 * 49 *
@@ -50,12 +51,14 @@
50 * return 0 on success. 51 * return 0 on success.
51 */ 52 */
52int send_announce_request(DHT *dht, Node_format *nodes, uint8_t *public_key, uint8_t *secret_key, uint8_t *ping_id, 53int send_announce_request(DHT *dht, Node_format *nodes, uint8_t *public_key, uint8_t *secret_key, uint8_t *ping_id,
53 uint8_t *client_id, uint8_t *sendback_data) 54 uint8_t *client_id, uint8_t *data_public_key, uint8_t *sendback_data)
54{ 55{
55 uint8_t plain[ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH]; 56 uint8_t plain[ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + crypto_box_PUBLICKEYBYTES + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH];
56 memcpy(plain, ping_id, ONION_PING_ID_SIZE); 57 memcpy(plain, ping_id, ONION_PING_ID_SIZE);
57 memcpy(plain + ONION_PING_ID_SIZE, client_id, crypto_box_PUBLICKEYBYTES); 58 memcpy(plain + ONION_PING_ID_SIZE, client_id, crypto_box_PUBLICKEYBYTES);
58 memcpy(plain + ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES, sendback_data, ONION_ANNOUNCE_SENDBACK_DATA_LENGTH); 59 memcpy(plain + ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES, data_public_key, crypto_box_PUBLICKEYBYTES);
60 memcpy(plain + ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + crypto_box_PUBLICKEYBYTES, sendback_data,
61 ONION_ANNOUNCE_SENDBACK_DATA_LENGTH);
59 uint8_t packet[ANNOUNCE_REQUEST_SIZE]; 62 uint8_t packet[ANNOUNCE_REQUEST_SIZE];
60 packet[0] = NET_PACKET_ANNOUNCE_REQUEST; 63 packet[0] = NET_PACKET_ANNOUNCE_REQUEST;
61 new_nonce(packet + 1); 64 new_nonce(packet + 1);
@@ -78,12 +81,15 @@ int send_announce_request(DHT *dht, Node_format *nodes, uint8_t *public_key, uin
78 * send the packet to that person in the form of a response) 81 * send the packet to that person in the form of a response)
79 * 82 *
80 * public_key is the real public key of the node which we want to send the data of length length to. 83 * public_key is the real public key of the node which we want to send the data of length length to.
84 * encrypt_public_key is the public key used to encrypt the data packet.
85 *
81 * nonce is the nonce to encrypt this packet with 86 * nonce is the nonce to encrypt this packet with
82 * 87 *
83 * return -1 on failure. 88 * return -1 on failure.
84 * return 0 on success. 89 * return 0 on success.
85 */ 90 */
86int send_data_request(DHT *dht, Node_format *nodes, uint8_t *public_key, uint8_t *nonce, uint8_t *data, uint16_t length) 91int send_data_request(DHT *dht, Node_format *nodes, uint8_t *public_key, uint8_t *encrypt_public_key, uint8_t *nonce,
92 uint8_t *data, uint16_t length)
87{ 93{
88 uint8_t packet[DATA_REQUEST_MIN_SIZE + length]; 94 uint8_t packet[DATA_REQUEST_MIN_SIZE + length];
89 packet[0] = NET_PACKET_ONION_DATA_REQUEST; 95 packet[0] = NET_PACKET_ONION_DATA_REQUEST;
@@ -96,7 +102,7 @@ int send_data_request(DHT *dht, Node_format *nodes, uint8_t *public_key, uint8_t
96 102
97 memcpy(packet + 1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES, random_public_key, crypto_box_PUBLICKEYBYTES); 103 memcpy(packet + 1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES, random_public_key, crypto_box_PUBLICKEYBYTES);
98 104
99 int len = encrypt_data(public_key, random_secret_key, packet + 1 + crypto_box_PUBLICKEYBYTES, 105 int len = encrypt_data(encrypt_public_key, random_secret_key, packet + 1 + crypto_box_PUBLICKEYBYTES,
100 data, length, packet + 1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES); 106 data, length, packet + 1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES);
101 107
102 if (1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES + (uint32_t)len != sizeof(packet)) 108 if (1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES + (uint32_t)len != sizeof(packet))
@@ -167,10 +173,11 @@ static int cmp_entry(const void *a, const void *b)
167 173
168/* add entry to entries list 174/* add entry to entries list
169 * 175 *
170 * return 0 if failure 176 * return -1 if failure
171 * return 1 if added 177 * return position if added
172 */ 178 */
173static int add_to_entries(Onion_Announce *onion_a, IP_Port ret_ip_port, uint8_t *public_key, uint8_t *ret) 179static int add_to_entries(Onion_Announce *onion_a, IP_Port ret_ip_port, uint8_t *public_key, uint8_t *data_public_key,
180 uint8_t *ret)
174{ 181{
175 182
176 int pos = in_entries(onion_a, public_key); 183 int pos = in_entries(onion_a, public_key);
@@ -190,16 +197,17 @@ static int add_to_entries(Onion_Announce *onion_a, IP_Port ret_ip_port, uint8_t
190 } 197 }
191 198
192 if (pos == -1) 199 if (pos == -1)
193 return 0; 200 return -1;
194 201
195 memcpy(onion_a->entries[pos].public_key, public_key, crypto_box_PUBLICKEYBYTES); 202 memcpy(onion_a->entries[pos].public_key, public_key, crypto_box_PUBLICKEYBYTES);
196 onion_a->entries[pos].ret_ip_port = ret_ip_port; 203 onion_a->entries[pos].ret_ip_port = ret_ip_port;
197 memcpy(onion_a->entries[pos].ret, ret, ONION_RETURN_3); 204 memcpy(onion_a->entries[pos].ret, ret, ONION_RETURN_3);
205 memcpy(onion_a->entries[pos].data_public_key, data_public_key, crypto_box_PUBLICKEYBYTES);
198 onion_a->entries[pos].time = unix_time(); 206 onion_a->entries[pos].time = unix_time();
199 207
200 memcpy(cmp_public_key, onion_a->dht->self_public_key, crypto_box_PUBLICKEYBYTES); 208 memcpy(cmp_public_key, onion_a->dht->self_public_key, crypto_box_PUBLICKEYBYTES);
201 qsort(onion_a->entries, ONION_ANNOUNCE_MAX_ENTRIES, sizeof(Onion_Announce_Entry), cmp_entry); 209 qsort(onion_a->entries, ONION_ANNOUNCE_MAX_ENTRIES, sizeof(Onion_Announce_Entry), cmp_entry);
202 return 1; 210 return pos;
203} 211}
204 212
205static int handle_announce_request(void *object, IP_Port source, uint8_t *packet, uint32_t length) 213static int handle_announce_request(void *object, IP_Port source, uint8_t *packet, uint32_t length)
@@ -209,10 +217,11 @@ static int handle_announce_request(void *object, IP_Port source, uint8_t *packet
209 if (length != ANNOUNCE_REQUEST_SIZE_RECV) 217 if (length != ANNOUNCE_REQUEST_SIZE_RECV)
210 return 1; 218 return 1;
211 219
212 uint8_t plain[ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH]; 220 uint8_t plain[ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + crypto_box_PUBLICKEYBYTES + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH];
213 int len = decrypt_data(packet + 1 + crypto_box_NONCEBYTES, onion_a->dht->self_secret_key, packet + 1, 221 int len = decrypt_data(packet + 1 + crypto_box_NONCEBYTES, onion_a->dht->self_secret_key, packet + 1,
214 packet + 1 + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES, 222 packet + 1 + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES,
215 ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH + crypto_box_MACBYTES, plain); 223 ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + crypto_box_PUBLICKEYBYTES + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH +
224 crypto_box_MACBYTES, plain);
216 225
217 if ((uint32_t)len != sizeof(plain)) 226 if ((uint32_t)len != sizeof(plain))
218 return 1; 227 return 1;
@@ -223,13 +232,14 @@ static int handle_announce_request(void *object, IP_Port source, uint8_t *packet
223 uint8_t ping_id2[ONION_PING_ID_SIZE]; 232 uint8_t ping_id2[ONION_PING_ID_SIZE];
224 generate_ping_id(onion_a, unix_time() + PING_ID_TIMEOUT, packet + 1 + crypto_box_NONCEBYTES, source, ping_id2); 233 generate_ping_id(onion_a, unix_time() + PING_ID_TIMEOUT, packet + 1 + crypto_box_NONCEBYTES, source, ping_id2);
225 234
226 int stored = 0; 235 int index = -1;
227 236
228 if (memcmp(ping_id1, plain, ONION_PING_ID_SIZE) == 0 || memcmp(ping_id2, plain, ONION_PING_ID_SIZE) == 0) { 237 if (memcmp(ping_id1, plain, ONION_PING_ID_SIZE) == 0 || memcmp(ping_id2, plain, ONION_PING_ID_SIZE) == 0) {
229 stored = add_to_entries(onion_a, source, packet + 1 + crypto_box_NONCEBYTES, 238 index = add_to_entries(onion_a, source, packet + 1 + crypto_box_NONCEBYTES,
230 packet + (ANNOUNCE_REQUEST_SIZE_RECV - ONION_RETURN_3)); 239 plain + ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES,
240 packet + (ANNOUNCE_REQUEST_SIZE_RECV - ONION_RETURN_3));
231 } else { 241 } else {
232 stored = (in_entries(onion_a, plain + ONION_PING_ID_SIZE) != -1); 242 index = in_entries(onion_a, plain + ONION_PING_ID_SIZE);
233 } 243 }
234 244
235 /*Respond with a announce response packet*/ 245 /*Respond with a announce response packet*/
@@ -245,24 +255,29 @@ static int handle_announce_request(void *object, IP_Port source, uint8_t *packet
245 uint8_t nonce[crypto_box_NONCEBYTES]; 255 uint8_t nonce[crypto_box_NONCEBYTES];
246 new_nonce(nonce); 256 new_nonce(nonce);
247 257
248 uint8_t pl[ONION_PING_ID_SIZE + sizeof(nodes_list)] = {0}; 258 uint8_t pl[1 + ONION_PING_ID_SIZE + sizeof(nodes_list)];
249 259
250 if (!stored) { 260 if (index == -1) {
251 memcpy(pl, ping_id2, ONION_PING_ID_SIZE); 261 pl[0] = 0;
262 memcpy(pl + 1, ping_id2, ONION_PING_ID_SIZE);
263 } else {
264 pl[0] = 1;
265 memcpy(pl + 1, onion_a->entries[index].data_public_key, crypto_box_PUBLICKEYBYTES);
252 } 266 }
253 267
254 memcpy(pl + ONION_PING_ID_SIZE, nodes_list, num_nodes * sizeof(Node_format)); 268 memcpy(pl + 1 + ONION_PING_ID_SIZE, nodes_list, num_nodes * sizeof(Node_format));
255 269
256 uint8_t data[ONION_ANNOUNCE_RESPONSE_MAX_SIZE]; 270 uint8_t data[ONION_ANNOUNCE_RESPONSE_MAX_SIZE];
257 len = encrypt_data(packet + 1 + crypto_box_NONCEBYTES, onion_a->dht->self_secret_key, nonce, pl, 271 len = encrypt_data(packet + 1 + crypto_box_NONCEBYTES, onion_a->dht->self_secret_key, nonce, pl,
258 ONION_PING_ID_SIZE + num_nodes * sizeof(Node_format), 272 1 + ONION_PING_ID_SIZE + num_nodes * sizeof(Node_format),
259 data + 1 + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH + crypto_box_NONCEBYTES); 273 data + 1 + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH + crypto_box_NONCEBYTES);
260 274
261 if ((uint32_t)len != ONION_PING_ID_SIZE + num_nodes * sizeof(Node_format) + crypto_box_MACBYTES) 275 if ((uint32_t)len != 1 + ONION_PING_ID_SIZE + num_nodes * sizeof(Node_format) + crypto_box_MACBYTES)
262 return 1; 276 return 1;
263 277
264 data[0] = NET_PACKET_ANNOUNCE_RESPONSE; 278 data[0] = NET_PACKET_ANNOUNCE_RESPONSE;
265 memcpy(data + 1, plain + ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES, ONION_ANNOUNCE_SENDBACK_DATA_LENGTH); 279 memcpy(data + 1, plain + ONION_PING_ID_SIZE + crypto_box_PUBLICKEYBYTES + crypto_box_PUBLICKEYBYTES,
280 ONION_ANNOUNCE_SENDBACK_DATA_LENGTH);
266 memcpy(data + 1 + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH, nonce, crypto_box_NONCEBYTES); 281 memcpy(data + 1 + ONION_ANNOUNCE_SENDBACK_DATA_LENGTH, nonce, crypto_box_NONCEBYTES);
267 282
268 if (send_onion_response(onion_a->net, source, data, 283 if (send_onion_response(onion_a->net, source, data,