summaryrefslogtreecommitdiff
path: root/ckcapi-session.c
diff options
context:
space:
mode:
Diffstat (limited to 'ckcapi-session.c')
-rw-r--r--ckcapi-session.c168
1 files changed, 150 insertions, 18 deletions
diff --git a/ckcapi-session.c b/ckcapi-session.c
index dc700c1..1076fbd 100644
--- a/ckcapi-session.c
+++ b/ckcapi-session.c
@@ -1,10 +1,10 @@
#include <stdlib.h>
-#include "cryptoki-capi.h"
+#include "ckcapi.h"
typedef struct _SessionList {
- Session **list;
+ CkCapiSession **list;
size_t lmax;
} SessionList;
@@ -12,10 +12,10 @@ typedef struct _SessionList {
static SessionList the_sessions = { NULL, 0 };
-Session*
+CkCapiSession*
ckcapi_session_create(void)
{
- Session* sess = calloc(1, sizeof(Session));
+ CkCapiSession* sess = calloc(1, sizeof(CkCapiSession));
if(!sess)
return NULL;
@@ -31,7 +31,7 @@ ckcapi_session_create(void)
}
CK_RV
-ckcapi_session_register(Session* sess)
+ckcapi_session_register(CkCapiSession* sess)
{
CK_ULONG id = 0;
CK_RV ret = CKR_OK;
@@ -67,13 +67,13 @@ ckcapi_session_register(Session* sess)
/* Couldn't find a handle, reallocate */
if(id == 0)
{
- Session** buf;
+ CkCapiSession** buf;
size_t oldmax, newmax;
oldmax = the_sessions.lmax;
newmax = oldmax + 16;
- buf = realloc(the_sessions.list, newmax * sizeof(Session*));
+ buf = realloc(the_sessions.list, newmax * sizeof(CkCapiSession*));
if(!buf)
{
DBGS(sess, ("couldn't allocate session list, out of memory"));
@@ -116,7 +116,7 @@ ckcapi_session_register(Session* sess)
}
void
-ckcapi_session_destroy(Session* sess)
+ckcapi_session_destroy(CkCapiSession* sess)
{
ASSERT(sess);
ASSERT(sess->refs == 0);
@@ -141,10 +141,10 @@ ckcapi_session_destroy(Session* sess)
}
static CK_RV
-find_lock_ref_internal(SessionList* sessions, CK_SESSION_HANDLE id,
- int remove, Session** sess_ret)
+lock_ref_internal(SessionList* sessions, CK_SESSION_HANDLE id,
+ int remove, CkCapiSession** sess_ret)
{
- Session *sess;
+ CkCapiSession *sess;
DWORD r;
ASSERT(sessions);
@@ -185,7 +185,7 @@ find_lock_ref_internal(SessionList* sessions, CK_SESSION_HANDLE id,
}
}
- /* Lock the CallSession */
+ /* Lock the CallCkCapiSession */
r = WaitForSingleObject(sess->mutex, INFINITE);
ASSERT(r == WAIT_OBJECT_0);
@@ -225,7 +225,7 @@ find_lock_ref_internal(SessionList* sessions, CK_SESSION_HANDLE id,
}
CK_RV
-ckcapi_session_find_lock_ref(CK_ULONG id, int remove, Session **sess)
+ckcapi_session_get_lock_ref(CK_ULONG id, int remove, CkCapiSession **sess)
{
/* This must be called without any locks held */
@@ -241,7 +241,7 @@ ckcapi_session_find_lock_ref(CK_ULONG id, int remove, Session **sess)
ckcapi_lock_global();
- ret = find_lock_ref_internal (&the_sessions, id, remove, sess);
+ ret = lock_ref_internal (&the_sessions, id, remove, sess);
ckcapi_unlock_global();
@@ -249,9 +249,9 @@ ckcapi_session_find_lock_ref(CK_ULONG id, int remove, Session **sess)
}
void
-ckcapi_session_unref_unlock(Session* sess)
+ckcapi_session_unref_unlock(CkCapiSession* sess)
{
- /* The CallSession must be locked at this point */
+ /* The CallCkCapiSession must be locked at this point */
int refs;
BOOL r;
@@ -284,7 +284,7 @@ ckcapi_session_close_all()
/* This must be called without any locks held */
SessionList sessions;
- Session *sess;
+ CkCapiSession *sess;
size_t i;
CK_RV ret;
@@ -313,7 +313,7 @@ ckcapi_session_close_all()
if(!sessions.list[i])
continue;
- ret = find_lock_ref_internal (&sessions, i, 1, &sess);
+ ret = lock_ref_internal (&sessions, i, 1, &sess);
ASSERT(ret == CKR_OK);
ckcapi_session_unref_unlock(sess);
@@ -327,3 +327,135 @@ ckcapi_session_close_all()
}
}
+/* ----------------------------------------------------------------------------
+ * FIND OPERATION
+ */
+
+static BOOL
+get_ulong_attribute(CK_ATTRIBUTE_TYPE type, CK_ATTRIBUTE_PTR templ,
+ CK_ULONG count, CK_ULONG* val)
+{
+ CK_ULONG i;
+
+ ASSERT(val);
+ ASSERT(!count || templ);
+
+ for(i = 0; i < count; ++i)
+ {
+ if(templ[i].type == type)
+ {
+ *val = *((CK_ULONG*)templ[i].pValue);
+ return TRUE;
+ }
+ }
+
+ return FALSE;
+}
+
+static CK_RV
+gather_objects(CkCapiSession* sess, CK_ATTRIBUTE_PTR match,
+ CK_ULONG count, CkCapiArray* arr)
+{
+ CK_OBJECT_CLASS ocls = CK_INVALID_HANDLE;
+ CK_RV ret = CKR_OK;
+
+ get_ulong_attribute(CKA_CLASS, match, count, &ocls);
+ switch(ocls)
+ {
+ /* all different classes */
+ case CK_INVALID_HANDLE:
+ case CKO_CERTIFICATE:
+ ret = ckcapi_cert_find_all(sess, match, count, arr);
+ break;
+ case CKO_PUBLIC_KEY:
+ case CKO_PRIVATE_KEY:
+ default:
+ break;
+ };
+
+ return ret;
+}
+
+void
+cleanup_find_operation(CkCapiSession* sess)
+{
+ ASSERT(sess->operation_type == OPERATION_FIND);
+ if(sess->operation_data)
+ ckcapi_array_free((CkCapiArray*)sess->operation_data, TRUE);
+ sess->operation_type = OPERATION_NONE;
+ sess->operation_data = NULL;
+ sess->operation_cancel = NULL;
+}
+
+CK_RV
+ckcapi_session_find_init(CkCapiSession* sess, CK_ATTRIBUTE_PTR match,
+ CK_ULONG count)
+{
+ CkCapiArray* arr;
+ CK_RV ret;
+
+ ASSERT(sess);
+ ASSERT(!count || match);
+
+ if(sess->operation_type != OPERATION_NONE)
+ return CKR_OPERATION_ACTIVE;
+
+ arr = ckcapi_array_new(0, 1, sizeof(CK_OBJECT_HANDLE));
+ if(!arr)
+ return CKR_HOST_MEMORY;
+
+ ret = gather_objects(sess, match, count, arr);
+ if(ret != CKR_OK)
+ {
+ ckcapi_array_free(arr, TRUE);
+ return ret;
+ }
+
+ sess->operation_type = OPERATION_FIND;
+ sess->operation_data = arr;
+ sess->operation_cancel = cleanup_find_operation;
+
+ return CKR_OK;
+}
+
+CK_RV
+ckcapi_session_find(CkCapiSession* sess, CK_OBJECT_HANDLE_PTR objects,
+ CK_ULONG max_object_count, CK_ULONG_PTR object_count)
+{
+ CkCapiArray* arr;
+ size_t i;
+
+ ASSERT(sess);
+ ASSERT(object_count);
+ ASSERT(!max_object_count || objects);
+
+ if(sess->operation_type != OPERATION_FIND)
+ return CKR_OPERATION_NOT_INITIALIZED;
+
+ if(!max_object_count)
+ {
+ *object_count = 0;
+ return CKR_OK;
+ }
+
+ arr = (CkCapiArray*)sess->operation_data;
+ *object_count = (max_object_count > arr->len ? arr->len : max_object_count);
+ for(i = 0; i < *object_count; ++i)
+ objects[i] = ckcapi_array_index(arr, CK_OBJECT_HANDLE, i);
+ ckcapi_array_remove_range(arr, 0, *object_count);
+
+ return CKR_OK;
+}
+
+CK_RV
+ckcapi_session_find_final(CkCapiSession* sess)
+{
+ ASSERT(sess);
+
+ if(sess->operation_type != OPERATION_FIND)
+ return CKR_OPERATION_NOT_INITIALIZED;
+
+ cleanup_find_operation(sess);
+ return CKR_OK;
+}
+