xref: /freebsd/crypto/openssl/test/radix/quic_tests.c (revision e7be843b4a162e68651d3911f0357ed464915629)
1 /*
2  * Copyright 2024-2025 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the Apache License 2.0 (the "License").  You may not use
5  * this file except in compliance with the License.  You can obtain a copy
6  * in the file LICENSE in the source distribution or at
7  * https://www.openssl.org/source/license.html
8  */
9 
10 #if defined(_AIX)
11 /*
12  * Some versions of AIX define macros for events and revents for use when
13  * accessing pollfd structures (see Github issue #24236). That interferes
14  * with our use of these names here. We simply undef them.
15  */
16 # undef revents
17 # undef events
18 #endif
19 
20 /*
21  * Test Scripts
22  * ============================================================================
23  */
24 
25 /*
26  * Test: simple_conn
27  * -----------------
28  */
29 DEF_SCRIPT(simple_conn, "simple connection to server")
30 {
31     size_t i;
32 
33     for (i = 0; i < 2; ++i) {
34         if (i == 0) {
35             OP_SIMPLE_PAIR_CONN_D();
36         } else {
37             OP_CLEAR();
38             OP_SIMPLE_PAIR_CONN();
39         }
40 
41         OP_WRITE_B(C, "apple");
42 
43         OP_ACCEPT_CONN_WAIT(L, La, 0);
44         OP_ACCEPT_CONN_NONE(L);
45 
46         OP_READ_EXPECT_B(La, "apple");
47         OP_WRITE_B(La, "orange");
48         OP_READ_EXPECT_B(C, "orange");
49     }
50 }
51 
52 DEF_SCRIPT(simple_thread_child,
53            "test that RADIX multithreading is working (child)")
54 {
55 }
56 
57 /*
58  * Test: simple_thread
59  * -------------------
60  */
61 DEF_SCRIPT(simple_thread,
62            "test that RADIX multithreading is working")
63 {
64     size_t i;
65 
66     for (i = 0; i < 2; ++i)
67         OP_SPAWN_THREAD(simple_thread_child);
68 }
69 
70 /*
71  * Test: ssl_poll
72  * --------------
73  */
74 DEF_SCRIPT(ssl_poll_child,
75            "test that SSL_poll is working (child)")
76 {
77     OP_SLEEP(100);
78     OP_WRITE_B(C0, "extra");
79 }
80 
DEF_FUNC(ssl_poll_check)81 DEF_FUNC(ssl_poll_check)
82 {
83     int ok = 0;
84     SSL *La, *Lax[4];
85     SSL_POLL_ITEM items[6] = {0}, expected_items[6] = {0};
86     size_t result_count = 0, i;
87     const struct timeval z_timeout = {0}, *p_timeout = &z_timeout;
88     struct timeval timeout = {0};
89     uint64_t mode;
90     size_t expected_result_count;
91     OSSL_TIME time_before, time_after;
92 
93     F_POP(mode);
94     REQUIRE_SSL_5(La, Lax[0], Lax[1], Lax[2], Lax[3]);
95 
96     items[0].desc      = SSL_as_poll_descriptor(La);
97     items[0].events    = 0;
98     items[0].revents   = 0;
99 
100     for (i = 0; i < 4; ++i) {
101         items[i + 1].desc        = SSL_as_poll_descriptor(Lax[i]);
102         items[i + 1].events      = SSL_POLL_EVENT_R | SSL_POLL_EVENT_I;
103         items[i + 1].revents     = 0;
104     }
105 
106     items[5].desc = SSL_as_poll_descriptor(SSL_get0_listener(La));
107 
108     switch (mode) {
109     case 0: /* Nothing ready */
110     case 2:
111         expected_result_count = 0;
112         break;
113     case 1: /* Various events reported correctly */
114         expected_result_count       = 5;
115         items[0].events             = SSL_POLL_EVENT_OS;
116         expected_items[0].revents   = SSL_POLL_EVENT_OS;
117 
118         expected_items[1].revents   = SSL_POLL_EVENT_R;
119 
120         for (i = 0; i < 4; ++i) {
121             items[i + 1].events             |= SSL_POLL_EVENT_W;
122             expected_items[i + 1].revents   |= SSL_POLL_EVENT_W;
123         }
124 
125         break;
126     case 3: /* Blocking test */
127         expected_result_count       = 1;
128         expected_items[1].revents   = SSL_POLL_EVENT_R;
129 
130         p_timeout = &timeout;
131         timeout.tv_sec  = 10;
132         timeout.tv_usec = 0;
133         break;
134     case 4: /* Listener test */
135         expected_result_count       = 1;
136         items[5].events             = SSL_POLL_EVENT_IC;
137         expected_items[5].revents   = SSL_POLL_EVENT_IC;
138         break;
139     default:
140         goto err;
141     }
142 
143     /* Zero-timeout call. */
144     result_count = SIZE_MAX;
145     time_before = ossl_time_now();
146     if (!TEST_true(SSL_poll(items, OSSL_NELEM(items), sizeof(SSL_POLL_ITEM),
147                             p_timeout, 0, &result_count)))
148         goto err;
149 
150     time_after = ossl_time_now();
151     if (!TEST_size_t_eq(result_count, expected_result_count))
152         goto err;
153 
154     for (i = 0; i < OSSL_NELEM(items); ++i)
155         if (!TEST_uint64_t_eq(items[i].revents, expected_items[i].revents))
156             goto err;
157 
158     /*
159      * The SSL_poll call for the blocking test definitely shouldn't have
160      * returned sooner than in 100ms.
161      */
162     if (i == 3 && !TEST_uint64_t_ge(ossl_time2ms(ossl_time_subtract(time_after, time_before)), 100))
163         goto err;
164 
165     ok = 1;
166 err:
167     return ok;
168 }
169 
170 DEF_SCRIPT(ssl_poll,
171            "test that SSL_poll is working")
172 {
173     size_t i;
174 
175     OP_SIMPLE_PAIR_CONN_ND();
176 
177     /* Setup streams */
178     OP_NEW_STREAM(C, C0, 0);
179     OP_WRITE_B(C0, "apple");
180 
181     OP_NEW_STREAM(C, C1, 0);
182     OP_WRITE_B(C1, "orange");
183 
184     OP_NEW_STREAM(C, C2, 0);
185     OP_WRITE_B(C2, "Strawberry");
186 
187     OP_NEW_STREAM(C, C3, 0);
188     OP_WRITE_B(C3, "sync");
189 
190     OP_ACCEPT_CONN_WAIT1_ND(L, La, 0);
191 
192     OP_ACCEPT_STREAM_WAIT(La, La0, 0);
193     OP_READ_EXPECT_B(La0, "apple");
194 
195     OP_ACCEPT_STREAM_WAIT(La, La1, 0);
196     OP_READ_EXPECT_B(La1, "orange");
197 
198     OP_ACCEPT_STREAM_WAIT(La, La2, 0);
199     OP_READ_EXPECT_B(La2, "Strawberry");
200 
201     OP_ACCEPT_STREAM_WAIT(La, La3, 0);
202     OP_READ_EXPECT_B(La3, "sync");
203 
204     for (i = 0; i <= 4; ++i) {
205         /* 0: Check nothing ready */
206         /* 1: Check that various events are reported correctly */
207         /* 2: Check nothing ready */
208         /* 3: Blocking call unblocked from child thread */
209         /* 4: Listener test */
210 
211         if (i == 1) {
212             OP_WRITE_B(C0, "orange");
213             OP_WRITE_B(C3, "sync");
214             OP_READ_EXPECT_B(La3, "sync");
215         } else if (i == 2) {
216             OP_READ_EXPECT_B(La0, "orange");
217         } else if (i == 3) {
218             OP_SPAWN_THREAD(ssl_poll_child);
219         } else if (i == 4) {
220             OP_NEW_SSL_C(Cb);
221             OP_SET_PEER_ADDR_FROM(Cb, L);
222             OP_CONNECT_WAIT(Cb);
223         }
224 
225         OP_SELECT_SSL(0, La);
226         OP_SELECT_SSL(1, La0);
227         OP_SELECT_SSL(2, La1);
228         OP_SELECT_SSL(3, La2);
229         OP_SELECT_SSL(4, La3);
230         OP_PUSH_U64(i);
231         OP_FUNC(ssl_poll_check);
232 
233         if (i == 3)
234             OP_READ_EXPECT_B(La0, "extra");
235 
236         if (i == 4) {
237             OP_ACCEPT_CONN_WAIT1_ND(L, Lb, 0);
238             OP_NEW_STREAM(Lb, Lb0, 0);
239             OP_WRITE_B(Lb0, "foo");
240             OP_READ_EXPECT_B(Cb, "foo");
241         }
242     }
243 }
244 
DEF_FUNC(check_writeable)245 DEF_FUNC(check_writeable)
246 {
247     int ok = 0;
248     SSL *ssl;
249     SSL_POLL_ITEM item;
250     size_t result_count = 0;
251     uint64_t expect;
252     const struct timeval z_timeout = {0}, *p_timeout = &z_timeout;
253 
254     F_POP(expect);
255     REQUIRE_SSL(ssl);
256 
257     item.desc      = SSL_as_poll_descriptor(ssl);
258     item.events    = SSL_POLL_EVENT_W;
259     item.revents   = 0;
260 
261     /* Zero-timeout call. */
262     result_count = SIZE_MAX;
263     if (!TEST_true(SSL_poll(&item, 1, sizeof(SSL_POLL_ITEM),
264                             p_timeout, 0, &result_count)))
265         goto err;
266 
267     ok = (!!(item.revents & SSL_POLL_EVENT_W) == expect);
268 
269  err:
270     return ok;
271 }
272 
273 DEF_SCRIPT(check_cwm, "check stream obeys cwm")
274 {
275     OP_SIMPLE_PAIR_CONN();
276 
277     /* Create the initial stream by writing some data */
278     OP_WRITE_RAND(C, 1024);
279 
280     /* We should be writeable at the start */
281     OP_PUSH_U64(1);
282     OP_SELECT_SSL(0, C);
283     OP_FUNC(check_writeable);
284 
285     /* Default stream cwm is 512k (we already sent 1k). Consume all the rest */
286     OP_WRITE_RAND(C, 511 * 1024);
287 
288     /* Confirm we are no longer writeable */
289     OP_PUSH_U64(0);
290     OP_SELECT_SSL(0, C);
291     OP_FUNC(check_writeable);
292 
293     /* We now expect writes to fail */
294     OP_WRITE_FAIL(C);
295 }
296 
297 /*
298  * List of Test Scripts
299  * ============================================================================
300  */
301 static SCRIPT_INFO *const scripts[] = {
302     USE(simple_conn)
303     USE(simple_thread)
304     USE(ssl_poll)
305     USE(check_cwm)
306 };
307