Backport certificate status request TLS extension support to 0.9.8.
This commit is contained in:
15
apps/apps.h
15
apps/apps.h
@@ -122,6 +122,9 @@
|
||||
#ifndef OPENSSL_NO_ENGINE
|
||||
#include <openssl/engine.h>
|
||||
#endif
|
||||
#ifndef OPENSSL_NO_OCSP
|
||||
#include <openssl/ocsp.h>
|
||||
#endif
|
||||
#include <openssl/ossl_typ.h>
|
||||
|
||||
int app_RAND_load_file(const char *file, BIO *bio_e, int dont_warn);
|
||||
@@ -228,6 +231,12 @@ extern BIO *bio_err;
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#ifdef OPENSSL_SYSNAME_WIN32
|
||||
# define openssl_fdset(a,b) FD_SET((unsigned int)a, b)
|
||||
#else
|
||||
# define openssl_fdset(a,b) FD_SET(a, b)
|
||||
#endif
|
||||
|
||||
typedef struct args_st
|
||||
{
|
||||
char **data;
|
||||
@@ -275,6 +284,12 @@ X509_STORE *setup_verify(BIO *bp, char *CAfile, char *CApath);
|
||||
ENGINE *setup_engine(BIO *err, const char *engine, int debug);
|
||||
#endif
|
||||
|
||||
#ifndef OPENSSL_NO_OCSP
|
||||
OCSP_RESPONSE *process_responder(BIO *err, OCSP_REQUEST *req,
|
||||
char *host, char *path, char *port, int use_ssl,
|
||||
int req_timeout);
|
||||
#endif
|
||||
|
||||
int load_config(BIO *err, CONF *cnf);
|
||||
char *make_config_name(void);
|
||||
|
||||
|
210
apps/ocsp.c
210
apps/ocsp.c
@@ -58,13 +58,14 @@
|
||||
#ifndef OPENSSL_NO_OCSP
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include "apps.h"
|
||||
#include <openssl/pem.h>
|
||||
#include <openssl/e_os2.h>
|
||||
#include <openssl/bio.h>
|
||||
#include <openssl/ocsp.h>
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/txt_db.h>
|
||||
#include <openssl/ssl.h>
|
||||
#include <openssl/bn.h>
|
||||
#include "apps.h"
|
||||
|
||||
/* Maximum leeway in validity period: default 5 minutes */
|
||||
#define MAX_VALIDITY_PERIOD (5 * 60)
|
||||
@@ -86,6 +87,8 @@ static char **lookup_serial(CA_DB *db, ASN1_INTEGER *ser);
|
||||
static BIO *init_responder(char *port);
|
||||
static int do_responder(OCSP_REQUEST **preq, BIO **pcbio, BIO *acbio, char *port);
|
||||
static int send_ocsp_response(BIO *cbio, OCSP_RESPONSE *resp);
|
||||
static OCSP_RESPONSE *query_responder(BIO *err, BIO *cbio, char *path,
|
||||
OCSP_REQUEST *req, int req_timeout);
|
||||
|
||||
#undef PROG
|
||||
#define PROG ocsp_main
|
||||
@@ -112,11 +115,11 @@ int MAIN(int argc, char **argv)
|
||||
BIO *acbio = NULL, *cbio = NULL;
|
||||
BIO *derbio = NULL;
|
||||
BIO *out = NULL;
|
||||
int req_timeout = -1;
|
||||
int req_text = 0, resp_text = 0;
|
||||
long nsec = MAX_VALIDITY_PERIOD, maxage = -1;
|
||||
char *CAfile = NULL, *CApath = NULL;
|
||||
X509_STORE *store = NULL;
|
||||
SSL_CTX *ctx = NULL;
|
||||
STACK_OF(X509) *sign_other = NULL, *verify_other = NULL, *rother = NULL;
|
||||
char *sign_certfile = NULL, *verify_certfile = NULL, *rcertfile = NULL;
|
||||
unsigned long sign_flags = 0, verify_flags = 0, rflags = 0;
|
||||
@@ -154,6 +157,22 @@ int MAIN(int argc, char **argv)
|
||||
}
|
||||
else badarg = 1;
|
||||
}
|
||||
else if (!strcmp(*args, "-timeout"))
|
||||
{
|
||||
if (args[1])
|
||||
{
|
||||
args++;
|
||||
req_timeout = atol(*args);
|
||||
if (req_timeout < 0)
|
||||
{
|
||||
BIO_printf(bio_err,
|
||||
"Illegal timeout value %s\n",
|
||||
*args);
|
||||
badarg = 1;
|
||||
}
|
||||
}
|
||||
else badarg = 1;
|
||||
}
|
||||
else if (!strcmp(*args, "-url"))
|
||||
{
|
||||
if (args[1])
|
||||
@@ -703,52 +722,14 @@ int MAIN(int argc, char **argv)
|
||||
else if (host)
|
||||
{
|
||||
#ifndef OPENSSL_NO_SOCK
|
||||
cbio = BIO_new_connect(host);
|
||||
resp = process_responder(bio_err, req, host, path,
|
||||
port, use_ssl, req_timeout);
|
||||
if (!resp)
|
||||
goto end;
|
||||
#else
|
||||
BIO_printf(bio_err, "Error creating connect BIO - sockets not supported.\n");
|
||||
goto end;
|
||||
#endif
|
||||
if (!cbio)
|
||||
{
|
||||
BIO_printf(bio_err, "Error creating connect BIO\n");
|
||||
goto end;
|
||||
}
|
||||
if (port) BIO_set_conn_port(cbio, port);
|
||||
if (use_ssl == 1)
|
||||
{
|
||||
BIO *sbio;
|
||||
#if !defined(OPENSSL_NO_SSL2) && !defined(OPENSSL_NO_SSL3)
|
||||
ctx = SSL_CTX_new(SSLv23_client_method());
|
||||
#elif !defined(OPENSSL_NO_SSL3)
|
||||
ctx = SSL_CTX_new(SSLv3_client_method());
|
||||
#elif !defined(OPENSSL_NO_SSL2)
|
||||
ctx = SSL_CTX_new(SSLv2_client_method());
|
||||
#else
|
||||
BIO_printf(bio_err, "SSL is disabled\n");
|
||||
goto end;
|
||||
#endif
|
||||
if (ctx == NULL)
|
||||
{
|
||||
BIO_printf(bio_err, "Error creating SSL context.\n");
|
||||
goto end;
|
||||
}
|
||||
SSL_CTX_set_mode(ctx, SSL_MODE_AUTO_RETRY);
|
||||
sbio = BIO_new_ssl(ctx, 1);
|
||||
cbio = BIO_push(sbio, cbio);
|
||||
}
|
||||
if (BIO_do_connect(cbio) <= 0)
|
||||
{
|
||||
BIO_printf(bio_err, "Error connecting BIO\n");
|
||||
goto end;
|
||||
}
|
||||
resp = OCSP_sendreq_bio(cbio, path, req);
|
||||
BIO_free_all(cbio);
|
||||
cbio = NULL;
|
||||
if (!resp)
|
||||
{
|
||||
BIO_printf(bio_err, "Error querying OCSP responsder\n");
|
||||
goto end;
|
||||
}
|
||||
}
|
||||
else if (respin)
|
||||
{
|
||||
@@ -897,7 +878,6 @@ end:
|
||||
OPENSSL_free(host);
|
||||
OPENSSL_free(port);
|
||||
OPENSSL_free(path);
|
||||
SSL_CTX_free(ctx);
|
||||
}
|
||||
|
||||
OPENSSL_EXIT(ret);
|
||||
@@ -1121,6 +1101,7 @@ static char **lookup_serial(CA_DB *db, ASN1_INTEGER *ser)
|
||||
char *itmp, *row[DB_NUMBER],**rrow;
|
||||
for (i = 0; i < DB_NUMBER; i++) row[i] = NULL;
|
||||
bn = ASN1_INTEGER_to_BN(ser,NULL);
|
||||
OPENSSL_assert(bn); /* FIXME: should report an error at this point and abort */
|
||||
if (BN_is_zero(bn))
|
||||
itmp = BUF_strdup("00");
|
||||
else
|
||||
@@ -1231,4 +1212,137 @@ static int send_ocsp_response(BIO *cbio, OCSP_RESPONSE *resp)
|
||||
return 1;
|
||||
}
|
||||
|
||||
static OCSP_RESPONSE *query_responder(BIO *err, BIO *cbio, char *path,
|
||||
OCSP_REQUEST *req, int req_timeout)
|
||||
{
|
||||
int fd;
|
||||
int rv;
|
||||
OCSP_REQ_CTX *ctx = NULL;
|
||||
OCSP_RESPONSE *rsp = NULL;
|
||||
fd_set confds;
|
||||
struct timeval tv;
|
||||
|
||||
if (req_timeout != -1)
|
||||
BIO_set_nbio(cbio, 1);
|
||||
|
||||
rv = BIO_do_connect(cbio);
|
||||
|
||||
if ((rv <= 0) && ((req_timeout == -1) || !BIO_should_retry(cbio)))
|
||||
{
|
||||
BIO_puts(err, "Error connecting BIO\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (req_timeout == -1)
|
||||
return OCSP_sendreq_bio(cbio, path, req);
|
||||
|
||||
if (BIO_get_fd(cbio, &fd) <= 0)
|
||||
{
|
||||
BIO_puts(err, "Can't get connection fd\n");
|
||||
goto err;
|
||||
}
|
||||
|
||||
if (rv <= 0)
|
||||
{
|
||||
FD_ZERO(&confds);
|
||||
openssl_fdset(fd, &confds);
|
||||
tv.tv_usec = 0;
|
||||
tv.tv_sec = req_timeout;
|
||||
rv = select(fd + 1, NULL, (void *)&confds, NULL, &tv);
|
||||
if (rv == 0)
|
||||
{
|
||||
BIO_puts(err, "Timeout on connect\n");
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
ctx = OCSP_sendreq_new(cbio, path, req, -1);
|
||||
if (!ctx)
|
||||
return NULL;
|
||||
|
||||
for (;;)
|
||||
{
|
||||
rv = OCSP_sendreq_nbio(&rsp, ctx);
|
||||
if (rv != -1)
|
||||
break;
|
||||
FD_ZERO(&confds);
|
||||
openssl_fdset(fd, &confds);
|
||||
tv.tv_usec = 0;
|
||||
tv.tv_sec = req_timeout;
|
||||
if (BIO_should_read(cbio))
|
||||
rv = select(fd + 1, (void *)&confds, NULL, NULL, &tv);
|
||||
else if (BIO_should_write(cbio))
|
||||
rv = select(fd + 1, NULL, (void *)&confds, NULL, &tv);
|
||||
else
|
||||
{
|
||||
BIO_puts(err, "Unexpected retry condition\n");
|
||||
goto err;
|
||||
}
|
||||
if (rv == 0)
|
||||
{
|
||||
BIO_puts(err, "Timeout on request\n");
|
||||
break;
|
||||
}
|
||||
if (rv == -1)
|
||||
{
|
||||
BIO_puts(err, "Select error\n");
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
err:
|
||||
if (ctx)
|
||||
OCSP_REQ_CTX_free(ctx);
|
||||
|
||||
return rsp;
|
||||
}
|
||||
|
||||
OCSP_RESPONSE *process_responder(BIO *err, OCSP_REQUEST *req,
|
||||
char *host, char *path, char *port, int use_ssl,
|
||||
int req_timeout)
|
||||
{
|
||||
BIO *cbio = NULL;
|
||||
SSL_CTX *ctx = NULL;
|
||||
OCSP_RESPONSE *resp = NULL;
|
||||
cbio = BIO_new_connect(host);
|
||||
if (!cbio)
|
||||
{
|
||||
BIO_printf(err, "Error creating connect BIO\n");
|
||||
goto end;
|
||||
}
|
||||
if (port) BIO_set_conn_port(cbio, port);
|
||||
if (use_ssl == 1)
|
||||
{
|
||||
BIO *sbio;
|
||||
#if !defined(OPENSSL_NO_SSL2) && !defined(OPENSSL_NO_SSL3)
|
||||
ctx = SSL_CTX_new(SSLv23_client_method());
|
||||
#elif !defined(OPENSSL_NO_SSL3)
|
||||
ctx = SSL_CTX_new(SSLv3_client_method());
|
||||
#elif !defined(OPENSSL_NO_SSL2)
|
||||
ctx = SSL_CTX_new(SSLv2_client_method());
|
||||
#else
|
||||
BIO_printf(err, "SSL is disabled\n");
|
||||
goto end;
|
||||
#endif
|
||||
if (ctx == NULL)
|
||||
{
|
||||
BIO_printf(err, "Error creating SSL context.\n");
|
||||
goto end;
|
||||
}
|
||||
SSL_CTX_set_mode(ctx, SSL_MODE_AUTO_RETRY);
|
||||
sbio = BIO_new_ssl(ctx, 1);
|
||||
cbio = BIO_push(sbio, cbio);
|
||||
}
|
||||
resp = query_responder(err, cbio, path, req, req_timeout);
|
||||
if (!resp)
|
||||
BIO_printf(bio_err, "Error querying OCSP responsder\n");
|
||||
end:
|
||||
if (ctx)
|
||||
SSL_CTX_free(ctx);
|
||||
if (cbio)
|
||||
BIO_free_all(cbio);
|
||||
return resp;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
@@ -134,6 +134,7 @@ typedef unsigned int u_int;
|
||||
#include <openssl/err.h>
|
||||
#include <openssl/pem.h>
|
||||
#include <openssl/rand.h>
|
||||
#include <openssl/ocsp.h>
|
||||
#include "s_apps.h"
|
||||
#include "timeouts.h"
|
||||
|
||||
@@ -173,12 +174,14 @@ static int c_Pause=0;
|
||||
static int c_debug=0;
|
||||
#ifndef OPENSSL_NO_TLSEXT
|
||||
static int c_tlsextdebug=0;
|
||||
static int c_status_req=0;
|
||||
#endif
|
||||
static int c_msg=0;
|
||||
static int c_showcerts=0;
|
||||
|
||||
static void sc_usage(void);
|
||||
static void print_stuff(BIO *berr,SSL *con,int full);
|
||||
static int ocsp_resp_cb(SSL *s, void *arg);
|
||||
static BIO *bio_c_out=NULL;
|
||||
static int c_quiet=0;
|
||||
static int c_ign_eof=0;
|
||||
@@ -239,6 +242,7 @@ static void sc_usage(void)
|
||||
#ifndef OPENSSL_NO_TLSEXT
|
||||
BIO_printf(bio_err," -servername host - Set TLS extension servername in ClientHello\n");
|
||||
BIO_printf(bio_err," -tlsextdebug - hex dump of all TLS extensions received\n");
|
||||
BIO_printf(bio_err," -status - request certificate status from server\n");
|
||||
BIO_printf(bio_err," -no_ticket - disable use of RFC4507bis session tickets\n");
|
||||
#endif
|
||||
}
|
||||
@@ -435,6 +439,8 @@ int MAIN(int argc, char **argv)
|
||||
#ifndef OPENSSL_NO_TLSEXT
|
||||
else if (strcmp(*argv,"-tlsextdebug") == 0)
|
||||
c_tlsextdebug=1;
|
||||
else if (strcmp(*argv,"-status") == 0)
|
||||
c_status_req=1;
|
||||
#endif
|
||||
#ifdef WATT32
|
||||
else if (strcmp(*argv,"-wdebug") == 0)
|
||||
@@ -826,6 +832,23 @@ re_start:
|
||||
SSL_set_tlsext_debug_callback(con, tlsext_cb);
|
||||
SSL_set_tlsext_debug_arg(con, bio_c_out);
|
||||
}
|
||||
if (c_status_req)
|
||||
{
|
||||
SSL_set_tlsext_status_type(con, TLSEXT_STATUSTYPE_ocsp);
|
||||
SSL_CTX_set_tlsext_status_cb(ctx, ocsp_resp_cb);
|
||||
SSL_CTX_set_tlsext_status_arg(ctx, bio_c_out);
|
||||
#if 0
|
||||
{
|
||||
STACK_OF(OCSP_RESPID) *ids = sk_OCSP_RESPID_new_null();
|
||||
OCSP_RESPID *id = OCSP_RESPID_new();
|
||||
id->value.byKey = ASN1_OCTET_STRING_new();
|
||||
id->type = V_OCSP_RESPID_KEY;
|
||||
ASN1_STRING_set(id->value.byKey, "Hello World", -1);
|
||||
sk_OCSP_RESPID_push(ids, id);
|
||||
SSL_set_tlsext_status_ids(con, ids);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
|
||||
SSL_set_bio(con,sbio,sbio);
|
||||
@@ -1430,3 +1453,28 @@ static void print_stuff(BIO *bio, SSL *s, int full)
|
||||
(void)BIO_flush(bio);
|
||||
}
|
||||
|
||||
static int ocsp_resp_cb(SSL *s, void *arg)
|
||||
{
|
||||
const unsigned char *p;
|
||||
int len;
|
||||
OCSP_RESPONSE *rsp;
|
||||
len = SSL_get_tlsext_status_ocsp_resp(s, &p);
|
||||
BIO_puts(arg, "OCSP response: ");
|
||||
if (!p)
|
||||
{
|
||||
BIO_puts(arg, "no response sent\n");
|
||||
return 1;
|
||||
}
|
||||
rsp = d2i_OCSP_RESPONSE(NULL, &p, len);
|
||||
if (!rsp)
|
||||
{
|
||||
BIO_puts(arg, "response parse error\n");
|
||||
BIO_dump_indent(arg, (char *)p, len, 4);
|
||||
return 0;
|
||||
}
|
||||
BIO_puts(arg, "\n======================================\n");
|
||||
OCSP_RESPONSE_print(arg, rsp, 0);
|
||||
BIO_puts(arg, "======================================\n");
|
||||
OCSP_RESPONSE_free(rsp);
|
||||
return 1;
|
||||
}
|
||||
|
182
apps/s_server.c
182
apps/s_server.c
@@ -153,6 +153,7 @@ typedef unsigned int u_int;
|
||||
#include <openssl/x509.h>
|
||||
#include <openssl/ssl.h>
|
||||
#include <openssl/rand.h>
|
||||
#include <openssl/ocsp.h>
|
||||
#ifndef OPENSSL_NO_DH
|
||||
#include <openssl/dh.h>
|
||||
#endif
|
||||
@@ -269,6 +270,8 @@ static BIO *bio_s_out=NULL;
|
||||
static int s_debug=0;
|
||||
#ifndef OPENSSL_NO_TLSEXT
|
||||
static int s_tlsextdebug=0;
|
||||
static int s_tlsextstatus=0;
|
||||
static int cert_status_cb(SSL *s, void *arg);
|
||||
#endif
|
||||
static int s_msg=0;
|
||||
static int s_quiet=0;
|
||||
@@ -585,6 +588,152 @@ static int MS_CALLBACK ssl_servername_cb(SSL *s, int *ad, void *arg)
|
||||
}
|
||||
return SSL_TLSEXT_ERR_OK;
|
||||
}
|
||||
|
||||
/* Structure passed to cert status callback */
|
||||
|
||||
typedef struct tlsextstatusctx_st {
|
||||
/* Default responder to use */
|
||||
char *host, *path, *port;
|
||||
int use_ssl;
|
||||
int timeout;
|
||||
BIO *err;
|
||||
int verbose;
|
||||
} tlsextstatusctx;
|
||||
|
||||
static tlsextstatusctx tlscstatp = {NULL, NULL, NULL, 0, -1, NULL, 0};
|
||||
|
||||
/* Certificate Status callback. This is called when a client includes a
|
||||
* certificate status request extension.
|
||||
*
|
||||
* This is a simplified version. It examines certificates each time and
|
||||
* makes one OCSP responder query for each request.
|
||||
*
|
||||
* A full version would store details such as the OCSP certificate IDs and
|
||||
* minimise the number of OCSP responses by caching them until they were
|
||||
* considered "expired".
|
||||
*/
|
||||
|
||||
static int cert_status_cb(SSL *s, void *arg)
|
||||
{
|
||||
tlsextstatusctx *srctx = arg;
|
||||
BIO *err = srctx->err;
|
||||
char *host, *port, *path;
|
||||
int use_ssl;
|
||||
unsigned char *rspder = NULL;
|
||||
int rspderlen;
|
||||
STACK *aia = NULL;
|
||||
X509 *x = NULL;
|
||||
X509_STORE_CTX inctx;
|
||||
X509_OBJECT obj;
|
||||
OCSP_REQUEST *req = NULL;
|
||||
OCSP_RESPONSE *resp = NULL;
|
||||
OCSP_CERTID *id = NULL;
|
||||
STACK_OF(X509_EXTENSION) *exts;
|
||||
int ret = SSL_TLSEXT_ERR_NOACK;
|
||||
int i;
|
||||
#if 0
|
||||
STACK_OF(OCSP_RESPID) *ids;
|
||||
SSL_get_tlsext_status_ids(s, &ids);
|
||||
BIO_printf(err, "cert_status: received %d ids\n", sk_OCSP_RESPID_num(ids));
|
||||
#endif
|
||||
if (srctx->verbose)
|
||||
BIO_puts(err, "cert_status: callback called\n");
|
||||
/* Build up OCSP query from server certificate */
|
||||
x = SSL_get_certificate(s);
|
||||
aia = X509_get1_ocsp(x);
|
||||
if (aia)
|
||||
{
|
||||
if (!OCSP_parse_url(sk_value(aia, 0),
|
||||
&host, &port, &path, &use_ssl))
|
||||
{
|
||||
BIO_puts(err, "cert_status: can't parse AIA URL\n");
|
||||
goto err;
|
||||
}
|
||||
if (srctx->verbose)
|
||||
BIO_printf(err, "cert_status: AIA URL: %s\n",
|
||||
sk_value(aia, 0));
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!srctx->host)
|
||||
{
|
||||
BIO_puts(srctx->err, "cert_status: no AIA and no default responder URL\n");
|
||||
goto done;
|
||||
}
|
||||
host = srctx->host;
|
||||
path = srctx->path;
|
||||
port = srctx->port;
|
||||
use_ssl = srctx->use_ssl;
|
||||
}
|
||||
|
||||
if (!X509_STORE_CTX_init(&inctx,
|
||||
SSL_CTX_get_cert_store(SSL_get_SSL_CTX(s)),
|
||||
NULL, NULL))
|
||||
goto err;
|
||||
if (X509_STORE_get_by_subject(&inctx,X509_LU_X509,
|
||||
X509_get_issuer_name(x),&obj) <= 0)
|
||||
{
|
||||
BIO_puts(err, "cert_status: Can't retrieve issuer certificate.\n");
|
||||
X509_STORE_CTX_cleanup(&inctx);
|
||||
goto done;
|
||||
}
|
||||
req = OCSP_REQUEST_new();
|
||||
if (!req)
|
||||
goto err;
|
||||
id = OCSP_cert_to_id(NULL, x, obj.data.x509);
|
||||
X509_free(obj.data.x509);
|
||||
X509_STORE_CTX_cleanup(&inctx);
|
||||
if (!id)
|
||||
goto err;
|
||||
if (!OCSP_request_add0_id(req, id))
|
||||
goto err;
|
||||
id = NULL;
|
||||
/* Add any extensions to the request */
|
||||
SSL_get_tlsext_status_exts(s, &exts);
|
||||
for (i = 0; i < sk_X509_EXTENSION_num(exts); i++)
|
||||
{
|
||||
X509_EXTENSION *ext = sk_X509_EXTENSION_value(exts, i);
|
||||
if (!OCSP_REQUEST_add_ext(req, ext, -1))
|
||||
goto err;
|
||||
}
|
||||
resp = process_responder(err, req, host, path, port, use_ssl,
|
||||
srctx->timeout);
|
||||
if (!resp)
|
||||
{
|
||||
BIO_puts(err, "cert_status: error querying responder\n");
|
||||
goto done;
|
||||
}
|
||||
rspderlen = i2d_OCSP_RESPONSE(resp, &rspder);
|
||||
if (rspderlen <= 0)
|
||||
goto err;
|
||||
SSL_set_tlsext_status_ocsp_resp(s, rspder, rspderlen);
|
||||
if (srctx->verbose)
|
||||
{
|
||||
BIO_puts(err, "cert_status: ocsp response sent:\n");
|
||||
OCSP_RESPONSE_print(err, resp, 2);
|
||||
}
|
||||
ret = SSL_TLSEXT_ERR_OK;
|
||||
done:
|
||||
if (ret != SSL_TLSEXT_ERR_OK)
|
||||
ERR_print_errors(err);
|
||||
if (aia)
|
||||
{
|
||||
OPENSSL_free(host);
|
||||
OPENSSL_free(path);
|
||||
OPENSSL_free(port);
|
||||
X509_email_free(aia);
|
||||
}
|
||||
if (id)
|
||||
OCSP_CERTID_free(id);
|
||||
if (req)
|
||||
OCSP_REQUEST_free(req);
|
||||
if (resp)
|
||||
OCSP_RESPONSE_free(resp);
|
||||
return ret;
|
||||
err:
|
||||
ret = SSL_TLSEXT_ERR_ALERT_FATAL;
|
||||
goto done;
|
||||
}
|
||||
#endif
|
||||
int MAIN(int, char **);
|
||||
|
||||
@@ -792,6 +941,33 @@ int MAIN(int argc, char *argv[])
|
||||
#ifndef OPENSSL_NO_TLSEXT
|
||||
else if (strcmp(*argv,"-tlsextdebug") == 0)
|
||||
s_tlsextdebug=1;
|
||||
else if (strcmp(*argv,"-status") == 0)
|
||||
s_tlsextstatus=1;
|
||||
else if (strcmp(*argv,"-status_verbose") == 0)
|
||||
{
|
||||
s_tlsextstatus=1;
|
||||
tlscstatp.verbose = 1;
|
||||
}
|
||||
else if (!strcmp(*argv, "-status_timeout"))
|
||||
{
|
||||
s_tlsextstatus=1;
|
||||
if (--argc < 1) goto bad;
|
||||
tlscstatp.timeout = atoi(*(++argv));
|
||||
}
|
||||
else if (!strcmp(*argv, "-status_url"))
|
||||
{
|
||||
s_tlsextstatus=1;
|
||||
if (--argc < 1) goto bad;
|
||||
if (!OCSP_parse_url(*(++argv),
|
||||
&tlscstatp.host,
|
||||
&tlscstatp.port,
|
||||
&tlscstatp.path,
|
||||
&tlscstatp.use_ssl))
|
||||
{
|
||||
BIO_printf(bio_err, "Error parsing URL\n");
|
||||
goto bad;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
else if (strcmp(*argv,"-msg") == 0)
|
||||
{ s_msg=1; }
|
||||
@@ -1430,6 +1606,12 @@ static int sv_body(char *hostname, int s, unsigned char *context)
|
||||
SSL_set_tlsext_debug_callback(con, tlsext_cb);
|
||||
SSL_set_tlsext_debug_arg(con, bio_s_out);
|
||||
}
|
||||
if (s_tlsextstatus)
|
||||
{
|
||||
SSL_CTX_set_tlsext_status_cb(ctx, cert_status_cb);
|
||||
tlscstatp.err = bio_err;
|
||||
SSL_CTX_set_tlsext_status_arg(ctx, &tlscstatp);
|
||||
}
|
||||
#endif
|
||||
#ifndef OPENSSL_NO_KRB5
|
||||
if ((con->kssl_ctx = kssl_ctx_new()) != NULL)
|
||||
|
11
apps/x509.c
11
apps/x509.c
@@ -114,6 +114,7 @@ static const char *x509_usage[]={
|
||||
" -alias - output certificate alias\n",
|
||||
" -noout - no certificate output\n",
|
||||
" -ocspid - print OCSP hash values for the subject name and public key\n",
|
||||
" -ocspurl - print OCSP Responder URL(s)\n",
|
||||
" -trustout - output a \"trusted\" certificate\n",
|
||||
" -clrtrust - clear all trusted purposes\n",
|
||||
" -clrreject - clear all rejected purposes\n",
|
||||
@@ -179,6 +180,7 @@ int MAIN(int argc, char **argv)
|
||||
int next_serial=0;
|
||||
int subject_hash=0,issuer_hash=0,ocspid=0;
|
||||
int noout=0,sign_flag=0,CA_flag=0,CA_createserial=0,email=0;
|
||||
int ocsp_uri=0;
|
||||
int trustout=0,clrtrust=0,clrreject=0,aliasout=0,clrext=0;
|
||||
int C=0;
|
||||
int x509req=0,days=DEF_DAYS,modulus=0,pubkey=0;
|
||||
@@ -378,6 +380,8 @@ int MAIN(int argc, char **argv)
|
||||
C= ++num;
|
||||
else if (strcmp(*argv,"-email") == 0)
|
||||
email= ++num;
|
||||
else if (strcmp(*argv,"-ocsp_uri") == 0)
|
||||
ocsp_uri= ++num;
|
||||
else if (strcmp(*argv,"-serial") == 0)
|
||||
serial= ++num;
|
||||
else if (strcmp(*argv,"-next_serial") == 0)
|
||||
@@ -731,11 +735,14 @@ bad:
|
||||
ASN1_INTEGER_free(ser);
|
||||
BIO_puts(out, "\n");
|
||||
}
|
||||
else if (email == i)
|
||||
else if ((email == i) || (ocsp_uri == i))
|
||||
{
|
||||
int j;
|
||||
STACK *emlst;
|
||||
emlst = X509_get1_email(x);
|
||||
if (email == i)
|
||||
emlst = X509_get1_email(x);
|
||||
else
|
||||
emlst = X509_get1_ocsp(x);
|
||||
for (j = 0; j < sk_num(emlst); j++)
|
||||
BIO_printf(STDout, "%s\n", sk_value(emlst, j));
|
||||
X509_email_free(emlst);
|
||||
|
Reference in New Issue
Block a user