summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNikos Mavrogiannopoulos <nmav@gnutls.org>2012-10-11 22:37:25 +0200
committerNikos Mavrogiannopoulos <nmav@gnutls.org>2012-10-11 22:38:48 +0200
commitbec28fe3c59134dd5c2b40f43c10733c312317bc (patch)
treed50637482a26bca06df5a87dcf59463fe99ac450
parentaf6861a057a299493e0ce56ffc084945c3926ce1 (diff)
downloadgnutls-bec28fe3c59134dd5c2b40f43c10733c312317bc.tar.gz
Added (back) RFC5081 support in client mode.
-rw-r--r--NEWS5
-rw-r--r--lib/auth/cert.c23
-rw-r--r--lib/gnutls_pcert.c11
-rw-r--r--lib/openpgp/pgp.c17
-rw-r--r--lib/openpgp/privkey.c20
5 files changed, 62 insertions, 14 deletions
diff --git a/NEWS b/NEWS
index efdd95c72f..294ca80e1f 100644
--- a/NEWS
+++ b/NEWS
@@ -10,8 +10,9 @@ Reported by danblack at http://savannah.gnu.org/support/?108146
** libgnutls: Added gnutls_ocsp_resp_check_crt() to check whether the OCSP
response corresponds to the given certificate.
-** libgnutls: Compatibility code with RFC5081 was removed. The OpenPGP
-code now is RFC6091 compliant only.
+** libgnutls: Several updates in the OpenPGP code. The generating code
+is fully RFC6091 compliant and RFC5081 support is only supported in client
+mode.
** API and ABI modifications:
gnutls_ocsp_resp_check_crt: Added
diff --git a/lib/auth/cert.c b/lib/auth/cert.c
index 9286fbb7d8..c5dd933fd7 100644
--- a/lib/auth/cert.c
+++ b/lib/auth/cert.c
@@ -1180,6 +1180,7 @@ _gnutls_proc_openpgp_server_crt (gnutls_session_t session,
int key_type;
gnutls_pcert_st *peer_certificate_list = NULL;
gnutls_datum_t tmp, akey = { NULL, 0 };
+ unsigned int compat = 0;
uint8_t subkey_id[GNUTLS_OPENPGP_KEYID_SIZE];
cred = (gnutls_certificate_credentials_t)
@@ -1294,10 +1295,18 @@ _gnutls_proc_openpgp_server_crt (gnutls_session_t session,
len = _gnutls_read_uint24 (p);
p += 3;
- if (len != 0) /* PGP_EMPTY_KEY */
- return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET_LENGTH);
- else
+ if (len == 0) /* PGP_EMPTY_KEY */
return GNUTLS_E_NO_CERTIFICATE_FOUND;
+ /* Uncomment to remove compatibility with RFC5081.
+ else
+ return gnutls_assert_val(GNUTLS_E_UNEXPECTED_PACKET_LENGTH);*/
+
+ DECR_LEN (dsize, len);
+
+ tmp.size = len;
+ tmp.data = p;
+
+ compat = 1;
}
else
{
@@ -1320,13 +1329,19 @@ _gnutls_proc_openpgp_server_crt (gnutls_session_t session,
gnutls_pcert_import_openpgp_raw (&peer_certificate_list[0],
&tmp,
GNUTLS_OPENPGP_FMT_RAW,
- subkey_id,
+ (compat==0)?subkey_id:NULL,
0);
if (ret < 0)
{
gnutls_assert ();
goto cleanup;
}
+
+ if (compat != 0)
+ {
+ size_t t = sizeof(subkey_id);
+ gnutls_pubkey_get_openpgp_key_id(peer_certificate_list[0].pubkey, 0, subkey_id, &t, NULL);
+ }
ret =
_gnutls_copy_certificate_auth_info (info,
diff --git a/lib/gnutls_pcert.c b/lib/gnutls_pcert.c
index 3a6b6fee5c..3341f88c5b 100644
--- a/lib/gnutls_pcert.c
+++ b/lib/gnutls_pcert.c
@@ -336,14 +336,11 @@ gnutls_openpgp_crt_t crt;
goto cleanup;
}
- if (keyid != NULL)
+ ret = gnutls_openpgp_crt_set_preferred_key_id(crt, keyid);
+ if (ret < 0)
{
- ret = gnutls_openpgp_crt_set_preferred_key_id(crt, keyid);
- if (ret < 0)
- {
- ret = gnutls_assert_val(ret);
- goto cleanup;
- }
+ ret = gnutls_assert_val(ret);
+ goto cleanup;
}
ret = gnutls_pcert_import_openpgp(pcert, crt, flags);
diff --git a/lib/openpgp/pgp.c b/lib/openpgp/pgp.c
index 87587e377b..b6946c5efa 100644
--- a/lib/openpgp/pgp.c
+++ b/lib/openpgp/pgp.c
@@ -1588,6 +1588,9 @@ gnutls_openpgp_crt_get_preferred_key_id (gnutls_openpgp_crt_t key,
* This allows setting a preferred key id for the given certificate.
* This key will be used by functions that involve key handling.
*
+ * If the provided @keyid is %NULL then the master key is
+ * set as preferred.
+ *
* Returns: On success, %GNUTLS_E_SUCCESS (0) is returned,
* otherwise a negative error code is returned.
**/
@@ -1602,6 +1605,20 @@ gnutls_openpgp_crt_set_preferred_key_id (gnutls_openpgp_crt_t key,
gnutls_assert ();
return GNUTLS_E_INVALID_REQUEST;
}
+
+ if (keyid == NULL) /* set the master as preferred */
+ {
+ uint8_t tmp[GNUTLS_OPENPGP_KEYID_SIZE];
+
+ ret = gnutls_openpgp_crt_get_key_id (key, tmp);
+ if (ret < 0)
+ return gnutls_assert_val(ret);
+
+ key->preferred_set = 1;
+ memcpy (key->preferred_keyid, tmp, GNUTLS_OPENPGP_KEYID_SIZE);
+
+ return 0;
+ }
/* check if the id is valid */
ret = gnutls_openpgp_crt_get_subkey_idx (key, keyid);
diff --git a/lib/openpgp/privkey.c b/lib/openpgp/privkey.c
index 6eb4df9c81..6ee2584b6b 100644
--- a/lib/openpgp/privkey.c
+++ b/lib/openpgp/privkey.c
@@ -1238,7 +1238,11 @@ gnutls_openpgp_privkey_get_preferred_key_id (gnutls_openpgp_privkey_t key,
* This allows setting a preferred key id for the given certificate.
* This key will be used by functions that involve key handling.
*
- * Returns: On success, 0 is returned, or an error code.
+ * If the provided @keyid is %NULL then the master key is
+ * set as preferred.
+ *
+ * Returns: On success, %GNUTLS_E_SUCCESS (0) is returned,
+ * otherwise a negative error code is returned.
**/
int
gnutls_openpgp_privkey_set_preferred_key_id (gnutls_openpgp_privkey_t key,
@@ -1253,6 +1257,20 @@ gnutls_openpgp_privkey_set_preferred_key_id (gnutls_openpgp_privkey_t key,
return GNUTLS_E_INVALID_REQUEST;
}
+ if (keyid == NULL) /* set the master as preferred */
+ {
+ uint8_t tmp[GNUTLS_OPENPGP_KEYID_SIZE];
+
+ ret = gnutls_openpgp_privkey_get_key_id (key, tmp);
+ if (ret < 0)
+ return gnutls_assert_val(ret);
+
+ key->preferred_set = 1;
+ memcpy (key->preferred_keyid, tmp, GNUTLS_OPENPGP_KEYID_SIZE);
+
+ return 0;
+ }
+
/* check if the id is valid */
ret = gnutls_openpgp_privkey_get_subkey_idx (key, keyid);
if (ret < 0)