sync with OpenBSD -current
This commit is contained in:
parent
a2b5593ce1
commit
19c768bf4f
67 changed files with 1526 additions and 522 deletions
|
@ -1,4 +1,4 @@
|
|||
/* $OpenBSD: asn1_local.h,v 1.5 2023/12/29 10:59:00 tb Exp $ */
|
||||
/* $OpenBSD: asn1_local.h,v 1.7 2024/01/06 20:47:01 tb Exp $ */
|
||||
/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
|
||||
* project 2006.
|
||||
*/
|
||||
|
@ -89,24 +89,6 @@ struct asn1_pctx_st {
|
|||
unsigned long str_flags;
|
||||
} /* ASN1_PCTX */;
|
||||
|
||||
/* Method to handle CRL access.
|
||||
* In general a CRL could be very large (several Mb) and can consume large
|
||||
* amounts of resources if stored in memory by multiple processes.
|
||||
* This method allows general CRL operations to be redirected to more
|
||||
* efficient callbacks: for example a CRL entry database.
|
||||
*/
|
||||
|
||||
#define X509_CRL_METHOD_DYNAMIC 1
|
||||
|
||||
struct x509_crl_method_st {
|
||||
int flags;
|
||||
int (*crl_init)(X509_CRL *crl);
|
||||
int (*crl_free)(X509_CRL *crl);
|
||||
int (*crl_lookup)(X509_CRL *crl, X509_REVOKED **ret,
|
||||
ASN1_INTEGER *ser, X509_NAME *issuer);
|
||||
int (*crl_verify)(X509_CRL *crl, EVP_PKEY *pk);
|
||||
};
|
||||
|
||||
int asn1_get_choice_selector(ASN1_VALUE **pval, const ASN1_ITEM *it);
|
||||
int asn1_set_choice_selector(ASN1_VALUE **pval, int value, const ASN1_ITEM *it);
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $OpenBSD: x_crl.c,v 1.41 2023/07/07 19:37:52 beck Exp $ */
|
||||
/* $OpenBSD: x_crl.c,v 1.42 2024/01/06 17:37:23 tb Exp $ */
|
||||
/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
|
||||
* All rights reserved.
|
||||
*
|
||||
|
@ -100,17 +100,6 @@ const ASN1_ITEM X509_REVOKED_it = {
|
|||
.sname = "X509_REVOKED",
|
||||
};
|
||||
|
||||
static int def_crl_verify(X509_CRL *crl, EVP_PKEY *r);
|
||||
static int def_crl_lookup(X509_CRL *crl, X509_REVOKED **ret,
|
||||
ASN1_INTEGER *serial, X509_NAME *issuer);
|
||||
|
||||
static X509_CRL_METHOD int_crl_meth = {
|
||||
.crl_lookup = def_crl_lookup,
|
||||
.crl_verify = def_crl_verify
|
||||
};
|
||||
|
||||
static const X509_CRL_METHOD *default_crl_method = &int_crl_meth;
|
||||
|
||||
/* The X509_CRL_INFO structure needs a bit of customisation.
|
||||
* Since we cache the original encoding the signature wont be affected by
|
||||
* reordering of the revoked field.
|
||||
|
@ -280,8 +269,6 @@ crl_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it, void *exarg)
|
|||
crl->flags = 0;
|
||||
crl->idp_flags = 0;
|
||||
crl->idp_reasons = CRLDP_ALL_REASONS;
|
||||
crl->meth = default_crl_method;
|
||||
crl->meth_data = NULL;
|
||||
crl->issuers = NULL;
|
||||
crl->crl_number = NULL;
|
||||
crl->base_crl_number = NULL;
|
||||
|
@ -335,18 +322,9 @@ crl_cb(int operation, ASN1_VALUE **pval, const ASN1_ITEM *it, void *exarg)
|
|||
|
||||
if (!crl_set_issuers(crl))
|
||||
return 0;
|
||||
|
||||
if (crl->meth->crl_init) {
|
||||
if (crl->meth->crl_init(crl) == 0)
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
|
||||
case ASN1_OP_FREE_POST:
|
||||
if (crl->meth->crl_free) {
|
||||
if (!crl->meth->crl_free(crl))
|
||||
rc = 0;
|
||||
}
|
||||
if (crl->akid)
|
||||
AUTHORITY_KEYID_free(crl->akid);
|
||||
if (crl->idp)
|
||||
|
@ -546,36 +524,10 @@ X509_CRL_add0_revoked(X509_CRL *crl, X509_REVOKED *rev)
|
|||
}
|
||||
|
||||
int
|
||||
X509_CRL_verify(X509_CRL *crl, EVP_PKEY *r)
|
||||
X509_CRL_verify(X509_CRL *crl, EVP_PKEY *pkey)
|
||||
{
|
||||
if (crl->meth->crl_verify)
|
||||
return crl->meth->crl_verify(crl, r);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
X509_CRL_get0_by_serial(X509_CRL *crl, X509_REVOKED **ret,
|
||||
ASN1_INTEGER *serial)
|
||||
{
|
||||
if (crl->meth->crl_lookup)
|
||||
return crl->meth->crl_lookup(crl, ret, serial, NULL);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
X509_CRL_get0_by_cert(X509_CRL *crl, X509_REVOKED **ret, X509 *x)
|
||||
{
|
||||
if (crl->meth->crl_lookup)
|
||||
return crl->meth->crl_lookup(crl, ret,
|
||||
X509_get_serialNumber(x), X509_get_issuer_name(x));
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
def_crl_verify(X509_CRL *crl, EVP_PKEY *r)
|
||||
{
|
||||
return(ASN1_item_verify(&X509_CRL_INFO_it,
|
||||
crl->sig_alg, crl->signature, crl->crl, r));
|
||||
return ASN1_item_verify(&X509_CRL_INFO_it, crl->sig_alg, crl->signature,
|
||||
crl->crl, pkey);
|
||||
}
|
||||
|
||||
static int
|
||||
|
@ -606,16 +558,13 @@ crl_revoked_issuer_match(X509_CRL *crl, X509_NAME *nm, X509_REVOKED *rev)
|
|||
}
|
||||
|
||||
static int
|
||||
def_crl_lookup(X509_CRL *crl, X509_REVOKED **ret, ASN1_INTEGER *serial,
|
||||
crl_lookup(X509_CRL *crl, X509_REVOKED **ret, ASN1_INTEGER *serial,
|
||||
X509_NAME *issuer)
|
||||
{
|
||||
X509_REVOKED rtmp, *rev;
|
||||
int idx;
|
||||
|
||||
rtmp.serialNumber = serial;
|
||||
/* Sort revoked into serial number order if not already sorted.
|
||||
* Do this under a lock to avoid race condition.
|
||||
*/
|
||||
if (!sk_X509_REVOKED_is_sorted(crl->crl->revoked)) {
|
||||
CRYPTO_w_lock(CRYPTO_LOCK_X509_CRL);
|
||||
sk_X509_REVOKED_sort(crl->crl->revoked);
|
||||
|
@ -640,13 +589,23 @@ def_crl_lookup(X509_CRL *crl, X509_REVOKED **ret, ASN1_INTEGER *serial,
|
|||
return 0;
|
||||
}
|
||||
|
||||
int
|
||||
X509_CRL_get0_by_serial(X509_CRL *crl, X509_REVOKED **ret,
|
||||
ASN1_INTEGER *serial)
|
||||
{
|
||||
return crl_lookup(crl, ret, serial, NULL);
|
||||
}
|
||||
|
||||
int
|
||||
X509_CRL_get0_by_cert(X509_CRL *crl, X509_REVOKED **ret, X509 *x)
|
||||
{
|
||||
return crl_lookup(crl, ret, X509_get_serialNumber(x),
|
||||
X509_get_issuer_name(x));
|
||||
}
|
||||
|
||||
void
|
||||
X509_CRL_set_default_method(const X509_CRL_METHOD *meth)
|
||||
{
|
||||
if (meth == NULL)
|
||||
default_crl_method = &int_crl_meth;
|
||||
else
|
||||
default_crl_method = meth;
|
||||
}
|
||||
|
||||
X509_CRL_METHOD *
|
||||
|
@ -656,40 +615,25 @@ X509_CRL_METHOD_new(int (*crl_init)(X509_CRL *crl),
|
|||
ASN1_INTEGER *ser, X509_NAME *issuer),
|
||||
int (*crl_verify)(X509_CRL *crl, EVP_PKEY *pk))
|
||||
{
|
||||
X509_CRL_METHOD *m;
|
||||
|
||||
if ((m = calloc(1, sizeof(X509_CRL_METHOD))) == NULL)
|
||||
return NULL;
|
||||
|
||||
m->crl_init = crl_init;
|
||||
m->crl_free = crl_free;
|
||||
m->crl_lookup = crl_lookup;
|
||||
m->crl_verify = crl_verify;
|
||||
m->flags = X509_CRL_METHOD_DYNAMIC;
|
||||
|
||||
return m;
|
||||
X509error(ERR_R_DISABLED);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void
|
||||
X509_CRL_METHOD_free(X509_CRL_METHOD *m)
|
||||
{
|
||||
if (m == NULL)
|
||||
return;
|
||||
if (!(m->flags & X509_CRL_METHOD_DYNAMIC))
|
||||
return;
|
||||
free(m);
|
||||
}
|
||||
|
||||
void
|
||||
X509_CRL_set_meth_data(X509_CRL *crl, void *dat)
|
||||
{
|
||||
crl->meth_data = dat;
|
||||
}
|
||||
|
||||
void *
|
||||
X509_CRL_get_meth_data(X509_CRL *crl)
|
||||
{
|
||||
return crl->meth_data;
|
||||
X509error(ERR_R_DISABLED);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $OpenBSD: crypto_init.c,v 1.13 2023/12/16 12:36:14 tb Exp $ */
|
||||
/* $OpenBSD: crypto_init.c,v 1.14 2024/01/06 17:43:39 tb Exp $ */
|
||||
/*
|
||||
* Copyright (c) 2018 Bob Beck <beck@openbsd.org>
|
||||
*
|
||||
|
@ -84,7 +84,6 @@ OPENSSL_cleanup(void)
|
|||
EVP_cleanup();
|
||||
|
||||
X509V3_EXT_cleanup();
|
||||
X509_PURPOSE_cleanup();
|
||||
X509_TRUST_cleanup();
|
||||
X509_VERIFY_PARAM_table_cleanup();
|
||||
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $OpenBSD: evp_key.c,v 1.30 2023/07/07 19:37:53 beck Exp $ */
|
||||
/* $OpenBSD: evp_key.c,v 1.33 2024/01/05 10:18:52 tb Exp $ */
|
||||
/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
|
||||
* All rights reserved.
|
||||
*
|
||||
|
@ -75,18 +75,17 @@ EVP_set_pw_prompt(const char *prompt)
|
|||
{
|
||||
if (prompt == NULL)
|
||||
prompt_string[0] = '\0';
|
||||
else {
|
||||
else
|
||||
strlcpy(prompt_string, prompt, sizeof(prompt_string));
|
||||
}
|
||||
}
|
||||
|
||||
char *
|
||||
EVP_get_pw_prompt(void)
|
||||
{
|
||||
if (prompt_string[0] == '\0')
|
||||
return (NULL);
|
||||
else
|
||||
return (prompt_string);
|
||||
return NULL;
|
||||
|
||||
return prompt_string;
|
||||
}
|
||||
|
||||
int
|
||||
|
@ -99,30 +98,35 @@ int
|
|||
EVP_read_pw_string_min(char *buf, int min, int len, const char *prompt,
|
||||
int verify)
|
||||
{
|
||||
int ret;
|
||||
UI *ui = NULL;
|
||||
char buff[BUFSIZ];
|
||||
UI *ui;
|
||||
int ret = -1;
|
||||
|
||||
if (len > BUFSIZ)
|
||||
len = BUFSIZ;
|
||||
/* Ensure that 0 <= min <= len - 1. In particular, 1 <= len. */
|
||||
if (min < 0 || len - 1 < min)
|
||||
return -1;
|
||||
if ((prompt == NULL) && (prompt_string[0] != '\0'))
|
||||
goto err;
|
||||
|
||||
if (prompt == NULL && prompt_string[0] != '\0')
|
||||
prompt = prompt_string;
|
||||
ui = UI_new();
|
||||
if (ui == NULL)
|
||||
return -1;
|
||||
|
||||
if ((ui = UI_new()) == NULL)
|
||||
goto err;
|
||||
if (UI_add_input_string(ui, prompt, 0, buf, min, len - 1) < 0)
|
||||
return -1;
|
||||
goto err;
|
||||
if (verify) {
|
||||
if (UI_add_verify_string(ui, prompt, 0, buff, min, len - 1, buf)
|
||||
< 0)
|
||||
return -1;
|
||||
if (UI_add_verify_string(ui, prompt, 0, buff, min, len - 1,
|
||||
buf) < 0)
|
||||
goto err;
|
||||
}
|
||||
|
||||
ret = UI_process(ui);
|
||||
|
||||
err:
|
||||
UI_free(ui);
|
||||
explicit_bzero(buff, BUFSIZ);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -150,7 +154,7 @@ EVP_BytesToKey(const EVP_CIPHER *type, const EVP_MD *md,
|
|||
}
|
||||
|
||||
if (data == NULL)
|
||||
return (nkey);
|
||||
return nkey;
|
||||
|
||||
EVP_MD_CTX_init(&c);
|
||||
for (;;) {
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $OpenBSD: p_lib.c,v 1.57 2024/01/04 17:22:29 tb Exp $ */
|
||||
/* $OpenBSD: p_lib.c,v 1.58 2024/01/05 21:22:01 tb Exp $ */
|
||||
/* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
|
||||
* All rights reserved.
|
||||
*
|
||||
|
@ -208,8 +208,7 @@ const EVP_PKEY_ASN1_METHOD *
|
|||
EVP_PKEY_asn1_find_str(ENGINE **engine, const char *str, int len)
|
||||
{
|
||||
const EVP_PKEY_ASN1_METHOD *ameth;
|
||||
size_t str_len;
|
||||
int i;
|
||||
size_t i, str_len;
|
||||
|
||||
if (engine != NULL)
|
||||
*engine = NULL;
|
||||
|
@ -223,7 +222,7 @@ EVP_PKEY_asn1_find_str(ENGINE **engine, const char *str, int len)
|
|||
|
||||
for (i = 0; i < N_ASN1_METHODS; i++) {
|
||||
ameth = asn1_methods[i];
|
||||
if (ameth->pkey_flags & ASN1_PKEY_ALIAS)
|
||||
if ((ameth->pkey_flags & ASN1_PKEY_ALIAS) != 0)
|
||||
continue;
|
||||
if (strlen(ameth->pem_str) != str_len)
|
||||
continue;
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $OpenBSD: x509_local.h,v 1.17 2023/12/29 05:33:32 tb Exp $ */
|
||||
/* $OpenBSD: x509_local.h,v 1.18 2024/01/06 17:37:23 tb Exp $ */
|
||||
/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
|
||||
* project 2013.
|
||||
*/
|
||||
|
@ -224,8 +224,6 @@ struct X509_crl_st {
|
|||
ASN1_INTEGER *base_crl_number;
|
||||
unsigned char hash[X509_CRL_HASH_LEN];
|
||||
STACK_OF(GENERAL_NAMES) *issuers;
|
||||
const X509_CRL_METHOD *meth;
|
||||
void *meth_data;
|
||||
} /* X509_CRL */;
|
||||
|
||||
struct pkcs8_priv_key_info_st {
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $OpenBSD: x509_purp.c,v 1.33 2023/12/31 07:19:13 tb Exp $ */
|
||||
/* $OpenBSD: x509_purp.c,v 1.34 2024/01/06 17:17:08 tb Exp $ */
|
||||
/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
|
||||
* project 2001.
|
||||
*/
|
||||
|
@ -95,9 +95,6 @@ static int check_purpose_timestamp_sign(const X509_PURPOSE *xp, const X509 *x,
|
|||
static int no_check(const X509_PURPOSE *xp, const X509 *x, int ca);
|
||||
static int ocsp_helper(const X509_PURPOSE *xp, const X509 *x, int ca);
|
||||
|
||||
static int xp_cmp(const X509_PURPOSE * const *a, const X509_PURPOSE * const *b);
|
||||
static void xptable_free(X509_PURPOSE *p);
|
||||
|
||||
static X509_PURPOSE xstandard[] = {
|
||||
{
|
||||
.purpose = X509_PURPOSE_SSL_CLIENT,
|
||||
|
@ -166,14 +163,6 @@ static X509_PURPOSE xstandard[] = {
|
|||
|
||||
#define X509_PURPOSE_COUNT (sizeof(xstandard) / sizeof(xstandard[0]))
|
||||
|
||||
static STACK_OF(X509_PURPOSE) *xptable = NULL;
|
||||
|
||||
static int
|
||||
xp_cmp(const X509_PURPOSE * const *a, const X509_PURPOSE * const *b)
|
||||
{
|
||||
return (*a)->purpose - (*b)->purpose;
|
||||
}
|
||||
|
||||
/* As much as I'd like to make X509_check_purpose use a "const" X509*
|
||||
* I really can't because it does recalculate hashes and do other non-const
|
||||
* things. */
|
||||
|
@ -211,20 +200,17 @@ LCRYPTO_ALIAS(X509_PURPOSE_set);
|
|||
int
|
||||
X509_PURPOSE_get_count(void)
|
||||
{
|
||||
if (!xptable)
|
||||
return X509_PURPOSE_COUNT;
|
||||
return sk_X509_PURPOSE_num(xptable) + X509_PURPOSE_COUNT;
|
||||
return X509_PURPOSE_COUNT;
|
||||
}
|
||||
LCRYPTO_ALIAS(X509_PURPOSE_get_count);
|
||||
|
||||
X509_PURPOSE *
|
||||
X509_PURPOSE_get0(int idx)
|
||||
{
|
||||
if (idx < 0)
|
||||
if (idx < 0 || (size_t)idx >= X509_PURPOSE_COUNT)
|
||||
return NULL;
|
||||
if (idx < (int)X509_PURPOSE_COUNT)
|
||||
return xstandard + idx;
|
||||
return sk_X509_PURPOSE_value(xptable, idx - X509_PURPOSE_COUNT);
|
||||
|
||||
return &xstandard[idx];
|
||||
}
|
||||
LCRYPTO_ALIAS(X509_PURPOSE_get0);
|
||||
|
||||
|
@ -246,18 +232,11 @@ LCRYPTO_ALIAS(X509_PURPOSE_get_by_sname);
|
|||
int
|
||||
X509_PURPOSE_get_by_id(int purpose)
|
||||
{
|
||||
X509_PURPOSE tmp;
|
||||
int idx;
|
||||
/* X509_PURPOSE_MIN == 1, so the bounds are correct. */
|
||||
if (purpose < X509_PURPOSE_MIN || purpose > X509_PURPOSE_MAX)
|
||||
return -1;
|
||||
|
||||
if ((purpose >= X509_PURPOSE_MIN) && (purpose <= X509_PURPOSE_MAX))
|
||||
return purpose - X509_PURPOSE_MIN;
|
||||
tmp.purpose = purpose;
|
||||
if (!xptable)
|
||||
return -1;
|
||||
idx = sk_X509_PURPOSE_find(xptable, &tmp);
|
||||
if (idx == -1)
|
||||
return -1;
|
||||
return idx + X509_PURPOSE_COUNT;
|
||||
return purpose - X509_PURPOSE_MIN;
|
||||
}
|
||||
LCRYPTO_ALIAS(X509_PURPOSE_get_by_id);
|
||||
|
||||
|
@ -266,95 +245,14 @@ X509_PURPOSE_add(int id, int trust, int flags,
|
|||
int (*ck)(const X509_PURPOSE *, const X509 *, int), const char *name,
|
||||
const char *sname, void *arg)
|
||||
{
|
||||
int idx;
|
||||
X509_PURPOSE *ptmp;
|
||||
char *name_dup, *sname_dup;
|
||||
|
||||
name_dup = sname_dup = NULL;
|
||||
|
||||
if (name == NULL || sname == NULL) {
|
||||
X509V3error(X509V3_R_INVALID_NULL_ARGUMENT);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* This is set according to what we change: application can't set it */
|
||||
flags &= ~X509_PURPOSE_DYNAMIC;
|
||||
/* This will always be set for application modified trust entries */
|
||||
flags |= X509_PURPOSE_DYNAMIC_NAME;
|
||||
/* Get existing entry if any */
|
||||
idx = X509_PURPOSE_get_by_id(id);
|
||||
/* Need a new entry */
|
||||
if (idx == -1) {
|
||||
if ((ptmp = malloc(sizeof(X509_PURPOSE))) == NULL) {
|
||||
X509V3error(ERR_R_MALLOC_FAILURE);
|
||||
return 0;
|
||||
}
|
||||
ptmp->flags = X509_PURPOSE_DYNAMIC;
|
||||
} else
|
||||
ptmp = X509_PURPOSE_get0(idx);
|
||||
|
||||
if ((name_dup = strdup(name)) == NULL)
|
||||
goto err;
|
||||
if ((sname_dup = strdup(sname)) == NULL)
|
||||
goto err;
|
||||
|
||||
/* free existing name if dynamic */
|
||||
if (ptmp->flags & X509_PURPOSE_DYNAMIC_NAME) {
|
||||
free(ptmp->name);
|
||||
free(ptmp->sname);
|
||||
}
|
||||
/* dup supplied name */
|
||||
ptmp->name = name_dup;
|
||||
ptmp->sname = sname_dup;
|
||||
/* Keep the dynamic flag of existing entry */
|
||||
ptmp->flags &= X509_PURPOSE_DYNAMIC;
|
||||
/* Set all other flags */
|
||||
ptmp->flags |= flags;
|
||||
|
||||
ptmp->purpose = id;
|
||||
ptmp->trust = trust;
|
||||
ptmp->check_purpose = ck;
|
||||
ptmp->usr_data = arg;
|
||||
|
||||
/* If its a new entry manage the dynamic table */
|
||||
if (idx == -1) {
|
||||
if (xptable == NULL &&
|
||||
(xptable = sk_X509_PURPOSE_new(xp_cmp)) == NULL)
|
||||
goto err;
|
||||
if (sk_X509_PURPOSE_push(xptable, ptmp) == 0)
|
||||
goto err;
|
||||
}
|
||||
return 1;
|
||||
|
||||
err:
|
||||
free(name_dup);
|
||||
free(sname_dup);
|
||||
if (idx == -1)
|
||||
free(ptmp);
|
||||
X509V3error(ERR_R_MALLOC_FAILURE);
|
||||
X509error(ERR_R_DISABLED);
|
||||
return 0;
|
||||
}
|
||||
LCRYPTO_ALIAS(X509_PURPOSE_add);
|
||||
|
||||
static void
|
||||
xptable_free(X509_PURPOSE *p)
|
||||
{
|
||||
if (!p)
|
||||
return;
|
||||
if (p->flags & X509_PURPOSE_DYNAMIC) {
|
||||
if (p->flags & X509_PURPOSE_DYNAMIC_NAME) {
|
||||
free(p->name);
|
||||
free(p->sname);
|
||||
}
|
||||
free(p);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
X509_PURPOSE_cleanup(void)
|
||||
{
|
||||
sk_X509_PURPOSE_pop_free(xptable, xptable_free);
|
||||
xptable = NULL;
|
||||
}
|
||||
LCRYPTO_ALIAS(X509_PURPOSE_cleanup);
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue