Add SSL_CTX_cipher_in_group.
This allows us to fix another consumer that directly accesses SSL_CTX.
I've made ssl_test use it for test coverage, though we're okay with
ssl_test depending on ssl/internal.h.
Bug: 6
Change-Id: I464325e3faa9f0194bbd357fbb31a996afc0c2e1
Reviewed-on: https://boringssl-review.googlesource.com/18964
Commit-Queue: David Benjamin <davidben@google.com>
Commit-Queue: Adam Langley <agl@google.com>
Reviewed-by: Adam Langley <agl@google.com>
diff --git a/include/openssl/ssl.h b/include/openssl/ssl.h
index 0eb2cc5..c989dd6 100644
--- a/include/openssl/ssl.h
+++ b/include/openssl/ssl.h
@@ -1414,6 +1414,11 @@
* preference. */
OPENSSL_EXPORT STACK_OF(SSL_CIPHER) *SSL_CTX_get_ciphers(const SSL_CTX *ctx);
+/* SSL_CTX_cipher_in_group returns one if the |i|th cipher (see
+ * |SSL_CTX_get_ciphers|) is in the same equipreference group as the one
+ * following it and zero otherwise. */
+OPENSSL_EXPORT int SSL_CTX_cipher_in_group(const SSL_CTX *ctx, size_t i);
+
/* SSL_get_ciphers returns the cipher list for |ssl|, in order of preference. */
OPENSSL_EXPORT STACK_OF(SSL_CIPHER) *SSL_get_ciphers(const SSL *ssl);
diff --git a/ssl/ssl_lib.cc b/ssl/ssl_lib.cc
index 950bbf8..10128d8 100644
--- a/ssl/ssl_lib.cc
+++ b/ssl/ssl_lib.cc
@@ -1658,10 +1658,17 @@
return 1;
}
-OPENSSL_EXPORT STACK_OF(SSL_CIPHER) *SSL_CTX_get_ciphers(const SSL_CTX *ctx) {
+STACK_OF(SSL_CIPHER) *SSL_CTX_get_ciphers(const SSL_CTX *ctx) {
return ctx->cipher_list->ciphers;
}
+int SSL_CTX_cipher_in_group(const SSL_CTX *ctx, size_t i) {
+ if (i >= sk_SSL_CIPHER_num(ctx->cipher_list->ciphers)) {
+ return 0;
+ }
+ return ctx->cipher_list->in_group_flags[i];
+}
+
STACK_OF(SSL_CIPHER) *SSL_get_ciphers(const SSL *ssl) {
if (ssl == NULL) {
return NULL;
diff --git a/ssl/ssl_test.cc b/ssl/ssl_test.cc
index 4556fb7..88c2ed2 100644
--- a/ssl/ssl_test.cc
+++ b/ssl/ssl_test.cc
@@ -361,12 +361,13 @@
":X25519:P-256",
};
-static std::string CipherListToString(ssl_cipher_preference_list_st *list) {
+static std::string CipherListToString(SSL_CTX *ctx) {
bool in_group = false;
std::string ret;
- for (size_t i = 0; i < sk_SSL_CIPHER_num(list->ciphers); i++) {
- const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(list->ciphers, i);
- if (!in_group && list->in_group_flags[i]) {
+ const STACK_OF(SSL_CIPHER) *ciphers = SSL_CTX_get_ciphers(ctx);
+ for (size_t i = 0; i < sk_SSL_CIPHER_num(ciphers); i++) {
+ const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(ciphers, i);
+ if (!in_group && SSL_CTX_cipher_in_group(ctx, i)) {
ret += "\t[\n";
in_group = true;
}
@@ -376,7 +377,7 @@
}
ret += SSL_CIPHER_get_name(cipher);
ret += "\n";
- if (in_group && !list->in_group_flags[i]) {
+ if (in_group && !SSL_CTX_cipher_in_group(ctx, i)) {
ret += "\t]\n";
in_group = false;
}
@@ -384,16 +385,17 @@
return ret;
}
-static bool CipherListsEqual(ssl_cipher_preference_list_st *list,
+static bool CipherListsEqual(SSL_CTX *ctx,
const std::vector<ExpectedCipher> &expected) {
- if (sk_SSL_CIPHER_num(list->ciphers) != expected.size()) {
+ const STACK_OF(SSL_CIPHER) *ciphers = SSL_CTX_get_ciphers(ctx);
+ if (sk_SSL_CIPHER_num(ciphers) != expected.size()) {
return false;
}
for (size_t i = 0; i < expected.size(); i++) {
- const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(list->ciphers, i);
+ const SSL_CIPHER *cipher = sk_SSL_CIPHER_value(ciphers, i);
if (expected[i].id != SSL_CIPHER_get_id(cipher) ||
- expected[i].in_group_flag != list->in_group_flags[i]) {
+ expected[i].in_group_flag != !!SSL_CTX_cipher_in_group(ctx, i)) {
return false;
}
}
@@ -409,18 +411,18 @@
// Test lax mode.
ASSERT_TRUE(SSL_CTX_set_cipher_list(ctx.get(), t.rule));
- EXPECT_TRUE(CipherListsEqual(ctx->cipher_list, t.expected))
+ EXPECT_TRUE(CipherListsEqual(ctx.get(), t.expected))
<< "Cipher rule evaluated to:\n"
- << CipherListToString(ctx->cipher_list);
+ << CipherListToString(ctx.get());
// Test strict mode.
if (t.strict_fail) {
EXPECT_FALSE(SSL_CTX_set_strict_cipher_list(ctx.get(), t.rule));
} else {
ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(ctx.get(), t.rule));
- EXPECT_TRUE(CipherListsEqual(ctx->cipher_list, t.expected))
+ EXPECT_TRUE(CipherListsEqual(ctx.get(), t.expected))
<< "Cipher rule evaluated to:\n"
- << CipherListToString(ctx->cipher_list);
+ << CipherListToString(ctx.get());
}
}
@@ -439,9 +441,8 @@
ASSERT_TRUE(ctx);
ASSERT_TRUE(SSL_CTX_set_strict_cipher_list(ctx.get(), rule));
- for (size_t i = 0; i < sk_SSL_CIPHER_num(ctx->cipher_list->ciphers); i++) {
- EXPECT_FALSE(SSL_CIPHER_is_NULL(
- sk_SSL_CIPHER_value(ctx->cipher_list->ciphers, i)));
+ for (const SSL_CIPHER *cipher : SSL_CTX_get_ciphers(ctx.get())) {
+ EXPECT_FALSE(SSL_CIPHER_is_NULL(cipher));
}
}
}