2 * Copyright (c) 2021 Cisco and/or its affiliates.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at:
7 * http://www.apache.org/licenses/LICENSE-2.0
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
16 #include <hs_apps/vcl/vcl_test.h>
19 vt_tcp_connect (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
24 ts->fd = vppcom_session_create (VPPCOM_PROTO_TCP, 0 /* is_nonblocking */);
27 vterr ("vppcom_session_create()", ts->fd);
31 /* Connect is blocking */
32 rv = vppcom_session_connect (ts->fd, endpt);
35 vterr ("vppcom_session_connect()", rv);
39 ts->read = vcl_test_read;
40 ts->write = vcl_test_write;
42 flen = sizeof (flags);
43 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_FLAGS, &flags, &flen);
44 vtinf ("Test session %d (fd %d) connected.", ts->session_index, ts->fd);
50 vt_tcp_listen (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
54 ts->fd = vppcom_session_create (VPPCOM_PROTO_TCP, 0 /* is_nonblocking */);
57 vterr ("vppcom_session_create()", ts->fd);
61 rv = vppcom_session_bind (ts->fd, endpt);
64 vterr ("vppcom_session_bind()", rv);
68 rv = vppcom_session_listen (ts->fd, 10);
71 vterr ("vppcom_session_listen()", rv);
79 vt_tcp_accept (int listen_fd, vcl_test_session_t *ts)
83 client_fd = vppcom_session_accept (listen_fd, &ts->endpt, 0);
86 vterr ("vppcom_session_accept()", client_fd);
91 ts->read = vcl_test_read;
92 ts->write = vcl_test_write;
97 static const vcl_test_proto_vft_t vcl_test_tcp = {
98 .open = vt_tcp_connect,
99 .listen = vt_tcp_listen,
100 .accept = vt_tcp_accept,
103 VCL_TEST_REGISTER_PROTO (VPPCOM_PROTO_TCP, vcl_test_tcp);
106 vt_udp_connect (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
108 uint32_t flags, flen;
111 ts->fd = vppcom_session_create (VPPCOM_PROTO_UDP, 0 /* is_nonblocking */);
114 vterr ("vppcom_session_create()", ts->fd);
118 /* Connect is blocking */
119 rv = vppcom_session_connect (ts->fd, endpt);
122 vterr ("vppcom_session_connect()", rv);
126 ts->read = vcl_test_read;
127 ts->write = vcl_test_write;
129 flen = sizeof (flags);
130 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_FLAGS, &flags, &flen);
131 vtinf ("Test session %d (fd %d) connected.", ts->session_index, ts->fd);
137 vt_udp_listen (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
141 ts->fd = vppcom_session_create (VPPCOM_PROTO_UDP, 0 /* is_nonblocking */);
144 vterr ("vppcom_session_create()", ts->fd);
148 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_CONNECTED, 0, 0);
150 /* Listen is implicit */
151 rv = vppcom_session_bind (ts->fd, endpt);
154 vterr ("vppcom_session_bind()", rv);
162 vt_udp_accept (int listen_fd, vcl_test_session_t *ts)
166 client_fd = vppcom_session_accept (listen_fd, &ts->endpt, 0);
169 vterr ("vppcom_session_accept()", client_fd);
174 ts->read = vcl_test_read;
175 ts->write = vcl_test_write;
180 static const vcl_test_proto_vft_t vcl_test_udp = {
181 .open = vt_udp_connect,
182 .listen = vt_udp_listen,
183 .accept = vt_udp_accept,
186 VCL_TEST_REGISTER_PROTO (VPPCOM_PROTO_UDP, vcl_test_udp);
189 * TLS server cert and keys to be used for testing only
191 static char vcl_test_crt_rsa[] =
192 "-----BEGIN CERTIFICATE-----\r\n"
193 "MIID5zCCAs+gAwIBAgIJALeMYCEHrTtJMA0GCSqGSIb3DQEBCwUAMIGJMQswCQYD\r\n"
194 "VQQGEwJVUzELMAkGA1UECAwCQ0ExETAPBgNVBAcMCFNhbiBKb3NlMQ4wDAYDVQQK\r\n"
195 "DAVDaXNjbzEOMAwGA1UECwwFZmQuaW8xFjAUBgNVBAMMDXRlc3R0bHMuZmQuaW8x\r\n"
196 "IjAgBgkqhkiG9w0BCQEWE3ZwcC1kZXZAbGlzdHMuZmQuaW8wHhcNMTgwMzA1MjEx\r\n"
197 "NTEyWhcNMjgwMzAyMjExNTEyWjCBiTELMAkGA1UEBhMCVVMxCzAJBgNVBAgMAkNB\r\n"
198 "MREwDwYDVQQHDAhTYW4gSm9zZTEOMAwGA1UECgwFQ2lzY28xDjAMBgNVBAsMBWZk\r\n"
199 "LmlvMRYwFAYDVQQDDA10ZXN0dGxzLmZkLmlvMSIwIAYJKoZIhvcNAQkBFhN2cHAt\r\n"
200 "ZGV2QGxpc3RzLmZkLmlvMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA\r\n"
201 "4C1k8a1DuStgggqT4o09fP9sJ2dC54bxhS/Xk2VEfaIZ222WSo4X/syRVfVy9Yah\r\n"
202 "cpI1zJ/RDxaZSFhgA+nPZBrFMsrULkrdAOpOVj8eDEp9JuWdO2ODSoFnCvLxcYWB\r\n"
203 "Yc5kHryJpEaGJl1sFQSesnzMFty/59ta0stk0Fp8r5NhIjWvSovGzPo6Bhz+VS2c\r\n"
204 "ebIZh4x1t2hHaFcgm0qJoJ6DceReWCW8w+yOVovTolGGq+bpb2Hn7MnRSZ2K2NdL\r\n"
205 "+aLXpkZbS/AODP1FF2vTO1mYL290LO7/51vJmPXNKSDYMy5EvILr5/VqtjsFCwRL\r\n"
206 "Q4jcM/+GeHSAFWx4qIv0BwIDAQABo1AwTjAdBgNVHQ4EFgQUWa1SOB37xmT53tZQ\r\n"
207 "aXuLLhRI7U8wHwYDVR0jBBgwFoAUWa1SOB37xmT53tZQaXuLLhRI7U8wDAYDVR0T\r\n"
208 "BAUwAwEB/zANBgkqhkiG9w0BAQsFAAOCAQEAoUht13W4ya27NVzQuCMvqPWL3VM4\r\n"
209 "3xbPFk02FaGz/WupPu276zGlzJAZrbuDcQowwwU1Ni1Yygxl96s1c2M5rHDTrOKG\r\n"
210 "rK0hbkSFBo+i6I8u4HiiQ4rYmG0Hv6+sXn3of0HsbtDPGgWZoipPWDljPYEURu3e\r\n"
211 "3HRe/Dtsj9CakBoSDzs8ndWaBR+f4sM9Tk1cjD46Gq2T/qpSPXqKxEUXlzhdCAn4\r\n"
212 "twub17Bq2kykHpppCwPg5M+v30tHG/R2Go15MeFWbEJthFk3TZMjKL7UFs7fH+x2\r\n"
213 "wSonXb++jY+KmCb93C+soABBizE57g/KmiR2IxQ/LMjDik01RSUIaM0lLA==\r\n"
214 "-----END CERTIFICATE-----\r\n";
215 static uint32_t vcl_test_crt_rsa_len = sizeof (vcl_test_crt_rsa);
217 static char vcl_test_key_rsa[] =
218 "-----BEGIN PRIVATE KEY-----\r\n"
219 "MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQDgLWTxrUO5K2CC\r\n"
220 "CpPijT18/2wnZ0LnhvGFL9eTZUR9ohnbbZZKjhf+zJFV9XL1hqFykjXMn9EPFplI\r\n"
221 "WGAD6c9kGsUyytQuSt0A6k5WPx4MSn0m5Z07Y4NKgWcK8vFxhYFhzmQevImkRoYm\r\n"
222 "XWwVBJ6yfMwW3L/n21rSy2TQWnyvk2EiNa9Ki8bM+joGHP5VLZx5shmHjHW3aEdo\r\n"
223 "VyCbSomgnoNx5F5YJbzD7I5Wi9OiUYar5ulvYefsydFJnYrY10v5otemRltL8A4M\r\n"
224 "/UUXa9M7WZgvb3Qs7v/nW8mY9c0pINgzLkS8guvn9Wq2OwULBEtDiNwz/4Z4dIAV\r\n"
225 "bHioi/QHAgMBAAECggEBAMzGipP8+oT166U+NlJXRFifFVN1DvdhG9PWnOxGL+c3\r\n"
226 "ILmBBC08WQzmHshPemBvR6DZkA1H23cV5JTiLWrFtC00CvhXsLRMrE5+uWotI6yE\r\n"
227 "iofybMroHvD6/X5R510UX9hQ6MHu5ShLR5VZ9zXHz5MpTmB/60jG5dLx+jgcwBK8\r\n"
228 "LuGv2YB/WCUwT9QJ3YU2eaingnXtz/MrFbkbltrqlnBdlD+kTtw6Yac9y1XuuQXc\r\n"
229 "BPeulLNDuPolJVWbUvDBZrpt2dXTgz8ws1sv+wCNE0xwQJsqW4Nx3QkpibUL9RUr\r\n"
230 "CVbKlNfa9lopT6nGKlgX69R/uH35yh9AOsfasro6w0ECgYEA82UJ8u/+ORah+0sF\r\n"
231 "Q0FfW5MTdi7OAUHOz16pUsGlaEv0ERrjZxmAkHA/VRwpvDBpx4alCv0Hc39PFLIk\r\n"
232 "nhSsM2BEuBkTAs6/GaoNAiBtQVE/hN7awNRWVmlieS0go3Y3dzaE9IUMyj8sPOFT\r\n"
233 "5JdJ6BM69PHKCkY3dKdnnfpFEuECgYEA68mRpteunF1mdZgXs+WrN+uLlRrQR20F\r\n"
234 "ZyMYiUCH2Dtn26EzA2moy7FipIIrQcX/j+KhYNGM3e7MU4LymIO29E18mn8JODnH\r\n"
235 "sQOXzBTsf8A4yIVMkcuQD3bfb0JiUGYUPOidTp2N7IJA7+6Yc3vQOyb74lnKnJoO\r\n"
236 "gougPT2wS+cCgYAn7muzb6xFsXDhyW0Tm6YJYBfRS9yAWEuVufINobeBZPSl2cN1\r\n"
237 "Jrnw+HlrfTNbrJWuJmjtZJXUXQ6cVp2rUbjutNyRV4vG6iRwEXYQ40EJdkr1gZpi\r\n"
238 "CHQhuShuuPih2MNAy7EEbM+sXrDjTBR3bFqzuHPzu7dp+BshCFX3lRfAAQKBgGQt\r\n"
239 "K5i7IhCFDjb/+3IPLgOAK7mZvsvZ4eXD33TQ2eZgtut1PXtBtNl17/b85uv293Fm\r\n"
240 "VDISVcsk3eLNS8zIiT6afUoWlxAwXEs0v5WRfjl4radkGvgGiJpJYvyeM67877RB\r\n"
241 "EDSKc/X8ESLfOB44iGvZUEMG6zJFscx9DgN25iQZAoGAbyd+JEWwdVH9/K3IH1t2\r\n"
242 "PBkZX17kNWv+iVM1WyFjbe++vfKZCrOJiyiqhDeEqgrP3AuNMlaaduC3VRC3G5oV\r\n"
243 "Mj1tlhDWQ/qhvKdCKNdIVQYDE75nw+FRWV8yYkHAnXYW3tNoweDIwixE0hkPR1bc\r\n"
244 "oEjPLVNtx8SOj/M4rhaPT3I=\r\n"
245 "-----END PRIVATE KEY-----\r\n";
246 static uint32_t vcl_test_key_rsa_len = sizeof (vcl_test_key_rsa);
249 vt_add_cert_key_pair ()
251 vcl_test_main_t *vt = &vcl_test_main;
252 vppcom_cert_key_pair_t ckpair;
255 vtinf ("Adding tls certs ...");
257 ckpair.cert = vcl_test_crt_rsa;
258 ckpair.key = vcl_test_key_rsa;
259 ckpair.cert_len = vcl_test_crt_rsa_len;
260 ckpair.key_len = vcl_test_key_rsa_len;
261 ckp_index = vppcom_add_cert_key_pair (&ckpair);
264 vterr ("vppcom_add_cert_key_pair()", ckp_index);
268 vt->ckpair_index = ckp_index;
273 vt_tls_init (vcl_test_cfg_t *cfg)
275 return vt_add_cert_key_pair ();
279 vt_tls_connect (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
281 vcl_test_main_t *vt = &vcl_test_main;
282 uint32_t flags, flen, ckp_len;
285 ts->fd = vppcom_session_create (VPPCOM_PROTO_TLS, 0 /* is_nonblocking */);
288 vterr ("vppcom_session_create()", ts->fd);
292 ckp_len = sizeof (vt->ckpair_index);
293 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_CKPAIR, &vt->ckpair_index,
296 /* Connect is blocking */
297 rv = vppcom_session_connect (ts->fd, endpt);
300 vterr ("vppcom_session_connect()", rv);
304 ts->read = vcl_test_read;
305 ts->write = vcl_test_write;
307 flen = sizeof (flags);
308 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_FLAGS, &flags, &flen);
309 vtinf ("Test session %d (fd %d) connected.", ts->session_index, ts->fd);
315 vt_tls_listen (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
317 vcl_test_main_t *vt = &vcl_test_main;
321 ts->fd = vppcom_session_create (VPPCOM_PROTO_TLS, 0 /* is_nonblocking */);
324 vterr ("vppcom_session_create()", ts->fd);
328 ckp_len = sizeof (vt->ckpair_index);
329 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_CKPAIR, &vt->ckpair_index,
332 rv = vppcom_session_bind (ts->fd, endpt);
335 vterr ("vppcom_session_bind()", rv);
339 rv = vppcom_session_listen (ts->fd, 10);
342 vterr ("vppcom_session_listen()", rv);
350 vt_tls_accept (int listen_fd, vcl_test_session_t *ts)
354 client_fd = vppcom_session_accept (listen_fd, &ts->endpt, 0);
357 vterr ("vppcom_session_accept()", client_fd);
362 ts->read = vcl_test_read;
363 ts->write = vcl_test_write;
368 static const vcl_test_proto_vft_t vcl_test_tls = {
370 .open = vt_tls_connect,
371 .listen = vt_tls_listen,
372 .accept = vt_tls_accept,
375 VCL_TEST_REGISTER_PROTO (VPPCOM_PROTO_TLS, vcl_test_tls);
378 vt_dtls_init (vcl_test_cfg_t *cfg)
380 return vt_add_cert_key_pair ();
384 vt_dtls_connect (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
386 vcl_test_main_t *vt = &vcl_test_main;
387 uint32_t flags, flen, ckp_len;
390 ts->fd = vppcom_session_create (VPPCOM_PROTO_DTLS, 0 /* is_nonblocking */);
393 vterr ("vppcom_session_create()", ts->fd);
397 ckp_len = sizeof (vt->ckpair_index);
398 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_CKPAIR, &vt->ckpair_index,
401 /* Connect is blocking */
402 rv = vppcom_session_connect (ts->fd, endpt);
405 vterr ("vppcom_session_connect()", rv);
409 ts->read = vcl_test_read;
410 ts->write = vcl_test_write;
412 flen = sizeof (flags);
413 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_FLAGS, &flags, &flen);
414 vtinf ("Test session %d (fd %d) connected.", ts->session_index, ts->fd);
420 vt_dtls_listen (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
422 vcl_test_main_t *vt = &vcl_test_main;
426 ts->fd = vppcom_session_create (VPPCOM_PROTO_DTLS, 0 /* is_nonblocking */);
429 vterr ("vppcom_session_create()", ts->fd);
433 ckp_len = sizeof (vt->ckpair_index);
434 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_CKPAIR, &vt->ckpair_index,
437 rv = vppcom_session_bind (ts->fd, endpt);
440 vterr ("vppcom_session_bind()", rv);
444 rv = vppcom_session_listen (ts->fd, 10);
447 vterr ("vppcom_session_listen()", rv);
455 vt_dtls_accept (int listen_fd, vcl_test_session_t *ts)
459 client_fd = vppcom_session_accept (listen_fd, &ts->endpt, 0);
462 vterr ("vppcom_session_accept()", client_fd);
467 ts->read = vcl_test_read;
468 ts->write = vcl_test_write;
473 static const vcl_test_proto_vft_t vcl_test_dtls = {
474 .init = vt_dtls_init,
475 .open = vt_dtls_connect,
476 .listen = vt_dtls_listen,
477 .accept = vt_dtls_accept,
480 VCL_TEST_REGISTER_PROTO (VPPCOM_PROTO_DTLS, vcl_test_dtls);
483 vt_quic_init (vcl_test_cfg_t *cfg)
485 vcl_test_main_t *vt = &vcl_test_main;
490 return vt_add_cert_key_pair ();
494 vt_quic_maybe_init_wrk (vcl_test_main_t *vt, vcl_test_wrk_t *wrk,
495 vppcom_endpt_t *endpt)
497 uint32_t size, i, flags, flen, ckp_len;
498 vcl_test_session_t *tq;
501 /* Test already initialized */
502 if (wrk->n_qsessions == vt->cfg.num_test_qsessions)
505 /* Make sure pool is large enough */
509 calloc (vt->cfg.num_test_qsessions, sizeof (vcl_test_session_t));
513 size = vt->cfg.num_test_qsessions * sizeof (vcl_test_session_t);
514 wrk->qsessions = realloc (wrk->qsessions, size);
519 vterr ("failed to alloc Qsessions", -errno);
523 for (i = 0; i < vt->cfg.num_test_qsessions; i++)
525 tq = &wrk->qsessions[i];
527 vppcom_session_create (VPPCOM_PROTO_QUIC, 0 /* is_nonblocking */);
528 tq->session_index = i;
531 vterr ("vppcom_session_create()", tq->fd);
535 ckp_len = sizeof (vt->ckpair_index);
536 vppcom_session_attr (tq->fd, VPPCOM_ATTR_SET_CKPAIR, &vt->ckpair_index,
539 /* Connect is blocking */
540 rv = vppcom_session_connect (tq->fd, endpt);
543 vterr ("vppcom_session_connect()", rv);
547 flen = sizeof (flags);
548 vppcom_session_attr (tq->fd, VPPCOM_ATTR_SET_FLAGS, &flags, &flen);
549 vtinf ("Test Qsession %d (fd %d) connected.", i, tq->fd);
551 wrk->n_qsessions = vt->cfg.num_test_qsessions;
557 vt_quic_connect (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
559 vcl_test_main_t *vt = &vcl_test_main;
560 uint32_t wrk_index, flags, flen;
561 vcl_test_session_t *tq;
565 wrk_index = vcl_test_worker_index ();
566 wrk = &vt->wrk[wrk_index];
568 /* Make sure qsessions are initialized */
569 vt_quic_maybe_init_wrk (vt, wrk, endpt);
571 ts->fd = vppcom_session_create (VPPCOM_PROTO_QUIC, 0 /* is_nonblocking */);
574 vterr ("vppcom_session_create()", ts->fd);
578 /* Choose qession to use for stream */
579 tq = &wrk->qsessions[ts->session_index / vt->cfg.num_test_sessions_perq];
581 rv = vppcom_session_stream_connect (ts->fd, tq->fd);
584 vterr ("vppcom_session_stream_connect()", rv);
589 flen = sizeof (flags);
590 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_FLAGS, &flags, &flen);
592 ts->read = vcl_test_read;
593 ts->write = vcl_test_write;
595 vtinf ("Test (quic stream) session %d (fd %d) connected.", ts->session_index,
602 vt_quic_listen (vcl_test_session_t *ts, vppcom_endpt_t *endpt)
604 vcl_test_main_t *vt = &vcl_test_main;
608 ts->fd = vppcom_session_create (VPPCOM_PROTO_QUIC, 1 /* is_nonblocking */);
611 vterr ("vppcom_session_create()", ts->fd);
615 ckp_len = sizeof (vt->ckpair_index);
616 vppcom_session_attr (ts->fd, VPPCOM_ATTR_SET_CKPAIR, &vt->ckpair_index,
619 rv = vppcom_session_bind (ts->fd, endpt);
622 vterr ("vppcom_session_bind()", rv);
626 rv = vppcom_session_listen (ts->fd, 10);
629 vterr ("vppcom_session_listen()", rv);
637 vt_quic_accept (int listen_fd, vcl_test_session_t *ts)
641 client_fd = vppcom_session_accept (listen_fd, &ts->endpt, 0);
644 vterr ("vppcom_session_accept()", client_fd);
649 ts->read = vcl_test_read;
650 ts->write = vcl_test_write;
656 vt_quic_close (vcl_test_session_t *ts)
658 int listener_fd = vppcom_session_listener (ts->fd);
660 if ((vppcom_session_n_accepted (listener_fd) == 0) &
661 vppcom_session_is_connectable_listener (listener_fd))
663 vtinf ("Connected Listener fd %x has no more sessions", listener_fd);
664 vppcom_session_close (listener_fd);
670 static const vcl_test_proto_vft_t vcl_test_quic = {
671 .init = vt_quic_init,
672 .open = vt_quic_connect,
673 .listen = vt_quic_listen,
674 .accept = vt_quic_accept,
675 .close = vt_quic_close,
678 VCL_TEST_REGISTER_PROTO (VPPCOM_PROTO_QUIC, vcl_test_quic);
681 * fd.io coding-style-patch-verification: ON
684 * eval: (c-set-style "gnu")