1 /* SPDX-License-Identifier: GPL-3.0-or-later
2  * Copyright © 2016-2018 The TokTok team.
3  * Copyright © 2015 Tox project.
4  */
5 
6 /*
7  * Handles TCP relay connections between two Tox clients.
8  */
9 #ifndef C_TOXCORE_TOXCORE_TCP_CONNECTION_H
10 #define C_TOXCORE_TOXCORE_TCP_CONNECTION_H
11 
12 #include "TCP_client.h"
13 
14 #define TCP_CONN_NONE 0
15 #define TCP_CONN_VALID 1
16 
17 /* NOTE: only used by TCP_con */
18 #define TCP_CONN_CONNECTED 2
19 
20 /* Connection is not connected but can be quickly reconnected in case it is needed. */
21 #define TCP_CONN_SLEEPING 3
22 
23 #define TCP_CONNECTIONS_STATUS_NONE 0
24 #define TCP_CONNECTIONS_STATUS_REGISTERED 1
25 #define TCP_CONNECTIONS_STATUS_ONLINE 2
26 
27 #define MAX_FRIEND_TCP_CONNECTIONS 6
28 
29 /* Time until connection to friend gets killed (if it doesn't get locked within that time) */
30 #define TCP_CONNECTION_ANNOUNCE_TIMEOUT TCP_CONNECTION_TIMEOUT
31 
32 /* The amount of recommended connections for each friend
33  * NOTE: Must be at most (MAX_FRIEND_TCP_CONNECTIONS / 2) */
34 #define RECOMMENDED_FRIEND_TCP_CONNECTIONS (MAX_FRIEND_TCP_CONNECTIONS / 2)
35 
36 /* Number of TCP connections used for onion purposes. */
37 #define NUM_ONION_TCP_CONNECTIONS RECOMMENDED_FRIEND_TCP_CONNECTIONS
38 
39 typedef struct TCP_Conn_to {
40     uint32_t tcp_connection;
41     unsigned int status;
42     unsigned int connection_id;
43 } TCP_Conn_to;
44 
45 typedef struct TCP_Connection_to {
46     uint8_t status;
47     uint8_t public_key[CRYPTO_PUBLIC_KEY_SIZE]; /* The dht public key of the peer */
48 
49     TCP_Conn_to connections[MAX_FRIEND_TCP_CONNECTIONS];
50 
51     int id; /* id used in callbacks. */
52 } TCP_Connection_to;
53 
54 typedef struct TCP_con {
55     uint8_t status;
56     TCP_Client_Connection *connection;
57     uint64_t connected_time;
58     uint32_t lock_count;
59     uint32_t sleep_count;
60     bool onion;
61 
62     /* Only used when connection is sleeping. */
63     IP_Port ip_port;
64     uint8_t relay_pk[CRYPTO_PUBLIC_KEY_SIZE];
65     bool unsleep; /* set to 1 to unsleep connection. */
66 } TCP_con;
67 
68 typedef struct TCP_Connections TCP_Connections;
69 
70 const uint8_t *tcp_connections_public_key(const TCP_Connections *tcp_c);
71 
72 /* Send a packet to the TCP connection.
73  *
74  * return -1 on failure.
75  * return 0 on success.
76  */
77 int send_packet_tcp_connection(TCP_Connections *tcp_c, int connections_number, const uint8_t *packet, uint16_t length);
78 
79 /* Return a random TCP connection number for use in send_tcp_onion_request.
80  *
81  * TODO(irungentoo): This number is just the index of an array that the elements
82  * can change without warning.
83  *
84  * return TCP connection number on success.
85  * return -1 on failure.
86  */
87 int get_random_tcp_onion_conn_number(TCP_Connections *tcp_c);
88 
89 /* Send an onion packet via the TCP relay corresponding to tcp_connections_number.
90  *
91  * return 0 on success.
92  * return -1 on failure.
93  */
94 int tcp_send_onion_request(TCP_Connections *tcp_c, unsigned int tcp_connections_number, const uint8_t *data,
95                            uint16_t length);
96 
97 /* Set if we want TCP_connection to allocate some connection for onion use.
98  *
99  * If status is 1, allocate some connections. if status is 0, don't.
100  *
101  * return 0 on success.
102  * return -1 on failure.
103  */
104 int set_tcp_onion_status(TCP_Connections *tcp_c, bool status);
105 
106 /* Send an oob packet via the TCP relay corresponding to tcp_connections_number.
107  *
108  * return 0 on success.
109  * return -1 on failure.
110  */
111 int tcp_send_oob_packet(TCP_Connections *tcp_c, unsigned int tcp_connections_number, const uint8_t *public_key,
112                         const uint8_t *packet, uint16_t length);
113 
114 typedef int tcp_data_cb(void *object, int id, const uint8_t *data, uint16_t length, void *userdata);
115 
116 /* Set the callback for TCP data packets.
117  */
118 void set_packet_tcp_connection_callback(TCP_Connections *tcp_c, tcp_data_cb *tcp_data_callback, void *object);
119 
120 typedef int tcp_onion_cb(void *object, const uint8_t *data, uint16_t length, void *userdata);
121 
122 /* Set the callback for TCP onion packets.
123  */
124 void set_onion_packet_tcp_connection_callback(TCP_Connections *tcp_c, tcp_onion_cb *tcp_onion_callback, void *object);
125 
126 typedef int tcp_oob_cb(void *object, const uint8_t *public_key, unsigned int tcp_connections_number,
127                        const uint8_t *data, uint16_t length, void *userdata);
128 
129 /* Set the callback for TCP oob data packets.
130  */
131 void set_oob_packet_tcp_connection_callback(TCP_Connections *tcp_c, tcp_oob_cb *tcp_oob_callback, void *object);
132 
133 /* Create a new TCP connection to public_key.
134  *
135  * public_key must be the counterpart to the secret key that the other peer used with new_tcp_connections().
136  *
137  * id is the id in the callbacks for that connection.
138  *
139  * return connections_number on success.
140  * return -1 on failure.
141  */
142 int new_tcp_connection_to(TCP_Connections *tcp_c, const uint8_t *public_key, int id);
143 
144 /* return 0 on success.
145  * return -1 on failure.
146  */
147 int kill_tcp_connection_to(TCP_Connections *tcp_c, int connections_number);
148 
149 /* Set connection status.
150  *
151  * status of 1 means we are using the connection.
152  * status of 0 means we are not using it.
153  *
154  * Unused tcp connections will be disconnected from but kept in case they are needed.
155  *
156  * return 0 on success.
157  * return -1 on failure.
158  */
159 int set_tcp_connection_to_status(TCP_Connections *tcp_c, int connections_number, bool status);
160 
161 /* return number of online tcp relays tied to the connection on success.
162  * return 0 on failure.
163  */
164 unsigned int tcp_connection_to_online_tcp_relays(TCP_Connections *tcp_c, int connections_number);
165 
166 /* Add a TCP relay tied to a connection.
167  *
168  * NOTE: This can only be used during the tcp_oob_callback.
169  *
170  * return 0 on success.
171  * return -1 on failure.
172  */
173 int add_tcp_number_relay_connection(TCP_Connections *tcp_c, int connections_number,
174                                     unsigned int tcp_connections_number);
175 
176 /* Add a TCP relay tied to a connection.
177  *
178  * This should be called with the same relay by two peers who want to create a TCP connection with each other.
179  *
180  * return 0 on success.
181  * return -1 on failure.
182  */
183 int add_tcp_relay_connection(TCP_Connections *tcp_c, int connections_number, IP_Port ip_port, const uint8_t *relay_pk);
184 
185 /* Add a TCP relay to the instance.
186  *
187  * return 0 on success.
188  * return -1 on failure.
189  */
190 int add_tcp_relay_global(TCP_Connections *tcp_c, IP_Port ip_port, const uint8_t *relay_pk);
191 
192 /* Copy a maximum of max_num TCP relays we are connected to to tcp_relays.
193  * NOTE that the family of the copied ip ports will be set to TCP_INET or TCP_INET6.
194  *
195  * return number of relays copied to tcp_relays on success.
196  * return 0 on failure.
197  */
198 uint32_t tcp_copy_connected_relays(TCP_Connections *tcp_c, Node_format *tcp_relays, uint16_t max_num);
199 
200 /* Returns a new TCP_Connections object associated with the secret_key.
201  *
202  * In order for others to connect to this instance new_tcp_connection_to() must be called with the
203  * public_key associated with secret_key.
204  *
205  * Returns NULL on failure.
206  */
207 TCP_Connections *new_tcp_connections(Mono_Time *mono_time, const uint8_t *secret_key, TCP_Proxy_Info *proxy_info);
208 
209 void do_tcp_connections(const Logger *logger, TCP_Connections *tcp_c, void *userdata);
210 
211 void kill_tcp_connections(TCP_Connections *tcp_c);
212 
213 #endif
214 
215