- SSL_CTX_set_tlsext_servername_arg()
SSL_CTRL_SET_TLSEXT_HOSTNAME - SSL_set_tlsext_hostname()
- openssl s_client has a new '-servername' option.
-
- openssl s_server has new options '-servername', '-cert2', and '-key2'
- (subject to change); this allows testing the HostName extension for a
- specific single host name ('-cert' and '-key' remain fallbacks for
- handshakes without HostName negotiation).
- The option servername_warn allows to return a warning alert instead of
- a fatal alert in case of servername mismatch.
+ openssl s_client has a new '-servername ...' option.
+
+ openssl s_server has new options '-servername_host ...', '-cert2 ...',
+ '-key2 ...', '-servername_fatal' (subject to change). This allows
+ testing the HostName extension for a specific single host name ('-cert'
+ and '-key' remain fallbacks for handshakes without HostName
+ negotiation). If the unrecogninzed_name alert has to be sent, this by
+ default is a warning; it becomes fatal with the '-servername_fatal'
+ option.
[Peter Sylvester, Remy Allais, Christophe Renou]
* [including the GNU Public Licence.]
*/
/* ====================================================================
- * Copyright (c) 1998-2001 The OpenSSL Project. All rights reserved.
+ * Copyright (c) 1998-2006 The OpenSSL Project. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
case 100:
str_details2 = " no_renegotiation";
break;
+ case 110:
+ str_details2 = " unsupported_extension";
+ break;
+ case 111:
+ str_details2 = " certificate_unobtainable";
+ break;
+ case 112:
+ str_details2 = " unrecognized_name";
+ break;
+ case 113:
+ str_details2 = " bad_certificate_status_response";
+ break;
+ case 114:
+ str_details2 = " bad_certificate_hash_value";
+ break;
}
}
}
else
BIO_printf(bio_err,"Can't use SSL_get_servername\n");
- return 1;
+ return SSL_TLSEXT_ERR_OK;
}
#endif
BIO_printf(bio_err," -rand file%cfile%c...\n", LIST_SEPARATOR_CHAR, LIST_SEPARATOR_CHAR);
#ifndef OPENSSL_NO_TLSEXT
BIO_printf(bio_err," -servername host - servername for HostName TLS extension\n");
- BIO_printf(bio_err," -servername_warn - on mismatch send warning (default fatal alert)\n");
+ BIO_printf(bio_err," -servername_fatal - on mismatch send fatal alert (default warning alert)\n");
BIO_printf(bio_err," -cert2 arg - certificate file to use for servername\n");
BIO_printf(bio_err," (default is %s)\n",TEST_CERT2);
BIO_printf(bio_err," -key2 arg - Private Key file to use for servername, in cert file if\n");
typedef struct tlsextctx_st {
char * servername;
BIO * biodebug;
- int servername_warn;
+ int extension_error;
} tlsextctx;
BIO_printf(p->biodebug,"Hostname in TLS extension: \"%s\"\n",servername);
if (!p->servername)
- return 1;
+ return SSL_TLSEXT_ERR_NOACK;
if (servername)
{
if (strcmp(servername,p->servername))
- return p->servername_warn;
- if (ctx2) {
+ return p->extension_error;
+ if (ctx2)
+ {
BIO_printf(p->biodebug,"Swiching server context.\n");
SSL_set_SSL_CTX(s,ctx2);
}
}
- return 1;
+ return SSL_TLSEXT_ERR_OK;
}
#endif
#endif
#ifndef OPENSSL_NO_TLSEXT
- tlsextctx tlsextcbp = {NULL, NULL, -1};
+ tlsextctx tlsextcbp = {NULL, NULL, SSL_TLSEXT_ERR_ALERT_WARNING};
#endif
#if !defined(OPENSSL_NO_SSL2) && !defined(OPENSSL_NO_SSL3)
meth=SSLv23_server_method();
if (--argc < 1) goto bad;
tlsextcbp.servername= *(++argv);
}
- else if (strcmp(*argv,"-servername_warn") == 0)
- { tlsextcbp.servername_warn = 0; }
+ else if (strcmp(*argv,"-servername_fatal") == 0)
+ { tlsextcbp.extension_error = SSL_TLSEXT_ERR_ALERT_FATAL; }
else if (strcmp(*argv,"-cert2") == 0)
{
if (--argc < 1) goto bad;
(p[5] == SSL3_MT_SERVER_HELLO))
{
/* we have sslv3 or tls1 */
+ have_sslv3_or_tls1:
if (!ssl_init_wbio_buffer(s,1)) goto err;
cb(s,SSL_CB_READ_ALERT,j);
}
+ if (p[5] == SSL3_AL_WARNING)
+ goto have_sslv3_or_tls1;
+
s->rwstate=SSL_NOTHING;
SSLerr(SSL_F_SSL23_GET_SERVER_HELLO,SSL_AD_REASON_OFFSET+p[6]);
goto err;
#ifndef OPENSSL_NO_TLSEXT
{
int al;
- if (ssl_check_tlsext(s,&al) <= 0)
+ switch (ssl_check_tlsext(s,&al))
{
- ssl3_send_alert(s,SSL3_AL_FATAL,al); /* XXX does this *have* to be fatal? */
+ case SSL_TLSEXT_ERR_ALERT_FATAL:
+ ssl3_send_alert(s,SSL3_AL_FATAL,al);
SSLerr(SSL_F_SSL3_CONNECT,SSL_R_SERVERHELLO_TLS_EXT);
ret = -1;
goto end;
+
+ case SSL_TLSEXT_ERR_ALERT_WARNING:
+ ssl3_send_alert(s,SSL3_AL_WARNING,al);
+
+ default:
+ ;
}
}
#endif
if (ret <= 0) goto end;
#ifndef OPENSSL_NO_TLSEXT
{
- int al,warn;
- warn = ssl_check_tlsext(s,&al);
- if (warn == 0)
- ssl3_send_alert(s,SSL3_AL_WARNING,al);
- else if (warn < 0) {
+ int al;
+ switch (ssl_check_tlsext(s,&al))
+ {
+ case SSL_TLSEXT_ERR_ALERT_FATAL:
ssl3_send_alert(s,SSL3_AL_FATAL,al);
SSLerr(SSL_F_SSL3_ACCEPT,SSL_R_CLIENTHELLO_TLS_EXT);
ret = -1;
goto end;
- }
+
+ case SSL_TLSEXT_ERR_ALERT_WARNING:
+ ssl3_send_alert(s,SSL3_AL_WARNING,al);
+
+ default:
+ break;
+ }
}
#endif
s->new_session = 2;
int ssl_check_tlsext(SSL *s,int *al)
{
- int ret;
+ int ret=SSL_TLSEXT_ERR_NOACK;
*al = SSL_AD_UNRECOGNIZED_NAME;
- if (s->ctx != NULL && s->ctx->tlsext_servername_callback != 0)
- {
+
+ if (s->ctx != NULL && s->ctx->tlsext_servername_callback != 0)
ret = s->ctx->tlsext_servername_callback(s, al, s->ctx->tlsext_servername_arg);
- if (ret <= 0)
- return ret;
- }
- else if (s->initial_ctx != NULL && s->initial_ctx->tlsext_servername_callback != 0)
- {
+ else if (s->initial_ctx != NULL && s->initial_ctx->tlsext_servername_callback != 0)
ret = s->initial_ctx->tlsext_servername_callback(s, al, s->initial_ctx->tlsext_servername_arg);
- if (ret <= 0)
- return ret;
- }
-
- return 1;
+
+ if (ret == SSL_TLSEXT_ERR_NOACK)
+ s->servername_done=0;
+ return ret;
}
#endif
#define SSL_CTX_set_tlsext_servername_callback(ctx, cb) \
SSL_CTX_callback_ctrl(ctx,SSL_CTRL_SET_TLSEXT_SERVERNAME_CB,(void (*)(void))cb)
+
+#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
+
#define SSL_CTX_set_tlsext_servername_arg(ctx, arg) \
SSL_CTX_ctrl(ctx,SSL_CTRL_SET_TLSEXT_SERVERNAME_ARG,0, (void *)arg)
-#define SSL_set_tlsext_servername_done(s,t) \
-SSL_ctrl(s,SSL_CTRL_SET_TLSEXT_SERVERNAME_DONE,t, NULL)
-
#endif