Blame SOURCES/libgcrypt-1.10.0-fips-indicator-pk-flags.patch

e35e9c
From 0c0268177666f6ce53c0a61e86c1c5bd2c53c0b0 Mon Sep 17 00:00:00 2001
e35e9c
From: Jakub Jelen <jjelen@redhat.com>
e35e9c
Date: Mon, 6 Mar 2023 15:57:40 +0100
e35e9c
Subject: [PATCH] fips: Explicitly allow only some PK flags
e35e9c
e35e9c
* src/fips.c (_gcry_fips_indicator_pk_flags): New function for explicit
e35e9c
  FIPS indicator for public key algorithm flags
e35e9c
* src/g10lib.h (_gcry_fips_indicator_pk_flags): New.
e35e9c
* src/gcrypt.h.in (GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS): New.
e35e9c
* src/global.c (_gcry_vcontrol): Handle the new option.
e35e9c
* doc/gcrypt.texi: Document new options.
e35e9c
--
e35e9c
e35e9c
Signed-off-by: Jakub Jelen <jjelen@redhat.com>
e35e9c
---
e35e9c
 doc/gcrypt.texi |  6 ++++++
e35e9c
 src/fips.c      | 15 +++++++++++++++
e35e9c
 src/g10lib.h    |  1 +
e35e9c
 src/gcrypt.h.in |  3 ++-
e35e9c
 src/global.c    |  7 +++++++
e35e9c
 5 files changed, 31 insertions(+), 1 deletion(-)
e35e9c
e35e9c
diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi
e35e9c
index 462c5931..750b6718 100644
e35e9c
--- a/doc/gcrypt.texi
e35e9c
+++ b/doc/gcrypt.texi
e35e9c
@@ -1005,6 +1005,12 @@ Check if the given message digest algorithm is approved under the current
e35e9c
 FIPS 140-3 certification. If the algorithm is approved, this function returns
e35e9c
 @code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned.
e35e9c
 
e35e9c
+@item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char *
e35e9c
+
e35e9c
+Check if the given public key operation flag is approved under the current
e35e9c
+FIPS 140-3 certification. If the flag is approved, this function returns
e35e9c
+@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned.
e35e9c
+
e35e9c
 @end table
e35e9c
 
e35e9c
 @end deftypefun
e35e9c
diff --git a/src/fips.c b/src/fips.c
e35e9c
index 974ed833..cb547aa2 100644
e35e9c
--- a/src/fips.c
e35e9c
+++ b/src/fips.c
e35e9c
@@ -457,6 +457,21 @@ _gcry_fips_indicator_function (va_list arg_ptr)
e35e9c
 }
e35e9c
 
e35e9c
 
e35e9c
+int
e35e9c
+_gcry_fips_indicator_pk_flags (va_list arg_ptr)
e35e9c
+{
e35e9c
+  const char *flag = va_arg (arg_ptr, const char *);
e35e9c
+
e35e9c
+  if (strcmp (flag, "param") == 0 ||
e35e9c
+      strcmp (flag, "raw") == 0 ||
e35e9c
+      strcmp (flag, "no-blinding") == 0 ||
e35e9c
+      strcmp (flag, "pss") == 0)
e35e9c
+    return GPG_ERR_NO_ERROR;
e35e9c
+
e35e9c
+  return GPG_ERR_NOT_SUPPORTED;
e35e9c
+}
e35e9c
+
e35e9c
+
e35e9c
 /* This is a test on whether the library is in the error or
e35e9c
    operational state. */
e35e9c
 int
e35e9c
diff --git a/src/g10lib.h b/src/g10lib.h
e35e9c
index 86337eed..acff2d6b 100644
e35e9c
--- a/src/g10lib.h
e35e9c
+++ b/src/g10lib.h
e35e9c
@@ -471,6 +471,7 @@ int _gcry_fips_indicator_mac (va_list arg_ptr);
e35e9c
 int _gcry_fips_indicator_md (va_list arg_ptr);
