Blame SOURCES/0008-EP11-Supply-CKA_PUBLIC_KEY_INFO-when-importing-priva.patch

971d89
From b8bc3e183b43e9aeee8a8f23c8e48fffb6eedc35 Mon Sep 17 00:00:00 2001
971d89
From: Ingo Franzki <ifranzki@linux.ibm.com>
971d89
Date: Fri, 4 Nov 2022 10:51:08 +0100
971d89
Subject: [PATCH 08/34] EP11: Supply CKA_PUBLIC_KEY_INFO when importing private
971d89
 keys
971d89
971d89
When importing private keys, the SPKI of the corresponding public key
971d89
is returned in parameters csum/cslen of the m_UnwrapKey() EP11 host
971d89
library call. Supply this SPKI as CKA_PUBLIC_KEY_INFO to the object.
971d89
971d89
For public key import, the common code already builds the SPKI from
971d89
the clear public key attributes of the imported public key.
971d89
971d89
Signed-off-by: Ingo Franzki <ifranzki@linux.ibm.com>
971d89
---
971d89
 usr/lib/common/obj_mgr.c           |   5 ++
971d89
 usr/lib/ep11_stdll/ep11_specific.c | 113 +++++++++++++++++++++++++------------
971d89
 2 files changed, 83 insertions(+), 35 deletions(-)
971d89
971d89
diff --git a/usr/lib/common/obj_mgr.c b/usr/lib/common/obj_mgr.c
971d89
index 8e61cbd4..347ec3f3 100644
971d89
--- a/usr/lib/common/obj_mgr.c
971d89
+++ b/usr/lib/common/obj_mgr.c
971d89
@@ -123,6 +123,11 @@ CK_RV object_mgr_add(STDLL_TokData_t *tokdata,
971d89
     switch(class) {
971d89
     case CKO_PUBLIC_KEY:
971d89
     case CKO_PRIVATE_KEY:
971d89
+        /* Skip if there is already a non-empty CKA_PUBLIC_KEY_INFO */
971d89
+        if (template_attribute_get_non_empty(o->template, CKA_PUBLIC_KEY_INFO,
971d89
+                                             &spki_attr) == CKR_OK)
971d89
+            break;
971d89
+
971d89
         rc = template_attribute_get_ulong(o->template, CKA_KEY_TYPE, &keytype);
971d89
         if (rc != CKR_OK) {
971d89
             TRACE_ERROR("Could not find CKA_KEY_TYPE for the key object.\n");
971d89
diff --git a/usr/lib/ep11_stdll/ep11_specific.c b/usr/lib/ep11_stdll/ep11_specific.c
971d89
index 886692c4..3b14a557 100644
971d89
--- a/usr/lib/ep11_stdll/ep11_specific.c
971d89
+++ b/usr/lib/ep11_stdll/ep11_specific.c
971d89
@@ -2745,9 +2745,10 @@ static int get_curve_type_from_template(TEMPLATE *tmpl)
971d89
  * SPKIs for public imported RSA keys.
971d89
  * Similar to rawkey_2_blob, but keys must follow a standard BER encoding.
971d89
  */
971d89
-static CK_RV import_RSA_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
-                            OBJECT * rsa_key_obj,
971d89
-                            CK_BYTE * blob, size_t * blob_size)
971d89
+static CK_RV import_RSA_key(STDLL_TokData_t *tokdata, SESSION *sess,
971d89
+                            OBJECT *rsa_key_obj,
971d89
+                            CK_BYTE *blob, size_t *blob_size,
971d89
+                            CK_BYTE *spki, size_t *spki_size)
971d89
 {
971d89
     ep11_private_data_t *ep11_data = tokdata->private_data;
971d89
     CK_RV rc;
971d89
@@ -2759,8 +2760,6 @@ static CK_RV import_RSA_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
     CK_ULONG attrs_len = 0;
971d89
     CK_ATTRIBUTE_PTR new_p_attrs = NULL;
971d89
     CK_ULONG new_attrs_len = 0;
971d89
-    CK_BYTE csum[MAX_BLOBSIZE];
971d89
-    CK_ULONG cslen = sizeof(csum);
971d89
     CK_OBJECT_CLASS class;
971d89
     CK_BYTE *data = NULL;
971d89
     CK_ULONG data_len;
971d89
@@ -2831,6 +2830,8 @@ static CK_RV import_RSA_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
             goto import_RSA_key_end;
971d89
         }
971d89
 
971d89
+        *spki_size = 0; /* common code will extract SPKI from object */
971d89
+
971d89
     } else {
971d89
 
971d89
         /* imported private RSA key goes here */
971d89
@@ -2884,7 +2885,7 @@ static CK_RV import_RSA_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                                  ep11_data->raw2key_wrap_blob_l, NULL, ~0,
971d89
                                  ep11_pin_blob, ep11_pin_blob_len, &mech_w,
971d89
                                  new_p_attrs, new_attrs_len, blob, blob_size,
971d89
-                                 csum, &cslen, target_info->target);
971d89
+                                 spki, spki_size, target_info->target);
971d89
         RETRY_END(rc, tokdata, sess)
971d89
 
971d89
         if (rc != CKR_OK) {
971d89
@@ -2921,9 +2922,10 @@ import_RSA_key_end:
971d89
  * SPKIs for public imported EC keys.
971d89
  * Similar to rawkey_2_blob, but keys must follow a standard BER encoding.
971d89
  */
971d89
-static CK_RV import_EC_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
-                           OBJECT * ec_key_obj,
971d89
-                           CK_BYTE * blob, size_t * blob_size)
971d89
+static CK_RV import_EC_key(STDLL_TokData_t *tokdata, SESSION *sess,
971d89
+                           OBJECT *ec_key_obj,
971d89
+                           CK_BYTE *blob, size_t *blob_size,
971d89
+                           CK_BYTE *spki, size_t *spki_size)
971d89
 {
971d89
     ep11_private_data_t *ep11_data = tokdata->private_data;
971d89
     CK_RV rc;
971d89
@@ -2935,8 +2937,6 @@ static CK_RV import_EC_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
     CK_ULONG attrs_len = 0;
971d89
     CK_ATTRIBUTE_PTR new_p_attrs = NULL;
971d89
     CK_ULONG new_attrs_len = 0;
971d89
-    CK_BYTE csum[MAX_BLOBSIZE];
971d89
-    CK_ULONG cslen = sizeof(csum);
971d89
     CK_OBJECT_CLASS class;
971d89
     CK_BYTE *data = NULL;
971d89
     CK_ULONG data_len;
971d89
@@ -3059,6 +3059,8 @@ static CK_RV import_EC_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
             goto import_EC_key_end;
971d89
         }
971d89
 
971d89
+        *spki_size = 0; /* common code will extract SPKI from object */
971d89
+
971d89
     } else {
971d89
 
971d89
         /* imported private EC key goes here */
971d89
@@ -3115,7 +3117,8 @@ static CK_RV import_EC_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                                  ep11_pin_blob,
971d89
                                  ep11_pin_blob_len, &mech_w,
971d89
                                  new_p_attrs, new_attrs_len, blob,
971d89
-                                 blob_size, csum, &cslen, target_info->target);
971d89
+                                 blob_size, spki, spki_size,
971d89
+                                 target_info->target);
971d89
         RETRY_END(rc, tokdata, sess)
971d89
 
