This is an automated email from the ASF dual-hosted git repository.

xiaoxiang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git

commit 3dbe2d790ebb323cb27a03588e4b8e399a029fd1
Author: makejian <makej...@xiaomi.com>
AuthorDate: Wed Sep 20 22:22:39 2023 +0800

    crypto/rsa_verify: export rsa verify via /dev/crypto
    
    kernel supports asymmetric encryption RSA signature verification
    Signed-off-by: makejian <makej...@xiaomi.com>
---
 crypto/cryptodev.c          |  4 +++
 crypto/cryptosoft.c         | 65 +++++++++++++++++++++++++++++++++++++++++++++
 include/crypto/cryptodev.h  | 26 +++++++++---------
 include/crypto/cryptosoft.h |  2 ++
 4 files changed, 85 insertions(+), 12 deletions(-)

diff --git a/crypto/cryptodev.c b/crypto/cryptodev.c
index aaa89a11ba..d810079008 100644
--- a/crypto/cryptodev.c
+++ b/crypto/cryptodev.c
@@ -588,6 +588,10 @@ int cryptodev_key(FAR struct crypt_kop *kop)
         if (in == 3 && out == 1)
           break;
         return -EINVAL;
+      case CRK_RSA_PCKS15_VERIFY:
+        if (in == 5 && out == 0)
+          break;
+        return -EINVAL;
       default:
         return -EINVAL;
     }
diff --git a/crypto/cryptosoft.c b/crypto/cryptosoft.c
index 1281e70281..fc007eb5cd 100644
--- a/crypto/cryptosoft.c
+++ b/crypto/cryptosoft.c
@@ -29,6 +29,7 @@
 #include <errno.h>
 #include <endian.h>
 #include <nuttx/kmalloc.h>
+#include <crypto/bn.h>
 #include <crypto/cryptodev.h>
 #include <crypto/cryptosoft.h>
 #include <crypto/xform.h>
@@ -1097,11 +1098,72 @@ done:
   return 0;
 }
 
+int swcr_rsa_verify(struct cryptkop *krp)
+{
+  uint8_t *exp = (uint8_t *)krp->krp_param[0].crp_p;
+  uint8_t *modulus = (uint8_t *)krp->krp_param[1].crp_p;
+  uint8_t *sig = (uint8_t *)krp->krp_param[2].crp_p;
+  uint8_t *hash = (uint8_t *)krp->krp_param[3].crp_p;
+  uint8_t *padding = (uint8_t *)krp->krp_param[4].crp_p;
+  int exp_len = krp->krp_param[0].crp_nbits / 8;
+  int modulus_len = krp->krp_param[1].crp_nbits / 8;
+  int sig_len = krp->krp_param[2].crp_nbits / 8;
+  int hash_len = krp->krp_param[3].crp_nbits / 8;
+  int padding_len = krp->krp_param[4].crp_nbits / 8;
+  struct bn a;
+  struct bn e;
+  struct bn n;
+  struct bn r;
+
+  bignum_init(&a);
+  bignum_init(&e);
+  bignum_init(&n);
+  bignum_init(&r);
+  memcpy(e.array, exp, exp_len);
+  memcpy(n.array, modulus, modulus_len);
+  memcpy(a.array, sig, sig_len);
+  pow_mod_faster(&a, &e, &n, &r);
+  return !!memcmp(r.array, hash, hash_len) +
+         !!memcmp(r.array + hash_len, padding, padding_len);
+}
+
+int swcr_kprocess(struct cryptkop *krp)
+{
+  /* Sanity check */
+
+  if (krp == NULL)
+    {
+      return -EINVAL;
+    }
+
+  /* Go through crypto descriptors, processing as we go */
+
+  switch (krp->krp_op)
+    {
+      case CRK_RSA_PCKS15_VERIFY:
+        if ((krp->krp_status = swcr_rsa_verify(krp)) != 0)
+          {
+            goto done;
+          }
+        break;
+      default:
+
+        /* Unknown/unsupported algorithm */
+
+        krp->krp_status = -EINVAL;
+        goto done;
+    }
+
+done:
+  return 0;
+}
+
 /* Initialize the driver, called from the kernel main(). */
 
 void swcr_init(void)
 {
   int algs[CRYPTO_ALGORITHM_MAX + 1];
+  int kalgs[CRK_ALGORITHM_MAX + 1];
   int flags = CRYPTOCAP_F_SOFTWARE | CRYPTOCAP_F_ENCRYPT_MAC |
               CRYPTOCAP_F_MAC_ENCRYPT;
 
@@ -1146,4 +1208,7 @@ void swcr_init(void)
 
   crypto_register(swcr_id, algs, swcr_newsession,
                   swcr_freesession, swcr_process);
+
+  kalgs[CRK_RSA_PCKS15_VERIFY] = CRYPTO_ALG_FLAG_SUPPORTED;
+  crypto_kregister(swcr_id, kalgs, swcr_kprocess);
 }
