[Pkg-gnupg-commit] [gnupg2] 167/185: gpg, sm: Fix compliance checking for decryption.

Daniel Kahn Gillmor dkg at fifthhorseman.net
Mon Aug 7 11:55:33 UTC 2017


This is an automated email from the git hooks/post-receive script.

dkg pushed a commit to branch experimental
in repository gnupg2.

commit a0d0cbee7654ad7582400efaa92d493cd8e669e9
Author: Werner Koch <wk at gnupg.org>
Date:   Thu Jul 27 13:56:38 2017 +0200

    gpg,sm: Fix compliance checking for decryption.
    
    * common/compliance.c (gnupg_pk_is_compliant): Remove the Elgamal
    signing check.  We don't support Elgamal signing at all.
    (gnupg_pk_is_allowed) <de-vs>: Revert encryption/decryption for RSA.
    Check the curvenames for ECDH.
    * g10/pubkey-enc.c (get_session_key): Print only a warning if the key
    is not compliant.
    * sm/decrypt.c (gpgsm_decrypt): Ditto.  Use the same string as in gpg
    so that we have only one translation.
    --
    
    We always allow decryption and print only a note if the key was not
    complaint at the encryption site.
    
    GnuPG-bug-id: 3308
    Signed-off-by: Werner Koch <wk at gnupg.org>
---
 common/compliance.c | 46 ++++++++++++++++++++++++++++++++--------------
 g10/pubkey-enc.c    | 42 ++++++++++++++++++------------------------
 sm/decrypt.c        | 22 ++++++++++++----------
 3 files changed, 62 insertions(+), 48 deletions(-)