e35e9c
 int _gcry_fips_indicator_kdf (va_list arg_ptr);
e35e9c
 int _gcry_fips_indicator_function (va_list arg_ptr);
e35e9c
+int _gcry_fips_indicator_pk_flags (va_list arg_ptr);
e35e9c
 
e35e9c
 int _gcry_fips_is_operational (void);
e35e9c
 
e35e9c
diff --git a/src/gcrypt.h.in b/src/gcrypt.h.in
e35e9c
index 54080d46..121a2061 100644
e35e9c
--- a/src/gcrypt.h.in
e35e9c
+++ b/src/gcrypt.h.in
e35e9c
@@ -332,7 +332,8 @@ enum gcry_ctl_cmds
e35e9c
     GCRYCTL_NO_FIPS_MODE = 83,
e35e9c
     GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION = 84,
e35e9c
     GCRYCTL_FIPS_SERVICE_INDICATOR_MAC = 85,
e35e9c
-    GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86
e35e9c
+    GCRYCTL_FIPS_SERVICE_INDICATOR_MD = 86,
e35e9c
+    GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS = 87
e35e9c
   };
e35e9c
 
e35e9c
 /* Perform various operations defined by CMD. */
e35e9c
diff --git a/src/global.c b/src/global.c
e35e9c
index d16d3709..f39df422 100644
e35e9c
--- a/src/global.c
e35e9c
+++ b/src/global.c
e35e9c
@@ -818,6 +818,13 @@ _gcry_vcontrol (enum gcry_ctl_cmds cmd, va_list arg_ptr)
e35e9c
       rc = _gcry_fips_indicator_function (arg_ptr);
e35e9c
       break;
e35e9c
 
e35e9c
+    case GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS:
e35e9c
+      /* Get FIPS Service Indicator for a public key operation flags.
e35e9c
+       * Returns GPG_ERR_NO_ERROR if the flag is allowed to be used or
e35e9c
+       * GPG_ERR_NOT_SUPPORTED otherwise */
e35e9c
+      rc = _gcry_fips_indicator_pk_flags (arg_ptr);
e35e9c
+      break;
e35e9c
+
e35e9c
     case PRIV_CTL_INIT_EXTRNG_TEST:  /* Init external random test.  */
e35e9c
       rc = GPG_ERR_NOT_SUPPORTED;
e35e9c
       break;
e35e9c
-- 
e35e9c
2.39.2
e35e9c
e35e9c
From 22a40df4c0210a671b331932a434f70b50354873 Mon Sep 17 00:00:00 2001
e35e9c
From: Jakub Jelen <jjelen@redhat.com>
e35e9c
Date: Mon, 6 Mar 2023 16:05:07 +0100
e35e9c
Subject: [PATCH] fips: Explicitly disable overriding random in FIPS mode
e35e9c
e35e9c
* src/fips.c: (_gcry_fips_indicator_function): Mark using random
e35e9c
  override non-approved in FIPS mode.
e35e9c
--
e35e9c
e35e9c
Signed-off-by: Jakub Jelen <jjelen@redhat.com>
e35e9c
---
e35e9c
 src/fips.c | 3 ++-
e35e9c
 1 file changed, 2 insertions(+), 1 deletion(-)
e35e9c
e35e9c
diff --git a/src/fips.c b/src/fips.c
e35e9c
index cb547aa2..a7342030 100644
e35e9c
--- a/src/fips.c
e35e9c
+++ b/src/fips.c
e35e9c
@@ -450,7 +450,8 @@ _gcry_fips_indicator_function (va_list arg_ptr)
e35e9c
   if (strcmp (function, "gcry_pk_sign") == 0 ||
e35e9c
       strcmp (function, "gcry_pk_verify") == 0 ||
e35e9c
       strcmp (function, "gcry_pk_encrypt") == 0 ||
e35e9c
-      strcmp (function, "gcry_pk_decrypt") == 0)
e35e9c
+      strcmp (function, "gcry_pk_decrypt") == 0 ||
e35e9c
+      strcmp (function, "gcry_pk_random_override_new") == 0)
e35e9c
     return GPG_ERR_NOT_SUPPORTED;