diff --git a/include/crypto/cryptodev.h b/include/crypto/cryptodev.h
index 9357669647..86c8e7e4dd 100644
--- a/include/crypto/cryptodev.h
+++ b/include/crypto/cryptodev.h
@@ -240,18 +240,20 @@ struct crypt_kop
   struct crparam crk_param[CRK_MAXPARAM];
 };
 
-#define CRK_MOD_EXP        0
-#define CRK_MOD_EXP_CRT    1
-#define CRK_DSA_SIGN       2
-#define CRK_DSA_VERIFY     3
-#define CRK_DH_COMPUTE_KEY 4
-#define CRK_ALGORITHM_MAX  4 /* Keep updated */
-
-#define CRF_MOD_EXP        (1 << CRK_MOD_EXP)
-#define CRF_MOD_EXP_CRT    (1 << CRK_MOD_EXP_CRT)
-#define CRF_DSA_SIGN       (1 << CRK_DSA_SIGN)
-#define CRF_DSA_VERIFY     (1 << CRK_DSA_VERIFY)
-#define CRF_DH_COMPUTE_KEY (1 << CRK_DH_COMPUTE_KEY)
+#define CRK_MOD_EXP           0
+#define CRK_MOD_EXP_CRT       1
+#define CRK_DSA_SIGN          2
+#define CRK_DSA_VERIFY        3
+#define CRK_DH_COMPUTE_KEY    4
+#define CRK_RSA_PCKS15_VERIFY 5
+#define CRK_ALGORITHM_MAX     5 /* Keep updated */
+
+#define CRF_MOD_EXP           (1 << CRK_MOD_EXP)
+#define CRF_MOD_EXP_CRT       (1 << CRK_MOD_EXP_CRT)
+#define CRF_DSA_SIGN          (1 << CRK_DSA_SIGN)
+#define CRF_DSA_VERIFY        (1 << CRK_DSA_VERIFY)
+#define CRF_DH_COMPUTE_KEY    (1 << CRK_DH_COMPUTE_KEY)
+#define CRF_RSA_PCKS15_VERIFY (1 << CRK_RSA_PCKS15_VERIFY)
 
 struct cryptkop
 {
diff --git a/include/crypto/cryptosoft.h b/include/crypto/cryptosoft.h
index 36aca9a838..e28f935412 100644
--- a/include/crypto/cryptosoft.h
+++ b/include/crypto/cryptosoft.h
@@ -83,7 +83,9 @@ int swcr_authcompute(FAR struct cryptop *, FAR struct 
cryptodesc *,
 int swcr_authenc(FAR struct cryptop *);
 int swcr_compdec(FAR struct cryptodesc *, FAR struct swcr_data *,
                  caddr_t, int);
+int swcr_rsa_verify(FAR struct cryptkop *);
 int swcr_process(FAR struct cryptop *);
+int swcr_kprocess(FAR struct cryptkop *);
 int swcr_newsession(FAR uint32_t *, FAR struct cryptoini *);
 int swcr_freesession(uint64_t);
 void swcr_init(void);

Reply via email to