971d89
         if (rc != CKR_OK) {
971d89
@@ -3149,9 +3152,10 @@ import_EC_key_end:
971d89
  * SPKIs for public imported DSA keys.
971d89
  * Similar to rawkey_2_blob, but keys must follow a standard BER encoding.
971d89
  */
971d89
-static CK_RV import_DSA_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
-                            OBJECT * dsa_key_obj,
971d89
-                            CK_BYTE * blob, size_t * blob_size)
971d89
+static CK_RV import_DSA_key(STDLL_TokData_t *tokdata, SESSION *sess,
971d89
+                            OBJECT *dsa_key_obj,
971d89
+                            CK_BYTE *blob, size_t *blob_size,
971d89
+                            CK_BYTE *spki, size_t *spki_size)
971d89
 {
971d89
     ep11_private_data_t *ep11_data = tokdata->private_data;
971d89
     CK_RV rc;
971d89
@@ -3163,8 +3167,6 @@ static CK_RV import_DSA_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
     CK_ULONG attrs_len = 0;
971d89
     CK_ATTRIBUTE_PTR new_p_attrs = NULL;
971d89
     CK_ULONG new_attrs_len = 0;
971d89
-    CK_BYTE csum[MAX_BLOBSIZE];
971d89
-    CK_ULONG cslen = sizeof(csum);
971d89
     CK_OBJECT_CLASS class;
971d89
     CK_BYTE *data = NULL;
971d89
     CK_ULONG data_len;
971d89
@@ -3251,6 +3253,8 @@ static CK_RV import_DSA_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
             goto import_DSA_key_end;
971d89
         }
971d89
 
971d89
+        *spki_size = 0; /* common code will extract SPKI from object */
971d89
+
971d89
     } else {
971d89
 
971d89
         /* imported private DSA key goes here */
971d89
@@ -3307,7 +3311,8 @@ static CK_RV import_DSA_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                                  ep11_pin_blob,
971d89
                                  ep11_pin_blob_len, &mech_w,
971d89
                                  new_p_attrs, new_attrs_len, blob,
971d89
-                                 blob_size, csum, &cslen, target_info->target);
971d89
+                                 blob_size, spki, spki_size,
971d89
+                                 target_info->target);
971d89
         RETRY_END(rc, tokdata, sess)
971d89
 
971d89
         if (rc != CKR_OK) {
971d89
@@ -3339,9 +3344,10 @@ import_DSA_key_end:
971d89
  * SPKIs for public imported DH keys.
971d89
  * Similar to rawkey_2_blob, but keys must follow a standard BER encoding.
971d89
  */
971d89
-static CK_RV import_DH_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
-                           OBJECT * dh_key_obj,
971d89
-                           CK_BYTE * blob, size_t * blob_size)
971d89
+static CK_RV import_DH_key(STDLL_TokData_t *tokdata, SESSION *sess,
971d89
+                           OBJECT *dh_key_obj,
971d89
+                           CK_BYTE *blob, size_t *blob_size,
971d89
+                           CK_BYTE *spki, size_t *spki_size)
971d89
 {
971d89
     ep11_private_data_t *ep11_data = tokdata->private_data;
971d89
     CK_RV rc;
971d89
@@ -3353,8 +3359,6 @@ static CK_RV import_DH_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
     CK_ULONG attrs_len = 0;
971d89
     CK_ATTRIBUTE_PTR new_p_attrs = NULL;
971d89
     CK_ULONG new_attrs_len = 0;
971d89
-    CK_BYTE csum[MAX_BLOBSIZE];
971d89
-    CK_ULONG cslen = sizeof(csum);
971d89
     CK_OBJECT_CLASS class;
971d89
     CK_BYTE *data = NULL;
971d89
     CK_ULONG data_len;
971d89
@@ -3433,6 +3437,8 @@ static CK_RV import_DH_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
             goto import_DH_key_end;
971d89
         }
971d89
 
971d89
+        *spki_size = 0; /* common code will extract SPKI from object */
971d89
+
971d89
     } else {
971d89
         CK_ATTRIBUTE *value;
971d89
         CK_ATTRIBUTE *value_bits;
971d89
@@ -3500,7 +3506,8 @@ static CK_RV import_DH_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                                  ep11_pin_blob,
971d89
                                  ep11_pin_blob_len, &mech_w,
971d89
                                  new_p_attrs, new_attrs_len, blob,
971d89
-                                 blob_size, csum, &cslen, target_info->target);
971d89
+                                 blob_size, spki, spki_size,
971d89
+                                 target_info->target);
971d89
         RETRY_END(rc, tokdata, sess)
971d89
 
971d89
         if (rc != CKR_OK) {
971d89
@@ -3547,9 +3554,10 @@ import_DH_key_end:
971d89
  * SPKIs for public imported IBM Dilithium keys.
971d89
  * Similar to rawkey_2_blob, but keys must follow a standard BER encoding.
971d89
  */
971d89
-static CK_RV import_IBM_Dilithium_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
-                           OBJECT * dilithium_key_obj,
971d89
-                           CK_BYTE * blob, size_t * blob_size)
971d89
+static CK_RV import_IBM_Dilithium_key(STDLL_TokData_t *tokdata, SESSION *sess,
971d89
+                                      OBJECT *dilithium_key_obj,
971d89
+                                      CK_BYTE *blob, size_t *blob_size,
971d89
+                                      CK_BYTE *spki, size_t *spki_size)
971d89
 {
971d89
     ep11_private_data_t *ep11_data = tokdata->private_data;
971d89
     CK_RV rc;
971d89
@@ -3561,8 +3569,6 @@ static CK_RV import_IBM_Dilithium_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
     CK_ULONG attrs_len = 0;
971d89
     CK_ATTRIBUTE_PTR new_p_attrs = NULL;
971d89
     CK_ULONG new_attrs_len = 0;
971d89
-    CK_BYTE csum[MAX_BLOBSIZE];
971d89
-    CK_ULONG cslen = sizeof(csum);
971d89
     CK_OBJECT_CLASS class;
971d89
     CK_BYTE *data = NULL;
971d89
     CK_ULONG data_len;
971d89
@@ -3652,6 +3658,8 @@ static CK_RV import_IBM_Dilithium_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
             goto done;
971d89
         }
971d89
 
971d89
+        *spki_size = 0; /* common code will extract SPKI from object */
971d89
+
971d89
     } else {
971d89
 
971d89
         /* imported private IBM Dilithium key goes here */
971d89
@@ -3709,7 +3717,8 @@ static CK_RV import_IBM_Dilithium_key(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                                  ep11_pin_blob,
971d89
                                  ep11_pin_blob_len, &mech_w,
971d89
                                  new_p_attrs, new_attrs_len, blob,
971d89
-                                 blob_size, csum, &cslen, target_info->target);
971d89
+                                 blob_size, spki, spki_size,
971d89
+                                 target_info->target);
971d89
         RETRY_END(rc, tokdata, sess)
971d89
 
