LCOV - code coverage report
Current view: top level - pkcs11/gkm - gkm-generic-key.c (source / functions) Coverage Total Hit
Test: coverage.info Lines: 71.4 % 70 50
Test Date: 2024-04-08 13:24:42 Functions: 91.7 % 12 11

            Line data    Source code
       1              : /*
       2              :  * gnome-keyring
       3              :  *
       4              :  * Copyright (C) 2011 Collabora Ltd.
       5              :  *
       6              :  * This program is free software; you can redistribute it and/or modify
       7              :  * it under the terms of the GNU Lesser General Public License as
       8              :  * published by the Free Software Foundation; either version 2.1 of
       9              :  * the License, or (at your option) any later version.
      10              :  *
      11              :  * This program is distributed in the hope that it will be useful, but
      12              :  * WITHOUT ANY WARRANTY; without even the implied warranty of
      13              :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      14              :  * Lesser General Public License for more details.
      15              :  *
      16              :  * You should have received a copy of the GNU Lesser General Public
      17              :  * License along with this program; if not, see
      18              :  * <http://www.gnu.org/licenses/>.
      19              :  *
      20              :  * Author: Stef Walter <stefw@collabora.co.uk>
      21              :  */
      22              : 
      23              : #include "config.h"
      24              : 
      25              : #include "pkcs11/pkcs11.h"
      26              : #include "pkcs11/pkcs11i.h"
      27              : 
      28              : #include "gkm-attributes.h"
      29              : #include "gkm-generic-key.h"
      30              : #include "gkm-session.h"
      31              : #include "gkm-transaction.h"
      32              : #include "gkm-util.h"
      33              : 
      34              : #include "egg/egg-secure-memory.h"
      35              : 
      36              : struct _GkmGenericKey {
      37              :         GkmSecretKey parent;
      38              :         gpointer value;
      39              :         gsize n_value;
      40              : };
      41              : 
      42           13 : G_DEFINE_TYPE (GkmGenericKey, gkm_generic_key, GKM_TYPE_SECRET_KEY);
      43              : 
      44              : static const CK_MECHANISM_TYPE GKM_GENERIC_MECHANISMS[] = {
      45              :         CKM_G_HKDF_SHA256_DERIVE
      46              : };
      47              : 
      48            1 : EGG_SECURE_DECLARE (generic_key);
      49              : 
      50              : /* -----------------------------------------------------------------------------
      51              :  * INTERNAL
      52              :  */
      53              : 
      54              : static CK_RV
      55            0 : attribute_set_check_value (GkmGenericKey *self, CK_ATTRIBUTE *attr)
      56              : {
      57              :         guchar buffer[20];
      58              : 
      59            0 :         g_assert (GKM_IS_GENERIC_KEY (self));
      60            0 :         g_assert (attr);
      61              : 
      62              :         /* Just asking for the length */
      63            0 :         if (!attr->pValue) {
      64            0 :                 attr->ulValueLen = 3;
      65            0 :                 return CKR_OK;
      66              :         }
      67              : 
      68              :         /* Just the a sha1 of the value */
      69            0 :         gcry_md_hash_buffer (GCRY_MD_SHA1, buffer, self->value, self->n_value);
      70              : 
      71              :         /* Use the first three bytes */
      72            0 :         return gkm_attribute_set_data (attr, buffer, 3);
      73              : }
      74              : 
      75              : static GkmObject*
      76            1 : factory_create_generic_key (GkmSession *session, GkmTransaction *transaction,
      77              :                             CK_ATTRIBUTE_PTR attrs, CK_ULONG n_attrs)
      78              : {
      79              :         GkmGenericKey *key;
      80              :         GkmManager *manager;
      81              :         CK_ATTRIBUTE_PTR value;
      82              : 
      83            1 :         value = gkm_attributes_find (attrs, n_attrs, CKA_VALUE);
      84            1 :         if (value == NULL) {
      85            0 :                 gkm_transaction_fail (transaction, CKR_TEMPLATE_INCOMPLETE);
      86            0 :                 return NULL;
      87              :         }
      88              : 
      89            1 :         if (gkm_attributes_find (attrs, n_attrs, CKA_VALUE_LEN)) {
      90            0 :                 gkm_transaction_fail (transaction, CKR_TEMPLATE_INCONSISTENT);
      91            0 :                 return NULL;
      92              :         }
      93              : 
      94            1 :         manager = gkm_manager_for_template (attrs, n_attrs, session);
      95            1 :         key = g_object_new (GKM_TYPE_GENERIC_KEY,
      96              :                             "module", gkm_session_get_module (session),
      97              :                             "manager", manager,
      98              :                             NULL);
      99              : 
     100            1 :         key->value = egg_secure_alloc (value->ulValueLen);
     101            1 :         key->n_value = value->ulValueLen;
     102            1 :         memcpy (key->value, value->pValue, key->n_value);
     103              : 
     104            1 :         gkm_attribute_consume (value);
     105              : 
     106            1 :         gkm_session_complete_object_creation (session, transaction, GKM_OBJECT (key),
     107              :                                               TRUE, attrs, n_attrs);
     108            1 :         return GKM_OBJECT (key);
     109              : }
     110              : 
     111              : /* -----------------------------------------------------------------------------
     112              :  * OBJECT
     113              :  */
     114              : 
     115              : static CK_RV
     116            8 : gkm_generic_key_get_attribute (GkmObject *base, GkmSession *session, CK_ATTRIBUTE *attr)
     117              : {
     118            8 :         GkmGenericKey *self = GKM_GENERIC_KEY (base);
     119              : 
     120            8 :         switch (attr->type)
     121              :         {
     122            1 :         case CKA_KEY_TYPE:
     123            1 :                 return gkm_attribute_set_ulong (attr, CKK_GENERIC_SECRET);
     124              : 
     125            1 :         case CKA_DERIVE:
     126            1 :                 return gkm_attribute_set_bool (attr, CK_TRUE);
     127              : 
     128            0 :         case CKA_UNWRAP:
     129              :         case CKA_WRAP:
     130            0 :                 return gkm_attribute_set_bool (attr, CK_FALSE);
     131              : 
     132            0 :         case CKA_VALUE:
     133            0 :                 return gkm_attribute_set_data (attr, self->value, self->n_value);
     134              : 
     135            0 :         case CKA_VALUE_LEN:
     136            0 :                 return gkm_attribute_set_ulong (attr, self->n_value);
     137              : 
     138            0 :         case CKA_CHECK_VALUE:
     139            0 :                 return attribute_set_check_value (self, attr);
     140              : 
     141            2 :         case CKA_ALLOWED_MECHANISMS:
     142            2 :                 return gkm_attribute_set_data (attr, (CK_VOID_PTR)GKM_GENERIC_MECHANISMS,
     143              :                                                sizeof (GKM_GENERIC_MECHANISMS));
     144              :         };
     145              : 
     146            4 :         return GKM_OBJECT_CLASS (gkm_generic_key_parent_class)->get_attribute (base, session, attr);
     147              : }
     148              : 
     149              : static gconstpointer
     150            1 : gkm_generic_key_get_key_value (GkmSecretKey *key, gsize *n_value)
     151              : {
     152            1 :         GkmGenericKey *self = GKM_GENERIC_KEY (key);
     153            1 :         *n_value = self->n_value;
     154            1 :         return self->value;
     155              : }
     156              : 
     157              : static void
     158            1 : gkm_generic_key_init (GkmGenericKey *self)
     159              : {
     160              : 
     161            1 : }
     162              : 
     163              : static void
     164            1 : gkm_generic_key_finalize (GObject *obj)
     165              : {
     166            1 :         GkmGenericKey *self = GKM_GENERIC_KEY (obj);
     167              : 
     168            1 :         if (self->value) {
     169            1 :                 egg_secure_clear (self->value, self->n_value);
     170            1 :                 egg_secure_free (self->value);
     171            1 :                 self->value = NULL;
     172            1 :                 self->n_value = 0;
     173              :         }
     174              : 
     175            1 :         G_OBJECT_CLASS (gkm_generic_key_parent_class)->finalize (obj);
     176            1 : }
     177              : 
     178              : static void
     179            1 : gkm_generic_key_class_init (GkmGenericKeyClass *klass)
     180              : {
     181            1 :         GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
     182            1 :         GkmObjectClass *gkm_class = GKM_OBJECT_CLASS (klass);
     183            1 :         GkmSecretKeyClass *key_class = GKM_SECRET_KEY_CLASS (klass);
     184              : 
     185            1 :         gkm_generic_key_parent_class = g_type_class_peek_parent (klass);
     186              : 
     187            1 :         gobject_class->finalize = gkm_generic_key_finalize;
     188              : 
     189            1 :         gkm_class->get_attribute = gkm_generic_key_get_attribute;
     190              : 
     191            1 :         key_class->get_key_value = gkm_generic_key_get_key_value;
     192            1 : }
     193              : 
     194              : /* -----------------------------------------------------------------------------
     195              :  * PUBLIC
     196              :  */
     197              : 
     198              : GkmFactory*
     199          287 : gkm_generic_key_get_factory (void)
     200              : {
     201              :         static CK_OBJECT_CLASS klass = CKO_SECRET_KEY;
     202              :         static CK_KEY_TYPE type = CKK_GENERIC_SECRET;
     203              : 
     204              :         static CK_ATTRIBUTE attributes[] = {
     205              :                 { CKA_CLASS, &klass, sizeof (klass) },
     206              :                 { CKA_KEY_TYPE, &type, sizeof (type) }
     207              :         };
     208              : 
     209              :         static GkmFactory factory = {
     210              :                 attributes,
     211              :                 G_N_ELEMENTS (attributes),
     212              :                 factory_create_generic_key
     213              :         };
     214              : 
     215          287 :         return &factory;
     216              : }
        

Generated by: LCOV version 2.0-1