summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/tex/asn1.tex2
-rw-r--r--lib/auth_dhe_rsa.c2
-rw-r--r--lib/auth_rsa.c14
-rw-r--r--lib/auth_x509.c14
-rw-r--r--lib/gnutls.asn5
-rw-r--r--lib/gnutls_cert.c23
-rw-r--r--lib/gnutls_cert.h11
-rw-r--r--lib/gnutls_gcry.c24
-rw-r--r--lib/gnutls_gcry.h3
-rw-r--r--lib/gnutls_pk.c256
-rw-r--r--lib/gnutls_pk.h14
-rw-r--r--lib/gnutls_privkey.c169
-rw-r--r--lib/gnutls_sig.c90
-rw-r--r--lib/x509_sig_check.c151
-rw-r--r--src/cli.c12
15 files changed, 397 insertions, 393 deletions
diff --git a/doc/tex/asn1.tex b/doc/tex/asn1.tex
index d0014dbce0..71c6301eb8 100644
--- a/doc/tex/asn1.tex
+++ b/doc/tex/asn1.tex
@@ -3,7 +3,7 @@
\section{Introduction}
This file describes the forth version of ASN.1 parser I
-developed\footnote{ASN.1 Structure handling in \gnutls is developed by Fabio
+developed\footnote{ASN.1 Structure handling in \gnutls{} is developed by Fabio
Fiorina}.
The main difference from the first version is the use of pointers and the
possibility to save/get ASN1 definitions in/from a C vector.
diff --git a/lib/auth_dhe_rsa.c b/lib/auth_dhe_rsa.c
index 697fe408a6..67363a49b9 100644
--- a/lib/auth_dhe_rsa.c
+++ b/lib/auth_dhe_rsa.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2000,2001 Nikos Mavroyanopoulos
+ * Copyright (C) 2000,2001,2002 Nikos Mavroyanopoulos
*
* This file is part of GNUTLS.
*
diff --git a/lib/auth_rsa.c b/lib/auth_rsa.c
index 31a8c3ebd1..8ac3e5064c 100644
--- a/lib/auth_rsa.c
+++ b/lib/auth_rsa.c
@@ -79,6 +79,7 @@ int proc_rsa_client_kx(GNUTLS_STATE state, opaque * data, int data_size)
gnutls_sdatum plaintext;
gnutls_datum ciphertext;
int ret, dsize;
+ MPI params[2];
if ( gnutls_protocol_get_version(state) == GNUTLS_SSL3) {
/* SSL 3.0 */
@@ -95,9 +96,10 @@ int proc_rsa_client_kx(GNUTLS_STATE state, opaque * data, int data_size)
ciphertext.size = dsize;
}
+ params[0] = state->gnutls_key->A;
+ params[1] = state->gnutls_key->u;
ret =
- _gnutls_pkcs1_rsa_decrypt(&plaintext, ciphertext, state->gnutls_key->u,
- state->gnutls_key->A, 2); /* btype==2 */
+ _gnutls_pkcs1_rsa_decrypt(&plaintext, ciphertext, params, 2); /* btype==2 */
if (ret < 0) {
/* in case decryption fails then don't inform
@@ -146,7 +148,7 @@ int gen_rsa_client_kx(GNUTLS_STATE state, opaque ** data)
{
X509PKI_AUTH_INFO auth = state->gnutls_key->auth_info;
gnutls_datum sdata; /* data to send */
- MPI pkey, n;
+ MPI params[RSA_PARAMS];
int ret;
GNUTLS_Version ver;
@@ -164,11 +166,11 @@ int gen_rsa_client_kx(GNUTLS_STATE state, opaque ** data)
state->gnutls_key->key.data[0] = _gnutls_version_get_major(ver);
state->gnutls_key->key.data[1] = _gnutls_version_get_minor(ver);
+ params[0] = state->gnutls_key->a;
+ params[1] = state->gnutls_key->x;
if ((ret =
- _gnutls_pkcs1_rsa_encrypt(&sdata, state->gnutls_key->key, state->gnutls_key->x, state->gnutls_key->a, 2)) < 0) {
+ _gnutls_pkcs1_rsa_encrypt(&sdata, state->gnutls_key->key, params, 2)) < 0) {
gnutls_assert();
- _gnutls_mpi_release(&pkey);
- _gnutls_mpi_release(&n);
return ret;
}
_gnutls_mpi_release(&state->gnutls_key->a);
diff --git a/lib/auth_x509.c b/lib/auth_x509.c
index fafed43535..8b5dc4931f 100644
--- a/lib/auth_x509.c
+++ b/lib/auth_x509.c
@@ -89,17 +89,19 @@ int _gnutls_copy_x509_auth_info(X509PKI_AUTH_INFO info, gnutls_cert * cert,
}
/* This function reads the RSA parameters from the given private key
- * cert is not a certificate but a der structure containing the private
- * key(s).
- * Ok this is no longer the case. We now precompile the pkcs1 key
- * to the gnutls_private_key structure.
*/
static int _gnutls_get_private_rsa_params(GNUTLS_KEY key,
gnutls_private_key * pkey)
{
- key->u = gcry_mpi_copy(pkey->params[0]);
- key->A = gcry_mpi_copy(pkey->params[1]);
+ key->u = gcry_mpi_copy(pkey->params[2]);
+ if (key->u==NULL) return GNUTLS_E_MEMORY_ERROR;
+
+ key->A = gcry_mpi_copy(pkey->params[0]);
+ if (key->A==NULL) {
+ _gnutls_mpi_release( &key->u);
+ return GNUTLS_E_MEMORY_ERROR;
+ }
return 0;
}
diff --git a/lib/gnutls.asn b/lib/gnutls.asn
index da195bfec6..010b8117a3 100644
--- a/lib/gnutls.asn
+++ b/lib/gnutls.asn
@@ -68,6 +68,11 @@ DSAParameters ::= SEQUENCE {
g INTEGER
}
+DSASignatureValue ::= SEQUENCE {
+ r INTEGER,
+ s INTEGER
+}
+
DSAPrivateKey ::= SEQUENCE {
version INTEGER, -- should be zero
p INTEGER,
diff --git a/lib/gnutls_cert.c b/lib/gnutls_cert.c
index f4e4fef452..9f27f46448 100644
--- a/lib/gnutls_cert.c
+++ b/lib/gnutls_cert.c
@@ -71,29 +71,6 @@ PKAlgorithm _gnutls_map_pk_get_pk(KXAlgorithm kx_algorithm)
return ret;
}
-/* this function reads an integer
- * from asn1 structs. Combines the read and mpi_scan
- * steps.
- */
-static
-int _gnutls_x509_read_int( node_asn* node, char* value, char* tmpstr, int tmpstr_size, MPI* ret_mpi) {
-int len, result;
-
- len = tmpstr_size - 1;
- result = asn1_read_value(node, value, tmpstr, &len);
- if (result != ASN_OK) {
- gnutls_assert();
- return GNUTLS_E_ASN1_PARSING_ERROR;
- }
-
- if (_gnutls_mpi_scan( ret_mpi, tmpstr, &len) != 0) {
- gnutls_assert();
- return GNUTLS_E_MPI_SCAN_FAILED;
- }
-
- return 0;
-}
-
void gnutls_free_cert(gnutls_cert cert)
{
int n, i;
diff --git a/lib/gnutls_cert.h b/lib/gnutls_cert.h
index a94854caf0..f9c49c711d 100644
--- a/lib/gnutls_cert.h
+++ b/lib/gnutls_cert.h
@@ -10,7 +10,7 @@
/* parameters should not be larger than this limit */
#define MAX_PARAMETER_SIZE 1200
#define DSA_PARAMS 5
-#define RSA_PARAMS 2
+#define RSA_PARAMS 3
#if MAX_PARAMS_SIZE - RSA_PARAMS < 0
# error INCREASE RSA_PARAMS
@@ -28,7 +28,7 @@ typedef struct gnutls_cert {
* DSA: [0] is p
* [1] is q
* [2] is g
- * [3] is pub
+ * [3] is public key
*/
PKAlgorithm subject_pk_algorithm;
@@ -58,11 +58,14 @@ typedef struct {
* key algorithm
*/
/*
+ * RSA: [0] is modulus
+ * [1] is public exponent
+ * [2] is private exponent
* DSA: [0] is p
* [1] is q
* [2] is g
- * [3] is Y (public)
- * [4] is priv
+ * [3] is y (public key)
+ * [4] is x (private key)
*/
PKAlgorithm pk_algorithm;
diff --git a/lib/gnutls_gcry.c b/lib/gnutls_gcry.c
index 7ea3abcca0..31e8b3f6be 100644
--- a/lib/gnutls_gcry.c
+++ b/lib/gnutls_gcry.c
@@ -19,6 +19,8 @@
*/
#include <gnutls_int.h>
+#include <x509_asn1.h>
+#include <gnutls_errors.h>
/* Functions that refer to the libgcrypt library.
*/
@@ -42,3 +44,25 @@ int _gnutls_mpi_print( opaque *buffer, size_t *nbytes, const GCRY_MPI a ) {
return gcry_mpi_print( GCRYMPI_FMT_USG, buffer, nbytes, a);
}
+
+/* this function reads an integer
+ * from asn1 structs. Combines the read and mpi_scan
+ * steps.
+ */
+int _gnutls_x509_read_int( node_asn* node, char* value, char* tmpstr, int tmpstr_size, MPI* ret_mpi) {
+int len, result;
+
+ len = tmpstr_size - 1;
+ result = asn1_read_value(node, value, tmpstr, &len);
+ if (result != ASN_OK) {
+ gnutls_assert();
+ return GNUTLS_E_ASN1_PARSING_ERROR;
+ }
+
+ if (_gnutls_mpi_scan( ret_mpi, tmpstr, &len) != 0) {
+ gnutls_assert();
+ return GNUTLS_E_MPI_SCAN_FAILED;
+ }
+
+ return 0;
+}
diff --git a/lib/gnutls_gcry.h b/lib/gnutls_gcry.h
index df42a09d66..1423f4c04a 100644
--- a/lib/gnutls_gcry.h
+++ b/lib/gnutls_gcry.h
@@ -2,6 +2,7 @@
# define GNUTLS_GCRY_H
# include <gcrypt.h>
+# include <x509_asn1.h>
MPI _gnutls_mpi_new( int);
@@ -13,4 +14,6 @@ int _gnutls_mpi_scan( GCRY_MPI *ret_mpi, const opaque *buffer, size_t *nbytes );
int _gnutls_mpi_print( opaque *buffer, size_t *nbytes, const GCRY_MPI a );
+int _gnutls_x509_read_int( node_asn* node, char* value, char* tmpstr, int tmpstr_size, MPI* ret_mpi);
+
#endif
diff --git a/lib/gnutls_pk.c b/lib/gnutls_pk.c
index a7a27cb80f..cd999e9f9c 100644
--- a/lib/gnutls_pk.c
+++ b/lib/gnutls_pk.c
@@ -27,26 +27,27 @@
#include <gnutls_errors.h>
#include <gnutls_random.h>
#include <gnutls_datum.h>
+#include <gnutls_global.h>
+#include <x509_der.h>
#include "debug.h"
-static int _gnutls_pk_sign(int algo, MPI* data, MPI hash, MPI ** pkey);
-static int _gnutls_pk_verify(int algo, MPI hash, MPI** data, MPI **pkey);
+static int _gnutls_pk_sign(int algo, MPI* data, MPI hash, MPI * pkey);
+static int _gnutls_pk_verify(int algo, MPI hash, MPI* data, MPI *pkey);
/* Do PKCS-1 RSA encryption.
- * pkey is the public key and n the modulus.
+ * params is modulus, public exp.
*/
-
int _gnutls_pkcs1_rsa_encrypt(gnutls_datum * ciphertext,
- gnutls_datum plaintext, MPI pkey, MPI n,
+ gnutls_datum plaintext, MPI* params,
int btype)
{
int k, psize, i, ret;
MPI m, res;
opaque *edata, *ps;
- MPI *_pkey[2];
+ MPI tmp_params[RSA_PARAMS];
- k = gcry_mpi_get_nbits(n) / 8;
+ k = gcry_mpi_get_nbits(params[0]) / 8;
if (plaintext.size > k - 11) {
gnutls_assert();
@@ -70,6 +71,10 @@ int _gnutls_pkcs1_rsa_encrypt(gnutls_datum * ciphertext,
ps = &edata[2];
switch (btype) {
case 2:
+ /* using public key */
+ tmp_params[0] = params[0];
+ tmp_params[1] = params[1];
+
_gnutls_get_random(ps, psize, GNUTLS_WEAK_RANDOM);
for (i = 0; i < psize; i++) {
if (ps[i] == 0)
@@ -77,6 +82,10 @@ int _gnutls_pkcs1_rsa_encrypt(gnutls_datum * ciphertext,
}
break;
case 1:
+ /* using private key */
+ tmp_params[0] = params[0];
+ tmp_params[1] = params[2];
+
for (i = 0; i < psize; i++)
ps[i] = 0xff;
break;
@@ -102,9 +111,7 @@ int _gnutls_pkcs1_rsa_encrypt(gnutls_datum * ciphertext,
}
gnutls_free(edata);
- _pkey[0] = &n;
- _pkey[1] = &pkey;
- ret = _gnutls_pk_encrypt(GCRY_PK_RSA, &res, m, _pkey);
+ ret = _gnutls_pk_encrypt(GCRY_PK_RSA, &res, m, tmp_params);
_gnutls_mpi_release(&m);
if (ret < 0) {
@@ -130,19 +137,18 @@ int _gnutls_pkcs1_rsa_encrypt(gnutls_datum * ciphertext,
/* Do PKCS-1 RSA decryption.
- * pkey is the private key and n the modulus.
+ * params is modulus, public exp.
* Can decrypt block type 1 and type packets.
*/
int _gnutls_pkcs1_rsa_decrypt(gnutls_sdatum * plaintext,
- gnutls_datum ciphertext, MPI pkey, MPI n,
+ gnutls_datum ciphertext, MPI* params,
int btype)
{
int k, esize, i, ret;
MPI c, res;
opaque *edata;
- MPI *_pkey[2];
- k = gcry_mpi_get_nbits(n) / 8;
+ k = gcry_mpi_get_nbits(params[0]) / 8;
esize = ciphertext.size;
if (esize != k) {
@@ -155,11 +161,7 @@ int _gnutls_pkcs1_rsa_decrypt(gnutls_sdatum * plaintext,
return GNUTLS_E_MPI_SCAN_FAILED;
}
-
- _pkey[0] = &n;
- _pkey[1] = &pkey;
-
- ret = _gnutls_pk_encrypt(GCRY_PK_RSA, &res, c, _pkey);
+ ret = _gnutls_pk_encrypt(GCRY_PK_RSA, &res, c, params);
_gnutls_mpi_release(&c);
if (ret < 0) {
@@ -239,13 +241,13 @@ int _gnutls_pkcs1_rsa_decrypt(gnutls_sdatum * plaintext,
int _gnutls_rsa_verify( const gnutls_datum* vdata, const gnutls_datum *ciphertext,
- MPI pkey, MPI n, int btype) {
+ MPI *params, int btype) {
gnutls_datum plain;
int ret;
/* decrypt signature */
- if ( (ret=_gnutls_pkcs1_rsa_decrypt( &plain, *ciphertext, pkey, n, btype)) < 0) {
+ if ( (ret=_gnutls_pkcs1_rsa_decrypt( &plain, *ciphertext, params, btype)) < 0) {
gnutls_assert();
return ret;
}
@@ -267,28 +269,92 @@ int _gnutls_rsa_verify( const gnutls_datum* vdata, const gnutls_datum *ciphertex
return 0; /* ok */
}
+/* encodes the Dss-Sig-Value structure
+ */
+static int encode_ber_rs( gnutls_datum* sig_value, MPI r, MPI s) {
+node_asn* sig;
+int result;
+opaque str[MAX_PARAMETER_SIZE];
+int len = sizeof(str);
+int tot_len = 0;
+
+ if (asn1_create_structure( _gnutls_get_gnutls_asn(), "GNUTLS.DSASignatureValue",
+ &sig, "sig")!=ASN_OK) {
+ gnutls_assert();
+ return GNUTLS_E_ASN1_ERROR;
+ }
+
+ if ( _gnutls_mpi_print( str, &len, r) < 0) {
+ gnutls_assert();
+ asn1_delete_structure(sig);
+ return GNUTLS_E_MPI_PRINT_FAILED;
+ }
+ tot_len += len;
+
+ result = asn1_write_value( sig, "sig.r", str, len);
+
+ if (result != ASN_OK) {
+ gnutls_assert();
+ asn1_delete_structure(sig);
+ return GNUTLS_E_ASN1_PARSING_ERROR;
+ }
+
+ len = sizeof(str) - 1;
+ if ( _gnutls_mpi_print( str, &len, s) < 0) {
+ gnutls_assert();
+ asn1_delete_structure(sig);
+ return GNUTLS_E_MPI_PRINT_FAILED;
+ }
+ tot_len += len;
+
+ result = asn1_write_value( sig, "sig.s", str, len);
+
+ if (result != ASN_OK) {
+ gnutls_assert();
+ asn1_delete_structure(sig);
+ return GNUTLS_E_ASN1_PARSING_ERROR;
+ }
+
+ sig_value->size = tot_len + 100;
+ sig_value->data = gnutls_malloc( sig_value->size);
+ if (sig_value->data==NULL) {
+ gnutls_assert();
+ asn1_delete_structure(sig);
+ }
+
+ result = asn1_create_der( sig, "sig", sig_value->data, &sig_value->size);
+ if (result != ASN_OK) {
+ gnutls_assert();
+ asn1_delete_structure(sig);
+ return GNUTLS_E_ASN1_PARSING_ERROR;
+ }
+
+ asn1_delete_structure(sig);
+
+ return 0;
+}
+
-/* Do DSA signature calculation
+/* Do DSA signature calculation. params is p, q, g, y, x in that order.
*/
-int _gnutls_dsa_sign(gnutls_datum * signature, gnutls_datum plaintext,
- MPI p, MPI q, MPI g, MPI y)
+int _gnutls_dsa_sign(gnutls_datum * signature, const gnutls_datum *hash,
+ MPI * params)
{
- MPI res[2], mdata;
- int sig_size;
- MPI *_pkey[DSA_PARAMS];
- int k, ret, psize;
+ MPI rs[2], mdata;
+ int k, ret;
+
+ k = hash->size;
+ if (k!=20) { /* SHA only */
+ gnutls_assert();
+ return GNUTLS_E_PK_SIGNATURE_FAILED;
+ }
- k = plaintext.size;
- if (_gnutls_mpi_scan(&mdata, plaintext.data, &k) != 0) {
+ if (_gnutls_mpi_scan(&mdata, hash->data, &k) != 0) {
gnutls_assert();
return GNUTLS_E_MPI_SCAN_FAILED;
}
- _pkey[0] = &p;
- _pkey[1] = &q;
- _pkey[2] = &g;
- _pkey[3] = &y;
- ret = _gnutls_pk_sign(GCRY_PK_DSA, res, mdata, _pkey);
+ ret = _gnutls_pk_sign(GCRY_PK_DSA, rs, mdata, params);
/* res now holds r,s */
_gnutls_mpi_release(&mdata);
@@ -297,34 +363,80 @@ int _gnutls_dsa_sign(gnutls_datum * signature, gnutls_datum plaintext,
return ret;
}
-#error FIX r,s
+ if (encode_ber_rs( signature, rs[0], rs[1])!=0) {
+ gnutls_assert();
+ _gnutls_mpi_release(&rs[0]);
+ _gnutls_mpi_release(&rs[1]);
+ return GNUTLS_E_MEMORY_ERROR;
+ }
+
+ /* free r,s */
+ _gnutls_mpi_release(&rs[0]);
+ _gnutls_mpi_release(&rs[1]);
+
+ return 0;
+}
+
+/* decodes the Dss-Sig-Value structure
+ */
+static int decode_ber_rs( const gnutls_datum* sig_value, MPI* r, MPI* s) {
+node_asn* sig;
+int result;
+opaque str[MAX_PARAMETER_SIZE];
- _gnutls_mpi_print(NULL, &sig_size, res[0]);
- signature->data = gnutls_malloc(sig_size);
- if (signature->data == NULL) {
+ if (asn1_create_structure( _gnutls_get_gnutls_asn(), "GNUTLS.DSASignatureValue", &sig, "sig")!=ASN_OK) {
gnutls_assert();
- _gnutls_mpi_release(&res[0]);
- return GNUTLS_E_MEMORY_ERROR;
+ return GNUTLS_E_ASN1_ERROR;
+ }
+
+ result = asn1_get_der( sig, sig_value->data, sig_value->size);
+ if (result != ASN_OK) {
+ gnutls_assert();
+ asn1_delete_structure(sig);
+ return GNUTLS_E_ASN1_PARSING_ERROR;
+ }
+
+ result =
+ _gnutls_x509_read_int( sig, "sig.r", str, sizeof(str)-1, r);
+ if (result < 0) {
+ gnutls_assert();
+ asn1_delete_structure(sig);
+ return result;
}
- _gnutls_mpi_print(signature->data, &psize, res[0]);
- signature->size = psize;
- _gnutls_mpi_release(&res[0]);
+ result =
+ _gnutls_x509_read_int( sig, "sig.s", str, sizeof(str)-1, s);
+ if (result < 0) {
+ gnutls_assert();
+ _gnutls_mpi_release( s);
+ asn1_delete_structure(sig);
+ return result;
+ }
+ asn1_delete_structure(sig);
+
return 0;
}
-int _gnutls_dsa_verify( const gnutls_datum* vdata, const gnutls_datum *ciphertext,
- MPI p, MPI q, MPI g, MPI y) {
+/* params is p, q, g, y in that order
+ */
+int _gnutls_dsa_verify( const gnutls_datum* vdata, const gnutls_datum *sig_value,
+ MPI * params) {
MPI mdata;
int ret, k;
- MPI *_pkey[DSA_PARAMS];
- MPI *_data[2];
- MPI r, s;
-
- #error FIX r,s
+ MPI rs[2];
+
+ if (vdata->size != 20) { /* sha-1 only */
+ gnutls_assert();
+ return GNUTLS_E_INTERNAL;
+ }
+
+ if (decode_ber_rs( sig_value, &rs[0], &rs[1])!=0) {
+ gnutls_assert();
+ return GNUTLS_E_MPI_SCAN_FAILED;
+ }
k = vdata->size;
if (_gnutls_mpi_scan(&mdata, vdata->data, &k) != 0) {
@@ -333,14 +445,7 @@ int _gnutls_dsa_verify( const gnutls_datum* vdata, const gnutls_datum *ciphertex
}
/* decrypt signature */
- _pkey[0] = &p;
- _pkey[1] = &q;
- _pkey[2] = &g;
- _pkey[3] = &y;
-
- _data[0] = &r;
- _data[1] = &s;
- if ( (ret=_gnutls_pk_verify( GCRY_PK_DSA, mdata, _data, _pkey)) < 0) {
+ if ( (ret=_gnutls_pk_verify( GCRY_PK_DSA, mdata, rs, params)) < 0) {
_gnutls_mpi_release(&mdata);
gnutls_assert();
return ret;
@@ -358,7 +463,7 @@ int _gnutls_dsa_verify( const gnutls_datum* vdata, const gnutls_datum *ciphertex
* Emulate our old PK interface here - sometime in the future we might
* change the internal design to directly fit to libgcrypt.
*/
-int _gnutls_pk_encrypt(int algo, MPI * resarr, MPI data, MPI ** pkey)
+int _gnutls_pk_encrypt(int algo, MPI * resarr, MPI data, MPI * pkey)
{
GCRY_SEXP s_ciph, s_data, s_pkey;
int rc;
@@ -368,7 +473,7 @@ int _gnutls_pk_encrypt(int algo, MPI * resarr, MPI data, MPI ** pkey)
case GCRY_PK_RSA:
rc = gcry_sexp_build(&s_pkey, NULL,
"(public-key(rsa(n%m)(e%m)))",
- *pkey[0], *pkey[1]);
+ pkey[0], pkey[1]);
break;
default:
@@ -384,6 +489,7 @@ int _gnutls_pk_encrypt(int algo, MPI * resarr, MPI data, MPI ** pkey)
/* put the data into a simple list */
if (gcry_sexp_build(&s_data, NULL, "%m", data)) {
gnutls_assert();
+ gcry_sexp_release(s_pkey);
return GNUTLS_E_UNKNOWN_ERROR;
}
@@ -410,7 +516,7 @@ int _gnutls_pk_encrypt(int algo, MPI * resarr, MPI data, MPI ** pkey)
if (resarr[0] == NULL) {
gnutls_assert();
gcry_sexp_release(s_ciph);
- return GNUTLS_E_UNKNOWN_ERROR;
+ return GNUTLS_E_INTERNAL;
}
}
@@ -421,7 +527,7 @@ int _gnutls_pk_encrypt(int algo, MPI * resarr, MPI data, MPI ** pkey)
/* in case of DSA puts into data, r,s
*/
static
-int _gnutls_pk_sign(int algo, MPI* data, MPI hash, MPI ** pkey)
+int _gnutls_pk_sign(int algo, MPI* data, MPI hash, MPI * pkey)
{
GCRY_SEXP s_hash, s_key, s_sig;
int rc;
@@ -430,9 +536,9 @@ int _gnutls_pk_sign(int algo, MPI* data, MPI hash, MPI ** pkey)
switch (algo) {
case GCRY_PK_DSA:
rc = gcry_sexp_build(&s_key, NULL,
- "(public-key(rsa(p%m)(q%m)(g%m)(y%m)(x%m)))",
- *pkey[0], *pkey[1], *pkey[2],
- *pkey[3], *pkey[4]);
+ "(private-key(dsa(p%m)(q%m)(g%m)(y%m)(x%m)))",
+ pkey[0], pkey[1], pkey[2],
+ pkey[3], pkey[4]);
break;
default:
@@ -458,7 +564,7 @@ int _gnutls_pk_sign(int algo, MPI* data, MPI hash, MPI ** pkey)
if (rc != 0) {
gnutls_assert();
- return GNUTLS_E_PK_ENCRYPTION_FAILED;
+ return GNUTLS_E_PK_SIGNATURE_FAILED;
} else {
GCRY_SEXP list = gcry_sexp_find_token( s_sig, "r" , 0);
@@ -488,7 +594,7 @@ int _gnutls_pk_sign(int algo, MPI* data, MPI hash, MPI ** pkey)
}
-static int _gnutls_pk_verify(int algo, MPI hash, MPI** data, MPI **pkey)
+static int _gnutls_pk_verify(int algo, MPI hash, MPI* data, MPI *pkey)
{
GCRY_SEXP s_sig, s_hash, s_pkey;
int rc;
@@ -498,18 +604,16 @@ static int _gnutls_pk_verify(int algo, MPI hash, MPI** data, MPI **pkey)
case GCRY_PK_DSA:
rc = gcry_sexp_build(&s_pkey, NULL,
"(public-key(dsa(p%m)(q%m)(g%m)(y%m)))",
- pkey[0], pkey[1], pkey[2],
- pkey[3]);
+ pkey[0], pkey[1], pkey[2], pkey[3]);
break;
default:
gnutls_assert();
- return GNUTLS_E_UNKNOWN_KX_ALGORITHM;
+ return GNUTLS_E_INTERNAL;
}
if (rc != 0) {
gnutls_assert();
- gcry_sexp_release(s_pkey);
return GNUTLS_E_INTERNAL;
}
@@ -524,20 +628,20 @@ static int _gnutls_pk_verify(int algo, MPI hash, MPI** data, MPI **pkey)
case GCRY_PK_DSA:
rc = gcry_sexp_build(&s_sig, NULL,
"(sig-val(dsa(r%m)(s%m)))",
- *data[0], *data[1]);
+ data[0], data[1]);
break;
default:
gnutls_assert();
gcry_sexp_release(s_pkey);
- gcry_sexp_release(s_sig);
- return GNUTLS_E_UNKNOWN_KX_ALGORITHM;
+ gcry_sexp_release(s_hash);
+ return GNUTLS_E_INTERNAL;
}
if (rc != 0) {
gnutls_assert();
gcry_sexp_release(s_pkey);
- gcry_sexp_release(s_sig);
+ gcry_sexp_release(s_hash);
return GNUTLS_E_INTERNAL;
}
diff --git a/lib/gnutls_pk.h b/lib/gnutls_pk.h
index 95a54f4ee3..125e6dbb45 100644
--- a/lib/gnutls_pk.h
+++ b/lib/gnutls_pk.h
@@ -5,14 +5,16 @@ typedef enum PKAlgorithm { GNUTLS_PK_RSA = 1, GNUTLS_PK_DSA, /* sign only */
GNUTLS_PK_DH, GNUTLS_PK_UNKNOWN
} PKAlgorithm;
-int _gnutls_pk_encrypt(int algo, MPI * resarr, MPI data, MPI ** pkey);
+int _gnutls_pk_encrypt(int algo, MPI * resarr, MPI data, MPI * pkey);
int _gnutls_pkcs1_rsa_encrypt(gnutls_datum * ciphertext, gnutls_datum plaintext,
- MPI pkey, MPI n, int btype);
-int _gnutls_dsa_sign(gnutls_datum * signature, gnutls_datum plaintext,
- MPI p, MPI q, MPI g, MPI Y);
+ MPI * params, int btype);
+int _gnutls_dsa_sign(gnutls_datum * signature, const gnutls_datum *plaintext,
+ MPI *params);
int _gnutls_pkcs1_rsa_decrypt(gnutls_datum * plaintext, gnutls_datum ciphertext,
- MPI pkey, MPI n, int btype);
+ MPI * params, int btype);
int _gnutls_rsa_verify( const gnutls_datum* vdata, const gnutls_datum *ciphertext,
- MPI pkey, MPI n, int btype);
+ MPI* params, int btype);
+int _gnutls_dsa_verify( const gnutls_datum* vdata, const gnutls_datum *sig_value,
+ MPI * params);
#endif /* GNUTLS_PK_H */
diff --git a/lib/gnutls_privkey.c b/lib/gnutls_privkey.c
index ac749ed47b..360f4236ab 100644
--- a/lib/gnutls_privkey.c
+++ b/lib/gnutls_privkey.c
@@ -37,12 +37,11 @@
int _gnutls_PKCS1key2gnutlsKey(gnutls_private_key * pkey, gnutls_datum raw_key) {
int result;
opaque str[MAX_PARAMETER_SIZE];
- int len = sizeof(str);
- node_asn *pkcs_asn;
+ node_asn *pkey_asn;
pkey->pk_algorithm = GNUTLS_PK_RSA;
- if (asn1_create_structure( _gnutls_get_gnutls_asn(), "GNUTLS.RSAPrivateKey", &pkcs_asn, "rsakey")!=ASN_OK) {
+ if (asn1_create_structure( _gnutls_get_gnutls_asn(), "GNUTLS.RSAPrivateKey", &pkey_asn, "rsakey")!=ASN_OK) {
gnutls_assert();
return GNUTLS_E_ASN1_ERROR;
}
@@ -53,51 +52,43 @@ int _gnutls_PKCS1key2gnutlsKey(gnutls_private_key * pkey, gnutls_datum raw_key)
return GNUTLS_E_INTERNAL;
}
- result = asn1_get_der( pkcs_asn, raw_key.data, raw_key.size);
+ result = asn1_get_der( pkey_asn, raw_key.data, raw_key.size);
if (result != ASN_OK) {
gnutls_assert();
return GNUTLS_E_ASN1_PARSING_ERROR;
}
- len = sizeof(str) - 1;
- result =
- asn1_read_value( pkcs_asn, "rsakey.privateExponent", str, &len);
- if (result != ASN_OK) {
- gnutls_assert();
- asn1_delete_structure(pkcs_asn);
- return GNUTLS_E_ASN1_PARSING_ERROR;
- }
- if (_gnutls_mpi_scan( &pkey->params[0], /* u */
- str, &len) != 0 || pkey->params[0]==NULL) {
+ if ( (result=_gnutls_x509_read_int( pkey_asn, "rsakey.modulus",
+ str, sizeof(str)-1, &pkey->params[0])) < 0) {
gnutls_assert();
- asn1_delete_structure(pkcs_asn);
- return GNUTLS_E_MPI_SCAN_FAILED;
+ asn1_delete_structure(pkey_asn);
+ return result;
}
-
- len = sizeof(str) - 1;
- result =
- asn1_read_value( pkcs_asn, "rsakey.modulus", str, &len);
- if (result != ASN_OK) {
+ if ( (result=_gnutls_x509_read_int( pkey_asn, "rsakey.publicExponent",
+ str, sizeof(str)-1, &pkey->params[1])) < 0) {
gnutls_assert();
- asn1_delete_structure(pkcs_asn);
+ asn1_delete_structure(pkey_asn);
_gnutls_mpi_release( &pkey->params[0]);
- return GNUTLS_E_ASN1_PARSING_ERROR;
+ return result;
}
- if (_gnutls_mpi_scan( &pkey->params[1], /* A */
- str, &len) != 0 || pkey->params[1] == NULL) {
+ if ( (result=_gnutls_x509_read_int( pkey_asn, "rsakey.privateExponent",
+ str, sizeof(str)-1, &pkey->params[2])) < 0) {
gnutls_assert();
- asn1_delete_structure(pkcs_asn);
_gnutls_mpi_release( &pkey->params[0]);
- return GNUTLS_E_MPI_SCAN_FAILED;
+ _gnutls_mpi_release( &pkey->params[1]);
+ asn1_delete_structure(pkey_asn);
+ return result;
}
- asn1_delete_structure(pkcs_asn);
+
+ asn1_delete_structure(pkey_asn);
if (gnutls_set_datum( &pkey->raw, raw_key.data, raw_key.size) < 0) {
_gnutls_mpi_release(&pkey->params[0]);
_gnutls_mpi_release(&pkey->params[1]);
+ _gnutls_mpi_release(&pkey->params[2]);
gnutls_assert();
return GNUTLS_E_MEMORY_ERROR;
}
@@ -110,12 +101,11 @@ int _gnutls_PKCS1key2gnutlsKey(gnutls_private_key * pkey, gnutls_datum raw_key)
int _gnutls_DSAkey2gnutlsKey(gnutls_private_key * pkey, gnutls_datum raw_key) {
int result;
opaque str[MAX_PARAMETER_SIZE];
- int len = sizeof(str);
- node_asn *pkix_asn;
+ node_asn *dsa_asn;
pkey->pk_algorithm = GNUTLS_PK_DSA;
- if (asn1_create_structure( _gnutls_get_gnutls_asn(), "GNUTLS.DSAPrivateKey", &pkix_asn, "dsakey")!=ASN_OK) {
+ if (asn1_create_structure( _gnutls_get_gnutls_asn(), "GNUTLS.DSAPrivateKey", &dsa_asn, "dsakey")!=ASN_OK) {
gnutls_assert();
return GNUTLS_E_ASN1_ERROR;
}
@@ -126,111 +116,58 @@ int _gnutls_DSAkey2gnutlsKey(gnutls_private_key * pkey, gnutls_datum raw_key) {
return GNUTLS_E_INTERNAL;
}
- result = asn1_get_der( pkix_asn, raw_key.data, raw_key.size);
+ result = asn1_get_der( dsa_asn, raw_key.data, raw_key.size);
if (result != ASN_OK) {
gnutls_assert();
return GNUTLS_E_ASN1_PARSING_ERROR;
}
- len = sizeof(str) - 1;
- result =
- asn1_read_value( pkix_asn, "dsakey.p", str, &len);
- if (result != ASN_OK) {
+ if ( (result=_gnutls_x509_read_int( dsa_asn, "dsakey.p",
+ str, sizeof(str)-1, &pkey->params[0])) < 0) {
gnutls_assert();
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_ASN1_PARSING_ERROR;
- }
-
- if (_gnutls_mpi_scan( &pkey->params[0], /* p */
- str, &len) != 0) {
- gnutls_assert();
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_MPI_SCAN_FAILED;
- }
-
- len = sizeof(str) - 1;
- result =
- asn1_read_value( pkix_asn, "dsakey.q", str, &len);
- if (result != ASN_OK) {
- gnutls_assert();
- _gnutls_mpi_release(&pkey->params[0]);
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_ASN1_PARSING_ERROR;
- }
-
- if (_gnutls_mpi_scan( &pkey->params[1], /* q */ str, &len) != 0) {
- gnutls_assert();
- _gnutls_mpi_release(&pkey->params[0]);
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_MPI_SCAN_FAILED;
- }
-
- len = sizeof(str) - 1;
- result =
- asn1_read_value( pkix_asn, "dsakey.g", str, &len);
- if (result != ASN_OK) {
- gnutls_assert();
- _gnutls_mpi_release(&pkey->params[0]);
- _gnutls_mpi_release(&pkey->params[1]);
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_ASN1_PARSING_ERROR;
+ asn1_delete_structure(dsa_asn);
+ return result;
}
- if (_gnutls_mpi_scan( &pkey->params[2], /* g */ str, &len) != 0) {
+ if ( (result=_gnutls_x509_read_int( dsa_asn, "dsakey.q",
+ str, sizeof(str)-1, &pkey->params[1])) < 0) {
gnutls_assert();
- _gnutls_mpi_release(&pkey->params[0]);
- _gnutls_mpi_release(&pkey->params[1]);
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_MPI_SCAN_FAILED;
+ asn1_delete_structure(dsa_asn);
+ _gnutls_mpi_release( &pkey->params[0]);
+ return result;
}
- len = sizeof(str) - 1;
- result =
- asn1_read_value( pkix_asn, "dsakey.Y", str, &len);
- if (result != ASN_OK) {
+ if ( (result=_gnutls_x509_read_int( dsa_asn, "dsakey.g",
+ str, sizeof(str)-1, &pkey->params[2])) < 0) {
gnutls_assert();
- _gnutls_mpi_release(&pkey->params[0]);
- _gnutls_mpi_release(&pkey->params[1]);
- _gnutls_mpi_release(&pkey->params[2]);
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_ASN1_PARSING_ERROR;
+ asn1_delete_structure(dsa_asn);
+ _gnutls_mpi_release( &pkey->params[0]);
+ _gnutls_mpi_release( &pkey->params[1]);
+ return result;
}
- if (_gnutls_mpi_scan( &pkey->params[3], /* priv key */
- str, &len) != 0) {
+ if ( (result=_gnutls_x509_read_int( dsa_asn, "dsakey.Y",
+ str, sizeof(str)-1, &pkey->params[3])) < 0) {
gnutls_assert();
- _gnutls_mpi_release(&pkey->params[0]);
- _gnutls_mpi_release(&pkey->params[1]);
- _gnutls_mpi_release(&pkey->params[2]);
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_MPI_SCAN_FAILED;
- }
-
- len = sizeof(str) - 1;
- result =
- asn1_read_value( pkix_asn, "dsakey.priv", str, &len);
- if (result != ASN_OK) {
- gnutls_assert();
- _gnutls_mpi_release(&pkey->params[0]);
- _gnutls_mpi_release(&pkey->params[1]);
- _gnutls_mpi_release(&pkey->params[2]);
- _gnutls_mpi_release(&pkey->params[3]);
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_ASN1_PARSING_ERROR;
+ asn1_delete_structure(dsa_asn);
+ _gnutls_mpi_release( &pkey->params[0]);
+ _gnutls_mpi_release( &pkey->params[1]);
+ _gnutls_mpi_release( &pkey->params[2]);
+ return result;
}
- if (_gnutls_mpi_scan( &pkey->params[4], /* priv key */
- str, &len) != 0) {
+ if ( (result=_gnutls_x509_read_int( dsa_asn, "dsakey.priv",
+ str, sizeof(str)-1, &pkey->params[4])) < 0) {
gnutls_assert();
- _gnutls_mpi_release(&pkey->params[0]);
- _gnutls_mpi_release(&pkey->params[1]);
- _gnutls_mpi_release(&pkey->params[2]);
- _gnutls_mpi_release(&pkey->params[3]);
- asn1_delete_structure(pkix_asn);
- return GNUTLS_E_MPI_SCAN_FAILED;
+ asn1_delete_structure(dsa_asn);
+ _gnutls_mpi_release( &pkey->params[0]);
+ _gnutls_mpi_release( &pkey->params[1]);
+ _gnutls_mpi_release( &pkey->params[2]);
+ _gnutls_mpi_release( &pkey->params[3]);
+ return result;
}
- asn1_delete_structure(pkix_asn);
+ asn1_delete_structure(dsa_asn);
if (gnutls_set_datum( &pkey->raw, raw_key.data, raw_key.size) < 0) {
_gnutls_mpi_release(&pkey->params[0]);
diff --git a/lib/gnutls_sig.c b/lib/gnutls_sig.c
index a2502705f6..8b6009a634 100644
--- a/lib/gnutls_sig.c
+++ b/lib/gnutls_sig.c
@@ -35,6 +35,8 @@
#include <gnutls_sig.h>
+int _gnutls_generate_sig( gnutls_cert* cert, gnutls_private_key *pkey, const gnutls_datum* hash_concat, gnutls_datum *signature);
+
/* Generates a signature of all the previous sent packets in the
* handshake procedure.
@@ -46,25 +48,36 @@ opaque concat[36];
GNUTLS_MAC_HANDLE td_md5;
GNUTLS_MAC_HANDLE td_sha;
- td_md5 = gnutls_hash_copy( state->gnutls_internals.handshake_mac_handle_md5);
- if (td_md5 == NULL) {
- gnutls_assert();
- return GNUTLS_E_HASH_FAILED;
- }
td_sha = gnutls_hash_copy( state->gnutls_internals.handshake_mac_handle_sha);
if (td_sha == NULL) {
gnutls_assert();
- gnutls_hash_deinit( td_md5, NULL);
return GNUTLS_E_HASH_FAILED;
}
- gnutls_hash_deinit(td_md5, concat);
gnutls_hash_deinit(td_sha, &concat[16]);
- dconcat.data = concat;
- dconcat.size = 36;
+ switch (cert->subject_pk_algorithm) {
+ case GNUTLS_PK_RSA:
+ td_md5 = gnutls_hash_copy( state->gnutls_internals.handshake_mac_handle_md5);
+ if (td_md5 == NULL) {
+ gnutls_assert();
+ return GNUTLS_E_HASH_FAILED;
+ }
+ gnutls_hash_deinit(td_md5, concat);
+ dconcat.data = concat;
+ dconcat.size = 36;
+ break;
+ case GNUTLS_PK_DSA:
+ dconcat.data = &concat[16];
+ dconcat.size = 20;
+ break;
+
+ default:
+ gnutls_assert();
+ return GNUTLS_E_INTERNAL;
+ }
ret = _gnutls_generate_sig( cert, pkey, &dconcat, signature);
if (ret < 0)
gnutls_assert();
@@ -84,33 +97,46 @@ GNUTLS_MAC_HANDLE td_md5;
GNUTLS_MAC_HANDLE td_sha;
opaque concat[36];
- td_md5 = gnutls_hash_init( GNUTLS_MAC_MD5);
- if (td_md5 == NULL) {
- gnutls_assert();
- return GNUTLS_E_HASH_FAILED;
- }
td_sha = gnutls_hash_init( GNUTLS_MAC_SHA);
if (td_sha == NULL) {
gnutls_assert();
- gnutls_hash_deinit( td_md5, NULL);
return GNUTLS_E_HASH_FAILED;
}
- gnutls_hash( td_md5, state->security_parameters.client_random, TLS_RANDOM_SIZE);
- gnutls_hash( td_md5, state->security_parameters.server_random, TLS_RANDOM_SIZE);
- gnutls_hash( td_md5, params->data, params->size);
-
gnutls_hash( td_sha, state->security_parameters.client_random, TLS_RANDOM_SIZE);
gnutls_hash( td_sha, state->security_parameters.server_random, TLS_RANDOM_SIZE);
gnutls_hash( td_sha, params->data, params->size);
- gnutls_hash_deinit(td_md5, concat);
gnutls_hash_deinit(td_sha, &concat[16]);
- dconcat.data = concat;
- dconcat.size = 36;
+ switch (cert->subject_pk_algorithm) {
+ case GNUTLS_PK_RSA:
+ td_md5 = gnutls_hash_init( GNUTLS_MAC_MD5);
+ if (td_md5 == NULL) {
+ gnutls_assert();
+ return GNUTLS_E_HASH_FAILED;
+ }
+
+ gnutls_hash( td_md5, state->security_parameters.client_random, TLS_RANDOM_SIZE);
+ gnutls_hash( td_md5, state->security_parameters.server_random, TLS_RANDOM_SIZE);
+ gnutls_hash( td_md5, params->data, params->size);
+
+ gnutls_hash_deinit(td_md5, concat);
+
+ dconcat.data = concat;
+ dconcat.size = 36;
+ break;
+ case GNUTLS_PK_DSA:
+ dconcat.data = &concat[16];
+ dconcat.size = 20;
+ break;
+
+ default:
+ gnutls_assert();
+ return GNUTLS_E_INTERNAL;
+ }
ret = _gnutls_generate_sig( cert, pkey, &dconcat, signature);
if (ret < 0)
gnutls_assert();
@@ -139,27 +165,23 @@ gnutls_datum tmpdata;
return GNUTLS_E_X509_KEY_USAGE_VIOLATION;
}
+ tmpdata.data = hash_concat->data;
+ tmpdata.size = hash_concat->size;
+
switch(pkey->pk_algorithm) {
case GNUTLS_PK_RSA:
- tmpdata.data = hash_concat->data;
- tmpdata.size = hash_concat->size; /* md5 + sha */
/* encrypt */
- if ((ret=_gnutls_pkcs1_rsa_encrypt( signature, tmpdata, pkey->params[0], pkey->params[1], 1)) < 0) {
+ if ((ret=_gnutls_pkcs1_rsa_encrypt( signature, tmpdata, pkey->params, 1)) < 0) {
gnutls_assert();
return ret;
}
break;
case GNUTLS_PK_DSA:
- /* Ok this is silly. We have calculated
- * md5 also!
- */
- tmpdata.data = &hash_concat->data[16];
- tmpdata.size = 20; /* sha */
/* sign */
- if ((ret=_gnutls_dsa_sign( signature, tmpdata, pkey->params[0], pkey->params[1], pkey->params[2], pkey->params[3])) < 0) {
+ if ((ret=_gnutls_dsa_sign( signature, &tmpdata, pkey->params)) < 0) {
gnutls_assert();
return ret;
}
@@ -204,7 +226,7 @@ int _gnutls_pkcs1_rsa_verify_sig( gnutls_cert *cert, const gnutls_datum *hash_co
vdata.size = hash_concat->size;
/* verify signature */
- if ( (ret=_gnutls_rsa_verify( &vdata, signature, cert->params[1], cert->params[0], 1)) < 0) {
+ if ( (ret=_gnutls_rsa_verify( &vdata, signature, cert->params, 1)) < 0) {
gnutls_assert();
return ret;
}
@@ -216,13 +238,13 @@ int _gnutls_pkcs1_rsa_verify_sig( gnutls_cert *cert, const gnutls_datum *hash_co
vdata.size = 20; /* sha1 */
/* decrypt signature */
- if ( (ret=_gnutls_dsa_verify( &vdata, *signature, cert->params[0],
- cert->params[1], cert->params[2], cert->params[3])) < 0) {
+ if ( (ret=_gnutls_dsa_verify( &vdata, signature, cert->params)) < 0) {
gnutls_assert();
return ret;
}
break;
+
default:
gnutls_assert();
return GNUTLS_E_UNIMPLEMENTED_FEATURE;
diff --git a/lib/x509_sig_check.c b/lib/x509_sig_check.c
index 1556ed1114..c1afde5b7c 100644
--- a/lib/x509_sig_check.c
+++ b/lib/x509_sig_check.c
@@ -33,6 +33,8 @@
#include <debug.h>
#include <gnutls_str.h>
+/* returns DER tbsCertificate
+ */
static gnutls_datum _gnutls_get_tbs( gnutls_cert* cert) {
node_asn *c2;
gnutls_datum ret = {NULL, 0};
@@ -137,8 +139,8 @@ int len;
* m is modulus
* e is public key
*/
-int
-_pkcs1_rsa_verify_sig( gnutls_datum* signature, gnutls_datum* text, MPI e, MPI m)
+static int
+_pkcs1_rsa_verify_sig( gnutls_datum* signature, gnutls_datum* text, MPI *params)
{
MACAlgorithm hash;
int ret;
@@ -148,7 +150,7 @@ _pkcs1_rsa_verify_sig( gnutls_datum* signature, gnutls_datum* text, MPI e, MPI m
gnutls_datum decrypted;
- if ( (ret=_gnutls_pkcs1_rsa_decrypt( &decrypted, *signature, e, m, 1)) < 0) {
+ if ( (ret=_gnutls_pkcs1_rsa_decrypt( &decrypted, *signature, params, 1)) < 0) {
gnutls_assert();
return ret;
}
@@ -182,136 +184,53 @@ _pkcs1_rsa_verify_sig( gnutls_datum* signature, gnutls_datum* text, MPI e, MPI m
return 0;
}
-#ifdef DEBUG
-/* This is for CA DSS params - can wait */
-# warning CHECK HERE FOR DSS
-#endif
-
/* verifies if the certificate is properly signed.
*/
CertificateStatus gnutls_x509_verify_signature(gnutls_cert* cert, gnutls_cert* issuer) {
gnutls_datum signature;
gnutls_datum tbs;
- if ( issuer->subject_pk_algorithm == GNUTLS_PK_RSA) {
- signature.data = cert->signature;
- signature.size = cert->signature_size;
-
- tbs = _gnutls_get_tbs( cert);
- if (tbs.data==NULL) {
- gnutls_assert();
- return GNUTLS_CERT_INVALID;
- }
+ signature.data = cert->signature;
+ signature.size = cert->signature_size;
- if (_pkcs1_rsa_verify_sig( &signature, &tbs, issuer->params[1], issuer->params[0])!=0) {
- gnutls_assert();
- gnutls_free_datum( &tbs);
- return GNUTLS_CERT_NOT_TRUSTED;
- }
- gnutls_free_datum(&tbs);
- return GNUTLS_CERT_TRUSTED;
+ tbs = _gnutls_get_tbs( cert);
+ if (tbs.data==NULL) {
+ gnutls_assert();
+ return GNUTLS_CERT_INVALID;
}
- _gnutls_log( "X509_sig: PK: %d\n", issuer->subject_pk_algorithm);
+ switch( issuer->subject_pk_algorithm) {
+ case GNUTLS_PK_RSA:
+
+ if (_pkcs1_rsa_verify_sig( &signature, &tbs, issuer->params)!=0) {
+ gnutls_assert();
+ gnutls_free_datum( &tbs);
+ return GNUTLS_CERT_NOT_TRUSTED;
+ }
- gnutls_assert();
- return GNUTLS_CERT_INVALID;
-}
+ gnutls_free_datum(&tbs);
+ return GNUTLS_CERT_TRUSTED;
+ break;
+ case GNUTLS_PK_DSA:
+ if (_gnutls_dsa_verify( &tbs, &signature, issuer->params)!=0) {
+ gnutls_assert();
+ gnutls_free_datum( &tbs);
+ return GNUTLS_CERT_NOT_TRUSTED;
+ }
-#if 0
-/* Signature generation - not tested */
-static int _gnutls_digestinfo_encode( opaque* data, int data_size, char* OID, gnutls_datum* der) {
-node_asn *di;
-int result;
+ gnutls_free_datum(&tbs);
+ return GNUTLS_CERT_TRUSTED;
+ break;
- if (asn1_create_structure( _gnutls_get_gnutls_asn(),
- "GNUTLS.DigestInfo", &di, "di") != ASN_OK) {
- gnutls_assert();
- return GNUTLS_E_ASN1_ERROR;
- }
-
- result = asn1_write_value( di, "di.digestAlgorithm.algorithm", OID, 1);
- if (result!=ASN_OK) {
- gnutls_assert();
- asn1_delete_structure( di);
- return GNUTLS_E_ASN1_ERROR;
- }
-
- result = asn1_write_value( di, "di.digestAlgorithm.parameters", NULL, 0);
- if (result!=ASN_OK) {
- gnutls_assert();
- asn1_delete_structure( di);
- return GNUTLS_E_ASN1_ERROR;
}
- result = asn1_write_value( di, "di.digest", data, data_size);
- if (result!=ASN_OK) {
- gnutls_assert();
- asn1_delete_structure( di);
- return GNUTLS_E_ASN1_ERROR;
- }
+ gnutls_free_datum(&tbs);
- der->size = data_size + 200;
- der->data = gnutls_malloc( der->size);
- if (der->data==NULL) {
- gnutls_assert();
- asn1_delete_structure( di);
- return GNUTLS_E_MEMORY_ERROR;
- }
-
- result = asn1_create_der( di, "di", der->data, &der->size);
- if (result!=ASN_OK) {
- gnutls_assert();
- asn1_delete_structure( di);
- gnutls_free_datum( der);
- return GNUTLS_E_ASN1_ERROR;
- }
- asn1_delete_structure( di);
+ _gnutls_log( "X509_sig: PK: %d\n", issuer->subject_pk_algorithm);
- return 0;
+ gnutls_assert();
+ return GNUTLS_CERT_INVALID;
}
-int _pkcs1_rsa_generate_sig( MACAlgorithm hash_algo, gnutls_private_key *pkey, const gnutls_datum *data, gnutls_datum *signature) {
- int ret;
- GNUTLS_HASH_HANDLE hd;
- opaque digest[MAX_HASH_SIZE];
- char OID[64];
- int digest_size = gnutls_hash_get_algo_len( hash_algo);
- gnutls_datum der;
-
- if (hash_algo==GNUTLS_MAC_MD5)
- _gnutls_str_cpy(OID, sizeof(OID), "1 2 840 113549 2 5");
- else if (hash_algo==GNUTLS_MAC_SHA)
- _gnutls_str_cpy(OID, sizeof(OID), "1 3 14 3 2 26");
- else {
- gnutls_assert();
- return GNUTLS_E_UNKNOWN_MAC_ALGORITHM;
- }
-
- /* hash data */
- hd = gnutls_hash_init( hash_algo);
- if (hd==NULL) {
- gnutls_assert();
- return GNUTLS_E_MEMORY_ERROR;
- }
- gnutls_hash( hd, data->data, data->size);
- gnutls_hash_deinit( hd, digest);
-
- /* encode digest to DigestInfo (der) */
- if ( (ret=_gnutls_digestinfo_encode( digest, digest_size, OID, &der)) < 0) {
- gnutls_assert();
- return ret;
- }
-
- der.data = digest;
- der.size = digest_size;
- /* encrypt der */
- if ( (ret=_gnutls_pkcs1_rsa_encrypt( signature, der, pkey->params[0], pkey->params[1], 1)) < 0) {
- gnutls_assert();
- return ret;
- }
- return 0;
-}
-#endif
diff --git a/src/cli.c b/src/cli.c
index b3a43c24f2..6f718de062 100644
--- a/src/cli.c
+++ b/src/cli.c
@@ -50,8 +50,11 @@
#define MAX(X,Y) (X >= Y ? X : Y);
#define CAFILE "x509/ca.pem"
#define CRLFILE NULL
-#define CLIKEYFILE "x509/clikey.pem"
-#define CLICERTFILE "x509/clicert.pem"
+#define CLIKEYFILE1 "x509/clikey-dsa.pem"
+#define CLICERTFILE1 "x509/clicert-dsa.pem"
+
+#define CLIKEYFILE2 "x509/clikey.pem"
+#define CLICERTFILE2 "x509/clicert.pem"
static int cert_callback( GNUTLS_STATE state, const gnutls_datum *client_certs, int ncerts, const gnutls_datum* req_ca_cert, int nreqs) {
@@ -130,12 +133,13 @@ int main(int argc, char** argv)
}
/* X509 stuff */
- if (gnutls_x509pki_allocate_client_sc( &xcred, 1) < 0) { /* space for 1 certificate */
+ if (gnutls_x509pki_allocate_client_sc( &xcred, 2) < 0) { /* space for 2 certificates */
fprintf(stderr, "memory error\n");
exit(1);
}
gnutls_x509pki_set_client_trust_file( xcred, CAFILE, CRLFILE);
- gnutls_x509pki_set_client_key_file( xcred, CLICERTFILE, CLIKEYFILE);
+ gnutls_x509pki_set_client_key_file( xcred, CLICERTFILE1, CLIKEYFILE1);
+ gnutls_x509pki_set_client_key_file( xcred, CLICERTFILE2, CLIKEYFILE2);
gnutls_x509pki_set_client_cert_callback( xcred, cert_callback);
/* SRP stuff */