971d89
         if (rc != CKR_OK) {
971d89
@@ -3747,9 +3756,13 @@ CK_RV token_specific_object_add(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
     CK_ATTRIBUTE *attr = NULL;
971d89
     CK_BYTE blob[MAX_BLOBSIZE];
971d89
     size_t blobsize = sizeof(blob);
971d89
+    CK_BYTE spki[MAX_BLOBSIZE];
971d89
+    size_t spkisize = sizeof(spki);
971d89
     CK_RV rc;
971d89
     CK_ULONG class;
971d89
     CK_BBOOL attrbound;
971d89
+    CK_BYTE *temp;
971d89
+    CK_ULONG temp_len;
971d89
 
971d89
     /* get key type */
971d89
     rc = template_attribute_get_ulong(obj->template, CKA_KEY_TYPE, &keytype);
971d89
@@ -3783,7 +3796,8 @@ CK_RV token_specific_object_add(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
     /* only these keys can be imported */
971d89
     switch (keytype) {
971d89
     case CKK_RSA:
971d89
-        rc = import_RSA_key(tokdata, sess, obj, blob, &blobsize);
971d89
+        rc = import_RSA_key(tokdata, sess, obj, blob, &blobsize,
971d89
+                            spki, &spkisize);
971d89
         if (rc != CKR_OK) {
971d89
             TRACE_ERROR("%s import RSA key rc=0x%lx blobsize=0x%zx\n",
971d89
                         __func__, rc, blobsize);
971d89
@@ -3793,7 +3807,8 @@ CK_RV token_specific_object_add(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                    __func__, rc, blobsize);
971d89
         break;
971d89
     case CKK_EC:
971d89
-        rc = import_EC_key(tokdata, sess, obj, blob, &blobsize);
971d89
+        rc = import_EC_key(tokdata, sess, obj, blob, &blobsize,
971d89
+                           spki, &spkisize);
971d89
         if (rc != CKR_OK) {
971d89
             TRACE_ERROR("%s import EC key rc=0x%lx blobsize=0x%zx\n",
971d89
                         __func__, rc, blobsize);
971d89
@@ -3803,7 +3818,8 @@ CK_RV token_specific_object_add(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                    __func__, rc, blobsize);
971d89
         break;
971d89
     case CKK_DSA:
971d89
-        rc = import_DSA_key(tokdata, sess, obj, blob, &blobsize);
971d89
+        rc = import_DSA_key(tokdata, sess, obj, blob, &blobsize,
971d89
+                            spki, &spkisize);
971d89
         if (rc != CKR_OK) {
971d89
             TRACE_ERROR("%s import DSA key rc=0x%lx blobsize=0x%zx\n",
971d89
                         __func__, rc, blobsize);
971d89
@@ -3813,7 +3829,8 @@ CK_RV token_specific_object_add(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                    __func__, rc, blobsize);
971d89
         break;
971d89
     case CKK_DH:
971d89
-        rc = import_DH_key(tokdata, sess, obj, blob, &blobsize);
971d89
+        rc = import_DH_key(tokdata, sess, obj, blob, &blobsize,
971d89
+                           spki, &spkisize);
971d89
         if (rc != CKR_OK) {
971d89
             TRACE_ERROR("%s import DH key rc=0x%lx blobsize=0x%zx\n",
971d89
                         __func__, rc, blobsize);
971d89
@@ -3823,7 +3840,8 @@ CK_RV token_specific_object_add(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
                    __func__, rc, blobsize);
971d89
         break;
971d89
     case CKK_IBM_PQC_DILITHIUM:
971d89
-        rc = import_IBM_Dilithium_key(tokdata, sess, obj, blob, &blobsize);
971d89
+        rc = import_IBM_Dilithium_key(tokdata, sess, obj, blob, &blobsize,
971d89
+                                      spki, &spkisize);
971d89
         if (rc != CKR_OK) {
971d89
             TRACE_ERROR("%s import IBM Dilithium key rc=0x%lx blobsize=0x%zx\n",
971d89
                         __func__, rc, blobsize);
971d89
@@ -3891,6 +3909,31 @@ CK_RV token_specific_object_add(STDLL_TokData_t * tokdata, SESSION * sess,
971d89
         return rc;
971d89
     }
971d89
 
971d89
+    if (spkisize > 0 && (class == CKO_PRIVATE_KEY || class == CKO_PUBLIC_KEY)) {
971d89
+        /* spki may be a MACed SPKI, get length of SPKI part only */
971d89
+        rc = ber_decode_SEQUENCE(spki, &temp, &temp_len, &spkisize);
971d89
+        if (rc != CKR_OK) {
971d89
+            TRACE_ERROR("%s ber_decode_SEQUENCE failed rc=0x%lx\n",
971d89
+                        __func__, rc);
971d89
+            return rc;
971d89
+        }
971d89
+
971d89
+        rc = build_attribute(CKA_PUBLIC_KEY_INFO, spki, spkisize, &attr);
971d89
+        if (rc != CKR_OK) {
971d89
+            TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__,
971d89
+                        rc);
971d89
+            return rc;
971d89
+        }
971d89
+
971d89
+        rc = template_update_attribute(obj->template, attr);
971d89
+        if (rc != CKR_OK) {
971d89
+            TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n",
971d89
+                        __func__, rc);
971d89
+            free(attr);
971d89
+            return rc;
971d89
+        }
971d89
+    }
971d89
+
971d89
     rc = update_ep11_attrs_from_blob(tokdata, sess, obj->template);
971d89
     if (rc != CKR_OK) {
971d89
         TRACE_ERROR("%s update_ep11_attrs_from_blob failed with rc=0x%lx\n",
971d89
-- 
971d89
2.16.2.windows.1
971d89