mirror of
git://git.gnupg.org/gnupg.git
synced 2025-03-11 22:52:47 +01:00
sm: Support import of PKCS#12 encoded ECC private keys.
* sm/minip12.c: Include ksba.h. (oid_pcPublicKey): New const. (parse_bag_data): Add arg 'r-curve'. Support parsing of ECC private keys. (p12_parse): Add arg 'r_curve'. * sm/import.c (parse_p12): Support ECC import. -- GnuPG-bug-id: 4921 Signed-off-by: Werner Koch <wk@gnupg.org>
This commit is contained in:
parent
a6d2f31337
commit
8dfef5197a
103
sm/import.c
103
sm/import.c
@ -717,6 +717,7 @@ parse_p12 (ctrl_t ctrl, ksba_reader_t reader, struct stats_s *stats)
|
|||||||
gcry_sexp_t s_key = NULL;
|
gcry_sexp_t s_key = NULL;
|
||||||
unsigned char grip[20];
|
unsigned char grip[20];
|
||||||
int bad_pass = 0;
|
int bad_pass = 0;
|
||||||
|
char *curve = NULL;
|
||||||
int i;
|
int i;
|
||||||
struct store_cert_parm_s store_cert_parm;
|
struct store_cert_parm_s store_cert_parm;
|
||||||
|
|
||||||
@ -777,7 +778,8 @@ parse_p12 (ctrl_t ctrl, ksba_reader_t reader, struct stats_s *stats)
|
|||||||
goto leave;
|
goto leave;
|
||||||
|
|
||||||
kparms = p12_parse (p12buffer + p12bufoff, p12buflen - p12bufoff,
|
kparms = p12_parse (p12buffer + p12bufoff, p12buflen - p12bufoff,
|
||||||
passphrase, store_cert_cb, &store_cert_parm, &bad_pass);
|
passphrase, store_cert_cb,
|
||||||
|
&store_cert_parm, &bad_pass, &curve);
|
||||||
|
|
||||||
xfree (passphrase);
|
xfree (passphrase);
|
||||||
passphrase = NULL;
|
passphrase = NULL;
|
||||||
@ -789,35 +791,79 @@ parse_p12 (ctrl_t ctrl, ksba_reader_t reader, struct stats_s *stats)
|
|||||||
goto leave;
|
goto leave;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* print_mpi (" n", kparms[0]); */
|
if (curve)
|
||||||
/* print_mpi (" e", kparms[1]); */
|
{
|
||||||
/* print_mpi (" d", kparms[2]); */
|
gcry_ctx_t ecctx = NULL;
|
||||||
/* print_mpi (" p", kparms[3]); */
|
|
||||||
/* print_mpi (" q", kparms[4]); */
|
|
||||||
/* print_mpi ("dmp1", kparms[5]); */
|
|
||||||
/* print_mpi ("dmq1", kparms[6]); */
|
|
||||||
/* print_mpi (" u", kparms[7]); */
|
|
||||||
|
|
||||||
sk.n = kparms[0];
|
/* log_debug ("curve: %s\n", curve); */
|
||||||
sk.e = kparms[1];
|
/* gcry_log_debugmpi ("MPI[0]", kparms[0]); */
|
||||||
sk.d = kparms[2];
|
|
||||||
sk.q = kparms[3];
|
|
||||||
sk.p = kparms[4];
|
|
||||||
sk.u = kparms[7];
|
|
||||||
err = rsa_key_check (&sk);
|
|
||||||
if (err)
|
|
||||||
goto leave;
|
|
||||||
/* print_mpi (" n", sk.n); */
|
|
||||||
/* print_mpi (" e", sk.e); */
|
|
||||||
/* print_mpi (" d", sk.d); */
|
|
||||||
/* print_mpi (" p", sk.p); */
|
|
||||||
/* print_mpi (" q", sk.q); */
|
|
||||||
/* print_mpi (" u", sk.u); */
|
|
||||||
|
|
||||||
/* Create an S-expression from the parameters. */
|
/* We need to get the public key. */
|
||||||
err = gcry_sexp_build (&s_key, NULL,
|
err = gcry_mpi_ec_new (&ecctx, NULL, curve);
|
||||||
"(private-key(rsa(n%m)(e%m)(d%m)(p%m)(q%m)(u%m)))",
|
if (err)
|
||||||
sk.n, sk.e, sk.d, sk.p, sk.q, sk.u, NULL);
|
{
|
||||||
|
log_error ("error creating context for curve '%s': %s\n",
|
||||||
|
curve, gpg_strerror (err));
|
||||||
|
goto leave;
|
||||||
|
}
|
||||||
|
err = gcry_mpi_ec_set_mpi ("d", kparms[0], ecctx);
|
||||||
|
if (err)
|
||||||
|
{
|
||||||
|
log_error ("error setting 'd' into context of curve '%s': %s\n",
|
||||||
|
curve, gpg_strerror (err));
|
||||||
|
gcry_ctx_release (ecctx);
|
||||||
|
goto leave;
|
||||||
|
}
|
||||||
|
|
||||||
|
kparms[1] = gcry_mpi_ec_get_mpi ("q", ecctx, 1);
|
||||||
|
if (!kparms[1])
|
||||||
|
{
|
||||||
|
log_error ("error computing 'q' from 'd' for curve '%s'\n", curve);
|
||||||
|
gcry_ctx_release (ecctx);
|
||||||
|
goto leave;
|
||||||
|
}
|
||||||
|
|
||||||
|
gcry_ctx_release (ecctx);
|
||||||
|
|
||||||
|
err = gcry_sexp_build (&s_key, NULL,
|
||||||
|
"(private-key(ecc(curve %s)(q%m)(d%m)))",
|
||||||
|
curve, kparms[1], kparms[0], NULL);
|
||||||
|
}
|
||||||
|
else /* RSA */
|
||||||
|
{
|
||||||
|
/* print_mpi (" n", kparms[0]); */
|
||||||
|
/* print_mpi (" e", kparms[1]); */
|
||||||
|
/* print_mpi (" d", kparms[2]); */
|
||||||
|
/* print_mpi (" p", kparms[3]); */
|
||||||
|
/* print_mpi (" q", kparms[4]); */
|
||||||
|
/* print_mpi ("dmp1", kparms[5]); */
|
||||||
|
/* print_mpi ("dmq1", kparms[6]); */
|
||||||
|
/* print_mpi (" u", kparms[7]); */
|
||||||
|
|
||||||
|
sk.n = kparms[0];
|
||||||
|
sk.e = kparms[1];
|
||||||
|
sk.d = kparms[2];
|
||||||
|
sk.q = kparms[3];
|
||||||
|
sk.p = kparms[4];
|
||||||
|
sk.u = kparms[7];
|
||||||
|
err = rsa_key_check (&sk);
|
||||||
|
if (err)
|
||||||
|
goto leave;
|
||||||
|
/* print_mpi (" n", sk.n); */
|
||||||
|
/* print_mpi (" e", sk.e); */
|
||||||
|
/* print_mpi (" d", sk.d); */
|
||||||
|
/* print_mpi (" p", sk.p); */
|
||||||
|
/* print_mpi (" q", sk.q); */
|
||||||
|
/* print_mpi (" u", sk.u); */
|
||||||
|
|
||||||
|
/* Create an S-expression from the parameters. */
|
||||||
|
err = gcry_sexp_build (&s_key, NULL,
|
||||||
|
"(private-key(rsa(n%m)(e%m)(d%m)(p%m)(q%m)(u%m)))",
|
||||||
|
sk.n, sk.e, sk.d, sk.p, sk.q, sk.u, NULL);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* The next is very ugly - we really should not rely on our
|
||||||
|
* knowledge of p12_parse internals. */
|
||||||
for (i=0; i < 8; i++)
|
for (i=0; i < 8; i++)
|
||||||
gcry_mpi_release (kparms[i]);
|
gcry_mpi_release (kparms[i]);
|
||||||
gcry_free (kparms);
|
gcry_free (kparms);
|
||||||
@ -923,6 +969,7 @@ parse_p12 (ctrl_t ctrl, ksba_reader_t reader, struct stats_s *stats)
|
|||||||
xfree (kek);
|
xfree (kek);
|
||||||
xfree (get_membuf (&p12mbuf, NULL));
|
xfree (get_membuf (&p12mbuf, NULL));
|
||||||
xfree (p12buffer);
|
xfree (p12buffer);
|
||||||
|
xfree (curve);
|
||||||
|
|
||||||
if (bad_pass)
|
if (bad_pass)
|
||||||
{
|
{
|
||||||
|
151
sm/minip12.c
151
sm/minip12.c
@ -33,6 +33,8 @@
|
|||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include <ksba.h>
|
||||||
|
|
||||||
#include "../common/logging.h"
|
#include "../common/logging.h"
|
||||||
#include "../common/utf8conv.h"
|
#include "../common/utf8conv.h"
|
||||||
#include "minip12.h"
|
#include "minip12.h"
|
||||||
@ -114,7 +116,8 @@ static unsigned char const oid_aes128_CBC[9] = {
|
|||||||
|
|
||||||
static unsigned char const oid_rsaEncryption[9] = {
|
static unsigned char const oid_rsaEncryption[9] = {
|
||||||
0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x01 };
|
0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x01, 0x01, 0x01 };
|
||||||
|
static unsigned char const oid_pcPublicKey[7] = {
|
||||||
|
0x2A, 0x86, 0x48, 0xCE, 0x3D, 0x02, 0x01 };
|
||||||
|
|
||||||
static unsigned char const data_3desiter2048[30] = {
|
static unsigned char const data_3desiter2048[30] = {
|
||||||
0x30, 0x1C, 0x06, 0x0A, 0x2A, 0x86, 0x48, 0x86,
|
0x30, 0x1C, 0x06, 0x0A, 0x2A, 0x86, 0x48, 0x86,
|
||||||
@ -642,7 +645,7 @@ bag_decrypted_data_p (const void *plaintext, size_t length)
|
|||||||
|
|
||||||
/* { */
|
/* { */
|
||||||
/* # warning debug code is enabled */
|
/* # warning debug code is enabled */
|
||||||
/* FILE *fp = fopen ("tmp-rc2-plain.der", "wb"); */
|
/* FILE *fp = fopen ("tmp-minip12-plain.der", "wb"); */
|
||||||
/* if (!fp || fwrite (p, n, 1, fp) != 1) */
|
/* if (!fp || fwrite (p, n, 1, fp) != 1) */
|
||||||
/* exit (2); */
|
/* exit (2); */
|
||||||
/* fclose (fp); */
|
/* fclose (fp); */
|
||||||
@ -1158,7 +1161,7 @@ bag_data_p (const void *plaintext, size_t length)
|
|||||||
|
|
||||||
/* { */
|
/* { */
|
||||||
/* # warning debug code is enabled */
|
/* # warning debug code is enabled */
|
||||||
/* FILE *fp = fopen ("tmp-3des-plain-key.der", "wb"); */
|
/* FILE *fp = fopen ("tmp-minip12-plain-key.der", "wb"); */
|
||||||
/* if (!fp || fwrite (p, n, 1, fp) != 1) */
|
/* if (!fp || fwrite (p, n, 1, fp) != 1) */
|
||||||
/* exit (2); */
|
/* exit (2); */
|
||||||
/* fclose (fp); */
|
/* fclose (fp); */
|
||||||
@ -1176,7 +1179,7 @@ bag_data_p (const void *plaintext, size_t length)
|
|||||||
|
|
||||||
static gcry_mpi_t *
|
static gcry_mpi_t *
|
||||||
parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
|
parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
|
||||||
size_t *r_consumed, const char *pw)
|
size_t *r_consumed, char **r_curve, const char *pw)
|
||||||
{
|
{
|
||||||
int rc;
|
int rc;
|
||||||
struct tag_info ti;
|
struct tag_info ti;
|
||||||
@ -1195,6 +1198,7 @@ parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
|
|||||||
unsigned char *cram_buffer = NULL;
|
unsigned char *cram_buffer = NULL;
|
||||||
size_t consumed = 0; /* Number of bytes consumed from the original buffer. */
|
size_t consumed = 0; /* Number of bytes consumed from the original buffer. */
|
||||||
int is_pbes2 = 0;
|
int is_pbes2 = 0;
|
||||||
|
char *curve = NULL;
|
||||||
|
|
||||||
where = "start";
|
where = "start";
|
||||||
if (parse_tag (&p, &n, &ti))
|
if (parse_tag (&p, &n, &ti))
|
||||||
@ -1409,13 +1413,43 @@ parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
|
|||||||
if (len < ti.nhdr)
|
if (len < ti.nhdr)
|
||||||
goto bailout;
|
goto bailout;
|
||||||
len -= ti.nhdr;
|
len -= ti.nhdr;
|
||||||
if (ti.class || ti.tag != TAG_OBJECT_ID
|
if (ti.class || ti.tag != TAG_OBJECT_ID)
|
||||||
|| ti.length != DIM(oid_rsaEncryption)
|
goto bailout;
|
||||||
|| memcmp (p, oid_rsaEncryption,
|
/* gpgrt_log_printhex (p, ti.length, "OID:"); */
|
||||||
DIM(oid_rsaEncryption)))
|
if (ti.length == DIM(oid_rsaEncryption)
|
||||||
|
&& !memcmp (p, oid_rsaEncryption, DIM(oid_rsaEncryption)))
|
||||||
|
{
|
||||||
|
p += DIM (oid_rsaEncryption);
|
||||||
|
n -= DIM (oid_rsaEncryption);
|
||||||
|
}
|
||||||
|
else if (ti.length == DIM(oid_pcPublicKey)
|
||||||
|
&& !memcmp (p, oid_pcPublicKey, DIM(oid_pcPublicKey)))
|
||||||
|
{
|
||||||
|
/* See RFC-5915 for the format. */
|
||||||
|
p += DIM (oid_pcPublicKey);
|
||||||
|
n -= DIM (oid_pcPublicKey);
|
||||||
|
if (len < ti.length)
|
||||||
|
goto bailout;
|
||||||
|
len -= ti.length;
|
||||||
|
if (n < len)
|
||||||
|
goto bailout;
|
||||||
|
if (parse_tag (&p, &n, &ti))
|
||||||
|
goto bailout;
|
||||||
|
/* gpgrt_log_debug ("ti=%d/%lu len=%lu\n",ti.class,ti.tag,ti.length); */
|
||||||
|
if (len < ti.nhdr)
|
||||||
|
goto bailout;
|
||||||
|
len -= ti.nhdr;
|
||||||
|
if (ti.class || ti.tag != TAG_OBJECT_ID)
|
||||||
|
goto bailout;
|
||||||
|
curve = ksba_oid_to_str (p, ti.length);
|
||||||
|
if (!curve)
|
||||||
|
goto bailout;
|
||||||
|
/* log_debug ("OID of curve is: %s\n", curve); */
|
||||||
|
p += ti.length;
|
||||||
|
n -= ti.length;
|
||||||
|
}
|
||||||
|
else
|
||||||
goto bailout;
|
goto bailout;
|
||||||
p += DIM (oid_rsaEncryption);
|
|
||||||
n -= DIM (oid_rsaEncryption);
|
|
||||||
if (len < ti.length)
|
if (len < ti.length)
|
||||||
goto bailout;
|
goto bailout;
|
||||||
len -= ti.length;
|
len -= ti.length;
|
||||||
@ -1438,7 +1472,7 @@ parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
|
|||||||
result_count = 0;
|
result_count = 0;
|
||||||
|
|
||||||
where = "reading.key-parameters";
|
where = "reading.key-parameters";
|
||||||
for (result_count=0; len && result_count < 9;)
|
if (curve) /* ECC case. */
|
||||||
{
|
{
|
||||||
if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_INTEGER)
|
if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_INTEGER)
|
||||||
goto bailout;
|
goto bailout;
|
||||||
@ -1448,30 +1482,68 @@ parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
|
|||||||
if (len < ti.length)
|
if (len < ti.length)
|
||||||
goto bailout;
|
goto bailout;
|
||||||
len -= ti.length;
|
len -= ti.length;
|
||||||
if (!result_count && ti.length == 1 && !*p)
|
if (ti.length != 1 && *p != 1)
|
||||||
; /* ignore the very first one if it is a 0 */
|
|
||||||
else
|
|
||||||
{
|
{
|
||||||
rc = gcry_mpi_scan (result+result_count, GCRYMPI_FMT_USG, p,
|
log_error ("error parsing private ecPublicKey parameter: %s\n",
|
||||||
ti.length, NULL);
|
"bad version");
|
||||||
if (rc)
|
goto bailout;
|
||||||
{
|
|
||||||
log_error ("error parsing key parameter: %s\n",
|
|
||||||
gpg_strerror (rc));
|
|
||||||
goto bailout;
|
|
||||||
}
|
|
||||||
result_count++;
|
|
||||||
}
|
}
|
||||||
p += ti.length;
|
p += ti.length;
|
||||||
n -= ti.length;
|
n -= ti.length;
|
||||||
|
if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_OCTET_STRING)
|
||||||
|
goto bailout;
|
||||||
|
if (len < ti.nhdr)
|
||||||
|
goto bailout;
|
||||||
|
len -= ti.nhdr;
|
||||||
|
if (len < ti.length)
|
||||||
|
goto bailout;
|
||||||
|
len -= ti.length;
|
||||||
|
/* log_printhex (p, ti.length, "ecc q="); */
|
||||||
|
rc = gcry_mpi_scan (result, GCRYMPI_FMT_USG, p, ti.length, NULL);
|
||||||
|
if (rc)
|
||||||
|
{
|
||||||
|
log_error ("error parsing key parameter: %s\n", gpg_strerror (rc));
|
||||||
|
goto bailout;
|
||||||
|
}
|
||||||
|
p += ti.length;
|
||||||
|
n -= ti.length;
|
||||||
|
|
||||||
|
len = 0; /* Skip the rest. */
|
||||||
|
}
|
||||||
|
else /* RSA case */
|
||||||
|
{
|
||||||
|
for (result_count=0; len && result_count < 9;)
|
||||||
|
{
|
||||||
|
if (parse_tag (&p, &n, &ti) || ti.class || ti.tag != TAG_INTEGER)
|
||||||
|
goto bailout;
|
||||||
|
if (len < ti.nhdr)
|
||||||
|
goto bailout;
|
||||||
|
len -= ti.nhdr;
|
||||||
|
if (len < ti.length)
|
||||||
|
goto bailout;
|
||||||
|
len -= ti.length;
|
||||||
|
if (!result_count && ti.length == 1 && !*p)
|
||||||
|
; /* ignore the very first one if it is a 0 */
|
||||||
|
else
|
||||||
|
{
|
||||||
|
rc = gcry_mpi_scan (result+result_count, GCRYMPI_FMT_USG, p,
|
||||||
|
ti.length, NULL);
|
||||||
|
if (rc)
|
||||||
|
{
|
||||||
|
log_error ("error parsing key parameter: %s\n",
|
||||||
|
gpg_strerror (rc));
|
||||||
|
goto bailout;
|
||||||
|
}
|
||||||
|
result_count++;
|
||||||
|
}
|
||||||
|
p += ti.length;
|
||||||
|
n -= ti.length;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (len)
|
if (len)
|
||||||
goto bailout;
|
goto bailout;
|
||||||
|
|
||||||
gcry_free (cram_buffer);
|
goto leave;
|
||||||
if (r_consumed)
|
|
||||||
*r_consumed = consumed;
|
|
||||||
return result;
|
|
||||||
|
|
||||||
bailout:
|
bailout:
|
||||||
gcry_free (plain);
|
gcry_free (plain);
|
||||||
@ -1481,12 +1553,23 @@ parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
|
|||||||
gcry_mpi_release (result[i]);
|
gcry_mpi_release (result[i]);
|
||||||
gcry_free (result);
|
gcry_free (result);
|
||||||
}
|
}
|
||||||
gcry_free (cram_buffer);
|
|
||||||
log_error ( "data error at \"%s\", offset %u\n",
|
log_error ( "data error at \"%s\", offset %u\n",
|
||||||
where, (unsigned int)((p - buffer) + startoffset));
|
where, (unsigned int)((p - buffer) + startoffset));
|
||||||
|
result = NULL;
|
||||||
|
|
||||||
|
leave:
|
||||||
|
if (r_curve && result)
|
||||||
|
{
|
||||||
|
*r_curve = curve;
|
||||||
|
curve = NULL;
|
||||||
|
}
|
||||||
|
else if (r_curve)
|
||||||
|
*r_curve = NULL;
|
||||||
|
ksba_free (curve);
|
||||||
|
gcry_free (cram_buffer);
|
||||||
if (r_consumed)
|
if (r_consumed)
|
||||||
*r_consumed = consumed;
|
*r_consumed = consumed;
|
||||||
return NULL;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -1499,7 +1582,7 @@ parse_bag_data (const unsigned char *buffer, size_t length, int startoffset,
|
|||||||
gcry_mpi_t *
|
gcry_mpi_t *
|
||||||
p12_parse (const unsigned char *buffer, size_t length, const char *pw,
|
p12_parse (const unsigned char *buffer, size_t length, const char *pw,
|
||||||
void (*certcb)(void*, const unsigned char*, size_t),
|
void (*certcb)(void*, const unsigned char*, size_t),
|
||||||
void *certcbarg, int *r_badpass)
|
void *certcbarg, int *r_badpass, char **r_curve)
|
||||||
{
|
{
|
||||||
struct tag_info ti;
|
struct tag_info ti;
|
||||||
const unsigned char *p = buffer;
|
const unsigned char *p = buffer;
|
||||||
@ -1510,6 +1593,7 @@ p12_parse (const unsigned char *buffer, size_t length, const char *pw,
|
|||||||
int bagseqndef, lenndef;
|
int bagseqndef, lenndef;
|
||||||
gcry_mpi_t *result = NULL;
|
gcry_mpi_t *result = NULL;
|
||||||
unsigned char *cram_buffer = NULL;
|
unsigned char *cram_buffer = NULL;
|
||||||
|
char *curve = NULL;
|
||||||
|
|
||||||
*r_badpass = 0;
|
*r_badpass = 0;
|
||||||
where = "pfx";
|
where = "pfx";
|
||||||
@ -1629,7 +1713,8 @@ p12_parse (const unsigned char *buffer, size_t length, const char *pw,
|
|||||||
n -= DIM(oid_data);
|
n -= DIM(oid_data);
|
||||||
if (!lenndef)
|
if (!lenndef)
|
||||||
len -= DIM(oid_data);
|
len -= DIM(oid_data);
|
||||||
result = parse_bag_data (p, n, (p - p_start), &consumed, pw);
|
result = parse_bag_data (p, n, (p - p_start),
|
||||||
|
&consumed, &curve, pw);
|
||||||
if (!result)
|
if (!result)
|
||||||
goto bailout;
|
goto bailout;
|
||||||
if (lenndef)
|
if (lenndef)
|
||||||
@ -1658,7 +1743,9 @@ p12_parse (const unsigned char *buffer, size_t length, const char *pw,
|
|||||||
}
|
}
|
||||||
|
|
||||||
gcry_free (cram_buffer);
|
gcry_free (cram_buffer);
|
||||||
|
*r_curve = curve;
|
||||||
return result;
|
return result;
|
||||||
|
|
||||||
bailout:
|
bailout:
|
||||||
log_error ("error at \"%s\", offset %u\n",
|
log_error ("error at \"%s\", offset %u\n",
|
||||||
where, (unsigned int)(p - p_start));
|
where, (unsigned int)(p - p_start));
|
||||||
@ -1671,6 +1758,8 @@ p12_parse (const unsigned char *buffer, size_t length, const char *pw,
|
|||||||
gcry_free (result);
|
gcry_free (result);
|
||||||
}
|
}
|
||||||
gcry_free (cram_buffer);
|
gcry_free (cram_buffer);
|
||||||
|
gcry_free (curve);
|
||||||
|
*r_curve = NULL;
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -25,7 +25,7 @@
|
|||||||
gcry_mpi_t *p12_parse (const unsigned char *buffer, size_t length,
|
gcry_mpi_t *p12_parse (const unsigned char *buffer, size_t length,
|
||||||
const char *pw,
|
const char *pw,
|
||||||
void (*certcb)(void*, const unsigned char*, size_t),
|
void (*certcb)(void*, const unsigned char*, size_t),
|
||||||
void *certcbarg, int *r_badpass);
|
void *certcbarg, int *r_badpass, char **r_curve);
|
||||||
|
|
||||||
unsigned char *p12_build (gcry_mpi_t *kparms,
|
unsigned char *p12_build (gcry_mpi_t *kparms,
|
||||||
const void *cert, size_t certlen,
|
const void *cert, size_t certlen,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user