ffi-tox 0.1.1 → 0.1.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (153) hide show
  1. checksums.yaml +4 -4
  2. data/ProjectTox-Core/AUTHORS +0 -0
  3. data/ProjectTox-Core/ChangeLog +0 -0
  4. data/ProjectTox-Core/INSTALL +370 -0
  5. data/ProjectTox-Core/INSTALL.md +455 -56
  6. data/ProjectTox-Core/Makefile.am +35 -0
  7. data/ProjectTox-Core/NEWS +0 -0
  8. data/ProjectTox-Core/README +43 -0
  9. data/ProjectTox-Core/README.md +34 -44
  10. data/ProjectTox-Core/auto_tests/Makefile.inc +110 -0
  11. data/ProjectTox-Core/auto_tests/TCP_test.c +519 -0
  12. data/ProjectTox-Core/auto_tests/assoc_test.c +160 -0
  13. data/ProjectTox-Core/auto_tests/crypto_test.c +302 -0
  14. data/ProjectTox-Core/auto_tests/dht_test.c +362 -0
  15. data/ProjectTox-Core/auto_tests/encryptsave_test.c +104 -0
  16. data/ProjectTox-Core/auto_tests/friends_test.c +238 -0
  17. data/ProjectTox-Core/auto_tests/helpers.h +15 -0
  18. data/ProjectTox-Core/auto_tests/messenger_test.c +365 -0
  19. data/ProjectTox-Core/auto_tests/network_test.c +171 -0
  20. data/ProjectTox-Core/auto_tests/onion_test.c +363 -0
  21. data/ProjectTox-Core/auto_tests/skeleton_test.c +49 -0
  22. data/ProjectTox-Core/auto_tests/tox_test.c +454 -0
  23. data/ProjectTox-Core/auto_tests/toxav_basic_test.c +597 -0
  24. data/ProjectTox-Core/auto_tests/toxav_many_test.c +402 -0
  25. data/ProjectTox-Core/autogen.sh +6 -0
  26. data/ProjectTox-Core/build/Makefile.am +14 -0
  27. data/ProjectTox-Core/configure.ac +694 -0
  28. data/ProjectTox-Core/dist-build/android-arm.sh +3 -0
  29. data/ProjectTox-Core/dist-build/android-armv7.sh +3 -0
  30. data/ProjectTox-Core/dist-build/android-build.sh +59 -0
  31. data/ProjectTox-Core/dist-build/android-mips.sh +3 -0
  32. data/ProjectTox-Core/dist-build/android-x86.sh +3 -0
  33. data/ProjectTox-Core/docs/Group-Chats.md +71 -0
  34. data/ProjectTox-Core/docs/Hardening.txt +60 -0
  35. data/ProjectTox-Core/docs/Hardening_docs.txt +30 -0
  36. data/ProjectTox-Core/docs/Prevent_Tracking.txt +160 -0
  37. data/ProjectTox-Core/docs/TCP_Network.txt +154 -0
  38. data/ProjectTox-Core/docs/TODO +62 -0
  39. data/ProjectTox-Core/docs/Tox_middle_level_network_protocol.txt +120 -0
  40. data/ProjectTox-Core/docs/av_api.md +194 -0
  41. data/ProjectTox-Core/libtoxav.pc.in +11 -0
  42. data/ProjectTox-Core/libtoxcore.pc.in +11 -0
  43. data/ProjectTox-Core/m4/ax_have_epoll.m4 +104 -0
  44. data/ProjectTox-Core/m4/ax_pthread.m4 +317 -0
  45. data/ProjectTox-Core/m4/pkg.m4 +199 -0
  46. data/ProjectTox-Core/other/DHT_bootstrap.c +121 -58
  47. data/ProjectTox-Core/other/DHTnodes +3 -0
  48. data/ProjectTox-Core/other/Makefile.inc +20 -0
  49. data/ProjectTox-Core/other/bootstrap_node_packets.c +65 -0
  50. data/ProjectTox-Core/other/tox.png +0 -0
  51. data/ProjectTox-Core/testing/DHT_test.c +170 -98
  52. data/ProjectTox-Core/testing/Makefile.inc +112 -0
  53. data/ProjectTox-Core/testing/Messenger_test.c +133 -69
  54. data/ProjectTox-Core/testing/dns3_test.c +115 -0
  55. data/ProjectTox-Core/testing/misc_tools.c +59 -13
  56. data/ProjectTox-Core/testing/nTox.c +1127 -264
  57. data/ProjectTox-Core/testing/nTox.h +10 -19
  58. data/ProjectTox-Core/testing/tox_shell.c +159 -0
  59. data/ProjectTox-Core/testing/tox_sync.c +299 -0
  60. data/ProjectTox-Core/tools/README +11 -0
  61. data/ProjectTox-Core/tools/astylerc +11 -0
  62. data/ProjectTox-Core/tools/pre-commit +17 -0
  63. data/ProjectTox-Core/toxav/Makefile.inc +36 -0
  64. data/ProjectTox-Core/toxav/codec.c +357 -0
  65. data/ProjectTox-Core/toxav/codec.h +116 -0
  66. data/ProjectTox-Core/toxav/msi.c +1949 -0
  67. data/ProjectTox-Core/toxav/msi.h +267 -0
  68. data/ProjectTox-Core/toxav/rtp.c +600 -0
  69. data/ProjectTox-Core/toxav/rtp.h +196 -0
  70. data/ProjectTox-Core/toxav/toxav.c +1148 -0
  71. data/ProjectTox-Core/toxav/toxav.h +389 -0
  72. data/ProjectTox-Core/toxcore/DHT.c +2521 -0
  73. data/ProjectTox-Core/toxcore/DHT.h +412 -0
  74. data/ProjectTox-Core/toxcore/LAN_discovery.c +322 -0
  75. data/ProjectTox-Core/{core → toxcore}/LAN_discovery.h +17 -12
  76. data/ProjectTox-Core/toxcore/Makefile.inc +67 -0
  77. data/ProjectTox-Core/toxcore/Messenger.c +3006 -0
  78. data/ProjectTox-Core/toxcore/Messenger.h +818 -0
  79. data/ProjectTox-Core/toxcore/TCP_client.c +858 -0
  80. data/ProjectTox-Core/toxcore/TCP_client.h +156 -0
  81. data/ProjectTox-Core/toxcore/TCP_server.c +1332 -0
  82. data/ProjectTox-Core/toxcore/TCP_server.h +181 -0
  83. data/ProjectTox-Core/toxcore/assoc.c +1033 -0
  84. data/ProjectTox-Core/toxcore/assoc.h +104 -0
  85. data/ProjectTox-Core/toxcore/crypto_core.c +278 -0
  86. data/ProjectTox-Core/toxcore/crypto_core.h +151 -0
  87. data/ProjectTox-Core/toxcore/friend_requests.c +175 -0
  88. data/ProjectTox-Core/toxcore/friend_requests.h +83 -0
  89. data/ProjectTox-Core/toxcore/group_chats.c +837 -0
  90. data/ProjectTox-Core/toxcore/group_chats.h +199 -0
  91. data/ProjectTox-Core/toxcore/list.c +256 -0
  92. data/ProjectTox-Core/toxcore/list.h +85 -0
  93. data/ProjectTox-Core/toxcore/logger.c +153 -0
  94. data/ProjectTox-Core/toxcore/logger.h +84 -0
  95. data/ProjectTox-Core/toxcore/misc_tools.h +70 -0
  96. data/ProjectTox-Core/toxcore/net_crypto.c +2753 -0
  97. data/ProjectTox-Core/toxcore/net_crypto.h +410 -0
  98. data/ProjectTox-Core/toxcore/network.c +979 -0
  99. data/ProjectTox-Core/toxcore/network.h +367 -0
  100. data/ProjectTox-Core/toxcore/onion.c +540 -0
  101. data/ProjectTox-Core/toxcore/onion.h +150 -0
  102. data/ProjectTox-Core/toxcore/onion_announce.c +433 -0
  103. data/ProjectTox-Core/toxcore/onion_announce.h +139 -0
  104. data/ProjectTox-Core/toxcore/onion_client.c +1347 -0
  105. data/ProjectTox-Core/toxcore/onion_client.h +253 -0
  106. data/ProjectTox-Core/toxcore/ping.c +346 -0
  107. data/ProjectTox-Core/toxcore/ping.h +47 -0
  108. data/ProjectTox-Core/toxcore/ping_array.c +162 -0
  109. data/ProjectTox-Core/toxcore/ping_array.h +75 -0
  110. data/ProjectTox-Core/toxcore/tox.c +940 -0
  111. data/ProjectTox-Core/toxcore/tox.h +734 -0
  112. data/ProjectTox-Core/toxcore/util.c +193 -0
  113. data/ProjectTox-Core/toxcore/util.h +63 -0
  114. data/ProjectTox-Core/toxdns/Makefile.inc +29 -0
  115. data/ProjectTox-Core/toxdns/toxdns.c +238 -0
  116. data/ProjectTox-Core/toxdns/toxdns.h +88 -0
  117. data/ProjectTox-Core/toxencryptsave/Makefile.inc +45 -0
  118. data/ProjectTox-Core/toxencryptsave/toxencryptsave.c +179 -0
  119. data/ProjectTox-Core/toxencryptsave/toxencryptsave.h +74 -0
  120. data/interfaces/libtox.i +2 -6
  121. data/lib/ffi-tox/libtox.rb +406 -28
  122. metadata +124 -46
  123. data/ProjectTox-Core/CMakeLists.txt +0 -50
  124. data/ProjectTox-Core/cmake/FindLIBCONFIG.cmake +0 -15
  125. data/ProjectTox-Core/cmake/FindNaCl.cmake +0 -17
  126. data/ProjectTox-Core/cmake/FindSODIUM.cmake +0 -15
  127. data/ProjectTox-Core/core/CMakeLists.txt +0 -19
  128. data/ProjectTox-Core/core/DHT.c +0 -1104
  129. data/ProjectTox-Core/core/DHT.h +0 -111
  130. data/ProjectTox-Core/core/LAN_discovery.c +0 -79
  131. data/ProjectTox-Core/core/Lossless_UDP.c +0 -755
  132. data/ProjectTox-Core/core/Lossless_UDP.h +0 -106
  133. data/ProjectTox-Core/core/Messenger.c +0 -596
  134. data/ProjectTox-Core/core/Messenger.h +0 -165
  135. data/ProjectTox-Core/core/friend_requests.c +0 -131
  136. data/ProjectTox-Core/core/friend_requests.h +0 -51
  137. data/ProjectTox-Core/core/net_crypto.c +0 -575
  138. data/ProjectTox-Core/core/net_crypto.h +0 -134
  139. data/ProjectTox-Core/core/network.c +0 -205
  140. data/ProjectTox-Core/core/network.h +0 -134
  141. data/ProjectTox-Core/docs/commands.md +0 -25
  142. data/ProjectTox-Core/docs/start_guide.de.md +0 -40
  143. data/ProjectTox-Core/docs/start_guide.md +0 -38
  144. data/ProjectTox-Core/other/CMakeLists.txt +0 -9
  145. data/ProjectTox-Core/testing/CMakeLists.txt +0 -18
  146. data/ProjectTox-Core/testing/DHT_cryptosendfiletest.c +0 -228
  147. data/ProjectTox-Core/testing/DHT_sendfiletest.c +0 -176
  148. data/ProjectTox-Core/testing/Lossless_UDP_testclient.c +0 -214
  149. data/ProjectTox-Core/testing/Lossless_UDP_testserver.c +0 -201
  150. data/ProjectTox-Core/testing/misc_tools.h +0 -29
  151. data/ProjectTox-Core/testing/nTox_win32.c +0 -387
  152. data/ProjectTox-Core/testing/nTox_win32.h +0 -40
  153. data/ProjectTox-Core/testing/rect.py +0 -45
@@ -0,0 +1,156 @@
1
+ /*
2
+ * TCP_client.h -- Implementation of the TCP relay client part of Tox.
3
+ *
4
+ * Copyright (C) 2014 Tox project All Rights Reserved.
5
+ *
6
+ * This file is part of Tox.
7
+ *
8
+ * Tox is free software: you can redistribute it and/or modify
9
+ * it under the terms of the GNU General Public License as published by
10
+ * the Free Software Foundation, either version 3 of the License, or
11
+ * (at your option) any later version.
12
+ *
13
+ * Tox is distributed in the hope that it will be useful,
14
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16
+ * GNU General Public License for more details.
17
+ *
18
+ * You should have received a copy of the GNU General Public License
19
+ * along with Tox. If not, see <http://www.gnu.org/licenses/>.
20
+ *
21
+ */
22
+
23
+
24
+ #ifndef TCP_CLIENT_H
25
+ #define TCP_CLIENT_H
26
+
27
+ #include "crypto_core.h"
28
+ #include "TCP_server.h"
29
+
30
+ #define TCP_CONNECTION_TIMEOUT 10
31
+
32
+ typedef struct {
33
+ IP_Port ip_port;
34
+ } TCP_Proxy_Info;
35
+
36
+ enum {
37
+ TCP_CLIENT_NO_STATUS,
38
+ TCP_CLIENT_PROXY_CONNECTING,
39
+ TCP_CLIENT_PROXY_UNCONFIRMED,
40
+ TCP_CLIENT_CONNECTING,
41
+ TCP_CLIENT_UNCONFIRMED,
42
+ TCP_CLIENT_CONFIRMED,
43
+ TCP_CLIENT_DISCONNECTED,
44
+ };
45
+ typedef struct {
46
+ uint8_t status;
47
+ sock_t sock;
48
+ uint8_t self_public_key[crypto_box_PUBLICKEYBYTES]; /* our public key */
49
+ uint8_t public_key[crypto_box_PUBLICKEYBYTES]; /* public key of the server */
50
+ IP_Port ip_port; /* The ip and port of the server */
51
+ TCP_Proxy_Info proxy_info;
52
+ uint8_t recv_nonce[crypto_box_NONCEBYTES]; /* Nonce of received packets. */
53
+ uint8_t sent_nonce[crypto_box_NONCEBYTES]; /* Nonce of sent packets. */
54
+ uint8_t shared_key[crypto_box_BEFORENMBYTES];
55
+ uint16_t next_packet_length;
56
+
57
+ uint8_t temp_secret_key[crypto_box_SECRETKEYBYTES];
58
+
59
+ uint8_t last_packet[2 + MAX_PACKET_SIZE];
60
+ uint16_t last_packet_length;
61
+ uint16_t last_packet_sent;
62
+
63
+ TCP_Priority_List *priority_queue_start, *priority_queue_end;
64
+
65
+ uint64_t kill_at;
66
+
67
+ uint64_t last_pinged;
68
+ uint64_t ping_id;
69
+
70
+ uint64_t ping_response_id;
71
+ uint64_t ping_request_id;
72
+
73
+ void *net_crypto_pointer;
74
+ uint32_t net_crypto_location;
75
+ struct {
76
+ uint8_t status; /* 0 if not used, 1 if other is offline, 2 if other is online. */
77
+ uint8_t public_key[crypto_box_PUBLICKEYBYTES];
78
+ uint32_t number;
79
+ } connections[NUM_CLIENT_CONNECTIONS];
80
+ int (*response_callback)(void *object, uint8_t connection_id, const uint8_t *public_key);
81
+ void *response_callback_object;
82
+ int (*status_callback)(void *object, uint32_t number, uint8_t connection_id, uint8_t status);
83
+ void *status_callback_object;
84
+ int (*data_callback)(void *object, uint32_t number, uint8_t connection_id, const uint8_t *data, uint16_t length);
85
+ void *data_callback_object;
86
+ int (*oob_data_callback)(void *object, const uint8_t *public_key, const uint8_t *data, uint16_t length);
87
+ void *oob_data_callback_object;
88
+
89
+ int (*onion_callback)(void *object, const uint8_t *data, uint16_t length);
90
+ void *onion_callback_object;
91
+ } TCP_Client_Connection;
92
+
93
+ /* Create new TCP connection to ip_port/public_key
94
+ */
95
+ TCP_Client_Connection *new_TCP_connection(IP_Port ip_port, const uint8_t *public_key, const uint8_t *self_public_key,
96
+ const uint8_t *self_secret_key, TCP_Proxy_Info *proxy_info);
97
+
98
+ /* Run the TCP connection
99
+ */
100
+ void do_TCP_connection(TCP_Client_Connection *TCP_connection);
101
+
102
+ /* Kill the TCP connection
103
+ */
104
+ void kill_TCP_connection(TCP_Client_Connection *TCP_connection);
105
+
106
+ /* return 1 on success.
107
+ * return 0 if could not send packet.
108
+ * return -1 on failure (connection must be killed).
109
+ */
110
+ int send_onion_request(TCP_Client_Connection *con, const uint8_t *data, uint16_t length);
111
+ void onion_response_handler(TCP_Client_Connection *con, int (*onion_callback)(void *object, const uint8_t *data,
112
+ uint16_t length), void *object);
113
+
114
+ /* return 1 on success.
115
+ * return 0 if could not send packet.
116
+ * return -1 on failure (connection must be killed).
117
+ */
118
+ int send_routing_request(TCP_Client_Connection *con, uint8_t *public_key);
119
+ void routing_response_handler(TCP_Client_Connection *con, int (*response_callback)(void *object, uint8_t connection_id,
120
+ const uint8_t *public_key), void *object);
121
+ void routing_status_handler(TCP_Client_Connection *con, int (*status_callback)(void *object, uint32_t number,
122
+ uint8_t connection_id, uint8_t status), void *object);
123
+
124
+ /* return 1 on success.
125
+ * return 0 if could not send packet.
126
+ * return -1 on failure (connection must be killed).
127
+ */
128
+ int send_disconnect_request(TCP_Client_Connection *con, uint8_t con_id);
129
+
130
+ /* Set the number that will be used as an argument in the callbacks related to con_id.
131
+ *
132
+ * When not set by this function, the number is ~0.
133
+ *
134
+ * return 0 on success.
135
+ * return -1 on failure.
136
+ */
137
+ int set_tcp_connection_number(TCP_Client_Connection *con, uint8_t con_id, uint32_t number);
138
+
139
+ /* return 1 on success.
140
+ * return 0 if could not send packet.
141
+ * return -1 on failure.
142
+ */
143
+ int send_data(TCP_Client_Connection *con, uint8_t con_id, const uint8_t *data, uint16_t length);
144
+ void routing_data_handler(TCP_Client_Connection *con, int (*data_callback)(void *object, uint32_t number,
145
+ uint8_t connection_id, const uint8_t *data, uint16_t length), void *object);
146
+
147
+ /* return 1 on success.
148
+ * return 0 if could not send packet.
149
+ * return -1 on failure.
150
+ */
151
+ int send_oob_packet(TCP_Client_Connection *con, const uint8_t *public_key, const uint8_t *data, uint16_t length);
152
+ void oob_data_handler(TCP_Client_Connection *con, int (*oob_data_callback)(void *object, const uint8_t *public_key,
153
+ const uint8_t *data, uint16_t length), void *object);
154
+
155
+
156
+ #endif
@@ -0,0 +1,1332 @@
1
+ /*
2
+ * TCP_server.c -- Implementation of the TCP relay server part of Tox.
3
+ *
4
+ * Copyright (C) 2014 Tox project All Rights Reserved.
5
+ *
6
+ * This file is part of Tox.
7
+ *
8
+ * Tox is free software: you can redistribute it and/or modify
9
+ * it under the terms of the GNU General Public License as published by
10
+ * the Free Software Foundation, either version 3 of the License, or
11
+ * (at your option) any later version.
12
+ *
13
+ * Tox is distributed in the hope that it will be useful,
14
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
15
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16
+ * GNU General Public License for more details.
17
+ *
18
+ * You should have received a copy of the GNU General Public License
19
+ * along with Tox. If not, see <http://www.gnu.org/licenses/>.
20
+ *
21
+ */
22
+
23
+ #ifdef HAVE_CONFIG_H
24
+ #include "config.h"
25
+ #endif
26
+
27
+ #include "TCP_server.h"
28
+
29
+ #if !defined(_WIN32) && !defined(__WIN32__) && !defined (WIN32)
30
+ #include <sys/ioctl.h>
31
+ #endif
32
+
33
+ #include "util.h"
34
+
35
+ /* return 1 on success
36
+ * return 0 on failure
37
+ */
38
+ static int bind_to_port(sock_t sock, int family, uint16_t port)
39
+ {
40
+ struct sockaddr_storage addr = {0};
41
+ size_t addrsize;
42
+
43
+ if (family == AF_INET) {
44
+ struct sockaddr_in *addr4 = (struct sockaddr_in *)&addr;
45
+
46
+ addrsize = sizeof(struct sockaddr_in);
47
+ addr4->sin_family = AF_INET;
48
+ addr4->sin_port = htons(port);
49
+ } else if (family == AF_INET6) {
50
+ struct sockaddr_in6 *addr6 = (struct sockaddr_in6 *)&addr;
51
+
52
+ addrsize = sizeof(struct sockaddr_in6);
53
+ addr6->sin6_family = AF_INET6;
54
+ addr6->sin6_port = htons(port);
55
+ } else {
56
+ return 0;
57
+ }
58
+
59
+ return (bind(sock, (struct sockaddr *)&addr, addrsize) == 0);
60
+ }
61
+
62
+ /* Set the size of the connection list to numfriends.
63
+ *
64
+ * return -1 if realloc fails.
65
+ * return 0 if it succeeds.
66
+ */
67
+ static int realloc_connection(TCP_Server *TCP_server, uint32_t num)
68
+ {
69
+ if (num == 0) {
70
+ free(TCP_server->accepted_connection_array);
71
+ TCP_server->accepted_connection_array = NULL;
72
+ TCP_server->size_accepted_connections = 0;
73
+ return 0;
74
+ }
75
+
76
+ if (num == TCP_server->size_accepted_connections) {
77
+ return 0;
78
+ }
79
+
80
+ TCP_Secure_Connection *new_connections = realloc(TCP_server->accepted_connection_array,
81
+ num * sizeof(TCP_Secure_Connection));
82
+
83
+ if (new_connections == NULL)
84
+ return -1;
85
+
86
+ if (num > TCP_server->size_accepted_connections) {
87
+ uint32_t old_size = TCP_server->size_accepted_connections;
88
+ uint32_t size_new_entries = (num - old_size) * sizeof(TCP_Secure_Connection);
89
+ memset(new_connections + old_size, 0, size_new_entries);
90
+ }
91
+
92
+ TCP_server->accepted_connection_array = new_connections;
93
+ TCP_server->size_accepted_connections = num;
94
+ return 0;
95
+ }
96
+
97
+ /* return index corresponding to connection with peer on success
98
+ * return -1 on failure.
99
+ */
100
+ static int get_TCP_connection_index(const TCP_Server *TCP_server, const uint8_t *public_key)
101
+ {
102
+ return bs_list_find(&TCP_server->accepted_key_list, public_key);
103
+ }
104
+
105
+
106
+ static int kill_accepted(TCP_Server *TCP_server, int index);
107
+
108
+ /* Add accepted TCP connection to the list.
109
+ *
110
+ * return index on success
111
+ * return -1 on failure
112
+ */
113
+ static int add_accepted(TCP_Server *TCP_server, const TCP_Secure_Connection *con)
114
+ {
115
+ int index = get_TCP_connection_index(TCP_server, con->public_key);
116
+
117
+ if (index != -1) { /* If an old connection to the same public key exists, kill it. */
118
+ kill_accepted(TCP_server, index);
119
+ index = -1;
120
+ }
121
+
122
+ if (TCP_server->size_accepted_connections == TCP_server->num_accepted_connections) {
123
+ if (realloc_connection(TCP_server, TCP_server->size_accepted_connections + 4) == -1)
124
+ return -1;
125
+
126
+ index = TCP_server->num_accepted_connections;
127
+ } else {
128
+ uint32_t i;
129
+
130
+ for (i = TCP_server->size_accepted_connections; i != 0; --i) {
131
+ if (TCP_server->accepted_connection_array[i - 1].status == TCP_STATUS_NO_STATUS) {
132
+ index = i - 1;
133
+ break;
134
+ }
135
+ }
136
+ }
137
+
138
+ if (index == -1) {
139
+ fprintf(stderr, "FAIL index is -1\n");
140
+ return -1;
141
+ }
142
+
143
+ if (!bs_list_add(&TCP_server->accepted_key_list, con->public_key, index))
144
+ return -1;
145
+
146
+ memcpy(&TCP_server->accepted_connection_array[index], con, sizeof(TCP_Secure_Connection));
147
+ TCP_server->accepted_connection_array[index].status = TCP_STATUS_CONFIRMED;
148
+ ++TCP_server->num_accepted_connections;
149
+ TCP_server->accepted_connection_array[index].identifier = ++TCP_server->counter;
150
+ TCP_server->accepted_connection_array[index].last_pinged = unix_time();
151
+ TCP_server->accepted_connection_array[index].ping_id = 0;
152
+
153
+ return index;
154
+ }
155
+
156
+ /* Delete accepted connection from list.
157
+ *
158
+ * return 0 on success
159
+ * return -1 on failure
160
+ */
161
+ static int del_accepted(TCP_Server *TCP_server, int index)
162
+ {
163
+ if ((uint32_t)index >= TCP_server->size_accepted_connections)
164
+ return -1;
165
+
166
+ if (TCP_server->accepted_connection_array[index].status == TCP_STATUS_NO_STATUS)
167
+ return -1;
168
+
169
+ if (!bs_list_remove(&TCP_server->accepted_key_list, TCP_server->accepted_connection_array[index].public_key, index))
170
+ return -1;
171
+
172
+ memset(&TCP_server->accepted_connection_array[index], 0, sizeof(TCP_Secure_Connection));
173
+ --TCP_server->num_accepted_connections;
174
+
175
+ if (TCP_server->num_accepted_connections == 0)
176
+ realloc_connection(TCP_server, 0);
177
+
178
+ return 0;
179
+ }
180
+
181
+ /* Read the next two bytes in TCP stream then convert them to
182
+ * length (host byte order).
183
+ *
184
+ * return length on success
185
+ * return 0 if nothing has been read from socket.
186
+ * return ~0 on failure.
187
+ */
188
+ uint16_t read_TCP_length(sock_t sock)
189
+ {
190
+ #if defined(_WIN32) || defined(__WIN32__) || defined (WIN32)
191
+ unsigned long count = 0;
192
+ ioctlsocket(sock, FIONREAD, &count);
193
+ #else
194
+ int count = 0;
195
+ ioctl(sock, FIONREAD, &count);
196
+ #endif
197
+
198
+ if ((unsigned int)count >= sizeof(uint16_t)) {
199
+ uint16_t length;
200
+ int len = recv(sock, (uint8_t *)&length, sizeof(uint16_t), MSG_NOSIGNAL);
201
+
202
+ if (len != sizeof(uint16_t)) {
203
+ fprintf(stderr, "FAIL recv packet\n");
204
+ return 0;
205
+ }
206
+
207
+ length = ntohs(length);
208
+
209
+ if (length > MAX_PACKET_SIZE) {
210
+ return ~0;
211
+ }
212
+
213
+ return length;
214
+ }
215
+
216
+ return 0;
217
+ }
218
+
219
+ /* Read length bytes from socket.
220
+ *
221
+ * return length on success
222
+ * return -1 on failure/no data in buffer.
223
+ */
224
+ int read_TCP_packet(sock_t sock, uint8_t *data, uint16_t length)
225
+ {
226
+ #if defined(_WIN32) || defined(__WIN32__) || defined (WIN32)
227
+ unsigned long count = 0;
228
+ ioctlsocket(sock, FIONREAD, &count);
229
+ #else
230
+ int count = 0;
231
+ ioctl(sock, FIONREAD, &count);
232
+ #endif
233
+
234
+ if (count >= length) {
235
+ int len = recv(sock, data, length, MSG_NOSIGNAL);
236
+
237
+ if (len != length) {
238
+ fprintf(stderr, "FAIL recv packet\n");
239
+ return -1;
240
+ }
241
+
242
+ return len;
243
+ }
244
+
245
+ return -1;
246
+ }
247
+
248
+ /* return length of received packet on success.
249
+ * return 0 if could not read any packet.
250
+ * return -1 on failure (connection must be killed).
251
+ */
252
+ int read_packet_TCP_secure_connection(sock_t sock, uint16_t *next_packet_length, const uint8_t *shared_key,
253
+ uint8_t *recv_nonce, uint8_t *data, uint16_t max_len)
254
+ {
255
+ if (*next_packet_length == 0) {
256
+ uint16_t len = read_TCP_length(sock);
257
+
258
+ if (len == (uint16_t)~0)
259
+ return -1;
260
+
261
+ if (len == 0)
262
+ return 0;
263
+
264
+ *next_packet_length = len;
265
+ }
266
+
267
+ if (max_len + crypto_box_MACBYTES < *next_packet_length)
268
+ return -1;
269
+
270
+ uint8_t data_encrypted[*next_packet_length];
271
+ int len_packet = read_TCP_packet(sock, data_encrypted, *next_packet_length);
272
+
273
+ if (len_packet != *next_packet_length)
274
+ return 0;
275
+
276
+ *next_packet_length = 0;
277
+
278
+ int len = decrypt_data_symmetric(shared_key, recv_nonce, data_encrypted, len_packet, data);
279
+
280
+ if (len + crypto_box_MACBYTES != len_packet)
281
+ return -1;
282
+
283
+ increment_nonce(recv_nonce);
284
+
285
+ return len;
286
+ }
287
+
288
+ /* return 0 if pending data was sent completely
289
+ * return -1 if it wasn't
290
+ */
291
+ static int send_pending_data_nonpriority(TCP_Secure_Connection *con)
292
+ {
293
+ if (con->last_packet_length == 0) {
294
+ return 0;
295
+ }
296
+
297
+ uint16_t left = con->last_packet_length - con->last_packet_sent;
298
+ int len = send(con->sock, con->last_packet + con->last_packet_sent, left, MSG_NOSIGNAL);
299
+
300
+ if (len <= 0)
301
+ return -1;
302
+
303
+ if (len == left) {
304
+ con->last_packet_length = 0;
305
+ con->last_packet_sent = 0;
306
+ return 0;
307
+ }
308
+
309
+ con->last_packet_sent += len;
310
+ return -1;
311
+
312
+ }
313
+
314
+ /* return 0 if pending data was sent completely
315
+ * return -1 if it wasn't
316
+ */
317
+ static int send_pending_data(TCP_Secure_Connection *con)
318
+ {
319
+ /* finish sending current non-priority packet */
320
+ if (send_pending_data_nonpriority(con) == -1) {
321
+ return -1;
322
+ }
323
+
324
+ TCP_Priority_List *p = con->priority_queue_start;
325
+
326
+ while (p) {
327
+ uint16_t left = p->size - p->sent;
328
+ int len = send(con->sock, p->data + p->sent, left, MSG_NOSIGNAL);
329
+
330
+ if (len != left) {
331
+ if (len > 0) {
332
+ p->sent += len;
333
+ }
334
+
335
+ break;
336
+ }
337
+
338
+ TCP_Priority_List *pp = p;
339
+ p = p->next;
340
+ free(pp);
341
+ }
342
+
343
+ con->priority_queue_start = p;
344
+
345
+ if (!p) {
346
+ con->priority_queue_end = NULL;
347
+ return 0;
348
+ }
349
+
350
+ return -1;
351
+ }
352
+
353
+ /* return 0 on failure (only if malloc fails)
354
+ * return 1 on success
355
+ */
356
+ static _Bool add_priority(TCP_Secure_Connection *con, const uint8_t *packet, uint16_t size, uint16_t sent)
357
+ {
358
+ TCP_Priority_List *p = con->priority_queue_end, *new;
359
+ new = malloc(sizeof(TCP_Priority_List) + size);
360
+
361
+ if (!new) {
362
+ return 0;
363
+ }
364
+
365
+ new->next = NULL;
366
+ new->size = size;
367
+ new->sent = sent;
368
+ memcpy(new->data, packet, size);
369
+
370
+ if (p) {
371
+ p->next = new;
372
+ } else {
373
+ con->priority_queue_start = new;
374
+ }
375
+
376
+ con->priority_queue_end = new;
377
+ return 1;
378
+ }
379
+
380
+ /* return 1 on success.
381
+ * return 0 if could not send packet.
382
+ * return -1 on failure (connection must be killed).
383
+ */
384
+ static int write_packet_TCP_secure_connection(TCP_Secure_Connection *con, const uint8_t *data, uint16_t length,
385
+ _Bool priority)
386
+ {
387
+ if (length + crypto_box_MACBYTES > MAX_PACKET_SIZE)
388
+ return -1;
389
+
390
+ _Bool sendpriority = 1;
391
+
392
+ if (send_pending_data(con) == -1) {
393
+ if (priority) {
394
+ sendpriority = 0;
395
+ } else {
396
+ return 0;
397
+ }
398
+ }
399
+
400
+ uint8_t packet[sizeof(uint16_t) + length + crypto_box_MACBYTES];
401
+
402
+ uint16_t c_length = htons(length + crypto_box_MACBYTES);
403
+ memcpy(packet, &c_length, sizeof(uint16_t));
404
+ int len = encrypt_data_symmetric(con->shared_key, con->sent_nonce, data, length, packet + sizeof(uint16_t));
405
+
406
+ if ((unsigned int)len != (sizeof(packet) - sizeof(uint16_t)))
407
+ return -1;
408
+
409
+ if (priority) {
410
+ len = sendpriority ? send(con->sock, packet, sizeof(packet), MSG_NOSIGNAL) : 0;
411
+
412
+ if (len <= 0) {
413
+ len = 0;
414
+ }
415
+
416
+ increment_nonce(con->sent_nonce);
417
+
418
+ if ((unsigned int)len == sizeof(packet)) {
419
+ return 1;
420
+ }
421
+
422
+ return add_priority(con, packet, sizeof(packet), len);
423
+ }
424
+
425
+ len = send(con->sock, packet, sizeof(packet), MSG_NOSIGNAL);
426
+
427
+ if (len <= 0)
428
+ return 0;
429
+
430
+ increment_nonce(con->sent_nonce);
431
+
432
+ if ((unsigned int)len == sizeof(packet))
433
+ return 1;
434
+
435
+ memcpy(con->last_packet, packet, sizeof(packet));
436
+ con->last_packet_length = sizeof(packet);
437
+ con->last_packet_sent = len;
438
+ return 1;
439
+ }
440
+
441
+ /* Kill a TCP_Secure_Connection
442
+ */
443
+ static void kill_TCP_connection(TCP_Secure_Connection *con)
444
+ {
445
+ kill_sock(con->sock);
446
+ memset(con, 0, sizeof(TCP_Secure_Connection));
447
+ }
448
+
449
+ static int rm_connection_index(TCP_Server *TCP_server, TCP_Secure_Connection *con, uint8_t con_number);
450
+
451
+ /* Kill an accepted TCP_Secure_Connection
452
+ *
453
+ * return -1 on failure.
454
+ * return 0 on success.
455
+ */
456
+ static int kill_accepted(TCP_Server *TCP_server, int index)
457
+ {
458
+ if ((uint32_t)index >= TCP_server->size_accepted_connections)
459
+ return -1;
460
+
461
+ uint32_t i;
462
+
463
+ for (i = 0; i < NUM_CLIENT_CONNECTIONS; ++i) {
464
+ rm_connection_index(TCP_server, &TCP_server->accepted_connection_array[index], i);
465
+ }
466
+
467
+ sock_t sock = TCP_server->accepted_connection_array[index].sock;
468
+
469
+ if (del_accepted(TCP_server, index) != 0)
470
+ return -1;
471
+
472
+ kill_sock(sock);
473
+ return 0;
474
+ }
475
+
476
+ /* return 1 if everything went well.
477
+ * return -1 if the connection must be killed.
478
+ */
479
+ static int handle_TCP_handshake(TCP_Secure_Connection *con, const uint8_t *data, uint16_t length,
480
+ const uint8_t *self_secret_key)
481
+ {
482
+ if (length != TCP_CLIENT_HANDSHAKE_SIZE)
483
+ return -1;
484
+
485
+ if (con->status != TCP_STATUS_CONNECTED)
486
+ return -1;
487
+
488
+ uint8_t shared_key[crypto_box_BEFORENMBYTES];
489
+ encrypt_precompute(data, self_secret_key, shared_key);
490
+ uint8_t plain[TCP_HANDSHAKE_PLAIN_SIZE];
491
+ int len = decrypt_data_symmetric(shared_key, data + crypto_box_PUBLICKEYBYTES,
492
+ data + crypto_box_PUBLICKEYBYTES + crypto_box_NONCEBYTES, TCP_HANDSHAKE_PLAIN_SIZE + crypto_box_MACBYTES, plain);
493
+
494
+ if (len != TCP_HANDSHAKE_PLAIN_SIZE)
495
+ return -1;
496
+
497
+ memcpy(con->public_key, data, crypto_box_PUBLICKEYBYTES);
498
+ uint8_t temp_secret_key[crypto_box_SECRETKEYBYTES];
499
+ uint8_t resp_plain[TCP_HANDSHAKE_PLAIN_SIZE];
500
+ crypto_box_keypair(resp_plain, temp_secret_key);
501
+ random_nonce(con->sent_nonce);
502
+ memcpy(resp_plain + crypto_box_PUBLICKEYBYTES, con->sent_nonce, crypto_box_NONCEBYTES);
503
+ memcpy(con->recv_nonce, plain + crypto_box_PUBLICKEYBYTES, crypto_box_NONCEBYTES);
504
+
505
+ uint8_t response[TCP_SERVER_HANDSHAKE_SIZE];
506
+ new_nonce(response);
507
+
508
+ len = encrypt_data_symmetric(shared_key, response, resp_plain, TCP_HANDSHAKE_PLAIN_SIZE,
509
+ response + crypto_box_NONCEBYTES);
510
+
511
+ if (len != TCP_HANDSHAKE_PLAIN_SIZE + crypto_box_MACBYTES)
512
+ return -1;
513
+
514
+ if (TCP_SERVER_HANDSHAKE_SIZE != send(con->sock, response, TCP_SERVER_HANDSHAKE_SIZE, MSG_NOSIGNAL))
515
+ return -1;
516
+
517
+ encrypt_precompute(plain, temp_secret_key, con->shared_key);
518
+ con->status = TCP_STATUS_UNCONFIRMED;
519
+ return 1;
520
+ }
521
+
522
+ /* return 1 if connection handshake was handled correctly.
523
+ * return 0 if we didn't get it yet.
524
+ * return -1 if the connection must be killed.
525
+ */
526
+ static int read_connection_handshake(TCP_Secure_Connection *con, const uint8_t *self_secret_key)
527
+ {
528
+ uint8_t data[TCP_CLIENT_HANDSHAKE_SIZE];
529
+ int len = 0;
530
+
531
+ if ((len = read_TCP_packet(con->sock, data, TCP_CLIENT_HANDSHAKE_SIZE)) != -1) {
532
+ return handle_TCP_handshake(con, data, len, self_secret_key);
533
+ }
534
+
535
+ return 0;
536
+ }
537
+
538
+ /* return 1 on success.
539
+ * return 0 if could not send packet.
540
+ * return -1 on failure (connection must be killed).
541
+ */
542
+ static int send_routing_response(TCP_Secure_Connection *con, uint8_t rpid, const uint8_t *public_key)
543
+ {
544
+ uint8_t data[1 + 1 + crypto_box_PUBLICKEYBYTES];
545
+ data[0] = TCP_PACKET_ROUTING_RESPONSE;
546
+ data[1] = rpid;
547
+ memcpy(data + 2, public_key, crypto_box_PUBLICKEYBYTES);
548
+
549
+ return write_packet_TCP_secure_connection(con, data, sizeof(data), 1);
550
+ }
551
+
552
+ /* return 1 on success.
553
+ * return 0 if could not send packet.
554
+ * return -1 on failure (connection must be killed).
555
+ */
556
+ static int send_connect_notification(TCP_Secure_Connection *con, uint8_t id)
557
+ {
558
+ uint8_t data[2] = {TCP_PACKET_CONNECTION_NOTIFICATION, id + NUM_RESERVED_PORTS};
559
+ return write_packet_TCP_secure_connection(con, data, sizeof(data), 1);
560
+ }
561
+
562
+ /* return 1 on success.
563
+ * return 0 if could not send packet.
564
+ * return -1 on failure (connection must be killed).
565
+ */
566
+ static int send_disconnect_notification(TCP_Secure_Connection *con, uint8_t id)
567
+ {
568
+ uint8_t data[2] = {TCP_PACKET_DISCONNECT_NOTIFICATION, id + NUM_RESERVED_PORTS};
569
+ return write_packet_TCP_secure_connection(con, data, sizeof(data), 1);
570
+ }
571
+
572
+ /* return 0 on success.
573
+ * return -1 on failure (connection must be killed).
574
+ */
575
+ static int handle_TCP_routing_req(TCP_Server *TCP_server, uint32_t con_id, const uint8_t *public_key)
576
+ {
577
+ uint32_t i;
578
+ uint32_t index = ~0;
579
+ TCP_Secure_Connection *con = &TCP_server->accepted_connection_array[con_id];
580
+
581
+ /* If person tries to cennect to himself we deny the request*/
582
+ if (memcmp(con->public_key, public_key, crypto_box_PUBLICKEYBYTES) == 0) {
583
+ if (send_routing_response(con, 0, public_key) == -1)
584
+ return -1;
585
+
586
+ return 0;
587
+ }
588
+
589
+ for (i = 0; i < NUM_CLIENT_CONNECTIONS; ++i) {
590
+ if (con->connections[i].status != 0) {
591
+ if (memcmp(public_key, con->connections[i].public_key, crypto_box_PUBLICKEYBYTES) == 0) {
592
+ if (send_routing_response(con, i + NUM_RESERVED_PORTS, public_key) == -1) {
593
+ return -1;
594
+ } else {
595
+ return 0;
596
+ }
597
+ }
598
+ } else if (index == (uint32_t)~0) {
599
+ index = i;
600
+ }
601
+ }
602
+
603
+ if (index == (uint32_t)~0) {
604
+ if (send_routing_response(con, 0, public_key) == -1)
605
+ return -1;
606
+
607
+ return 0;
608
+ }
609
+
610
+ int ret = send_routing_response(con, index + NUM_RESERVED_PORTS, public_key);
611
+
612
+ if (ret == 0)
613
+ return 0;
614
+
615
+ if (ret == -1)
616
+ return -1;
617
+
618
+ con->connections[index].status = 1;
619
+ memcpy(con->connections[index].public_key, public_key, crypto_box_PUBLICKEYBYTES);
620
+ int other_index = get_TCP_connection_index(TCP_server, public_key);
621
+
622
+ if (other_index != -1) {
623
+ uint32_t other_id = ~0;
624
+ TCP_Secure_Connection *other_conn = &TCP_server->accepted_connection_array[other_index];
625
+
626
+ for (i = 0; i < NUM_CLIENT_CONNECTIONS; ++i) {
627
+ if (other_conn->connections[i].status == 1
628
+ && memcmp(other_conn->connections[i].public_key, con->public_key, crypto_box_PUBLICKEYBYTES) == 0) {
629
+ other_id = i;
630
+ break;
631
+ }
632
+ }
633
+
634
+ if (other_id != (uint32_t)~0) {
635
+ con->connections[index].status = 2;
636
+ con->connections[index].index = other_index;
637
+ con->connections[index].other_id = other_id;
638
+ other_conn->connections[other_id].status = 2;
639
+ other_conn->connections[other_id].index = con_id;
640
+ other_conn->connections[other_id].other_id = index;
641
+ //TODO: return values?
642
+ send_connect_notification(con, index);
643
+ send_connect_notification(other_conn, other_id);
644
+ }
645
+ }
646
+
647
+ return 0;
648
+ }
649
+
650
+ /* return 0 on success.
651
+ * return -1 on failure (connection must be killed).
652
+ */
653
+ static int handle_TCP_oob_send(TCP_Server *TCP_server, uint32_t con_id, const uint8_t *public_key, const uint8_t *data,
654
+ uint16_t length)
655
+ {
656
+ if (length == 0 || length > TCP_MAX_OOB_DATA_LENGTH)
657
+ return -1;
658
+
659
+ TCP_Secure_Connection *con = &TCP_server->accepted_connection_array[con_id];
660
+
661
+ int other_index = get_TCP_connection_index(TCP_server, public_key);
662
+
663
+ if (other_index != -1) {
664
+ uint8_t resp_packet[1 + crypto_box_PUBLICKEYBYTES + length];
665
+ resp_packet[0] = TCP_PACKET_OOB_RECV;
666
+ memcpy(resp_packet + 1, con->public_key, crypto_box_PUBLICKEYBYTES);
667
+ memcpy(resp_packet + 1 + crypto_box_PUBLICKEYBYTES, data, length);
668
+ write_packet_TCP_secure_connection(&TCP_server->accepted_connection_array[other_index], resp_packet,
669
+ sizeof(resp_packet), 0);
670
+ }
671
+
672
+ return 0;
673
+ }
674
+
675
+ /* Remove connection with con_number from the connections array of con.
676
+ *
677
+ * return -1 on failure.
678
+ * return 0 on success.
679
+ */
680
+ static int rm_connection_index(TCP_Server *TCP_server, TCP_Secure_Connection *con, uint8_t con_number)
681
+ {
682
+ if (con_number >= NUM_CLIENT_CONNECTIONS)
683
+ return -1;
684
+
685
+ if (con->connections[con_number].status) {
686
+ uint32_t index = con->connections[con_number].index;
687
+ uint8_t other_id = con->connections[con_number].other_id;
688
+
689
+ if (con->connections[con_number].status == 2) {
690
+
691
+ if (index >= TCP_server->size_accepted_connections)
692
+ return -1;
693
+
694
+ TCP_server->accepted_connection_array[index].connections[other_id].other_id = 0;
695
+ TCP_server->accepted_connection_array[index].connections[other_id].index = 0;
696
+ TCP_server->accepted_connection_array[index].connections[other_id].status = 1;
697
+ //TODO: return values?
698
+ send_disconnect_notification(&TCP_server->accepted_connection_array[index], other_id);
699
+ }
700
+
701
+ con->connections[con_number].index = 0;
702
+ con->connections[con_number].other_id = 0;
703
+ con->connections[con_number].status = 0;
704
+ return 0;
705
+ } else {
706
+ return -1;
707
+ }
708
+ }
709
+
710
+ static int handle_onion_recv_1(void *object, IP_Port dest, const uint8_t *data, uint16_t length)
711
+ {
712
+ TCP_Server *TCP_server = object;
713
+ uint32_t index = dest.ip.ip6.uint32[0];
714
+
715
+ if (index >= TCP_server->size_accepted_connections)
716
+ return 1;
717
+
718
+ TCP_Secure_Connection *con = &TCP_server->accepted_connection_array[index];
719
+
720
+ if (con->identifier != dest.ip.ip6.uint64[1])
721
+ return 1;
722
+
723
+ uint8_t packet[1 + length];
724
+ memcpy(packet + 1, data, length);
725
+ packet[0] = TCP_PACKET_ONION_RESPONSE;
726
+
727
+ if (write_packet_TCP_secure_connection(con, packet, sizeof(packet), 0) != 1)
728
+ return 1;
729
+
730
+ return 0;
731
+ }
732
+
733
+ /* return 0 on success
734
+ * return -1 on failure
735
+ */
736
+ static int handle_TCP_packet(TCP_Server *TCP_server, uint32_t con_id, const uint8_t *data, uint16_t length)
737
+ {
738
+ if (length == 0)
739
+ return -1;
740
+
741
+ TCP_Secure_Connection *con = &TCP_server->accepted_connection_array[con_id];
742
+
743
+ switch (data[0]) {
744
+ case TCP_PACKET_ROUTING_REQUEST: {
745
+ if (length != 1 + crypto_box_PUBLICKEYBYTES)
746
+ return -1;
747
+
748
+ return handle_TCP_routing_req(TCP_server, con_id, data + 1);
749
+ }
750
+
751
+ case TCP_PACKET_CONNECTION_NOTIFICATION: {
752
+ if (length != 2)
753
+ return -1;
754
+
755
+ break;
756
+ }
757
+
758
+ case TCP_PACKET_DISCONNECT_NOTIFICATION: {
759
+ if (length != 2)
760
+ return -1;
761
+
762
+ return rm_connection_index(TCP_server, con, data[1] - NUM_RESERVED_PORTS);
763
+ }
764
+
765
+ case TCP_PACKET_PING: {
766
+ if (length != 1 + sizeof(uint64_t))
767
+ return -1;
768
+
769
+ uint8_t response[1 + sizeof(uint64_t)];
770
+ response[0] = TCP_PACKET_PONG;
771
+ memcpy(response + 1, data + 1, sizeof(uint64_t));
772
+ write_packet_TCP_secure_connection(con, response, sizeof(response), 1);
773
+ return 0;
774
+ }
775
+
776
+ case TCP_PACKET_PONG: {
777
+ if (length != 1 + sizeof(uint64_t))
778
+ return -1;
779
+
780
+ uint64_t ping_id;
781
+ memcpy(&ping_id, data + 1, sizeof(uint64_t));
782
+
783
+ if (ping_id) {
784
+ if (ping_id == con->ping_id) {
785
+ con->ping_id = 0;
786
+ }
787
+
788
+ return 0;
789
+ } else {
790
+ return -1;
791
+ }
792
+ }
793
+
794
+ case TCP_PACKET_OOB_SEND: {
795
+ if (length <= 1 + crypto_box_PUBLICKEYBYTES)
796
+ return -1;
797
+
798
+ return handle_TCP_oob_send(TCP_server, con_id, data + 1, data + 1 + crypto_box_PUBLICKEYBYTES,
799
+ length - (1 + crypto_box_PUBLICKEYBYTES));
800
+ }
801
+
802
+ case TCP_PACKET_ONION_REQUEST: {
803
+ if (TCP_server->onion) {
804
+ if (length <= 1 + crypto_box_NONCEBYTES + ONION_SEND_BASE * 2)
805
+ return -1;
806
+
807
+ IP_Port source;
808
+ source.ip.family = TCP_ONION_FAMILY;
809
+ source.ip.ip6.uint32[0] = con_id;
810
+ source.ip.ip6.uint64[1] = con->identifier;
811
+ onion_send_1(TCP_server->onion, data + 1 + crypto_box_NONCEBYTES, length - (1 + crypto_box_NONCEBYTES), source,
812
+ data + 1);
813
+ }
814
+
815
+ return 0;
816
+ }
817
+
818
+ case TCP_PACKET_ONION_RESPONSE: {
819
+ return -1;
820
+ }
821
+
822
+ default: {
823
+ if (data[0] < NUM_RESERVED_PORTS)
824
+ return -1;
825
+
826
+ uint8_t c_id = data[0] - NUM_RESERVED_PORTS;
827
+
828
+ if (c_id >= NUM_CLIENT_CONNECTIONS)
829
+ return -1;
830
+
831
+ if (con->connections[c_id].status == 0)
832
+ return -1;
833
+
834
+ if (con->connections[c_id].status != 2)
835
+ return 0;
836
+
837
+ uint32_t index = con->connections[c_id].index;
838
+ uint8_t other_c_id = con->connections[c_id].other_id + NUM_RESERVED_PORTS;
839
+ uint8_t new_data[length];
840
+ memcpy(new_data, data, length);
841
+ new_data[0] = other_c_id;
842
+ int ret = write_packet_TCP_secure_connection(&TCP_server->accepted_connection_array[index], new_data, length, 0);
843
+
844
+ if (ret == -1)
845
+ return -1;
846
+
847
+ return 0;
848
+ }
849
+ }
850
+
851
+ return 0;
852
+ }
853
+
854
+
855
+ static int confirm_TCP_connection(TCP_Server *TCP_server, TCP_Secure_Connection *con, const uint8_t *data,
856
+ uint16_t length)
857
+ {
858
+ int index = add_accepted(TCP_server, con);
859
+
860
+ if (index == -1)
861
+ return -1;
862
+
863
+ if (handle_TCP_packet(TCP_server, index, data, length) == -1) {
864
+ kill_accepted(TCP_server, index);
865
+ }
866
+
867
+ return index;
868
+ }
869
+
870
+ /* return 1 on success
871
+ * return 0 on failure
872
+ */
873
+ static int accept_connection(TCP_Server *TCP_server, sock_t sock)
874
+ {
875
+ if (!sock_valid(sock))
876
+ return 0;
877
+
878
+ if (!set_socket_nonblock(sock)) {
879
+ kill_sock(sock);
880
+ return 0;
881
+ }
882
+
883
+ if (!set_socket_nosigpipe(sock)) {
884
+ kill_sock(sock);
885
+ return 0;
886
+ }
887
+
888
+ TCP_Secure_Connection *conn =
889
+ &TCP_server->incomming_connection_queue[TCP_server->incomming_connection_queue_index % MAX_INCOMMING_CONNECTIONS];
890
+
891
+ if (conn->status != TCP_STATUS_NO_STATUS)
892
+ kill_TCP_connection(conn);
893
+
894
+ conn->status = TCP_STATUS_CONNECTED;
895
+ conn->sock = sock;
896
+ conn->next_packet_length = 0;
897
+
898
+ ++TCP_server->incomming_connection_queue_index;
899
+ return 1;
900
+ }
901
+
902
+ static sock_t new_listening_TCP_socket(int family, uint16_t port)
903
+ {
904
+ sock_t sock = socket(family, SOCK_STREAM, IPPROTO_TCP);
905
+
906
+ if (!sock_valid(sock)) {
907
+ return ~0;
908
+ }
909
+
910
+ #ifndef TCP_SERVER_USE_EPOLL
911
+ int ok = set_socket_nonblock(sock);
912
+ #else
913
+ int ok = 1;
914
+ #endif
915
+
916
+ if (ok && family == AF_INET6) {
917
+ ok = set_socket_dualstack(sock);
918
+ }
919
+
920
+ ok = ok && bind_to_port(sock, family, port) && (listen(sock, TCP_MAX_BACKLOG) == 0);
921
+
922
+ if (!ok) {
923
+ kill_sock(sock);
924
+ return ~0;
925
+ }
926
+
927
+ return sock;
928
+ }
929
+
930
+ TCP_Server *new_TCP_server(uint8_t ipv6_enabled, uint16_t num_sockets, const uint16_t *ports, const uint8_t *public_key,
931
+ const uint8_t *secret_key, Onion *onion)
932
+ {
933
+ if (num_sockets == 0 || ports == NULL)
934
+ return NULL;
935
+
936
+ if (networking_at_startup() != 0) {
937
+ return NULL;
938
+ }
939
+
940
+ TCP_Server *temp = calloc(1, sizeof(TCP_Server));
941
+
942
+ if (temp == NULL)
943
+ return NULL;
944
+
945
+ temp->socks_listening = calloc(num_sockets, sizeof(sock_t));
946
+
947
+ if (temp->socks_listening == NULL) {
948
+ free(temp);
949
+ return NULL;
950
+ }
951
+
952
+ #ifdef TCP_SERVER_USE_EPOLL
953
+ temp->efd = epoll_create(8);
954
+
955
+ if (temp->efd == -1) {
956
+ free(temp->socks_listening);
957
+ free(temp);
958
+ return NULL;
959
+ }
960
+
961
+ #endif
962
+
963
+ uint8_t family;
964
+
965
+ if (ipv6_enabled) {
966
+ family = AF_INET6;
967
+ } else {
968
+ family = AF_INET;
969
+ }
970
+
971
+ uint32_t i;
972
+ #ifdef TCP_SERVER_USE_EPOLL
973
+ struct epoll_event ev;
974
+ #endif
975
+
976
+ for (i = 0; i < num_sockets; ++i) {
977
+ sock_t sock = new_listening_TCP_socket(family, ports[i]);
978
+
979
+ if (sock_valid(sock)) {
980
+ #ifdef TCP_SERVER_USE_EPOLL
981
+ ev.events = EPOLLIN;
982
+ ev.data.u64 = sock | ((uint64_t)TCP_SOCKET_LISTENING << 32);
983
+
984
+ if (epoll_ctl(temp->efd, EPOLL_CTL_ADD, sock, &ev) == -1) {
985
+ continue;
986
+ }
987
+
988
+ #endif
989
+
990
+ temp->socks_listening[temp->num_listening_socks] = sock;
991
+ ++temp->num_listening_socks;
992
+ }
993
+ }
994
+
995
+ if (temp->num_listening_socks == 0) {
996
+ free(temp->socks_listening);
997
+ free(temp);
998
+ return NULL;
999
+ }
1000
+
1001
+ if (onion) {
1002
+ temp->onion = onion;
1003
+ set_callback_handle_recv_1(onion, &handle_onion_recv_1, temp);
1004
+ }
1005
+
1006
+ memcpy(temp->public_key, public_key, crypto_box_PUBLICKEYBYTES);
1007
+ memcpy(temp->secret_key, secret_key, crypto_box_SECRETKEYBYTES);
1008
+
1009
+ bs_list_init(&temp->accepted_key_list, crypto_box_PUBLICKEYBYTES, 8);
1010
+
1011
+ return temp;
1012
+ }
1013
+
1014
+ static void do_TCP_accept_new(TCP_Server *TCP_server)
1015
+ {
1016
+ uint32_t i;
1017
+
1018
+ for (i = 0; i < TCP_server->num_listening_socks; ++i) {
1019
+ struct sockaddr_storage addr;
1020
+ unsigned int addrlen = sizeof(addr);
1021
+ sock_t sock;
1022
+
1023
+ do {
1024
+ sock = accept(TCP_server->socks_listening[i], (struct sockaddr *)&addr, &addrlen);
1025
+ } while (accept_connection(TCP_server, sock));
1026
+ }
1027
+ }
1028
+
1029
+ static int do_incoming(TCP_Server *TCP_server, uint32_t i)
1030
+ {
1031
+ if (TCP_server->incomming_connection_queue[i].status != TCP_STATUS_CONNECTED)
1032
+ return -1;
1033
+
1034
+ int ret = read_connection_handshake(&TCP_server->incomming_connection_queue[i], TCP_server->secret_key);
1035
+
1036
+ if (ret == -1) {
1037
+ kill_TCP_connection(&TCP_server->incomming_connection_queue[i]);
1038
+ } else if (ret == 1) {
1039
+ int index_new = TCP_server->unconfirmed_connection_queue_index % MAX_INCOMMING_CONNECTIONS;
1040
+ TCP_Secure_Connection *conn_old = &TCP_server->incomming_connection_queue[i];
1041
+ TCP_Secure_Connection *conn_new = &TCP_server->unconfirmed_connection_queue[index_new];
1042
+
1043
+ if (conn_new->status != TCP_STATUS_NO_STATUS)
1044
+ kill_TCP_connection(conn_new);
1045
+
1046
+ memcpy(conn_new, conn_old, sizeof(TCP_Secure_Connection));
1047
+ memset(conn_old, 0, sizeof(TCP_Secure_Connection));
1048
+ ++TCP_server->unconfirmed_connection_queue_index;
1049
+
1050
+ return index_new;
1051
+ }
1052
+
1053
+ return -1;
1054
+ }
1055
+
1056
+ static int do_unconfirmed(TCP_Server *TCP_server, uint32_t i)
1057
+ {
1058
+ TCP_Secure_Connection *conn = &TCP_server->unconfirmed_connection_queue[i];
1059
+
1060
+ if (conn->status != TCP_STATUS_UNCONFIRMED)
1061
+ return -1;
1062
+
1063
+ uint8_t packet[MAX_PACKET_SIZE];
1064
+ int len = read_packet_TCP_secure_connection(conn->sock, &conn->next_packet_length, conn->shared_key, conn->recv_nonce,
1065
+ packet, sizeof(packet));
1066
+
1067
+ if (len == 0) {
1068
+ return -1;
1069
+ } else if (len == -1) {
1070
+ kill_TCP_connection(conn);
1071
+ return -1;
1072
+ } else {
1073
+ int index_new;
1074
+
1075
+ if ((index_new = confirm_TCP_connection(TCP_server, conn, packet, len)) == -1) {
1076
+ kill_TCP_connection(conn);
1077
+ } else {
1078
+ memset(conn, 0, sizeof(TCP_Secure_Connection));
1079
+ }
1080
+
1081
+ return index_new;
1082
+ }
1083
+ }
1084
+
1085
+ static void do_confirmed_recv(TCP_Server *TCP_server, uint32_t i)
1086
+ {
1087
+ TCP_Secure_Connection *conn = &TCP_server->accepted_connection_array[i];
1088
+
1089
+ uint8_t packet[MAX_PACKET_SIZE];
1090
+ int len;
1091
+
1092
+ while ((len = read_packet_TCP_secure_connection(conn->sock, &conn->next_packet_length, conn->shared_key,
1093
+ conn->recv_nonce, packet, sizeof(packet)))) {
1094
+ if (len == -1) {
1095
+ kill_accepted(TCP_server, i);
1096
+ break;
1097
+ }
1098
+
1099
+ if (handle_TCP_packet(TCP_server, i, packet, len) == -1) {
1100
+ kill_accepted(TCP_server, i);
1101
+ break;
1102
+ }
1103
+ }
1104
+ }
1105
+
1106
+ static void do_TCP_incomming(TCP_Server *TCP_server)
1107
+ {
1108
+ uint32_t i;
1109
+
1110
+ for (i = 0; i < MAX_INCOMMING_CONNECTIONS; ++i) {
1111
+ do_incoming(TCP_server, i);
1112
+ }
1113
+ }
1114
+
1115
+ static void do_TCP_unconfirmed(TCP_Server *TCP_server)
1116
+ {
1117
+ uint32_t i;
1118
+
1119
+ for (i = 0; i < MAX_INCOMMING_CONNECTIONS; ++i) {
1120
+ do_unconfirmed(TCP_server, i);
1121
+ }
1122
+ }
1123
+
1124
+ static void do_TCP_confirmed(TCP_Server *TCP_server)
1125
+ {
1126
+ #ifdef TCP_SERVER_USE_EPOLL
1127
+
1128
+ if (TCP_server->last_run_pinged == unix_time())
1129
+ return;
1130
+
1131
+ TCP_server->last_run_pinged = unix_time();
1132
+ #endif
1133
+ uint32_t i;
1134
+
1135
+ for (i = 0; i < TCP_server->size_accepted_connections; ++i) {
1136
+ TCP_Secure_Connection *conn = &TCP_server->accepted_connection_array[i];
1137
+
1138
+ if (conn->status != TCP_STATUS_CONFIRMED)
1139
+ continue;
1140
+
1141
+ if (is_timeout(conn->last_pinged, TCP_PING_FREQUENCY)) {
1142
+ uint8_t ping[1 + sizeof(uint64_t)];
1143
+ ping[0] = TCP_PACKET_PING;
1144
+ uint64_t ping_id = random_64b();
1145
+
1146
+ if (!ping_id)
1147
+ ++ping_id;
1148
+
1149
+ memcpy(ping + 1, &ping_id, sizeof(uint64_t));
1150
+ int ret = write_packet_TCP_secure_connection(conn, ping, sizeof(ping), 1);
1151
+
1152
+ if (ret == 1) {
1153
+ conn->last_pinged = unix_time();
1154
+ conn->ping_id = ping_id;
1155
+ } else {
1156
+ if (is_timeout(conn->last_pinged, TCP_PING_FREQUENCY + TCP_PING_TIMEOUT)) {
1157
+ kill_accepted(TCP_server, i);
1158
+ continue;
1159
+ }
1160
+ }
1161
+ }
1162
+
1163
+ if (conn->ping_id && is_timeout(conn->last_pinged, TCP_PING_TIMEOUT)) {
1164
+ kill_accepted(TCP_server, i);
1165
+ continue;
1166
+ }
1167
+
1168
+ send_pending_data(conn);
1169
+
1170
+ #ifndef TCP_SERVER_USE_EPOLL
1171
+
1172
+ do_confirmed_recv(TCP_server, i);
1173
+
1174
+ #endif
1175
+ }
1176
+ }
1177
+
1178
+ #ifdef TCP_SERVER_USE_EPOLL
1179
+ static void do_TCP_epoll(TCP_Server *TCP_server)
1180
+ {
1181
+ #define MAX_EVENTS 16
1182
+ struct epoll_event events[MAX_EVENTS];
1183
+ int nfds;
1184
+
1185
+ while ((nfds = epoll_wait(TCP_server->efd, events, MAX_EVENTS, 0)) > 0) {
1186
+ int n;
1187
+
1188
+ for (n = 0; n < nfds; ++n) {
1189
+ sock_t sock = events[n].data.u64 & 0xFFFFFFFF;
1190
+ int status = (events[n].data.u64 >> 32) & 0xFFFF, index = (events[n].data.u64 >> 48);
1191
+
1192
+ if ((events[n].events & EPOLLERR) || (events[n].events & EPOLLHUP)) {
1193
+ switch (status) {
1194
+ case TCP_SOCKET_LISTENING: {
1195
+ //should never happen
1196
+ break;
1197
+ }
1198
+
1199
+ case TCP_SOCKET_INCOMING: {
1200
+ kill_TCP_connection(&TCP_server->incomming_connection_queue[index]);
1201
+ break;
1202
+ }
1203
+
1204
+ case TCP_SOCKET_UNCONFIRMED: {
1205
+ kill_TCP_connection(&TCP_server->unconfirmed_connection_queue[index]);
1206
+ break;
1207
+ }
1208
+
1209
+ case TCP_SOCKET_CONFIRMED: {
1210
+ kill_accepted(TCP_server, index);
1211
+ break;
1212
+ }
1213
+ }
1214
+
1215
+ continue;
1216
+ }
1217
+
1218
+
1219
+ if (!(events[n].events & EPOLLIN)) {
1220
+ continue;
1221
+ }
1222
+
1223
+ switch (status) {
1224
+ case TCP_SOCKET_LISTENING: {
1225
+ //socket is from socks_listening, accept connection
1226
+ struct sockaddr_storage addr;
1227
+ unsigned int addrlen = sizeof(addr);
1228
+ sock_t sock_new;
1229
+
1230
+ sock_new = accept(sock, (struct sockaddr *)&addr, &addrlen);
1231
+
1232
+ int index_new = TCP_server->incomming_connection_queue_index % MAX_INCOMMING_CONNECTIONS;
1233
+
1234
+ if (!accept_connection(TCP_server, sock_new)) {
1235
+ break;
1236
+ }
1237
+
1238
+ struct epoll_event ev = {
1239
+ .events = EPOLLIN | EPOLLET,
1240
+ .data.u64 = sock_new | ((uint64_t)TCP_SOCKET_INCOMING << 32) | ((uint64_t)index_new << 48)
1241
+ };
1242
+
1243
+ if (epoll_ctl(TCP_server->efd, EPOLL_CTL_ADD, sock_new, &ev) == -1) {
1244
+ kill_TCP_connection(&TCP_server->incomming_connection_queue[index_new]);
1245
+ break;
1246
+ }
1247
+
1248
+ break;
1249
+ }
1250
+
1251
+ case TCP_SOCKET_INCOMING: {
1252
+ int index_new;
1253
+
1254
+ if ((index_new = do_incoming(TCP_server, index)) != -1) {
1255
+ events[n].events = EPOLLIN | EPOLLET;
1256
+ events[n].data.u64 = sock | ((uint64_t)TCP_SOCKET_UNCONFIRMED << 32) | ((uint64_t)index_new << 48);
1257
+
1258
+ if (epoll_ctl(TCP_server->efd, EPOLL_CTL_MOD, sock, &events[n]) == -1) {
1259
+ kill_TCP_connection(&TCP_server->unconfirmed_connection_queue[index_new]);
1260
+ break;
1261
+ }
1262
+ }
1263
+
1264
+ break;
1265
+ }
1266
+
1267
+ case TCP_SOCKET_UNCONFIRMED: {
1268
+ int index_new;
1269
+
1270
+ if ((index_new = do_unconfirmed(TCP_server, index)) != -1) {
1271
+ events[n].events = EPOLLIN | EPOLLET;
1272
+ events[n].data.u64 = sock | ((uint64_t)TCP_SOCKET_CONFIRMED << 32) | ((uint64_t)index_new << 48);
1273
+
1274
+ if (epoll_ctl(TCP_server->efd, EPOLL_CTL_MOD, sock, &events[n]) == -1) {
1275
+ //remove from confirmed connections
1276
+ kill_accepted(TCP_server, index_new);
1277
+ break;
1278
+ }
1279
+ }
1280
+
1281
+ break;
1282
+ }
1283
+
1284
+ case TCP_SOCKET_CONFIRMED: {
1285
+ do_confirmed_recv(TCP_server, index);
1286
+ break;
1287
+ }
1288
+ }
1289
+ }
1290
+ }
1291
+
1292
+ #undef MAX_EVENTS
1293
+ }
1294
+ #endif
1295
+
1296
+ void do_TCP_server(TCP_Server *TCP_server)
1297
+ {
1298
+ unix_time_update();
1299
+
1300
+ #ifdef TCP_SERVER_USE_EPOLL
1301
+ do_TCP_epoll(TCP_server);
1302
+
1303
+ #else
1304
+ do_TCP_accept_new(TCP_server);
1305
+ do_TCP_incomming(TCP_server);
1306
+ do_TCP_unconfirmed(TCP_server);
1307
+ #endif
1308
+
1309
+ do_TCP_confirmed(TCP_server);
1310
+ }
1311
+
1312
+ void kill_TCP_server(TCP_Server *TCP_server)
1313
+ {
1314
+ uint32_t i;
1315
+
1316
+ for (i = 0; i < TCP_server->num_listening_socks; ++i) {
1317
+ kill_sock(TCP_server->socks_listening[i]);
1318
+ }
1319
+
1320
+ if (TCP_server->onion) {
1321
+ set_callback_handle_recv_1(TCP_server->onion, NULL, NULL);
1322
+ }
1323
+
1324
+ bs_list_free(&TCP_server->accepted_key_list);
1325
+
1326
+ #ifdef TCP_SERVER_USE_EPOLL
1327
+ close(TCP_server->efd);
1328
+ #endif
1329
+
1330
+ free(TCP_server->socks_listening);
1331
+ free(TCP_server);
1332
+ }