mirror of
https://github.com/irungentoo/toxcore.git
synced 2024-03-22 13:30:51 +08:00
Some work on the onion part done.
This commit is contained in:
parent
d46891c3b7
commit
7e2d21271a
|
@ -10,7 +10,7 @@
|
|||
#include <time.h>
|
||||
|
||||
#include "../toxcore/onion.h"
|
||||
|
||||
#include "../toxcore/onion_announce.h"
|
||||
|
||||
void do_onion(Onion *onion)
|
||||
{
|
||||
|
@ -26,7 +26,7 @@ static int handle_test_1(void *object, IP_Port source, uint8_t *packet, uint32_t
|
|||
if (memcmp(packet, "Install Gentoo", sizeof("Install Gentoo")) != 0)
|
||||
return 1;
|
||||
|
||||
if (send_onion_response(onion->net, source, "install gentoo", sizeof("install gentoo"),
|
||||
if (send_onion_response(onion->net, source, (uint8_t *)"install gentoo", sizeof("install gentoo"),
|
||||
packet + sizeof("Install Gentoo")) == -1)
|
||||
return 1;
|
||||
|
||||
|
@ -40,12 +40,13 @@ static int handle_test_2(void *object, IP_Port source, uint8_t *packet, uint32_t
|
|||
if (length != sizeof("install Gentoo"))
|
||||
return 1;
|
||||
|
||||
if (memcmp(packet, "install gentoo", sizeof("install gentoo")) != 0)
|
||||
if (memcmp(packet, (uint8_t *)"install gentoo", sizeof("install gentoo")) != 0)
|
||||
return 1;
|
||||
|
||||
handled_test_2 = 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
START_TEST(test_basic)
|
||||
{
|
||||
IP ip;
|
||||
|
@ -71,7 +72,7 @@ START_TEST(test_basic)
|
|||
nodes[1] = n2;
|
||||
nodes[2] = n1;
|
||||
nodes[3] = n2;
|
||||
int ret = send_onion_packet(onion1, nodes, "Install Gentoo", sizeof("Install Gentoo"));
|
||||
int ret = send_onion_packet(onion1, nodes, (uint8_t *)"Install Gentoo", sizeof("Install Gentoo"));
|
||||
ck_assert_msg(ret == 0, "Failed to create/send onion packet.");
|
||||
|
||||
handled_test_1 = 0;
|
||||
|
@ -91,6 +92,12 @@ START_TEST(test_basic)
|
|||
}
|
||||
END_TEST
|
||||
|
||||
START_TEST(test_announce)
|
||||
{
|
||||
|
||||
|
||||
}
|
||||
END_TEST
|
||||
|
||||
#define DEFTESTCASE(NAME) \
|
||||
TCase *tc_##NAME = tcase_create(#NAME); \
|
||||
|
@ -105,6 +112,7 @@ Suite *onion_suite(void)
|
|||
Suite *s = suite_create("Onion");
|
||||
|
||||
DEFTESTCASE_SLOW(basic, 5);
|
||||
DEFTESTCASE_SLOW(announce, 5);
|
||||
return s;
|
||||
}
|
||||
|
||||
|
|
|
@ -104,8 +104,9 @@ encrypted (with our real long term private key if we want to announce ourselves,
|
|||
add the part used to send data to our list (if the list is full make it replace the furthest entry))
|
||||
|
||||
data to route request packet:
|
||||
[uint8_t packet id (133)][public key of destination node][nonce][temporary just generated public key]encrypted with that temporary private key and the nonce:[data]
|
||||
(if Node D contains the used to send data for, it sends the stuff in this packet as a data to route response packet to the right node)
|
||||
[uint8_t packet id (133)][public key of destination node][nonce][temporary just generated public key]
|
||||
encrypted with that temporary private key and the nonce and the real public key of the destination node:[data]
|
||||
(if Node D contains the ret data for the node, it sends the stuff in this packet as a data to route response packet to the right node)
|
||||
|
||||
Data sent to us:
|
||||
announce response packet:
|
||||
|
@ -114,8 +115,8 @@ encrypted with the DHT private key of Node D, the public key in the request and
|
|||
(if the ping id is zero, it means the information to reach the client id we are searching for is stored on this node)
|
||||
|
||||
data to route response packet:
|
||||
[uint8_t packet id (134)][nonce]encrypted with that temporary private key and the nonce:[data]
|
||||
|
||||
[uint8_t packet id (134)][nonce][temporary just generated public key]
|
||||
encrypted with that temporary private key and the nonce and the real public key of the destination node:[data]
|
||||
Onion packet (response):
|
||||
|
||||
initial (sent from node D to node C):
|
||||
|
|
|
@ -31,6 +31,8 @@ libtoxcore_la_SOURCES = ../toxcore/DHT.h \
|
|||
../toxcore/assoc.c \
|
||||
../toxcore/onion.h \
|
||||
../toxcore/onion.c \
|
||||
../toxcore/onion_announce.h \
|
||||
../toxcore/onion_announce.c \
|
||||
../toxcore/misc_tools.h
|
||||
|
||||
libtoxcore_la_CFLAGS = -I$(top_srcdir) \
|
||||
|
|
|
@ -20,6 +20,9 @@
|
|||
*
|
||||
*/
|
||||
|
||||
#ifndef ONION_H
|
||||
#define ONION_H
|
||||
|
||||
#include "DHT.h"
|
||||
|
||||
typedef struct {
|
||||
|
@ -58,3 +61,6 @@ int send_onion_response(Networking_Core *net, IP_Port dest, uint8_t *data, uint3
|
|||
Onion *new_onion(DHT *dht);
|
||||
|
||||
void kill_onion(Onion *onion);
|
||||
|
||||
|
||||
#endif
|
||||
|
|
|
@ -34,6 +34,8 @@
|
|||
#define ANNOUNCE_RESPONSE_MIN_SIZE (1 + crypto_box_NONCEBYTES + PING_ID_SIZE + crypto_box_MACBYTES)
|
||||
#define ANNOUNCE_RESPONSE_MAX_SIZE (ANNOUNCE_RESPONSE_MIN_SIZE + sizeof(Node_format)*MAX_SENT_NODES)
|
||||
|
||||
#define DATA_REQUEST_MIN_SIZE (1 + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES + crypto_box_PUBLICKEYBYTES + crypto_box_MACBYTES + ONION_RETURN_3)
|
||||
|
||||
/* Generate a ping_id and put it in ping_id */
|
||||
static void generate_ping_id(Onion_Announce *onion_a, uint64_t time, uint8_t *public_key, uint8_t *ret,
|
||||
uint8_t *ping_id)
|
||||
|
@ -47,26 +49,89 @@ static void generate_ping_id(Onion_Announce *onion_a, uint64_t time, uint8_t *pu
|
|||
crypto_hash_sha256(ping_id, data, sizeof(data));
|
||||
}
|
||||
|
||||
/* check if public key is in entries list
|
||||
*
|
||||
* return -1 if no
|
||||
* return position in list if yes
|
||||
*/
|
||||
static int in_entries(Onion_Announce *onion_a, uint8_t *public_key)
|
||||
{
|
||||
uint32_t i;
|
||||
|
||||
for (i = 0; i < ONION_ANNOUNCE_MAX_ENTRIES; ++i) {
|
||||
if (!is_timeout(onion_a->entries[i].time, ONION_ANNOUNCE_TIMEOUT)
|
||||
&& memcpy(onion_a->entries[i].public_key, public_key, crypto_box_PUBLICKEYBYTES) == 0)
|
||||
return i;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
uint8_t cmp_public_key[crypto_box_PUBLICKEYBYTES];
|
||||
static int cmp_entry(const void *a, const void *b)
|
||||
{
|
||||
Onion_Announce_Entry entry1, entry2;
|
||||
memcpy(&entry1, a, sizeof(Onion_Announce_Entry));
|
||||
memcpy(&entry2, b, sizeof(Onion_Announce_Entry));
|
||||
int t1 = is_timeout(entry1.time, ONION_ANNOUNCE_TIMEOUT);
|
||||
int t2 = is_timeout(entry2.time, ONION_ANNOUNCE_TIMEOUT);
|
||||
|
||||
if (t1 && t2)
|
||||
return 0;
|
||||
|
||||
if (t1)
|
||||
return -1;
|
||||
|
||||
if (t2)
|
||||
return 1;
|
||||
|
||||
int close = id_closest(cmp_public_key, entry1.public_key, entry2.public_key);
|
||||
|
||||
if (close == 1)
|
||||
return 1;
|
||||
|
||||
if (close == 2)
|
||||
return -1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* add entry to entries list
|
||||
*
|
||||
* return 0 if failure
|
||||
* return 1 if added
|
||||
*/
|
||||
static int add_to_entries(Onion_Announce *onion_a, uint8_t *public_key, uint8_t *ret)
|
||||
static int add_to_entries(Onion_Announce *onion_a, IP_Port ret_ip_port, uint8_t *public_key, uint8_t *ret)
|
||||
{
|
||||
|
||||
return 0;
|
||||
}
|
||||
int pos = in_entries(onion_a, public_key);
|
||||
|
||||
/* check if public key is in entries list
|
||||
*
|
||||
* return 0 if no
|
||||
* return 1 if yes
|
||||
*/
|
||||
static int in_entries(Onion_Announce *onion_a, uint8_t *public_key)
|
||||
{
|
||||
uint32_t i;
|
||||
|
||||
return 0;
|
||||
if (pos == -1) {
|
||||
for (i = 0; i < ONION_ANNOUNCE_MAX_ENTRIES; ++i) {
|
||||
if (is_timeout(onion_a->entries[i].time, ONION_ANNOUNCE_TIMEOUT))
|
||||
pos = i;
|
||||
}
|
||||
}
|
||||
|
||||
if (pos == -1) {
|
||||
if (id_closest(onion_a->dht->self_public_key, public_key, onion_a->entries[0].public_key) == 1)
|
||||
pos = 0;
|
||||
}
|
||||
|
||||
if (pos == -1)
|
||||
return 0;
|
||||
|
||||
|
||||
memcpy(onion_a->entries[pos].public_key, public_key, crypto_box_PUBLICKEYBYTES);
|
||||
onion_a->entries[pos].ret_ip_port = ret_ip_port;
|
||||
memcpy(onion_a->entries[pos].ret, ret, ONION_RETURN_3);
|
||||
onion_a->entries[pos].time = unix_time();
|
||||
|
||||
memcpy(cmp_public_key, onion_a->dht->self_public_key, crypto_box_PUBLICKEYBYTES);
|
||||
qsort(onion_a->entries, ONION_ANNOUNCE_MAX_ENTRIES, sizeof(Onion_Announce_Entry), cmp_entry);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int handle_announce_request(void *object, IP_Port source, uint8_t *packet, uint32_t length)
|
||||
|
@ -95,10 +160,10 @@ static int handle_announce_request(void *object, IP_Port source, uint8_t *packet
|
|||
int stored = 0;
|
||||
|
||||
if (memcmp(ping_id1, plain, PING_ID_SIZE) == 0 || memcmp(ping_id2, plain, PING_ID_SIZE) == 0) {
|
||||
stored = add_to_entries(onion_a, packet + 1 + crypto_box_NONCEBYTES,
|
||||
stored = add_to_entries(onion_a, source, packet + 1 + crypto_box_NONCEBYTES,
|
||||
packet + (ANNOUNCE_REQUEST_SIZE - ONION_RETURN_3));
|
||||
} else {
|
||||
stored = in_entries(onion_a, plain + PING_ID_SIZE);
|
||||
stored = (in_entries(onion_a, plain + PING_ID_SIZE) != -1);
|
||||
}
|
||||
|
||||
/*Respond with a announce response packet*/
|
||||
|
@ -138,6 +203,25 @@ static int handle_data_request(void *object, IP_Port source, uint8_t *packet, ui
|
|||
{
|
||||
Onion_Announce *onion_a = object;
|
||||
|
||||
if (length <= DATA_REQUEST_MIN_SIZE)
|
||||
return 1;
|
||||
|
||||
if (length >= MAX_DATA_SIZE)
|
||||
return 1;
|
||||
|
||||
int index = in_entries(onion_a, packet + 1);
|
||||
|
||||
if (index == -1)
|
||||
return 1;
|
||||
|
||||
uint8_t data[length - (crypto_box_PUBLICKEYBYTES + ONION_RETURN_3)];
|
||||
data[0] = NET_PACKET_ONION_DATA_RESPONSE;
|
||||
memcpy(data + 1, packet + 1 + crypto_box_PUBLICKEYBYTES, length - (1 + crypto_box_PUBLICKEYBYTES + ONION_RETURN_3));
|
||||
|
||||
if (send_onion_response(onion_a->net, onion_a->entries[index].ret_ip_port, data, sizeof(data),
|
||||
onion_a->entries[index].ret) == -1)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -20,17 +20,25 @@
|
|||
*
|
||||
*/
|
||||
|
||||
#ifndef ONION_ANNOUNCE_H
|
||||
#define ONION_ANNOUNCE_H
|
||||
|
||||
#include "onion.h"
|
||||
|
||||
#define ONION_ANNOUNCE_MAX_ENTRIES 32
|
||||
#define ONION_ANNOUNCE_TIMEOUT 300
|
||||
|
||||
typedef struct {
|
||||
uint8_t public_key[crypto_box_PUBLICKEYBYTES];
|
||||
IP_Port ret_ip_port;
|
||||
uint8_t ret[ONION_RETURN_3];
|
||||
uint64_t time;
|
||||
} Onion_Announce_Entry;
|
||||
|
||||
typedef struct {
|
||||
DHT *dht;
|
||||
Networking_Core *net;
|
||||
struct {
|
||||
uint8_t public_key[crypto_box_PUBLICKEYBYTES];
|
||||
IP_Port first;
|
||||
uint8_t ret[ONION_RETURN_3];
|
||||
} entries[ONION_ANNOUNCE_MAX_ENTRIES];
|
||||
Onion_Announce_Entry entries[ONION_ANNOUNCE_MAX_ENTRIES];
|
||||
/* This is crypto_secretbox_KEYBYTES long just so we can use new_symmetric_key() to fill it */
|
||||
uint8_t secret_bytes[crypto_secretbox_KEYBYTES];
|
||||
} Onion_Announce;
|
||||
|
@ -40,3 +48,6 @@ typedef struct {
|
|||
Onion_Announce *new_onion_announce(DHT *dht);
|
||||
|
||||
void kill_onion_announce(Onion_Announce *onion_a);
|
||||
|
||||
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue
Block a user