]> git.ipfire.org Git - thirdparty/openssl.git/commitdiff
Add a DTLSv1_listen() test
authorMatt Caswell <matt@openssl.org>
Mon, 11 Apr 2022 13:37:16 +0000 (14:37 +0100)
committerMatt Caswell <matt@openssl.org>
Thu, 18 Aug 2022 15:38:12 +0000 (16:38 +0100)
Add a test to ensure that a connection started via DTLSv1_listen() can
be completed through to handshake success. Previous DTLSv1_listen()
testing only tested the function itself and did not confirm that a
connection can actually be achieved using it.

This is important to test some codepaths being affected by the record layer
refactor.

Reviewed-by: Hugo Landau <hlandau@openssl.org>
Reviewed-by: Tomas Mraz <tomas@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/18132)

test/dtlstest.c
test/helpers/ssltestlib.c
test/helpers/ssltestlib.h
test/quicapitest.c
test/sslapitest.c

index f84f2c1299a0351e6410d15e1f16965be8af0cef..8016a112e92cd768d4c2d2aca4e6568620ed4d65 100644 (file)
@@ -109,7 +109,7 @@ static int test_dtls_unprocessed(int testidx)
      * they will fail to decrypt.
      */
     if (!TEST_true(create_bare_ssl_connection(serverssl1, clientssl1,
-                                              SSL_ERROR_NONE, 0)))
+                                              SSL_ERROR_NONE, 0, 0)))
         goto end;
 
     if (timer_cb_count == 0) {
@@ -606,6 +606,56 @@ static int test_swap_app_data(void)
     SSL_free(sssl);
     SSL_CTX_free(cctx);
     SSL_CTX_free(sctx);
+
+    return testresult;
+}
+
+/* Confirm that we can create a connections using DTLSv1_listen() */
+static int test_listen(void)
+{
+    SSL_CTX *sctx = NULL, *cctx = NULL;
+    SSL *serverssl = NULL, *clientssl = NULL;
+    int testresult = 0;
+
+    if (!TEST_true(create_ssl_ctx_pair(NULL, DTLS_server_method(),
+                                       DTLS_client_method(),
+                                       DTLS1_VERSION, 0,
+                                       &sctx, &cctx, cert, privkey)))
+        return 0;
+
+#ifdef OPENSSL_NO_DTLS1_2
+    /* Default sigalgs are SHA1 based in <DTLS1.2 which is in security level 0 */
+    if (!TEST_true(SSL_CTX_set_cipher_list(sctx, "DEFAULT:@SECLEVEL=0"))
+            || !TEST_true(SSL_CTX_set_cipher_list(cctx,
+                                                  "DEFAULT:@SECLEVEL=0")))
+        goto end;
+#endif
+
+    SSL_CTX_set_cookie_generate_cb(sctx, generate_cookie_cb);
+    SSL_CTX_set_cookie_verify_cb(sctx, verify_cookie_cb);
+
+    if (!TEST_true(create_ssl_objects(sctx, cctx, &serverssl, &clientssl,
+                                      NULL, NULL)))
+        goto end;
+
+    DTLS_set_timer_cb(clientssl, timer_cb);
+    DTLS_set_timer_cb(serverssl, timer_cb);
+
+    /*
+     * The last parameter to create_bare_ssl_connection() requests that
+     * DLTSv1_listen() is used.
+     */
+    if (!TEST_true(create_bare_ssl_connection(serverssl, clientssl,
+                                              SSL_ERROR_NONE, 1, 1)))
+        goto end;
+
+    testresult = 1;
+ end:
+    SSL_free(serverssl);
+    SSL_free(clientssl);
+    SSL_CTX_free(sctx);
+    SSL_CTX_free(cctx);
+
     return testresult;
 }
 
@@ -631,6 +681,7 @@ int setup_tests(void)
     ADD_TEST(test_just_finished);
     ADD_TEST(test_swap_epoch);
     ADD_TEST(test_swap_app_data);
+    ADD_TEST(test_listen);
 
     return 1;
 }
