OPENSSL_free(*tplext);
*grpext = glist;
*grpextlen = ngroups;
- kslist[0] = glist[0];
+ /*
+ * No * prefix was used, let tls_construct_ctos_key_share choose a key
+ * share. This has the advantage that it will filter unsupported groups
+ * before choosing one, which this function does not do. See also the
+ * comment for tls1_get_requested_keyshare_groups.
+ */
+ kslist[0] = 0;
*ksext = kslist;
*ksextlen = 1;
tpllist[0] = ngroups;
}
#endif
+/*
+ * Test that SSL_CTX_set1_groups() when called with a list where the first
+ * entry is unsupported, will send a key_share that uses the next usable entry.
+ */
+static int test_ssl_set_groups_unsupported_keyshare(void)
+{
+#if !defined(OPENSSL_NO_EC) || !defined(OPENSSL_NO_DH)
+ int testresult = 0;
+ SSL_CTX *sctx = NULL, *cctx = NULL;
+ SSL *serverssl = NULL, *clientssl = NULL;
+ int client_groups[] = {
+ NID_brainpoolP256r1tls13,
+ NID_sect163k1,
+ NID_secp384r1,
+ NID_ffdhe2048,
+ };
+
+ if (!TEST_true(create_ssl_ctx_pair(libctx,
+ TLS_server_method(),
+ TLS_client_method(),
+ 0, 0,
+ &sctx,
+ &cctx,
+ cert,
+ privkey)))
+ goto end;
+
+ if (!TEST_true(SSL_CTX_set1_groups(cctx,
+ client_groups,
+ OSSL_NELEM(client_groups))))
+ goto end;
+
+ if (!TEST_true(create_ssl_objects(sctx, cctx, &serverssl, &clientssl, NULL,
+ NULL)))
+ goto end;
+
+ if (!TEST_true(create_ssl_connection(serverssl, clientssl, SSL_ERROR_NONE)))
+ goto end;
+
+ testresult = 1;
+ end:
+ SSL_free(serverssl);
+ SSL_free(clientssl);
+ SSL_CTX_free(sctx);
+ SSL_CTX_free(cctx);
+
+ return testresult;
+#else /* !defined(OPENSSL_NO_EC) || !defined(OPENSSL_NO_DH) */
+ return TEST_skip("No EC and DH support.");
+#endif /* !defined(OPENSSL_NO_EC) || !defined(OPENSSL_NO_DH) */
+}
+
OPT_TEST_DECLARE_USAGE("certfile privkeyfile srpvfile tmpfile provider config dhfile\n")
int setup_tests(void)
if (datadir != NULL)
ADD_TEST(test_ssl_trace);
#endif
+ ADD_TEST(test_ssl_set_groups_unsupported_keyshare);
return 1;
err: