INCLUDE[quic_client_test]=../include ../apps/include
DEPEND[quic_client_test]=../libcrypto.a ../libssl.a libtestutil.a
- SOURCE[quic_multistream_test]=quic_multistream_test.c helpers/ssltestlib.c helpers/quictestlib.c
+ SOURCE[quic_multistream_test]=quic_multistream_test.c helpers/ssltestlib.c helpers/quictestlib.c helpers/noisydgrambio.c
INCLUDE[quic_multistream_test]=../include ../apps/include
DEPEND[quic_multistream_test]=../libcrypto.a ../libssl.a libtestutil.a
INCLUDE[event_queue_test]=../include ../apps/include
DEPEND[event_queue_test]=../libcrypto ../libssl.a libtestutil.a
- SOURCE[quicfaultstest]=quicfaultstest.c helpers/ssltestlib.c helpers/quictestlib.c
+ SOURCE[quicfaultstest]=quicfaultstest.c helpers/ssltestlib.c helpers/quictestlib.c helpers/noisydgrambio.c
INCLUDE[quicfaultstest]=../include ../apps/include ..
DEPEND[quicfaultstest]=../libcrypto.a ../libssl.a libtestutil.a
- SOURCE[quicapitest]=quicapitest.c helpers/ssltestlib.c helpers/quictestlib.c
+ SOURCE[quicapitest]=quicapitest.c helpers/ssltestlib.c helpers/quictestlib.c helpers/noisydgrambio.c
INCLUDE[quicapitest]=../include ../apps/include
DEPEND[quicapitest]=../libcrypto.a ../libssl.a libtestutil.a
- SOURCE[quic_newcid_test]=quic_newcid_test.c helpers/ssltestlib.c helpers/quictestlib.c
+ SOURCE[quic_newcid_test]=quic_newcid_test.c helpers/ssltestlib.c helpers/quictestlib.c helpers/noisydgrambio.c
INCLUDE[quic_newcid_test]=../include ../apps/include ..
DEPEND[quic_newcid_test]=../libcrypto.a ../libssl.a libtestutil.a
ENDIF
--- /dev/null
+/*
+ * Copyright 2023 The OpenSSL Project Authors. All Rights Reserved.
+ *
+ * Licensed under the Apache License 2.0 (the "License"). You may not use
+ * this file except in compliance with the License. You can obtain a copy
+ * in the file LICENSE in the source distribution or at
+ * https://www.openssl.org/source/license.html
+ */
+
+#include <openssl/bio.h>
+#include "quictestlib.h"
+
+static int noisy_dgram_read(BIO *bio, char *out, int outl)
+{
+ /* We don't support this - not needed anyway */
+ return -1;
+}
+
+static int noisy_dgram_write(BIO *bio, const char *in, int inl)
+{
+ /* We don't support this - not needed anyway */
+ return -1;
+}
+
+static long noisy_dgram_ctrl(BIO *bio, int cmd, long num, void *ptr)
+{
+ long ret;
+ BIO *next = BIO_next(bio);
+
+ if (next == NULL)
+ return 0;
+
+ switch (cmd) {
+ case BIO_CTRL_DUP:
+ ret = 0L;
+ break;
+ default:
+ ret = BIO_ctrl(next, cmd, num, ptr);
+ break;
+ }
+ return ret;
+}
+
+static int noisy_dgram_gets(BIO *bio, char *buf, int size)
+{
+ /* We don't support this - not needed anyway */
+ return -1;
+}
+
+static int noisy_dgram_puts(BIO *bio, const char *str)
+{
+ /* We don't support this - not needed anyway */
+ return -1;
+}
+
+static int noisy_dgram_sendmmsg(BIO *bio, BIO_MSG *msg, size_t stride,
+ size_t num_msg, uint64_t flags,
+ size_t *msgs_processed)
+{
+ BIO *next = BIO_next(bio);
+
+ if (next == NULL)
+ return 0;
+
+ /*
+ * We only introduce noise when receiving messages. We just pass this on
+ * to the underlying BIO.
+ */
+ return BIO_sendmmsg(next, msg, stride, num_msg, flags, msgs_processed);
+}
+
+static int noisy_dgram_recvmmsg(BIO *bio, BIO_MSG *msg, size_t stride,
+ size_t num_msg, uint64_t flags,
+ size_t *msgs_processed)
+{
+ BIO *next = BIO_next(bio);
+
+ if (next == NULL)
+ return 0;
+
+ /*
+ * We will introduce noise here. None implemented yet.
+ */
+ return BIO_recvmmsg(next, msg, stride, num_msg, flags, msgs_processed);
+}
+
+static int noisy_dgram_new(BIO *bio)
+{
+ BIO_set_init(bio, 1);
+
+ return 1;
+}
+
+static int noisy_dgram_free(BIO *bio)
+{
+ BIO_set_init(bio, 0);
+
+ return 1;
+}
+
+/* Choose a sufficiently large type likely to be unused for this custom BIO */
+#define BIO_TYPE_NOISY_DGRAM_FILTER (0x80 | BIO_TYPE_FILTER)
+
+static BIO_METHOD *method_noisy_dgram = NULL;
+
+/* Note: Not thread safe! */
+const BIO_METHOD *bio_f_noisy_dgram_filter(void)
+{
+ if (method_noisy_dgram == NULL) {
+ method_noisy_dgram = BIO_meth_new(BIO_TYPE_NOISY_DGRAM_FILTER,
+ "Nosiy datagram filter");
+ if (method_noisy_dgram == NULL
+ || !BIO_meth_set_write(method_noisy_dgram, noisy_dgram_write)
+ || !BIO_meth_set_read(method_noisy_dgram, noisy_dgram_read)
+ || !BIO_meth_set_puts(method_noisy_dgram, noisy_dgram_puts)
+ || !BIO_meth_set_gets(method_noisy_dgram, noisy_dgram_gets)
+ || !BIO_meth_set_ctrl(method_noisy_dgram, noisy_dgram_ctrl)
+ || !BIO_meth_set_sendmmsg(method_noisy_dgram, noisy_dgram_sendmmsg)
+ || !BIO_meth_set_recvmmsg(method_noisy_dgram, noisy_dgram_recvmmsg)
+ || !BIO_meth_set_create(method_noisy_dgram, noisy_dgram_new)
+ || !BIO_meth_set_destroy(method_noisy_dgram, noisy_dgram_free))
+ return NULL;
+ }
+ return method_noisy_dgram;
+}
+
+void bio_f_noisy_dgram_filter_free(void)
+{
+ BIO_meth_free(method_noisy_dgram);
+}
/* Flags for use with qtest_create_quic_objects() */
/* Indicates whether we are using blocking mode or not */
-#define QTEST_FLAG_BLOCK 1
+#define QTEST_FLAG_BLOCK (1 << 0)
/* Use fake time rather than real time */
-#define QTEST_FLAG_FAKE_TIME 2
+#define QTEST_FLAG_FAKE_TIME (1 << 1)
+/* Introduce noise in the BIO */
+#define QTEST_FLAG_NOISE (1 << 2)
/*
* Given an SSL_CTX for the client and filenames for the server certificate and
* exceeds the over allocation.
*/
int qtest_fault_resize_datagram(QTEST_FAULT *fault, size_t newlen);
+
+/* BIO filter for simulating a noisy UDP socket */
+const BIO_METHOD *bio_f_noisy_dgram_filter(void);
+
+/* Free the BIO filter method object */
+void bio_f_noisy_dgram_filter_free(void);
\ No newline at end of file
return testresult;
}
+static int test_noisy_dgram(void)
+{
+ SSL_CTX *cctx = SSL_CTX_new_ex(libctx, NULL, OSSL_QUIC_client_method());
+ SSL *clientquic = NULL;
+ QUIC_TSERVER *qtserv = NULL;
+ int testresult = 0;
+
+ if (!TEST_ptr(cctx)
+ || !TEST_true(qtest_create_quic_objects(libctx, cctx, NULL, cert,
+ privkey,
+ QTEST_FLAG_NOISE,
+ &qtserv,
+ &clientquic, NULL)))
+ goto err;
+
+ if (!TEST_true(qtest_create_quic_connection(qtserv, clientquic)))
+ goto err;
+
+ testresult = 1;
+ err:
+ ossl_quic_tserver_free(qtserv);
+ SSL_free(clientquic);
+ SSL_CTX_free(cctx);
+
+ return testresult;
+}
+
+
OPT_TEST_DECLARE_USAGE("provider config certsdir datadir\n")
int setup_tests(void)
ADD_ALL_TESTS(test_non_io_retry, 2);
ADD_TEST(test_quic_psk);
ADD_ALL_TESTS(test_alpn, 2);
+ ADD_TEST(test_noisy_dgram);
+
return 1;
err:
cleanup_tests();
void cleanup_tests(void)
{
+ bio_f_noisy_dgram_filter_free();
OPENSSL_free(cert);
OPENSSL_free(privkey);
OSSL_PROVIDER_unload(defctxnull);