index 2c33851167b1bec8bfaaa536e3a307d265057de3..d95cfef6c574177b9a02cd9f3783a9c9d977fffb 100644 (file)
@@ -1055,11 +1055,29 @@ int create_ssl_objects(SSL_CTX *serverctx, SSL_CTX *clientctx, SSL **sssl,
  * attempt could be restarted by a subsequent call to this function.
  */
 int create_bare_ssl_connection(SSL *serverssl, SSL *clientssl, int want,
-                               int read)
+                               int read, int listen)
 {
-    int retc = -1, rets = -1, err, abortctr = 0;
+    int retc = -1, rets = -1, err, abortctr = 0, ret = 0;
     int clienterr = 0, servererr = 0;
     int isdtls = SSL_is_dtls(serverssl);
+#ifndef OPENSSL_NO_SOCK
+    BIO_ADDR *peer = NULL;
+
+    if (listen) {
+        if (!isdtls) {
+            TEST_error("DTLSv1_listen requested for non-DTLS object\n");
+            return 0;
+        }
+        peer = BIO_ADDR_new();
+        if (!TEST_ptr(peer))
+            return 0;
+    }
+#else
+    if (listen) {
+        TEST_error("DTLSv1_listen requested in a no-sock build\n");
+        return 0;
+    }
+#endif
 
     do {
         err = SSL_ERROR_WANT_WRITE;
@@ -1076,13 +1094,29 @@ int create_bare_ssl_connection(SSL *serverssl, SSL *clientssl, int want,
             clienterr = 1;
         }
         if (want != SSL_ERROR_NONE && err == want)
-            return 0;
+            goto err;
 
         err = SSL_ERROR_WANT_WRITE;
         while (!servererr && rets <= 0 && err == SSL_ERROR_WANT_WRITE) {
-            rets = SSL_accept(serverssl);
-            if (rets <= 0)
-                err = SSL_get_error(serverssl, rets);
+#ifndef OPENSSL_NO_SOCK
+            if (listen) {
+                rets = DTLSv1_listen(serverssl, peer);
+                if (rets < 0) {
+                    err = SSL_ERROR_SSL;
+                } else if (rets == 0) {
+                    err = SSL_ERROR_WANT_READ;
+                } else {
+                    /* Success - stop listening and call SSL_accept from now on */
+                    listen = 0;
+                    rets = 0;
+                }
+            } else
+#endif
+            {
+                rets = SSL_accept(serverssl);
+                if (rets <= 0)
+                    err = SSL_get_error(serverssl, rets);
+            }
         }
 
         if (!servererr && rets <= 0
@@ -1094,9 +1128,9 @@ int create_bare_ssl_connection(SSL *serverssl, SSL *clientssl, int want,
             servererr = 1;
         }
         if (want != SSL_ERROR_NONE && err == want)
-            return 0;
+            goto err;
         if (clienterr && servererr)
-            return 0;
+            goto err;
         if (isdtls && read) {
             unsigned char buf[20];
 
@@ -1105,20 +1139,20 @@ int create_bare_ssl_connection(SSL *serverssl, SSL *clientssl, int want,
                 if (SSL_read(serverssl, buf, sizeof(buf)) > 0) {
                     /* We don't expect this to succeed! */
                     TEST_info("Unexpected SSL_read() success!");
-                    return 0;
+                    goto err;
                 }
             }
             if (retc > 0 && rets <= 0) {
                 if (SSL_read(clientssl, buf, sizeof(buf)) > 0) {
                     /* We don't expect this to succeed! */
                     TEST_info("Unexpected SSL_read() success!");
-                    return 0;
+                    goto err;
                 }
             }
         }
         if (++abortctr == MAXLOOPS) {
             TEST_info("No progress made");
-            return 0;
+            goto err;
         }
         if (isdtls && abortctr <= 50 && (abortctr % 10) == 0) {
             /*
@@ -1130,7 +1164,12 @@ int create_bare_ssl_connection(SSL *serverssl, SSL *clientssl, int want,
         }
     } while (retc <=0 || rets <= 0);
 
-    return 1;
+    ret = 1;
+ err:
+#ifndef OPENSSL_NO_SOCK
+    BIO_ADDR_free(peer);
+#endif
+    return ret;
 }
 
 /*
@@ -1143,7 +1182,7 @@ int create_ssl_connection(SSL *serverssl, SSL *clientssl, int want)
     unsigned char buf;
     size_t readbytes;
 
-    if (!create_bare_ssl_connection(serverssl, clientssl, want, 1))
+    if (!create_bare_ssl_connection(serverssl, clientssl, want, 1, 0))
         return 0;
 
     /*
index 6f39388fca95eaffc96c5153a699a61679af6eb4..d8ee6a9b7d04d639c3cc4d279e5e1f61d53cae38 100644 (file)
@@ -19,7 +19,7 @@ int create_ssl_ctx_pair(OSSL_LIB_CTX *libctx, const SSL_METHOD *sm,
 int create_ssl_objects(SSL_CTX *serverctx, SSL_CTX *clientctx, SSL **sssl,
                        SSL **cssl, BIO *s_to_c_fbio, BIO *c_to_s_fbio);
 int create_bare_ssl_connection(SSL *serverssl, SSL *clientssl, int want,
-                               int read);
+                               int read, int listen);
 int create_ssl_objects2(SSL_CTX *serverctx, SSL_CTX *clientctx, SSL **sssl,
                        SSL **cssl, int sfd, int cfd);
 int create_test_sockets(int *cfd, int *sfd);
index 1b647768d4272e9da85681d4cc75cdb40080e923..896b7bc3a1285a04440338e7b4c0c5d837155ae4 100644 (file)
@@ -43,7 +43,7 @@ static int test_quic_write_read(void)
             || !TEST_true(create_ssl_objects(sctx, cctx, &serverquic, &clientquic,
                                              NULL, NULL))
             || !TEST_true(create_bare_ssl_connection(serverquic, clientquic,
-                                                     SSL_ERROR_NONE, 0)))
+                                                     SSL_ERROR_NONE, 0, 0)))
         goto end;
 
     for (j = 0; j < 2; j++) {
index 3f8cbd9da288a4f247947e83790ae4909fcdc7bb..00e9ba39ae2cb5d102321d6ddd489c4bba4361c0 100644 (file)
@@ -7902,7 +7902,7 @@ static int test_shutdown(int tst)
 
     if (tst == 3) {
         if (!TEST_true(create_bare_ssl_connection(serverssl, clientssl,
-                                                  SSL_ERROR_NONE, 1))
+                                                  SSL_ERROR_NONE, 1, 0))
                 || !TEST_ptr_ne(sess = SSL_get_session(clientssl), NULL)
                 || !TEST_false(SSL_SESSION_is_resumable(sess)))
             goto end;