e35e9c
 
e35e9c
   return GPG_ERR_NO_ERROR;
e35e9c
-- 
e35e9c
2.39.2
e35e9c
e35e9c
From 1c916b8c99ea0e30f1d81d606fd63b0c45657186 Mon Sep 17 00:00:00 2001
e35e9c
From: NIIBE Yutaka <gniibe@fsij.org>
e35e9c
Date: Fri, 24 Mar 2023 13:12:56 +0900
e35e9c
Subject: [PATCH] fips: More elaborate way of getting FIPS pk flags indicators.
e35e9c
e35e9c
* src/fips.c (_gcry_fips_indicator_pk_flags): List more allowed string
e35e9c
in the S-expression.
e35e9c
* doc/gcrypt.texi: Add document for the FIPS service indicator
e35e9c
GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS with example.
e35e9c
e35e9c
--
e35e9c
e35e9c
GnuPG-bug-id: 6417
e35e9c
Signed-off-by: Jakub Jelen <jjelen@redhat.com>
e35e9c
Signed-off-by: NIIBE Yutaka <gniibe@fsij.org>
e35e9c
---
e35e9c
 doc/gcrypt.texi | 42 +++++++++++++++++++++++++++++++++++++++---
e35e9c
 src/fips.c      | 41 +++++++++++++++++++++++++++++++++++++----
e35e9c
 2 files changed, 76 insertions(+), 7 deletions(-)
e35e9c
e35e9c
diff --git a/doc/gcrypt.texi b/doc/gcrypt.texi
e35e9c
index 750b6718..752f64d6 100644
e35e9c
--- a/doc/gcrypt.texi
e35e9c
+++ b/doc/gcrypt.texi
e35e9c
@@ -1007,9 +1007,45 @@ FIPS 140-3 certification. If the algorithm is approved, this function returns
e35e9c
 
e35e9c
 @item GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS; Arguments: const char *
e35e9c
 
e35e9c
-Check if the given public key operation flag is approved under the current
e35e9c
-FIPS 140-3 certification. If the flag is approved, this function returns
e35e9c
-@code{GPG_ERR_NO_ERROR}. Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned.
e35e9c
+Check if the given public key operation flag or s-expression object name is
e35e9c
+approved under the current FIPS 140-3 certification.  If the flag is
e35e9c
+approved, this function returns @code{GPG_ERR_NO_ERROR}.
e35e9c
+
e35e9c
+Otherwise @code{GPG_ERR_NOT_SUPPORTED} is returned.
e35e9c
+
e35e9c
+For compound s-expression objects, if the object name is allowed, the user
e35e9c
+is responsible to check also the internal members.  For example:
e35e9c
+
e35e9c
+@example
e35e9c
+  gcry_sexp_t s_sig = NULL;
e35e9c
+  gcry_md_hd_t hd = NULL;
e35e9c
+  gcry_sexp_t s_sk = NULL;
e35e9c
+  const char *data_tmpl = "(data(flags pss)(hash %s %b)(salt-length 1:0))";
e35e9c
+
e35e9c
+  if (err = gcry_control(GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION, "gcry_md_open") &&
e35e9c
+      err = gcry_control(GCRYCTL_FIPS_SERVICE_INDICATOR_MD, GCRY_MD_SHA512) &&
e35e9c
+      err = gcry_md_open (&hd, GCRY_MD_SHA512, 0))
e35e9c
+    @{
e35e9c
+      printf ("gcry_md_open failed: %s", gpg_strerror (err));
e35e9c
+      return;
e35e9c
+    @}
e35e9c
+  gcry_md_write (hd, buffer, buflen);
e35e9c
+
e35e9c
+  /* initialize the key in s_sk */
e35e9c
+
e35e9c
+  if (err = gcry_control(GCRYCTL_FIPS_SERVICE_INDICATOR_FUNCTION, "gcry_pk_hash_sign") &&
e35e9c
+      err = gcry_control(GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS, "data") &&
e35e9c
+      err = gcry_control(GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS, "flags") &&
e35e9c
+      err = gcry_control(GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS, "pss") &&
e35e9c
+      err = gcry_control(GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS, "hash") &&
e35e9c
+      err = gcry_control(GCRYCTL_FIPS_SERVICE_INDICATOR_PK_FLAGS, "salt-length")
e35e9c
+      err = gcry_pk_hash_sign (&s_sig, data_tmpl, s_sk, hd, NULL))
e35e9c
+    @{
e35e9c
+      printf ("gcry_pk_hash_sign failed: %s", gpg_strerror (err));
e35e9c
+      return;
e35e9c
+    @}
e35e9c
+  /* ok */
e35e9c
+@end example
e35e9c
 
