summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog12
-rw-r--r--gp11/gp11-module.c49
-rw-r--r--gp11/gp11-object.c52
-rw-r--r--gp11/gp11-slot.c51
-rw-r--r--gp11/gp11.h15
-rw-r--r--gp11/tests/unit-test-gp11-module.c22
-rw-r--r--gp11/tests/unit-test-gp11-object.c31
-rw-r--r--gp11/tests/unit-test-gp11-slot.c27
8 files changed, 259 insertions, 0 deletions
diff --git a/ChangeLog b/ChangeLog
index 8d8de730..4e8579e6 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,6 +1,18 @@
2009-01-20 Stef Walter <stef@memberwebs.com>
* gp11/gp11.h:
+ * gp11/gp11-module.c:
+ * gp11/gp11-object.c:
+ * gp11/gp11-slot.c:
+ * gp11/tests/unit-test-gp11-module.c:
+ * gp11/tests/unit-test-gp11-object.c:
+ * gp11/tests/unit-test-gp11-slot.c: Add hash and equals functions for
+ PKCS#11 modules, slots, and objects. Allows them to be used in hash tables
+ and searches.
+
+2009-01-20 Stef Walter <stef@memberwebs.com>
+
+ * gp11/gp11.h:
* gp11/gp11-misc.c:
* gp11/gp11-module.c:
* gp11/gp11-private.h:
diff --git a/gp11/gp11-module.c b/gp11/gp11-module.c
index 07696819..04de6368 100644
--- a/gp11/gp11-module.c
+++ b/gp11/gp11-module.c
@@ -684,6 +684,55 @@ gp11_module_new (CK_FUNCTION_LIST_PTR funcs)
}
/**
+ * gp11_module_equal:
+ * @module1: A pointer to the first GP11Module
+ * @module2: A pointer to the second GP11Module
+ *
+ * Checks equality of two modules. Two GP11Module objects can point to the same
+ * underlying PKCS#11 module.
+ *
+ * Return value: TRUE if module1 and module2 are equal. FALSE if either is not a GP11Module.
+ **/
+gboolean
+gp11_module_equal (gconstpointer module1, gconstpointer module2)
+{
+ GP11ModuleData *data1, *data2;
+
+ if (module1 == module2)
+ return TRUE;
+ if (!GP11_IS_MODULE (module1) || !GP11_IS_MODULE (module2))
+ return FALSE;
+
+ data1 = GP11_MODULE_GET_DATA (module1);
+ data2 = GP11_MODULE_GET_DATA (module2);
+
+ return data1->funcs == data2->funcs;
+}
+
+/**
+ * gp11_module_hash:
+ * @module: A pointer to a GP11Module
+ *
+ * Create a hash value for the GP11Module.
+ *
+ * This function is intended for easily hashing a GP11Module to add to
+ * a GHashTable or similar data structure.
+ *
+ * Return value: An integer that can be used as a hash value, or 0 if invalid.
+ **/
+guint
+gp11_module_hash (gconstpointer module)
+{
+ GP11ModuleData *data;
+
+ g_return_val_if_fail (GP11_IS_MODULE (module), 0);
+
+ data = GP11_MODULE_GET_DATA (module);
+
+ return g_direct_hash (data->funcs);
+}
+
+/**
* gp11_module_get_info:
* @self: The module to get info for.
*
diff --git a/gp11/gp11-object.c b/gp11/gp11-object.c
index 2bf0770b..0c07d071 100644
--- a/gp11/gp11-object.c
+++ b/gp11/gp11-object.c
@@ -310,6 +310,58 @@ gp11_objects_from_handle_array (GP11Slot *slot, CK_OBJECT_HANDLE_PTR handles, CK
}
/**
+ * gp11_object_equal:
+ * @object1: A pointer to the first GP11Object
+ * @object2: A pointer to the second GP11Object
+ *
+ * Checks equality of two objects. Two GP11Object objects can point to the same
+ * underlying PKCS#11 object.
+ *
+ * Return value: TRUE if object1 and object2 are equal. FALSE if either is not a GP11Object.
+ **/
+gboolean
+gp11_object_equal (gconstpointer object1, gconstpointer object2)
+{
+ GP11ObjectData *data1, *data2;
+
+ if (object1 == object2)
+ return TRUE;
+ if (!GP11_IS_OBJECT (object1) || !GP11_IS_OBJECT (object2))
+ return FALSE;
+
+ data1 = GP11_OBJECT_GET_DATA (object1);
+ data2 = GP11_OBJECT_GET_DATA (object2);
+
+ return data1->handle == data2->handle &&
+ gp11_slot_equal (data1->slot, data2->slot);
+}
+
+/**
+ * gp11_object_hash:
+ * @object: A pointer to a GP11Object
+ *
+ * Create a hash value for the GP11Object.
+ *
+ * This function is intended for easily hashing a GP11Object to add to
+ * a GHashTable or similar data structure.
+ *
+ * Return value: An integer that can be used as a hash value, or 0 if invalid.
+ **/
+guint
+gp11_object_hash (gconstpointer object)
+{
+ GP11ObjectData *data;
+
+ g_return_val_if_fail (GP11_IS_OBJECT (object), 0);
+
+ data = GP11_OBJECT_GET_DATA (object);
+
+ return _gp11_ulong_hash (&data->handle) ^
+ gp11_slot_hash (data->slot);
+}
+
+
+/**
* gp11_object_get_handle:
* @self: The object.
*
diff --git a/gp11/gp11-slot.c b/gp11/gp11-slot.c
index 47974e38..d843f6e5 100644
--- a/gp11/gp11-slot.c
+++ b/gp11/gp11-slot.c
@@ -295,6 +295,57 @@ gp11_mechanisms_check (GP11Mechanisms *mechanisms, ...)
}
/**
+ * gp11_slot_equal:
+ * @slot1: A pointer to the first GP11Slot
+ * @slot2: A pointer to the second GP11Slot
+ *
+ * Checks equality of two slots. Two GP11Slot objects can point to the same
+ * underlying PKCS#11 slot.
+ *
+ * Return value: TRUE if slot1 and slot2 are equal. FALSE if either is not a GP11Slot.
+ **/
+gboolean
+gp11_slot_equal (gconstpointer slot1, gconstpointer slot2)
+{
+ GP11SlotData *data1, *data2;
+
+ if (slot1 == slot2)
+ return TRUE;
+ if (!GP11_IS_SLOT (slot1) || !GP11_IS_SLOT (slot2))
+ return FALSE;
+
+ data1 = GP11_SLOT_GET_DATA (slot1);
+ data2 = GP11_SLOT_GET_DATA (slot2);
+
+ return data1->handle == data2->handle &&
+ gp11_module_equal (data1->module, data2->module);
+}
+
+/**
+ * gp11_slot_hash:
+ * @slot: A pointer to a GP11Slot
+ *
+ * Create a hash value for the GP11Slot.
+ *
+ * This function is intended for easily hashing a GP11Slot to add to
+ * a GHashTable or similar data structure.
+ *
+ * Return value: An integer that can be used as a hash value, or 0 if invalid.
+ **/
+guint
+gp11_slot_hash (gconstpointer slot)
+{
+ GP11SlotData *data;
+
+ g_return_val_if_fail (GP11_IS_SLOT (slot), 0);
+
+ data = GP11_SLOT_GET_DATA (slot);
+
+ return _gp11_ulong_hash (&data->handle) ^
+ gp11_module_hash (data->module);
+}
+
+/**
* gp11_slot_get_handle:
* @self: The slot to get the handle of.
*
diff --git a/gp11/gp11.h b/gp11/gp11.h
index 17fae662..85098e0a 100644
--- a/gp11/gp11.h
+++ b/gp11/gp11.h
@@ -288,6 +288,11 @@ GP11Module* gp11_module_initialize (const gchar *path
gpointer reserved,
GError **err);
+gboolean gp11_module_equal (gconstpointer module1,
+ gconstpointer module2);
+
+guint gp11_module_hash (gconstpointer module);
+
const gchar* gp11_module_get_path (GP11Module *self);
CK_FUNCTION_LIST_PTR gp11_module_get_functions (GP11Module *self);
@@ -428,6 +433,11 @@ struct _GP11SlotClass {
GType gp11_slot_get_type (void) G_GNUC_CONST;
+gboolean gp11_slot_equal (gconstpointer slot1,
+ gconstpointer slot2);
+
+guint gp11_slot_hash (gconstpointer slot);
+
GP11Module* gp11_slot_get_module (GP11Slot *self);
CK_SLOT_ID gp11_slot_get_handle (GP11Slot *self);
@@ -1265,6 +1275,11 @@ GList* gp11_objects_from_handle_array (GP11Slot *slot,
CK_OBJECT_HANDLE_PTR handles,
CK_ULONG n_handles);
+gboolean gp11_object_equal (gconstpointer slot1,
+ gconstpointer slot2);
+
+guint gp11_object_hash (gconstpointer slot);
+
GP11Module* gp11_object_get_module (GP11Object *self);
GP11Slot* gp11_object_get_slot (GP11Object *self);
diff --git a/gp11/tests/unit-test-gp11-module.c b/gp11/tests/unit-test-gp11-module.c
index 63b15392..0d89d047 100644
--- a/gp11/tests/unit-test-gp11-module.c
+++ b/gp11/tests/unit-test-gp11-module.c
@@ -33,7 +33,29 @@ DEFINE_TEST(invalid_modules)
/* Shouldn't be able to load any file successfully */
invalid = gp11_module_initialize ("/usr/lib/libm.so", NULL, &err);
FAIL_RES (invalid, err);
+}
+DEFINE_TEST(module_equals_hash)
+{
+ GP11Module *other;
+ GObject *obj;
+ guint hash;
+
+ hash = gp11_module_hash (module);
+ g_assert (hash != 0);
+
+ g_assert (gp11_module_equal (module, module));
+
+ other = gp11_module_new (gp11_module_get_functions (module));
+ obj = g_object_new (G_TYPE_OBJECT, NULL);
+
+ g_assert (gp11_module_equal (module, other));
+
+ /* TODO: Could do with another test for inequality */
+ g_assert (!gp11_module_equal (module, obj));
+
+ g_object_unref (other);
+ g_object_unref (obj);
}
DEFINE_TEST(module_props)
diff --git a/gp11/tests/unit-test-gp11-object.c b/gp11/tests/unit-test-gp11-object.c
index 2345ddb4..f4fbc3be 100644
--- a/gp11/tests/unit-test-gp11-object.c
+++ b/gp11/tests/unit-test-gp11-object.c
@@ -58,6 +58,37 @@ DEFINE_TEST(object_props)
g_assert (handle == 2);
}
+DEFINE_TEST(object_equals_hash)
+{
+ GP11Slot *other_slot;
+ GP11Object *other_object;
+ GObject *obj;
+ guint hash;
+
+ hash = gp11_object_hash (object);
+ g_assert (hash != 0);
+
+ g_assert (gp11_object_equal (object, object));
+
+ other_slot = g_object_new (GP11_TYPE_SLOT, "module", module, "handle", 5895, NULL);
+ other_object = gp11_object_from_handle (other_slot, gp11_object_get_handle (object));
+ g_assert (!gp11_object_equal (object, other_object));
+ g_object_unref (other_slot);
+ g_object_unref (other_object);
+
+ obj = g_object_new (G_TYPE_OBJECT, NULL);
+ g_assert (!gp11_object_equal (object, obj));
+ g_object_unref (obj);
+
+ other_object = gp11_object_from_handle (slot, 383838);
+ g_assert (!gp11_object_equal (object, other_object));
+ g_object_unref (other_object);
+
+ other_object = gp11_object_from_handle (slot, gp11_object_get_handle (object));
+ g_assert (gp11_object_equal (object, other_object));
+ g_object_unref (other_object);
+}
+
static void
fetch_async_result (GObject *source, GAsyncResult *result, gpointer user_data)
{
diff --git a/gp11/tests/unit-test-gp11-slot.c b/gp11/tests/unit-test-gp11-slot.c
index c4fdedfb..dc431d39 100644
--- a/gp11/tests/unit-test-gp11-slot.c
+++ b/gp11/tests/unit-test-gp11-slot.c
@@ -99,6 +99,33 @@ DEFINE_TEST(slot_props)
g_object_unref (mod);
}
+DEFINE_TEST(slot_equals_hash)
+{
+ GP11Module *other_mod;
+ GP11Slot *other_slot;
+ GObject *obj;
+ guint hash;
+
+ hash = gp11_slot_hash (slot);
+ g_assert (hash != 0);
+
+ g_assert (gp11_slot_equal (slot, slot));
+
+ other_mod = gp11_module_new (gp11_module_get_functions (module));
+ other_slot = g_object_new (GP11_TYPE_SLOT, "module", other_mod, "handle", gp11_slot_get_handle (slot), NULL);
+ g_assert (gp11_slot_equal (slot, other_slot));
+ g_object_unref (other_mod);
+ g_object_unref (other_slot);
+
+ obj = g_object_new (G_TYPE_OBJECT, NULL);
+ g_assert (!gp11_slot_equal (slot, obj));
+ g_object_unref (obj);
+
+ other_slot = g_object_new (GP11_TYPE_SLOT, "module", module, "handle", 8909, NULL);
+ g_assert (!gp11_slot_equal (slot, obj));
+ g_object_unref (other_slot);
+}
+
DEFINE_TEST(slot_mechanisms)
{
GP11Mechanisms *mechs;