aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/core/security/security_context.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/core/security/security_context.c')
-rw-r--r--src/core/security/security_context.c64
1 files changed, 49 insertions, 15 deletions
diff --git a/src/core/security/security_context.c b/src/core/security/security_context.c
index 0a65480b2f..62264e4105 100644
--- a/src/core/security/security_context.c
+++ b/src/core/security/security_context.c
@@ -43,7 +43,9 @@
#include "src/core/support/file.h"
#include "src/core/support/string.h"
#include "src/core/transport/chttp2/alpn.h"
+
#include <grpc/support/alloc.h>
+#include <grpc/support/host_port.h>
#include <grpc/support/log.h>
#include <grpc/support/slice_buffer.h>
#include "src/core/tsi/fake_transport_security.h"
@@ -51,20 +53,33 @@
/* -- Constants. -- */
-/* Defines the cipher suites that we accept. All these cipher suites are
- compliant with TLS 1.2 and use an RSA public key. We prefer GCM over CBC
- and ECDHE-RSA over just RSA. */
-#define GRPC_SSL_CIPHER_SUITES \
- "ECDHE-RSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-GCM-SHA384:AES128-GCM-SHA256:" \
- "AES256-GCM-SHA384:ECDHE-RSA-AES128-SHA256:ECDHE-RSA-AES256-SHA384:AES128-" \
- "SHA256:AES256-SHA256"
-
#ifndef INSTALL_PREFIX
static const char *installed_roots_path = "/usr/share/grpc/roots.pem";
#else
static const char *installed_roots_path = INSTALL_PREFIX "/share/grpc/roots.pem";
#endif
+/* -- Cipher suites. -- */
+
+/* Defines the cipher suites that we accept by default. All these cipher suites
+ are compliant with HTTP2. */
+#define GRPC_SSL_CIPHER_SUITES \
+ "ECDHE-RSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-RSA-AES256-" \
+ "SHA384:ECDHE-RSA-AES256-GCM-SHA384"
+
+static gpr_once cipher_suites_once = GPR_ONCE_INIT;
+static const char *cipher_suites = NULL;
+
+static void init_cipher_suites(void) {
+ char *overridden = gpr_getenv("GRPC_SSL_CIPHER_SUITES");
+ cipher_suites = overridden != NULL ? overridden : GRPC_SSL_CIPHER_SUITES;
+}
+
+static const char *ssl_cipher_suites(void) {
+ gpr_once_init(&cipher_suites_once, init_cipher_suites);
+ return cipher_suites;
+}
+
/* -- Common methods. -- */
grpc_security_status grpc_security_context_create_handshaker(
@@ -322,6 +337,24 @@ static grpc_security_status ssl_server_create_handshaker(
return ssl_create_handshaker(c->handshaker_factory, 0, NULL, handshaker);
}
+static int ssl_host_matches_name(const tsi_peer *peer,
+ const char *peer_name) {
+ char *allocated_name = NULL;
+ int r;
+
+ if (strchr(peer_name, ':') != NULL) {
+ char *ignored_port;
+ gpr_split_host_port(peer_name, &allocated_name, &ignored_port);
+ gpr_free(ignored_port);
+ peer_name = allocated_name;
+ if (!peer_name) return 0;
+ }
+
+ r = tsi_ssl_peer_matches_name(peer, peer_name);
+ gpr_free(allocated_name);
+ return r;
+}
+
static grpc_security_status ssl_check_peer(const char *peer_name,
const tsi_peer *peer) {
/* Check the ALPN. */
@@ -343,10 +376,11 @@ static grpc_security_status ssl_check_peer(const char *peer_name,
/* Check the peer name if specified. */
if (peer_name != NULL &&
- !tsi_ssl_peer_matches_name(peer, peer_name)) {
+ !ssl_host_matches_name(peer, peer_name)) {
gpr_log(GPR_ERROR, "Peer name %s is not in peer certificate", peer_name);
return GRPC_SECURITY_ERROR;
}
+
return GRPC_SECURITY_OK;
}
@@ -382,7 +416,7 @@ static grpc_security_status ssl_channel_check_call_host(
grpc_ssl_channel_security_context *c =
(grpc_ssl_channel_security_context *)ctx;
- if (tsi_ssl_peer_matches_name(&c->peer, host)) return GRPC_SECURITY_OK;
+ if (ssl_host_matches_name(&c->peer, host)) return GRPC_SECURITY_OK;
/* If the target name was overridden, then the original target_name was
'checked' transitively during the previous peer check at the end of the
@@ -442,6 +476,7 @@ grpc_security_status grpc_ssl_channel_security_context_create(
size_t i;
const unsigned char *pem_root_certs;
size_t pem_root_certs_size;
+ char *port;
for (i = 0; i < num_alpn_protocols; i++) {
alpn_protocol_strings[i] =
@@ -467,9 +502,8 @@ grpc_security_status grpc_ssl_channel_security_context_create(
c->base.base.url_scheme = GRPC_SSL_URL_SCHEME;
c->base.request_metadata_creds = grpc_credentials_ref(request_metadata_creds);
c->base.check_call_host = ssl_channel_check_call_host;
- if (target_name != NULL) {
- c->target_name = gpr_strdup(target_name);
- }
+ gpr_split_host_port(target_name, &c->target_name, &port);
+ gpr_free(port);
if (overridden_target_name != NULL) {
c->overridden_target_name = gpr_strdup(overridden_target_name);
}
@@ -486,7 +520,7 @@ grpc_security_status grpc_ssl_channel_security_context_create(
result = tsi_create_ssl_client_handshaker_factory(
config->pem_private_key, config->pem_private_key_size,
config->pem_cert_chain, config->pem_cert_chain_size, pem_root_certs,
- pem_root_certs_size, GRPC_SSL_CIPHER_SUITES, alpn_protocol_strings,
+ pem_root_certs_size, ssl_cipher_suites(), alpn_protocol_strings,
alpn_protocol_string_lengths, num_alpn_protocols, &c->handshaker_factory);
if (result != TSI_OK) {
gpr_log(GPR_ERROR, "Handshaker factory creation failed with %s.",
@@ -540,7 +574,7 @@ grpc_security_status grpc_ssl_server_security_context_create(
(const unsigned char **)config->pem_cert_chains,
config->pem_cert_chains_sizes, config->num_key_cert_pairs,
config->pem_root_certs, config->pem_root_certs_size,
- GRPC_SSL_CIPHER_SUITES, alpn_protocol_strings,
+ ssl_cipher_suites(), alpn_protocol_strings,
alpn_protocol_string_lengths, num_alpn_protocols, &c->handshaker_factory);
if (result != TSI_OK) {
gpr_log(GPR_ERROR, "Handshaker factory creation failed with %s.",