Move remaining functions out of tls1.h. Now tls1.h is just a pile of protocol constants with no more circular dependency problem. I've preserved SSL_get_servername's behavior where it's simultaneously a lookup of handshake state and local configuration. I've removed it from SSL_get_servername_type. It got the logic wrong anyway with the order of the s->session check. (Searching through code, neither is used on the client, but the SSL_get_servername one is easy.) Change-Id: I61bb8fb0858b07d76a7835bffa6dc793812fb027 Reviewed-on: https://boringssl-review.googlesource.com/6298 Reviewed-by: Adam Langley <alangley@gmail.com>
diff --git a/include/openssl/ssl.h b/include/openssl/ssl.h index bdf28dc..ed61839 100644 --- a/include/openssl/ssl.h +++ b/include/openssl/ssl.h
@@ -150,6 +150,7 @@ #include <openssl/lhash.h> #include <openssl/pem.h> #include <openssl/thread.h> +#include <openssl/tls1.h> #include <openssl/x509.h> #if !defined(OPENSSL_WINDOWS) @@ -1194,6 +1195,16 @@ * renegotiation (RFC 5746) and zero otherwise. */ OPENSSL_EXPORT int SSL_get_secure_renegotiation_support(const SSL *ssl); +/* SSL_export_keying_material exports a value derived from the master secret, as + * specified in RFC 5705. It writes |out_len| bytes to |out| given a label and + * optional context. (Since a zero length context is allowed, the |use_context| + * flag controls whether a context is included.) + * + * It returns one on success and zero otherwise. */ +OPENSSL_EXPORT int SSL_export_keying_material( + SSL *ssl, uint8_t *out, size_t out_len, const char *label, size_t label_len, + const uint8_t *context, size_t context_len, int use_context); + /* Custom extensions. * @@ -2075,6 +2086,52 @@ const char *dir); +/* Server name indication. + * + * The server_name extension (RFC 3546) allows the client to advertise the name + * of the server it is connecting to. This is used in virtual hosting + * deployments to select one of a several certificates on a single IP. Only the + * host_name name type is supported. */ + +#define TLSEXT_NAMETYPE_host_name 0 + +/* SSL_set_tlsext_host_name, for a client, configures |ssl| to advertise |name| + * in the server_name extension. It returns one on success and zero on error. */ +OPENSSL_EXPORT int SSL_set_tlsext_host_name(SSL *ssl, const char *name); + +/* SSL_get_servername, for a server, returns the hostname supplied by the + * client or NULL if there was none. The |type| argument must be + * |TLSEXT_NAMETYPE_host_name|. */ +OPENSSL_EXPORT const char *SSL_get_servername(const SSL *ssl, const int type); + +/* SSL_get_servername_type, for a server, returns |TLSEXT_NAMETYPE_host_name| + * if the client sent a hostname and -1 otherwise. */ +OPENSSL_EXPORT int SSL_get_servername_type(const SSL *ssl); + +/* SSL_CTX_set_tlsext_servername_callback configures |callback| to be called on + * the server after ClientHello extensions have been parsed and returns one. + * The callback may use |SSL_get_servername| to examine the server_name extension + * and returns a |SSL_TLSEXT_ERR_*| value. The value of |arg| may be set by + * calling |SSL_CTX_set_tlsext_servername_arg|. + * + * If the callback returns |SSL_TLSEXT_ERR_NOACK|, the server_name extension is + * not acknowledged in the ServerHello. If the return value is + * |SSL_TLSEXT_ERR_ALERT_FATAL| or |SSL_TLSEXT_ERR_ALERT_WARNING| then + * |*out_alert| must be set to the alert value to send. */ +OPENSSL_EXPORT int SSL_CTX_set_tlsext_servername_callback( + SSL_CTX *ctx, int (*callback)(SSL *ssl, int *out_alert, void *arg)); + +/* SSL_CTX_set_tlsext_servername_arg sets the argument to the servername + * callback and returns one. See |SSL_CTX_set_tlsext_servername_callback|. */ +OPENSSL_EXPORT int SSL_CTX_set_tlsext_servername_arg(SSL_CTX *ctx, void *arg); + +/* SSL_TLSEXT_ERR_* are values returned by some extension-related callbacks. */ +#define SSL_TLSEXT_ERR_OK 0 +#define SSL_TLSEXT_ERR_ALERT_WARNING 1 +#define SSL_TLSEXT_ERR_ALERT_FATAL 2 +#define SSL_TLSEXT_ERR_NOACK 3 + + /* Application-layer protocol negotation. * * The ALPN extension (RFC 7301) allows negotiating different application-layer @@ -3902,7 +3959,6 @@ * declarations should move to ssl.h. Many of the constants can probably be * pruned or unexported. */ #include <openssl/ssl3.h> -#include <openssl/tls1.h> /* This is mostly sslv3 with a few tweaks */ /* BEGIN ERROR CODES */
diff --git a/include/openssl/tls1.h b/include/openssl/tls1.h index 45c4779..a0f299d 100644 --- a/include/openssl/tls1.h +++ b/include/openssl/tls1.h
@@ -147,11 +147,10 @@ * OTHERWISE. */ -#ifndef HEADER_TLS1_H -#define HEADER_TLS1_H +#ifndef OPENSSL_HEADER_TLS1_H +#define OPENSSL_HEADER_TLS1_H -#include <openssl/buf.h> -#include <openssl/stack.h> +#include <openssl/base.h> #ifdef __cplusplus extern "C" { @@ -237,8 +236,6 @@ /* This is not an IANA defined extension number */ #define TLSEXT_TYPE_channel_id 30032 -/* NameType value from RFC 3546 */ -#define TLSEXT_NAMETYPE_host_name 0 /* status request value from RFC 3546 */ #define TLSEXT_STATUSTYPE_ocsp 1 @@ -273,42 +270,6 @@ #define TLSEXT_MAXLEN_host_name 255 -OPENSSL_EXPORT const char *SSL_get_servername(const SSL *s, const int type); -OPENSSL_EXPORT int SSL_get_servername_type(const SSL *s); - -/* SSL_export_keying_material exports a value derived from the master secret, as - * specified in RFC 5705. It writes |out_len| bytes to |out| given a label and - * optional context. (Since a zero length context is allowed, the |use_context| - * flag controls whether a context is included.) - * - * It returns one on success and zero otherwise. */ -OPENSSL_EXPORT int SSL_export_keying_material( - SSL *s, uint8_t *out, size_t out_len, const char *label, size_t label_len, - const uint8_t *context, size_t context_len, int use_context); - -/* SSL_set_tlsext_host_name, for a client, configures |ssl| to advertise |name| - * in the server_name extension. It returns one on success and zero on error. */ -OPENSSL_EXPORT int SSL_set_tlsext_host_name(SSL *ssl, const char *name); - -/* SSL_CTX_set_tlsext_servername_callback configures |callback| to be called on - * the server after ClientHello extensions have been parsed and returns one. - * |callback| may use |SSL_get_servername| to examine the server_name extension - * and return a |SSL_TLSEXT_ERR_*| value. If it returns |SSL_TLSEXT_ERR_NOACK|, - * the server_name extension is not acknowledged in the ServerHello. If the - * return value signals an alert, |callback| should set |*out_alert| to the - * alert to send. */ -OPENSSL_EXPORT int SSL_CTX_set_tlsext_servername_callback( - SSL_CTX *ctx, int (*callback)(SSL *ssl, int *out_alert, void *arg)); - -#define SSL_TLSEXT_ERR_OK 0 -#define SSL_TLSEXT_ERR_ALERT_WARNING 1 -#define SSL_TLSEXT_ERR_ALERT_FATAL 2 -#define SSL_TLSEXT_ERR_NOACK 3 - -/* SSL_CTX_set_tlsext_servername_arg sets the argument to the servername - * callback and returns one. See |SSL_CTX_set_tlsext_servername_callback|. */ -OPENSSL_EXPORT int SSL_CTX_set_tlsext_servername_arg(SSL_CTX *ctx, void *arg); - /* PSK ciphersuites from 4279 */ #define TLS1_CK_PSK_WITH_RC4_128_SHA 0x0300008A #define TLS1_CK_PSK_WITH_3DES_EDE_CBC_SHA 0x0300008B @@ -662,6 +623,7 @@ #ifdef __cplusplus -} +} /* extern C */ #endif -#endif + +#endif /* OPENSSL_HEADER_TLS1_H */
diff --git a/ssl/ssl_lib.c b/ssl/ssl_lib.c index 57a76fa..1baf355 100644 --- a/ssl/ssl_lib.c +++ b/ssl/ssl_lib.c
@@ -1562,21 +1562,25 @@ return NULL; } - -/* return a servername extension value if provided in Client Hello, or NULL. So - * far, only host_name types are defined (RFC 3546). */ -const char *SSL_get_servername(const SSL *s, const int type) { +const char *SSL_get_servername(const SSL *ssl, const int type) { if (type != TLSEXT_NAMETYPE_host_name) { return NULL; } - return s->session && !s->tlsext_hostname ? s->session->tlsext_hostname - : s->tlsext_hostname; + /* Historically, |SSL_get_servername| was also the configuration getter + * corresponding to |SSL_set_tlsext_host_name|. */ + if (ssl->tlsext_hostname != NULL) { + return ssl->tlsext_hostname; + } + + if (ssl->session == NULL) { + return NULL; + } + return ssl->session->tlsext_hostname; } -int SSL_get_servername_type(const SSL *s) { - if (s->session && - (!s->tlsext_hostname ? s->session->tlsext_hostname : s->tlsext_hostname)) { +int SSL_get_servername_type(const SSL *ssl) { + if (ssl->session != NULL && ssl->session->tlsext_hostname != NULL) { return TLSEXT_NAMETYPE_host_name; } @@ -1761,16 +1765,16 @@ } } -int SSL_export_keying_material(SSL *s, uint8_t *out, size_t out_len, +int SSL_export_keying_material(SSL *ssl, uint8_t *out, size_t out_len, const char *label, size_t label_len, const uint8_t *context, size_t context_len, int use_context) { - if (s->version < TLS1_VERSION) { + if (ssl->version < TLS1_VERSION) { return 0; } - return s->enc_method->export_keying_material( - s, out, out_len, label, label_len, context, context_len, use_context); + return ssl->enc_method->export_keying_material( + ssl, out, out_len, label, label_len, context, context_len, use_context); } void SSL_CTX_set_cert_verify_callback(SSL_CTX *ctx,