[glib-networking/wip/tingping/pkcs11-2: 2/2] fixup! b2e8104fda64aea32ddae319a87f33772609718f



commit ed03c192fc56ab52d7ea414f02fd2fa05f816984
Author: Patrick Griffis <pgriffis igalia com>
Date:   Wed Jul 31 13:18:13 2019 -0700

    fixup! b2e8104fda64aea32ddae319a87f33772609718f

 tls/gnutls/gtlscertificate-gnutls.c |  28 ++------
 tls/gnutls/gtlsconnection-gnutls.c  |  72 ++++++++++++++++++-
 tls/tests/certificate.c             |   4 +-
 tls/tests/connection.c              |   7 ++
 tls/tests/meson.build               |   2 +-
 tls/tests/mock-pkcs11.c             | 137 +++++++++++++++++++++++-------------
 6 files changed, 175 insertions(+), 75 deletions(-)
---
diff --git a/tls/gnutls/gtlscertificate-gnutls.c b/tls/gnutls/gtlscertificate-gnutls.c
index c33755b..e32a6b5 100644
--- a/tls/gnutls/gtlscertificate-gnutls.c
+++ b/tls/gnutls/gtlscertificate-gnutls.c
@@ -162,16 +162,6 @@ g_tls_certificate_gnutls_get_property (GObject    *object,
     }
 }
 
-static int callback (void *userdata, int attempt,
-                                      const char *token_url,
-                                      const char *token_label,
-                                      unsigned int flags,
-                                      char *pin, size_t pin_max)
-{
-  // TODO
-  return -1;
-}
-
 static void
 g_tls_certificate_gnutls_set_property (GObject      *object,
                                        guint         prop_id,
@@ -324,8 +314,6 @@ static void
 g_tls_certificate_gnutls_init (GTlsCertificateGnutls *gnutls)
 {
   gnutls_x509_crt_init (&gnutls->cert);
-  // gnutls_x509_crt_set_pin_function ();
-  // gnutls_privkey_set_pin_function ()
 }
 
 static gboolean
@@ -527,29 +515,21 @@ g_tls_certificate_gnutls_copy  (GTlsCertificateGnutls  *gnutls,
   if (gnutls->key)
     {
       gnutls_x509_privkey_t x509_privkey;
-      gnutls_privkey_t privkey;
 
-      gnutls_privkey_init (&privkey);
       gnutls_privkey_export_x509 (gnutls->key, &x509_privkey);
-      gnutls_privkey_import_x509 (privkey, x509_privkey, GNUTLS_PRIVKEY_IMPORT_COPY);
+      gnutls_privkey_import_x509 (*pkey, x509_privkey, GNUTLS_PRIVKEY_IMPORT_COPY);
       gnutls_x509_privkey_deinit (x509_privkey);
-
-      *pkey = privkey;
     }
   else if (gnutls->pkcs11_key_uri != NULL)
     {
-      gnutls_privkey_t privkey;
-      gnutls_privkey_init (&privkey);
-      gnutls_privkey_set_pin_function (privkey, callback, NULL);
       int status;
-      
-      status = gnutls_privkey_import_pkcs11_url (privkey, gnutls->pkcs11_key_uri);
-      g_debug ("Copying PKCS #11 private key result: %s", gnutls_strerror (status));
 
-      *pkey = privkey;
+      status = gnutls_privkey_import_pkcs11_url (*pkey, gnutls->pkcs11_key_uri);
+      g_debug ("Copying PKCS #11 private key result: %s", gnutls_strerror (status));
     }
   else
     {
+      gnutls_privkey_deinit (*pkey);
       *pkey = NULL;
     }
 }
diff --git a/tls/gnutls/gtlsconnection-gnutls.c b/tls/gnutls/gtlsconnection-gnutls.c
index 4e883a7..a4d5931 100644
--- a/tls/gnutls/gtlsconnection-gnutls.c
+++ b/tls/gnutls/gtlsconnection-gnutls.c
@@ -280,6 +280,70 @@ g_tls_connection_gnutls_get_session (GTlsConnectionGnutls *gnutls)
   return priv->session;
 }
 
+static int callback (void *userdata,
+                     int attempt,
+                     const char *token_url,
+                     const char *token_label,
+                     unsigned int callback_flags,
+                     char *pin,
+                     size_t pin_max)
+{
+  GTlsConnection *connection = G_TLS_CONNECTION (userdata);
+  GTlsInteraction *interaction = g_tls_connection_get_interaction (connection);
+  GTlsInteractionResult result;
+  GTlsPassword *password;
+  GTlsPasswordFlags password_flags = 0;
+  GError *error = NULL;
+  gchar *description;
+  int ret = -1;
+
+  if (interaction == NULL)
+    return -1;
+
+  // FIXME: Mock module isn't triggering this codepath?
+  if (callback_flags & GNUTLS_PIN_WRONG)
+    password_flags |= G_TLS_PASSWORD_RETRY;
+  if (callback_flags & GNUTLS_PIN_COUNT_LOW)
+    password_flags |= G_TLS_PASSWORD_MANY_TRIES;
+  if (callback_flags & GNUTLS_PIN_FINAL_TRY || attempt > 5) /* Give up at some point */
+    password_flags |= G_TLS_PASSWORD_FINAL_TRY;
+
+  description = g_strdup_printf (_("PIN for PKCS #11 token: %s (%s)"), token_label, token_url);
+  password = g_tls_password_new (password_flags, description);
+  // FIXME: Cancellation
+  result = g_tls_interaction_invoke_ask_password (interaction, password, NULL, &error);
+  g_free (description);
+
+  g_message("RESULT %d", result);
+  switch (result)
+    {
+    case G_TLS_INTERACTION_FAILED:
+      if (!g_error_matches (error, G_IO_ERROR, G_IO_ERROR_CANCELLED))
+        g_warning ("Error getting PIN: %s", error->message);
+      g_error_free (error);
+      break;
+    case G_TLS_INTERACTION_UNHANDLED:
+      break;
+    case G_TLS_INTERACTION_HANDLED:
+      {
+        size_t password_size;
+        const guchar *password_data = g_tls_password_get_value (password, &password_size);
+        if (password_size > pin_max)
+          g_warning ("PIN is larger than max PIN size");
+
+        memcpy (pin, password_data, MIN (password_size, pin_max));
+        ret = GNUTLS_E_SUCCESS;
+        break;
+      }
+    default:
+      g_assert_not_reached ();
+    }
+
+  g_object_unref (password);
+
+  return ret;
+}
+
 void
 g_tls_connection_gnutls_get_certificate (GTlsConnectionGnutls  *gnutls,
                                          gnutls_pcert_st      **pcert,
@@ -293,9 +357,15 @@ g_tls_connection_gnutls_get_certificate (GTlsConnectionGnutls  *gnutls,
 
   if (cert)
     {
+      /* Send along a pre-initialized privkey so we can handle the callback here */
+      gnutls_privkey_t privkey;
+      gnutls_privkey_init (&privkey);
+      gnutls_privkey_set_pin_function (privkey, callback, gnutls); // FXIME: Ensure gnutls is a valid object
+
       g_tls_certificate_gnutls_copy (G_TLS_CERTIFICATE_GNUTLS (cert),
                                      priv->interaction_id,
-                                     pcert, pcert_length, pkey);
+                                     pcert, pcert_length, &privkey);
+      *pkey = privkey;
     }
   else
     {
diff --git a/tls/tests/certificate.c b/tls/tests/certificate.c
index ce5739e..63adc10 100644
--- a/tls/tests/certificate.c
+++ b/tls/tests/certificate.c
@@ -259,8 +259,8 @@ test_create_certificate_pkcs11 (TestCertificate *test,
   GError *error = NULL;
 
   cert = g_initable_new (test->cert_gtype, NULL, &error,
-                         "pkcs11-certificate-uri", 
"pkcs11:model=mock;manufacturer=GLib-Networking;serial=1;token=Mock%20Certificate;id=%4D%6F%63%6B%20%43%65%72%74%69%66%69%63%61%74%65;object=Mock%20Certificate;type=cert",
-                         "pkcs11-private-key-uri", 
"pkcs11:model=mock;manufacturer=GLib-Networking;serial=1;token=Mock%20Certificate;id=%4D%6F%63%6B%20%50%72%69%76%61%74%65%20%4B%65%79;object=Mock%20Private%20Key;type=private",
+                         "pkcs11-certificate-uri", 
"pkcs11:model=mock;token=Mock%20Certificate;object=Mock%20Certificate;type=cert",
+                         "pkcs11-private-key-uri", 
"pkcs11:model=mock;token=Mock%20Certificate;object=Mock%20Private%20Key;type=private",
                          NULL);
 
   g_assert_no_error (error);
diff --git a/tls/tests/connection.c b/tls/tests/connection.c
index e99df3e..dda3ce5 100644
--- a/tls/tests/connection.c
+++ b/tls/tests/connection.c
@@ -1068,17 +1068,21 @@ test_client_auth_pkcs11_connection (TestConnection *test,
   GTlsCertificate *peer;
   gboolean cas_changed;
   GSocketClient *client;
+  GTlsInteraction *interaction;
 
   test->database = g_tls_file_database_new (tls_test_file_path ("ca-roots.pem"), &error);
   g_assert_no_error (error);
   g_assert_nonnull (test->database);
 
+  interaction = mock_interaction_new_static_password ("ABC123");
+
   connection = start_async_server_and_connect_to_it (test, G_TLS_AUTHENTICATION_REQUIRED);
   test->client_connection = g_tls_client_connection_new (connection, test->identity, &error);
   g_assert_no_error (error);
   g_assert_nonnull (test->client_connection);
   g_object_unref (connection);
 
+  g_tls_connection_set_interaction (G_TLS_CONNECTION (test->client_connection), interaction);
   g_tls_connection_set_database (G_TLS_CONNECTION (test->client_connection), test->database);
 
   cert = g_tls_certificate_new_from_pkcs11_uris 
("pkcs11:model=mock;manufacturer=GLib-Networking;token=Mock%20Certificate;object=Mock%20Certificate;type=cert",
@@ -1123,6 +1127,7 @@ test_client_auth_pkcs11_connection (TestConnection *test,
   g_assert_nonnull (test->client_connection);
   g_object_unref (connection);
 
+  g_tls_connection_set_interaction (G_TLS_CONNECTION (test->client_connection), interaction);
   g_tls_client_connection_set_validation_flags (G_TLS_CLIENT_CONNECTION (test->client_connection),
                                                 0);
   cert = g_tls_certificate_new_from_pkcs11_uris 
("pkcs11:model=mock;manufacturer=GLib-Networking;token=Mock%20Certificate;object=Mock%20Certificate%202;type=cert",
@@ -1144,6 +1149,8 @@ test_client_auth_pkcs11_connection (TestConnection *test,
   peer = g_tls_connection_get_peer_certificate (G_TLS_CONNECTION (test->server_connection));
   g_assert_nonnull (peer);
   g_assert_true (g_tls_certificate_is_same (peer, cert));
+
+  g_object_unref (interaction);
 #endif
 }
 
diff --git a/tls/tests/meson.build b/tls/tests/meson.build
index 46f6b29..729a9cd 100644
--- a/tls/tests/meson.build
+++ b/tls/tests/meson.build
@@ -32,7 +32,7 @@ mock_pkcs11_module = shared_module('mock-pkcs11',
 )
 
 test_programs = [
-  ['certificate', [], deps, [], []],
+  ['certificate', [], deps, [], [mock_pkcs11_module]],
   ['file-database', [], deps, [], []],
   ['connection', ['mock-interaction.c'], deps, [], [mock_pkcs11_module]],
 # DTLS tests are disabled until we fix https://gitlab.gnome.org/GNOME/glib-networking/issues/49
diff --git a/tls/tests/mock-pkcs11.c b/tls/tests/mock-pkcs11.c
index c3a8820..1e749f4 100644
--- a/tls/tests/mock-pkcs11.c
+++ b/tls/tests/mock-pkcs11.c
@@ -49,6 +49,8 @@
 
 #define MOCK_MANUFACTURER_ID "GLib-Networking"
 #define MOCK_MODEL "mock"
+#define PKCS11_MOCK_CK_TOKEN_INFO_MAX_PIN_LEN 256
+#define PKCS11_MOCK_CK_TOKEN_INFO_MIN_PIN_LEN 4
 
 static CK_INFO mock_info = {
         .cryptokiVersion = { CRYPTOKI_VERSION_MAJOR, CRYPTOKI_VERSION_MINOR },
@@ -73,7 +75,8 @@ static MockObject mock_objects[] = {
                         .label = "Mock Certificate",
                         .serialNumber = "1",
                         .manufacturerID = MOCK_MANUFACTURER_ID,
-                        .flags = CKF_TOKEN_INITIALIZED | CKF_WRITE_PROTECTED,
+                        // FIXME: Login seems to be per-slot not per-object
+                        .flags = CKF_TOKEN_INITIALIZED | CKF_WRITE_PROTECTED | CKF_LOGIN_REQUIRED | 
CKF_USER_PIN_INITIALIZED,
                         .ulMaxSessionCount = 1,
                 },
         },
@@ -84,8 +87,10 @@ static MockObject mock_objects[] = {
                         .label = "Mock Private Key",
                         .serialNumber = "2",
                         .manufacturerID = MOCK_MANUFACTURER_ID,
-                        .flags = CKF_TOKEN_INITIALIZED | CKF_WRITE_PROTECTED | CKF_LOGIN_REQUIRED,
+                        .flags = CKF_TOKEN_INITIALIZED | CKF_WRITE_PROTECTED | CKF_LOGIN_REQUIRED | 
CKF_USER_PIN_INITIALIZED,
                         .ulMaxSessionCount = 1,
+                        .ulMaxPinLen = PKCS11_MOCK_CK_TOKEN_INFO_MAX_PIN_LEN,
+                        .ulMinPinLen = PKCS11_MOCK_CK_TOKEN_INFO_MIN_PIN_LEN,
                 },
         },
         {
@@ -95,8 +100,10 @@ static MockObject mock_objects[] = {
                         .label = "Mock Private Key 2",
                         .serialNumber = "3",
                         .manufacturerID = MOCK_MANUFACTURER_ID,
-                        .flags = CKF_TOKEN_INITIALIZED | CKF_WRITE_PROTECTED | CKF_LOGIN_REQUIRED,
+                        .flags = CKF_TOKEN_INITIALIZED | CKF_WRITE_PROTECTED | CKF_LOGIN_REQUIRED | 
CKF_USER_PIN_INITIALIZED,
                         .ulMaxSessionCount = 1,
+                        .ulMaxPinLen = PKCS11_MOCK_CK_TOKEN_INFO_MAX_PIN_LEN,
+                        .ulMinPinLen = PKCS11_MOCK_CK_TOKEN_INFO_MIN_PIN_LEN,
                 },
         },
         {
@@ -133,15 +140,7 @@ static const MockSlot mock_slots[] = {
 #define PKCS11_MOCK_CK_OBJECT_HANDLE_SECRET_KEY 2
 #define PKCS11_MOCK_CK_OBJECT_HANDLE_PUBLIC_KEY 3
 #define PKCS11_MOCK_CK_OBJECT_HANDLE_PRIVATE_KEY 4
-#define PKCS11_MOCK_CK_SLOT_ID 1
-
-
-#define PKCS11_MOCK_CK_TOKEN_INFO_LABEL "Mock"
-#define PKCS11_MOCK_CK_TOKEN_INFO_MANUFACTURER_ID "GLib"
-#define PKCS11_MOCK_CK_TOKEN_INFO_MODEL "Mock token"
-#define PKCS11_MOCK_CK_TOKEN_INFO_SERIAL_NUMBER "0123456789A"
-#define PKCS11_MOCK_CK_TOKEN_INFO_MAX_PIN_LEN 256
-#define PKCS11_MOCK_CK_TOKEN_INFO_MIN_PIN_LEN 4
+#define PKCS11_MOCK_CK_SLOT_ID 0
 
 #define PKCS11_MOCK_CK_SESSION_ID 1
 
@@ -172,6 +171,8 @@ static CK_ULONG pkcs11_mock_sign_key = 0;
 static CK_LONG mock_search_template_class = PKCS11_MOCK_CKO_ANYTHING;
 static char *mock_search_template_label;
 static CK_ULONG mock_search_iterator = 0;
+static gboolean mock_logged_in_state = FALSE;
+static size_t mock_login_attempts = 0;
 
 static CK_FUNCTION_LIST pkcs11_mock_functions = 
 {
@@ -436,7 +437,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_GetSlotInfo)(CK_SLOT_ID slotID, CK_SLOT_INFO_PTR pIn
 
 CK_DEFINE_FUNCTION(CK_RV, C_GetTokenInfo)(CK_SLOT_ID slotID, CK_TOKEN_INFO_PTR pInfo)
 {
-        g_debug ("C_GetTokenInfo");
+        g_debug ("C_GetTokenInfo %lu", slotID);
         if (CK_FALSE == pkcs11_mock_initialized)
                 return CKR_CRYPTOKI_NOT_INITIALIZED;
 
@@ -446,13 +447,13 @@ CK_DEFINE_FUNCTION(CK_RV, C_GetTokenInfo)(CK_SLOT_ID slotID, CK_TOKEN_INFO_PTR p
         if (NULL == pInfo)
                 return CKR_ARGUMENTS_BAD;
 
-        CK_TOKEN_INFO token = mock_objects[0].info;
+        CK_TOKEN_INFO token = mock_objects[slotID].info;
 
         copy_padded_string(pInfo->label, token.label, sizeof(pInfo->label));
         copy_padded_string(pInfo->manufacturerID, token.manufacturerID, sizeof(pInfo->manufacturerID));
         copy_padded_string(pInfo->serialNumber, token.serialNumber, sizeof(pInfo->serialNumber));
         copy_padded_string(pInfo->model, token.model, sizeof(pInfo->model));
-        pInfo->flags = token.flags; // CKF_TOKEN_INITIALIZED; //CKF_RNG | CKF_LOGIN_REQUIRED | 
CKF_USER_PIN_INITIALIZED | CKF_TOKEN_INITIALIZED;
+        pInfo->flags = token.flags;
         pInfo->ulMaxSessionCount = token.ulMaxSessionCount;
         pInfo->ulSessionCount = (CK_TRUE == pkcs11_mock_session_opened) ? 1 : 0;
         pInfo->ulMaxRwSessionCount = token.ulMaxRwSessionCount;
@@ -467,13 +468,19 @@ CK_DEFINE_FUNCTION(CK_RV, C_GetTokenInfo)(CK_SLOT_ID slotID, CK_TOKEN_INFO_PTR p
         pInfo->firmwareVersion = token.firmwareVersion;
         memset(pInfo->utcTime, ' ', sizeof(pInfo->utcTime));
 
+        // FIXME: Not picked up by gnutls
+        if (mock_login_attempts > 2)
+        {
+                pInfo->flags |= CKF_USER_PIN_COUNT_LOW;
+        }
+
         return CKR_OK;
 }
 
 
 CK_DEFINE_FUNCTION(CK_RV, C_GetMechanismList)(CK_SLOT_ID slotID, CK_MECHANISM_TYPE_PTR pMechanismList, 
CK_ULONG_PTR pulCount)
 {
-        g_message ("C_GetMechanismList");
+        g_debug ("C_GetMechanismList");
         if (CK_FALSE == pkcs11_mock_initialized)
                 return CKR_CRYPTOKI_NOT_INITIALIZED;
 
@@ -805,9 +812,9 @@ CK_DEFINE_FUNCTION(CK_RV, C_SetOperationState)(CK_SESSION_HANDLE hSession, CK_BY
 
 CK_DEFINE_FUNCTION(CK_RV, C_Login)(CK_SESSION_HANDLE hSession, CK_USER_TYPE userType, CK_UTF8CHAR_PTR pPin, 
CK_ULONG ulPinLen)
 {
-        CK_RV rv = CKR_OK;
+        // CK_RV rv = CKR_OK;
 
-        g_debug ("C_Login");
+        g_debug ("C_Login %lu %s", userType, pPin);
 
         if (CK_FALSE == pkcs11_mock_initialized)
                 return CKR_CRYPTOKI_NOT_INITIALIZED;
@@ -815,7 +822,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_Login)(CK_SESSION_HANDLE hSession, CK_USER_TYPE user
         if ((CK_FALSE == pkcs11_mock_session_opened) || (PKCS11_MOCK_CK_SESSION_ID != hSession))
                 return CKR_SESSION_HANDLE_INVALID;
 
-        if ((CKU_SO != userType) && (CKU_USER != userType))
+        if ((CKU_SO != userType) && (CKU_USER != userType) && (CKU_CONTEXT_SPECIFIC != userType))
                 return CKR_USER_TYPE_INVALID;
 
         if (NULL == pPin)
@@ -824,38 +831,60 @@ CK_DEFINE_FUNCTION(CK_RV, C_Login)(CK_SESSION_HANDLE hSession, CK_USER_TYPE user
         if ((ulPinLen < PKCS11_MOCK_CK_TOKEN_INFO_MIN_PIN_LEN) || (ulPinLen > 
PKCS11_MOCK_CK_TOKEN_INFO_MAX_PIN_LEN))
                 return CKR_PIN_LEN_RANGE;
 
-        switch (pkcs11_mock_session_state)
+        // FIXME: gnutls bug? It calls this before an operation
+        // if (pkcs11_mock_active_operation == PKCS11_MOCK_CK_OPERATION_NONE && CKU_CONTEXT_SPECIFIC != 
userType)
+        //         return CKR_OPERATION_NOT_INITIALIZED;
+
+        if (mock_logged_in_state == TRUE)
+                return CKR_USER_ALREADY_LOGGED_IN;
+
+        // More hardcoding
+        const char *password = "ABC123";
+        if (ulPinLen == strlen (password) && strncmp ((char*)pPin, password, ulPinLen) == 0)
         {
-                case CKS_RO_PUBLIC_SESSION:
+                mock_logged_in_state = TRUE;
+                mock_login_attempts = 0;
+                return CKR_OK;
+        }
+        else
+        {
+                mock_login_attempts += 1;
+                return CKR_PIN_INCORRECT;
+        }
 
-                        if (CKU_SO == userType)
-                                rv = CKR_SESSION_READ_ONLY_EXISTS;
-                        else
-                                pkcs11_mock_session_state = CKS_RO_USER_FUNCTIONS;
+        // TODO: We don't test any of these states atm
+        // switch (pkcs11_mock_session_state)
+        // {
+        //         case CKS_RO_PUBLIC_SESSION:
 
-                        break;
+        //                 if (CKU_SO == userType)
+        //                         rv = CKR_SESSION_READ_ONLY_EXISTS;
+        //                 else
+        //                         pkcs11_mock_session_state = CKS_RO_USER_FUNCTIONS;
 
-                case CKS_RO_USER_FUNCTIONS:
-                case CKS_RW_USER_FUNCTIONS:
+        //                 break;
 
-                        rv = (CKU_SO == userType) ? CKR_USER_ANOTHER_ALREADY_LOGGED_IN : 
CKR_USER_ALREADY_LOGGED_IN;
+        //         case CKS_RO_USER_FUNCTIONS:
+        //         case CKS_RW_USER_FUNCTIONS:
 
-                        break;
+        //                 rv = (CKU_SO == userType) ? CKR_USER_ANOTHER_ALREADY_LOGGED_IN : 
CKR_USER_ALREADY_LOGGED_IN;
 
-                case CKS_RW_PUBLIC_SESSION:
+        //                 break;
 
-                        pkcs11_mock_session_state = (CKU_SO == userType) ? CKS_RW_SO_FUNCTIONS : 
CKS_RW_USER_FUNCTIONS;
+        //         case CKS_RW_PUBLIC_SESSION:
 
-                        break;
+        //                 pkcs11_mock_session_state = (CKU_SO == userType) ? CKS_RW_SO_FUNCTIONS : 
CKS_RW_USER_FUNCTIONS;
 
-                case CKS_RW_SO_FUNCTIONS:
+        //                 break;
 
-                        rv = (CKU_SO == userType) ? CKR_USER_ALREADY_LOGGED_IN : 
CKR_USER_ANOTHER_ALREADY_LOGGED_IN;
+        //         case CKS_RW_SO_FUNCTIONS:
 
-                        break;
-        }
+        //                 rv = (CKU_SO == userType) ? CKR_USER_ALREADY_LOGGED_IN : 
CKR_USER_ANOTHER_ALREADY_LOGGED_IN;
 
-        return rv;
+        //                 break;
+        // }
+
+        // return rv;
 }
 
 
@@ -869,9 +898,14 @@ CK_DEFINE_FUNCTION(CK_RV, C_Logout)(CK_SESSION_HANDLE hSession)
         if ((CK_FALSE == pkcs11_mock_session_opened) || (PKCS11_MOCK_CK_SESSION_ID != hSession))
                 return CKR_SESSION_HANDLE_INVALID;
 
-        if ((pkcs11_mock_session_state == CKS_RO_PUBLIC_SESSION) || (pkcs11_mock_session_state == 
CKS_RW_PUBLIC_SESSION))
+        if (mock_logged_in_state == FALSE)
                 return CKR_USER_NOT_LOGGED_IN;
 
+        // if ((pkcs11_mock_session_state == CKS_RO_PUBLIC_SESSION) || (pkcs11_mock_session_state == 
CKS_RW_PUBLIC_SESSION))
+        //         return CKR_USER_NOT_LOGGED_IN;
+
+        mock_logged_in_state =  FALSE;
+
         return CKR_OK;
 }
 
@@ -1050,15 +1084,12 @@ CK_DEFINE_FUNCTION(CK_RV, C_GetAttributeValue)(CK_SESSION_HANDLE hSession, CK_OB
                         
                         int status;
                         gnutls_datum_t data;
-                        gnutls_x509_dn_t dn;
+                        gnutls_x509_dn_t dn; /* Owned by cert */
 
-                        gnutls_x509_dn_init(&dn);
-                        gnutls_x509_crt_get_subject(obj.cert, &dn);
+                        status = gnutls_x509_crt_get_subject(obj.cert, &dn);
+                        g_assert(status == GNUTLS_E_SUCCESS);
                         status = gnutls_x509_dn_get_str(dn, &data);
                         g_assert(status == GNUTLS_E_SUCCESS);
-                        gnutls_x509_dn_deinit(dn);
-
-                        g_debug("SUBJECT: %s", data.data);
 
                         if (data.size > pTemplate[i].ulValueLen)
                         {
@@ -1109,6 +1140,16 @@ CK_DEFINE_FUNCTION(CK_RV, C_GetAttributeValue)(CK_SESSION_HANDLE hSession, CK_OB
                         if (NULL != pTemplate[i].pValue)
                                 *((CK_ULONG *) pTemplate[i].pValue) = obj.object_class;
                         pTemplate[i].ulValueLen = sizeof (obj.object_class);
+                }
+                 else if (CKA_CERTIFICATE_TYPE == pTemplate[i].type)
+                {
+                        CK_CERTIFICATE_TYPE ret = CKC_X_509;
+
+                       if (pTemplate[i].ulValueLen != sizeof(CK_CERTIFICATE_TYPE))
+                               return CKR_ARGUMENTS_BAD;
+
+                        /* TODO: Test both TRUE and FALSE */
+                       memcpy(pTemplate[i].pValue, &ret, sizeof(CK_CERTIFICATE_TYPE));
                 }
                else if (CKA_KEY_TYPE == pTemplate[i].type)
                {
@@ -1150,7 +1191,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_GetAttributeValue)(CK_SESSION_HANDLE hSession, CK_OB
                         /* TODO: Test both TRUE and FALSE */
                        memcpy(pTemplate[i].pValue, &ret, sizeof(CK_BBOOL));
                }
-               else if (CKA_MODULUS == pTemplate[i].type && obj.object_class == CKO_PRIVATE_KEY) /* Any key 
type in future */
+               else if (CKA_MODULUS == pTemplate[i].type && obj.object_class == CKO_PRIVATE_KEY)
                {
                         /* Hardcode RSA for now */
                         gnutls_datum_t modulus;
@@ -1248,7 +1289,7 @@ CK_DEFINE_FUNCTION(CK_RV, C_FindObjectsInit)(CK_SESSION_HANDLE hSession, CK_ATTR
         if ((CK_FALSE == pkcs11_mock_session_opened) || (PKCS11_MOCK_CK_SESSION_ID != hSession))
                 return CKR_SESSION_HANDLE_INVALID;
 
-        if (NULL == pTemplate)
+        if (NULL == pTemplate && ulCount != 0)
                 return CKR_ARGUMENTS_BAD;
 
         mock_search_template_class = PKCS11_MOCK_CKO_ANYTHING;
@@ -2004,6 +2045,8 @@ CK_DEFINE_FUNCTION(CK_RV, C_Sign)(CK_SESSION_HANDLE hSession, CK_BYTE_PTR pData,
         if (NULL == pulSignatureLen)
                 return CKR_ARGUMENTS_BAD;
 
+        // TODO: Handle user not logged in
+
         const gnutls_datum_t data = {
                 .data = pData,
                 .size = ulDataLen,


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]