diff --git a/common/compliance.c b/common/compliance.c
index 268ea4d..9511724 100644
--- a/common/compliance.c
+++ b/common/compliance.c
@@ -99,7 +99,7 @@ gnupg_pk_is_compliant (enum gnupg_compliance_mode compliance, int algo,
 		       gcry_mpi_t key[], unsigned int keylength,
                        const char *curvename)
 {
-  enum { is_rsa, is_dsa, is_pgp5, is_elg_sign, is_ecc } algotype;
+  enum { is_rsa, is_dsa, is_elg, is_ecc } algotype;
   int result = 0;
 
   if (! initialized)
@@ -118,7 +118,7 @@ gnupg_pk_is_compliant (enum gnupg_compliance_mode compliance, int algo,
       break;
 
     case PUBKEY_ALGO_ELGAMAL_E:
-      algotype = is_pgp5;
+      algotype = is_elg;
       break;
 
     case PUBKEY_ALGO_ECDH:
@@ -128,8 +128,7 @@ gnupg_pk_is_compliant (enum gnupg_compliance_mode compliance, int algo,
       break;
 
     case PUBKEY_ALGO_ELGAMAL:
-      algotype = is_elg_sign;
-      break;
+      return 0; /* Signing with Elgamal is not at all supported.  */
 
     default: /* Unknown.  */
       return 0;
@@ -141,7 +140,7 @@ gnupg_pk_is_compliant (enum gnupg_compliance_mode compliance, int algo,
 
       switch (algotype)
         {
-        case is_pgp5:
+        case is_elg:
           result = 0;
           break;
 
@@ -183,11 +182,6 @@ gnupg_pk_is_compliant (enum gnupg_compliance_mode compliance, int algo,
         }
       xfree (curve);
     }
-  else if (algotype == is_elg_sign)
-    {
-      /* An Elgamal signing key is only RFC-2440 compliant.  */
-      result = (compliance == CO_RFC2440);
-    }
   else
     {
       result = 1; /* Assume compliance.  */
@@ -219,9 +213,9 @@ gnupg_pk_is_allowed (enum gnupg_compliance_mode compliance,
 	case PUBKEY_ALGO_RSA_S:
 	  switch (use)
 	    {
-	    case PK_USE_ENCRYPTION:
-	      return 1;
 	    case PK_USE_DECRYPTION:
+	      return 1;
+	    case PK_USE_ENCRYPTION:
 	    case PK_USE_SIGNING:
 	      return (keylength == 2048
 		      || keylength == 3072
@@ -253,10 +247,34 @@ gnupg_pk_is_allowed (enum gnupg_compliance_mode compliance,
 
 	case PUBKEY_ALGO_ELGAMAL:
 	case PUBKEY_ALGO_ELGAMAL_E:
-	  return use == PK_USE_ENCRYPTION;
+	  return use == PK_USE_DECRYPTION;
 
 	case PUBKEY_ALGO_ECDH:
-	  return use == PK_USE_ENCRYPTION;
+	  if (use == PK_USE_DECRYPTION)
+            return 1;
+          else if (use == PK_USE_ENCRYPTION)
+            {
+              int result = 0;
+              char *curve = NULL;
+
+              if (!curvename && key)
+                {
+                  curve = openpgp_oid_to_str (key[0]);
+                  curvename = openpgp_oid_to_curve (curve, 0);
+                  if (!curvename)
+                    curvename = curve;
+                }
+
+              result = (curvename
+                        && (!strcmp (curvename, "brainpoolP256r1")
+                            || !strcmp (curvename, "brainpoolP384r1")
+                            || !strcmp (curvename, "brainpoolP512r1")));
+
+              xfree (curve);
+              return result;
+            }
+          else
+            return 0;
 
 	case PUBKEY_ALGO_ECDSA:
 	  {
diff --git a/g10/pubkey-enc.c b/g10/pubkey-enc.c
index 0ddb8d7..013fd2f 100644
--- a/g10/pubkey-enc.c
+++ b/g10/pubkey-enc.c
@@ -90,19 +90,16 @@ get_session_key (ctrl_t ctrl, PKT_pubkey_enc * k, DEK * dek)
       sk->pubkey_algo = k->pubkey_algo; /* We want a pubkey with this algo.  */
       if (!(rc = get_seckey (ctrl, sk, k->keyid)))
         {
-          /* Check compliance.  */
-          if (! gnupg_pk_is_allowed (opt.compliance, PK_USE_DECRYPTION,
-                                     sk->pubkey_algo,
-                                     sk->pkey, nbits_from_pk (sk), NULL))
-            {
-              log_info (_("key %s not suitable for decryption"
-                          " while in %s mode\n"),
-                        keystr_from_pk (sk),
-                        gnupg_compliance_option_string (opt.compliance));
-              rc = gpg_error (GPG_ERR_PUBKEY_ALGO);
-            }
-          else
-            rc = get_it (ctrl, k, dek, sk, k->keyid);
+          /* Print compliance warning.  */
+          if (!gnupg_pk_is_compliant (opt.compliance,
+                                      sk->pubkey_algo,
+                                      sk->pkey, nbits_from_pk (sk), NULL))
+            log_info (_("Note: key %s was not suitable for encryption"
+                        " in %s mode\n"),
+                      keystr_from_pk (sk),
+                      gnupg_compliance_option_string (opt.compliance));
+
+          rc = get_it (ctrl, k, dek, sk, k->keyid);
         }
     }
   else if (opt.skip_hidden_recipients)
@@ -131,17 +128,14 @@ get_session_key (ctrl_t ctrl, PKT_pubkey_enc * k, DEK * dek)
             log_info (_("anonymous recipient; trying secret key %s ...\n"),
                       keystr (keyid));
 
-          /* Check compliance.  */
-          if (! gnupg_pk_is_allowed (opt.compliance, PK_USE_DECRYPTION,
-                                     sk->pubkey_algo,
-                                     sk->pkey, nbits_from_pk (sk), NULL))
-            {
-              log_info (_("key %s not suitable for decryption"
-                          " while in %s mode\n"),
-                          keystr_from_pk (sk),
-                          gnupg_compliance_option_string (opt.compliance));
-              continue;
-            }
+          /* Print compliance warning.  */
+          if (!gnupg_pk_is_compliant (opt.compliance,
+                                      sk->pubkey_algo,
+                                      sk->pkey, nbits_from_pk (sk), NULL))
+            log_info (_("Note: key %s was not suitable for encryption"
+                        " in %s mode\n"),
+                      keystr_from_pk (sk),
+                      gnupg_compliance_option_string (opt.compliance));
 
           rc = get_it (ctrl, k, dek, sk, keyid);
           if (!rc)
diff --git a/sm/decrypt.c b/sm/decrypt.c
index 170ad5a..3de742a 100644
--- a/sm/decrypt.c
+++ b/sm/decrypt.c
@@ -480,17 +480,19 @@ gpgsm_decrypt (ctrl_t ctrl, int in_fd, estream_t out_fp)
                     unsigned int nbits;
                     int pk_algo = gpgsm_get_key_algo_info (cert, &nbits);
 
-                    /* Check compliance.  */
-                    if (! gnupg_pk_is_allowed (opt.compliance,
-                                               PK_USE_DECRYPTION,
-                                               pk_algo, NULL, nbits, NULL))
+                    /* Print compliance warning.  */
+                    if (! gnupg_pk_is_compliant (opt.compliance,
+                                                 pk_algo, NULL, nbits, NULL))
                       {
-                        log_error ("certificate ID 0x%08lX not suitable for "
-                                   "decryption while in %s mode\n",
-                                   gpgsm_get_short_fingerprint (cert, NULL),
-                                   gnupg_compliance_option_string (opt.compliance));
-                        rc = gpg_error (GPG_ERR_PUBKEY_ALGO);
-                        goto oops;
+                        char  kidstr[10+1];
+
+                        snprintf (kidstr, sizeof kidstr, "0x%08lX",
+                                  gpgsm_get_short_fingerprint (cert, NULL));
+                        log_info
+                          (_("Note: key %s was not suitable for encryption"
+                             " in %s mode\n"),
+                           kidstr,
+                           gnupg_compliance_option_string (opt.compliance));
                       }
 
                     /* Check that all certs are compliant with CO_DE_VS.  */

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-gnupg/gnupg2.git



More information about the Pkg-gnupg-commit mailing list