e35e9c
 @end table
e35e9c
 
e35e9c
diff --git a/src/fips.c b/src/fips.c
e35e9c
index a7342030..669cfd0e 100644
e35e9c
--- a/src/fips.c
e35e9c
+++ b/src/fips.c
e35e9c
@@ -457,16 +457,49 @@ _gcry_fips_indicator_function (va_list arg_ptr)
e35e9c
   return GPG_ERR_NO_ERROR;
e35e9c
 }
e35e9c
 
e35e9c
+/* Note: the array should be sorted.  */
e35e9c
+static const char *valid_string_in_sexp[] = {
e35e9c
+  "curve",
e35e9c
+  "d",
e35e9c
+  "data",
e35e9c
+  "e",
e35e9c
+  "ecdsa",
e35e9c
+  "flags",
e35e9c
+  "genkey",
e35e9c
+  "hash",
e35e9c
+  "n",
e35e9c
+  "nbits",
e35e9c
+  "pkcs1",
e35e9c
+  "private-key",
e35e9c
+  "pss",
e35e9c
+  "public-key",
e35e9c
+  "q",
e35e9c
+  "r",
e35e9c
+  "raw",
e35e9c
+  "rsa",
e35e9c
+  "rsa-use-e",
e35e9c
+  "s",
e35e9c
+  "salt-length",
e35e9c
+  "sig-val",
e35e9c
+  "value"
e35e9c
+};
e35e9c
+
e35e9c
+static int
e35e9c
+compare_string (const void *v1, const void *v2)
e35e9c
+{
e35e9c
+  const char * const *p_str1 = v1;
e35e9c
+  const char * const *p_str2 = v2;
e35e9c
+
e35e9c
+  return strcmp (*p_str1, *p_str2);
e35e9c
+}
e35e9c
 
e35e9c
 int
e35e9c
 _gcry_fips_indicator_pk_flags (va_list arg_ptr)
e35e9c
 {
e35e9c
   const char *flag = va_arg (arg_ptr, const char *);
e35e9c
 
e35e9c
-  if (strcmp (flag, "param") == 0 ||
e35e9c
-      strcmp (flag, "raw") == 0 ||
e35e9c
-      strcmp (flag, "no-blinding") == 0 ||
e35e9c
-      strcmp (flag, "pss") == 0)
e35e9c
+  if (bsearch (&flag, valid_string_in_sexp, DIM (valid_string_in_sexp),
e35e9c
+               sizeof (char *), compare_string))
e35e9c
     return GPG_ERR_NO_ERROR;
e35e9c
 
e35e9c
   return GPG_ERR_NOT_SUPPORTED;
e35e9c
-- 
e35e9c
2.39.2
e35e9c