/work/auto_tests/tox_dispatch_test.c
Line | Count | Source (jump to first uncovered line) |
1 | | /* Auto Tests: Many clients. |
2 | | */ |
3 | | |
4 | | #include <stdio.h> |
5 | | #include <stdlib.h> |
6 | | #include <string.h> |
7 | | #include <time.h> |
8 | | |
9 | | #include "../testing/misc_tools.h" |
10 | | #include "../toxcore/tox.h" |
11 | | #include "../toxcore/tox_dispatch.h" |
12 | | #include "../toxcore/tox_events.h" |
13 | | #include "../toxcore/tox_private.h" |
14 | | #include "../toxcore/tox_unpack.h" |
15 | | #include "auto_test_support.h" |
16 | | #include "check_compat.h" |
17 | | |
18 | | // Set to true to produce an msgpack file at /tmp/test.mp. |
19 | | static const bool want_dump_events = false; |
20 | | |
21 | | static void handle_events_friend_message(const Tox_Event_Friend_Message *event, void *user_data) |
22 | 1 | { |
23 | 1 | bool *success = (bool *)user_data; |
24 | | |
25 | 1 | ck_assert(tox_event_friend_message_get_message_length(event) == sizeof("hello")); |
26 | 1 | const uint8_t *msg = tox_event_friend_message_get_message(event); |
27 | 1 | ck_assert_msg(memcmp(msg, "hello", sizeof("hello")) == 0, |
28 | 1 | "message was not expected 'hello' but '%s'", (const char *)msg); |
29 | | |
30 | 1 | *success = true; |
31 | 1 | } |
32 | | |
33 | | static void dump_events(const char *path, const Tox_Events *events) |
34 | 0 | { |
35 | 0 | FILE *fh = fopen(path, "w"); |
36 | 0 | ck_assert(fh != nullptr); |
37 | 0 | const uint32_t len = tox_events_bytes_size(events); |
38 | 0 | uint8_t *buf = (uint8_t *)malloc(len); |
39 | 0 | ck_assert(buf != nullptr); |
40 | 0 | ck_assert(tox_events_get_bytes(events, buf)); |
41 | 0 | fwrite(buf, 1, len, fh); |
42 | 0 | free(buf); |
43 | 0 | fclose(fh); |
44 | 0 | } |
45 | | |
46 | | static void print_events(const Tox_System *sys, Tox_Events *events) |
47 | 402 | { |
48 | 402 | const uint32_t size = tox_events_bytes_size(events); |
49 | | |
50 | 402 | uint8_t *bytes1 = (uint8_t *)malloc(size); |
51 | 402 | uint8_t *bytes2 = (uint8_t *)malloc(size); |
52 | 402 | ck_assert(bytes1 != nullptr); |
53 | 402 | ck_assert(bytes2 != nullptr); |
54 | | |
55 | 402 | ck_assert(tox_events_get_bytes(events, bytes1)); |
56 | 402 | ck_assert(tox_events_get_bytes(events, bytes2)); |
57 | | |
58 | | // Make sure get_bytes is deterministic. |
59 | 402 | ck_assert(memcmp(bytes1, bytes2, size) == 0); |
60 | | |
61 | 402 | Tox_Events *events_copy = tox_events_load(sys, bytes1, size); |
62 | 402 | ck_assert(events_copy != nullptr); |
63 | 402 | free(bytes1); |
64 | 402 | free(bytes2); |
65 | | |
66 | 402 | ck_assert(tox_events_equal(sys, events, events_copy)); |
67 | | |
68 | 402 | tox_events_free(events_copy); |
69 | 402 | tox_events_free(events); |
70 | 402 | } |
71 | | |
72 | | static bool await_message(Tox **toxes, const Tox_Dispatch *dispatch) |
73 | 1 | { |
74 | 1 | const Tox_System *sys = tox_get_system(toxes[0]); |
75 | | |
76 | 1 | for (uint32_t i = 0; i < 100; ++i) { |
77 | | // Ignore events on tox 1. |
78 | 1 | print_events(sys, tox_events_iterate(toxes[0], false, nullptr)); |
79 | | // Check if tox 2 got the message from tox 1. |
80 | 1 | Tox_Events *events = tox_events_iterate(toxes[1], false, nullptr); |
81 | | |
82 | 1 | if (want_dump_events) { |
83 | 0 | dump_events("/tmp/test.mp", events); |
84 | 0 | } |
85 | | |
86 | 1 | bool success = false; |
87 | 1 | tox_dispatch_invoke(dispatch, events, &success); |
88 | 1 | print_events(sys, events); |
89 | | |
90 | 1 | if (success) { |
91 | 1 | return true; |
92 | 1 | } |
93 | | |
94 | 0 | c_sleep(tox_iteration_interval(toxes[0])); |
95 | 0 | } |
96 | | |
97 | 0 | return false; |
98 | 1 | } |
99 | | |
100 | | static void test_tox_events(void) |
101 | 1 | { |
102 | 1 | uint8_t message[sizeof("hello")]; |
103 | 1 | memcpy(message, "hello", sizeof(message)); |
104 | | |
105 | 1 | Tox *toxes[2]; |
106 | 1 | uint32_t index[2]; |
107 | | |
108 | 3 | for (uint32_t i = 0; i < 2; ++i) { |
109 | 2 | index[i] = i + 1; |
110 | 2 | toxes[i] = tox_new_log(nullptr, nullptr, &index[i]); |
111 | 2 | tox_events_init(toxes[i]); |
112 | 2 | ck_assert_msg(toxes[i] != nullptr, "failed to create tox instances %u", i); |
113 | 2 | } |
114 | | |
115 | 1 | const Tox_System *sys = tox_get_system(toxes[0]); |
116 | | |
117 | 1 | Tox_Err_Dispatch_New err_new; |
118 | 1 | Tox_Dispatch *dispatch = tox_dispatch_new(&err_new); |
119 | 1 | ck_assert_msg(dispatch != nullptr, "failed to create event dispatcher"); |
120 | 1 | ck_assert(err_new == TOX_ERR_DISPATCH_NEW_OK); |
121 | | |
122 | 1 | tox_events_callback_friend_message(dispatch, handle_events_friend_message); |
123 | | |
124 | 1 | uint8_t pk[TOX_PUBLIC_KEY_SIZE]; |
125 | 1 | tox_self_get_dht_id(toxes[0], pk); |
126 | 1 | tox_bootstrap(toxes[1], "localhost", tox_self_get_udp_port(toxes[0], nullptr), pk, nullptr); |
127 | | |
128 | 1 | tox_self_get_public_key(toxes[0], pk); |
129 | 1 | tox_friend_add_norequest(toxes[1], pk, nullptr); |
130 | | |
131 | 1 | tox_self_get_public_key(toxes[1], pk); |
132 | 1 | tox_friend_add_norequest(toxes[0], pk, nullptr); |
133 | | |
134 | 1 | printf("bootstrapping and connecting 2 toxes\n"); |
135 | | |
136 | 159 | while (tox_self_get_connection_status(toxes[0]) == TOX_CONNECTION_NONE || |
137 | 159 | tox_self_get_connection_status(toxes[1]) == TOX_CONNECTION_NONE) { |
138 | | // Ignore connection events for now. |
139 | 158 | print_events(sys, tox_events_iterate(toxes[0], false, nullptr)); |
140 | 158 | print_events(sys, tox_events_iterate(toxes[1], false, nullptr)); |
141 | | |
142 | 158 | c_sleep(tox_iteration_interval(toxes[0])); |
143 | 158 | } |
144 | | |
145 | 1 | printf("toxes online, waiting for friend connection\n"); |
146 | | |
147 | 43 | while (tox_friend_get_connection_status(toxes[0], 0, nullptr) == TOX_CONNECTION_NONE || |
148 | 43 | tox_friend_get_connection_status(toxes[1], 0, nullptr) == TOX_CONNECTION_NONE) { |
149 | | // Ignore connection events for now. |
150 | 42 | print_events(sys, tox_events_iterate(toxes[0], false, nullptr)); |
151 | 42 | print_events(sys, tox_events_iterate(toxes[1], false, nullptr)); |
152 | | |
153 | 42 | c_sleep(tox_iteration_interval(toxes[0])); |
154 | 42 | } |
155 | | |
156 | 1 | printf("friends are connected via %s, now sending message\n", |
157 | 1 | tox_friend_get_connection_status(toxes[0], 0, nullptr) == TOX_CONNECTION_TCP ? "TCP" : "UDP"); |
158 | | |
159 | 1 | Tox_Err_Friend_Send_Message err; |
160 | 1 | tox_friend_send_message(toxes[0], 0, TOX_MESSAGE_TYPE_NORMAL, message, sizeof(message), &err); |
161 | 1 | ck_assert(err == TOX_ERR_FRIEND_SEND_MESSAGE_OK); |
162 | | |
163 | 1 | ck_assert(await_message(toxes, dispatch)); |
164 | | |
165 | 1 | tox_dispatch_free(dispatch); |
166 | | |
167 | 3 | for (uint32_t i = 0; i < 2; ++i) { |
168 | 2 | tox_kill(toxes[i]); |
169 | 2 | } |
170 | 1 | } |
171 | | |
172 | | int main(void) |
173 | 545 | { |
174 | 545 | setvbuf(stdout, nullptr, _IONBF, 0); |
175 | 545 | test_tox_events(); |
176 | 545 | return 0; |
177 | 545 | } |