Commit 4fa0719d authored by Daiki Ueno's avatar Daiki Ueno

Merge branch 'wip/header-order' into 'master'

Don't assume iterating a hash table will give items in the same order they were inserted

Closes #21

See merge request !9
parents 7a2a4a26 7aba0e6a
Pipeline #54753 passed with stages
in 41 minutes and 36 seconds
...@@ -59,6 +59,8 @@ EGG_SECURE_DECLARE (armor); ...@@ -59,6 +59,8 @@ EGG_SECURE_DECLARE (armor);
#define ARMOR_PREF_END "-----END " #define ARMOR_PREF_END "-----END "
#define ARMOR_PREF_END_L 9 #define ARMOR_PREF_END_L 9
static const gchar * const ORDERED_HEADERS[] = { "Proc-Type", "DEK-Info", NULL };
static void static void
parse_header_lines (const gchar *hbeg, parse_header_lines (const gchar *hbeg,
const gchar *hend, const gchar *hend,
...@@ -336,13 +338,16 @@ egg_armor_parse (GBytes *data, ...@@ -336,13 +338,16 @@ egg_armor_parse (GBytes *data,
} }
static void static void
append_each_header (gpointer key, gpointer value, gpointer user_data) append_each_header (gconstpointer key, gconstpointer value, gpointer user_data)
{ {
GString *string = (GString*)user_data; GString *string = (GString*)user_data;
g_string_append (string, (gchar*)key); if (g_strv_contains (ORDERED_HEADERS, (const gchar *) key))
return;
g_string_append (string, (const gchar *)key);
g_string_append (string, ": "); g_string_append (string, ": ");
g_string_append (string, (gchar*)value); g_string_append (string, (const gchar *)value);
g_string_append_c (string, '\n'); g_string_append_c (string, '\n');
} }
...@@ -357,6 +362,7 @@ egg_armor_write (const guchar *data, ...@@ -357,6 +362,7 @@ egg_armor_write (const guchar *data,
gint state, save; gint state, save;
gsize i, length; gsize i, length;
gsize n_prefix, estimate; gsize n_prefix, estimate;
gchar *value;
g_return_val_if_fail (data || !n_data, NULL); g_return_val_if_fail (data || !n_data, NULL);
g_return_val_if_fail (type, NULL); g_return_val_if_fail (type, NULL);
...@@ -370,9 +376,19 @@ egg_armor_write (const guchar *data, ...@@ -370,9 +376,19 @@ egg_armor_write (const guchar *data,
g_string_append_len (string, ARMOR_SUFF, ARMOR_SUFF_L); g_string_append_len (string, ARMOR_SUFF, ARMOR_SUFF_L);
g_string_append_c (string, '\n'); g_string_append_c (string, '\n');
/* The headers */ /* The headers. Some must come in a specific order. */
for (i = 0; ORDERED_HEADERS[i] != NULL; i++) {
value = g_hash_table_lookup (headers, ORDERED_HEADERS[i]);
if (value != NULL)
g_string_append_printf (string,
"%s: %s\n",
ORDERED_HEADERS[i],
value);
}
/* And the rest we output in any arbitrary order. */
if (headers && g_hash_table_size (headers) > 0) { if (headers && g_hash_table_size (headers) > 0) {
g_hash_table_foreach (headers, append_each_header, string); g_hash_table_foreach (headers, (GHFunc) append_each_header, string);
g_string_append_c (string, '\n'); g_string_append_c (string, '\n');
} }
......
...@@ -72,6 +72,7 @@ typedef struct _Session { ...@@ -72,6 +72,7 @@ typedef struct _Session {
static guint unique_identifier = 100; static guint unique_identifier = 100;
static GHashTable *the_sessions = NULL; static GHashTable *the_sessions = NULL;
static GHashTable *the_objects = NULL; static GHashTable *the_objects = NULL;
static GSList *the_objects_list = NULL;
static GArray *the_credential_template = NULL; static GArray *the_credential_template = NULL;
enum { enum {
...@@ -102,6 +103,39 @@ lookup_object (Session *session, CK_OBJECT_HANDLE hObject) ...@@ -102,6 +103,39 @@ lookup_object (Session *session, CK_OBJECT_HANDLE hObject)
return attrs; return attrs;
} }
typedef struct {
guint handle;
GArray *template; /* owned by the_objects */
} ObjectData;
static gint
list_find_handle (gconstpointer l, gconstpointer r)
{
guint handle;
ObjectData *item;
handle = GPOINTER_TO_UINT (r);
item = (ObjectData *) l;
if (item->handle == handle)
return 0;
return -1;
}
static void
insert_template (guint handle, GArray *template)
{
ObjectData *data;
data = g_new0 (ObjectData, 1);
data->handle = handle;
data->template = template;
g_hash_table_insert (the_objects, GUINT_TO_POINTER (handle), template);
the_objects_list = g_slist_append (the_objects_list, data);
}
CK_OBJECT_HANDLE CK_OBJECT_HANDLE
gkm_mock_module_take_object (GArray *template) gkm_mock_module_take_object (GArray *template)
{ {
...@@ -115,7 +149,7 @@ gkm_mock_module_take_object (GArray *template) ...@@ -115,7 +149,7 @@ gkm_mock_module_take_object (GArray *template)
g_return_val_if_fail (token == TRUE, 0); g_return_val_if_fail (token == TRUE, 0);
else else
gkm_template_set_boolean (template, CKA_TOKEN, CK_TRUE); gkm_template_set_boolean (template, CKA_TOKEN, CK_TRUE);
g_hash_table_insert (the_objects, GUINT_TO_POINTER (handle), template); insert_template (handle, template);
return handle; return handle;
} }
...@@ -127,14 +161,16 @@ gkm_mock_module_enumerate_objects (CK_SESSION_HANDLE handle, GkmMockEnumerator f ...@@ -127,14 +161,16 @@ gkm_mock_module_enumerate_objects (CK_SESSION_HANDLE handle, GkmMockEnumerator f
gpointer key; gpointer key;
gpointer value; gpointer value;
Session *session; Session *session;
ObjectData *data;
GSList *l = NULL;
g_assert (the_objects); g_assert (the_objects);
g_assert (func); g_assert (func);
/* Token objects */ /* Token objects */
g_hash_table_iter_init (&iter, the_objects); for (l = the_objects_list; l != NULL; l = l->next) {
while (g_hash_table_iter_next (&iter, &key, &value)) { data = (ObjectData *) l->data;
if (!(func) (GPOINTER_TO_UINT (key), value, user_data)) if (!(func) (data->handle, data->template, user_data))
return; return;
} }
...@@ -267,7 +303,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs) ...@@ -267,7 +303,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs)
attrs = gkm_template_new (NULL, 0); attrs = gkm_template_new (NULL, 0);
gkm_template_set_ulong (attrs, CKA_CLASS, CKO_DATA); gkm_template_set_ulong (attrs, CKA_CLASS, CKO_DATA);
gkm_template_set_string (attrs, CKA_LABEL, "TEST LABEL"); gkm_template_set_string (attrs, CKA_LABEL, "TEST LABEL");
g_hash_table_insert (the_objects, GUINT_TO_POINTER (2), attrs); insert_template (2, attrs);
/* Private capitalize key */ /* Private capitalize key */
value = CKM_MOCK_CAPITALIZE; value = CKM_MOCK_CAPITALIZE;
...@@ -282,7 +318,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs) ...@@ -282,7 +318,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs)
gkm_template_set_boolean (attrs, CKA_DERIVE, CK_TRUE); gkm_template_set_boolean (attrs, CKA_DERIVE, CK_TRUE);
gkm_template_set_string (attrs, CKA_VALUE, "value"); gkm_template_set_string (attrs, CKA_VALUE, "value");
gkm_template_set_string (attrs, CKA_GNOME_UNIQUE, "unique1"); gkm_template_set_string (attrs, CKA_GNOME_UNIQUE, "unique1");
g_hash_table_insert (the_objects, GUINT_TO_POINTER (PRIVATE_KEY_CAPITALIZE), attrs); insert_template (PRIVATE_KEY_CAPITALIZE, attrs);
/* Public capitalize key */ /* Public capitalize key */
value = CKM_MOCK_CAPITALIZE; value = CKM_MOCK_CAPITALIZE;
...@@ -294,7 +330,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs) ...@@ -294,7 +330,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs)
gkm_template_set_boolean (attrs, CKA_PRIVATE, CK_FALSE); gkm_template_set_boolean (attrs, CKA_PRIVATE, CK_FALSE);
gkm_template_set_string (attrs, CKA_VALUE, "value"); gkm_template_set_string (attrs, CKA_VALUE, "value");
gkm_template_set_string (attrs, CKA_GNOME_UNIQUE, "unique2"); gkm_template_set_string (attrs, CKA_GNOME_UNIQUE, "unique2");
g_hash_table_insert (the_objects, GUINT_TO_POINTER (PUBLIC_KEY_CAPITALIZE), attrs); insert_template (PUBLIC_KEY_CAPITALIZE, attrs);
/* Private prefix key */ /* Private prefix key */
value = CKM_MOCK_PREFIX; value = CKM_MOCK_PREFIX;
...@@ -307,7 +343,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs) ...@@ -307,7 +343,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs)
gkm_template_set_boolean (attrs, CKA_ALWAYS_AUTHENTICATE, CK_TRUE); gkm_template_set_boolean (attrs, CKA_ALWAYS_AUTHENTICATE, CK_TRUE);
gkm_template_set_string (attrs, CKA_VALUE, "value"); gkm_template_set_string (attrs, CKA_VALUE, "value");
gkm_template_set_string (attrs, CKA_GNOME_UNIQUE, "unique3"); gkm_template_set_string (attrs, CKA_GNOME_UNIQUE, "unique3");
g_hash_table_insert (the_objects, GUINT_TO_POINTER (PRIVATE_KEY_PREFIX), attrs); insert_template (PRIVATE_KEY_PREFIX, attrs);
/* Private prefix key */ /* Private prefix key */
value = CKM_MOCK_PREFIX; value = CKM_MOCK_PREFIX;
...@@ -319,7 +355,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs) ...@@ -319,7 +355,7 @@ gkm_mock_C_Initialize (CK_VOID_PTR pInitArgs)
gkm_template_set_boolean (attrs, CKA_PRIVATE, CK_FALSE); gkm_template_set_boolean (attrs, CKA_PRIVATE, CK_FALSE);
gkm_template_set_string (attrs, CKA_VALUE, "value"); gkm_template_set_string (attrs, CKA_VALUE, "value");
gkm_template_set_string (attrs, CKA_GNOME_UNIQUE, "unique4"); gkm_template_set_string (attrs, CKA_GNOME_UNIQUE, "unique4");
g_hash_table_insert (the_objects, GUINT_TO_POINTER (PUBLIC_KEY_PREFIX), attrs); insert_template (PUBLIC_KEY_PREFIX, attrs);
initialized = TRUE; initialized = TRUE;
return CKR_OK; return CKR_OK;
...@@ -336,6 +372,9 @@ gkm_mock_C_Finalize (CK_VOID_PTR pReserved) ...@@ -336,6 +372,9 @@ gkm_mock_C_Finalize (CK_VOID_PTR pReserved)
g_hash_table_destroy (the_objects); g_hash_table_destroy (the_objects);
the_objects = NULL; the_objects = NULL;
g_slist_free_full (the_objects_list, g_free);
the_objects_list = NULL;
g_hash_table_destroy (the_sessions); g_hash_table_destroy (the_sessions);
the_sessions = NULL; the_sessions = NULL;
...@@ -802,7 +841,7 @@ gkm_mock_C_CreateObject (CK_SESSION_HANDLE hSession, CK_ATTRIBUTE_PTR pTemplate, ...@@ -802,7 +841,7 @@ gkm_mock_C_CreateObject (CK_SESSION_HANDLE hSession, CK_ATTRIBUTE_PTR pTemplate,
*phObject = ++unique_identifier; *phObject = ++unique_identifier;
if (gkm_template_find_boolean (attrs, CKA_TOKEN, &token) && token) if (gkm_template_find_boolean (attrs, CKA_TOKEN, &token) && token)
g_hash_table_insert (the_objects, GUINT_TO_POINTER (*phObject), attrs); insert_template (*phObject, attrs);
else else
g_hash_table_insert (session->objects, GUINT_TO_POINTER (*phObject), attrs); g_hash_table_insert (session->objects, GUINT_TO_POINTER (*phObject), attrs);
...@@ -822,6 +861,7 @@ gkm_mock_C_DestroyObject (CK_SESSION_HANDLE hSession, CK_OBJECT_HANDLE hObject) ...@@ -822,6 +861,7 @@ gkm_mock_C_DestroyObject (CK_SESSION_HANDLE hSession, CK_OBJECT_HANDLE hObject)
{ {
GArray *attrs; GArray *attrs;
Session *session; Session *session;
GSList *list;
gboolean priv; gboolean priv;
session = g_hash_table_lookup (the_sessions, GUINT_TO_POINTER (hSession)); session = g_hash_table_lookup (the_sessions, GUINT_TO_POINTER (hSession));
...@@ -836,6 +876,13 @@ gkm_mock_C_DestroyObject (CK_SESSION_HANDLE hSession, CK_OBJECT_HANDLE hObject) ...@@ -836,6 +876,13 @@ gkm_mock_C_DestroyObject (CK_SESSION_HANDLE hSession, CK_OBJECT_HANDLE hObject)
} }
g_hash_table_remove (the_objects, GUINT_TO_POINTER (hObject)); g_hash_table_remove (the_objects, GUINT_TO_POINTER (hObject));
do {
list = g_slist_find_custom (the_objects_list, GUINT_TO_POINTER (hObject), list_find_handle);
if (list != NULL) {
g_free (list->data);
the_objects_list = g_slist_delete_link (the_objects_list, list);
}
} while (list != NULL);
g_hash_table_remove (session->objects, GUINT_TO_POINTER (hObject)); g_hash_table_remove (session->objects, GUINT_TO_POINTER (hObject));
return CKR_OK; return CKR_OK;
......
...@@ -214,9 +214,9 @@ gkm_secret_fields_serialize (CK_ATTRIBUTE_PTR attr, ...@@ -214,9 +214,9 @@ gkm_secret_fields_serialize (CK_ATTRIBUTE_PTR attr,
GHashTable *fields, GHashTable *fields,
const gchar *schema_name) const gchar *schema_name)
{ {
GHashTableIter iter; GList *l, *keys;
gboolean saw_schema = FALSE; gboolean saw_schema = FALSE;
gpointer key; const gchar *key;
gpointer value; gpointer value;
GString *result; GString *result;
CK_RV rv; CK_RV rv;
...@@ -224,10 +224,15 @@ gkm_secret_fields_serialize (CK_ATTRIBUTE_PTR attr, ...@@ -224,10 +224,15 @@ gkm_secret_fields_serialize (CK_ATTRIBUTE_PTR attr,
g_assert (attr != NULL); g_assert (attr != NULL);
g_assert (fields != NULL); g_assert (fields != NULL);
keys = g_hash_table_get_keys (fields);
keys = g_list_sort (keys, (GCompareFunc) g_strcmp0);
if (!attr->pValue) { if (!attr->pValue) {
attr->ulValueLen = 0; attr->ulValueLen = 0;
g_hash_table_iter_init (&iter, fields); for (l = keys; l != NULL; l = l->next) {
while (g_hash_table_iter_next (&iter, &key, &value)) { key = (const gchar *) l->data;
value = g_hash_table_lookup (fields, key);
if (g_str_equal (key, GKM_SECRET_FIELD_SCHEMA)) if (g_str_equal (key, GKM_SECRET_FIELD_SCHEMA))
saw_schema = TRUE; saw_schema = TRUE;
attr->ulValueLen += strlen (key); attr->ulValueLen += strlen (key);
...@@ -239,12 +244,14 @@ gkm_secret_fields_serialize (CK_ATTRIBUTE_PTR attr, ...@@ -239,12 +244,14 @@ gkm_secret_fields_serialize (CK_ATTRIBUTE_PTR attr,
attr->ulValueLen += strlen (schema_name); attr->ulValueLen += strlen (schema_name);
attr->ulValueLen += 2; attr->ulValueLen += 2;
} }
g_list_free (keys);
return CKR_OK; return CKR_OK;
} }
result = g_string_sized_new (256); result = g_string_sized_new (256);
g_hash_table_iter_init (&iter, fields); for (l = keys; l != NULL; l = l->next) {
while (g_hash_table_iter_next (&iter, &key, &value)) { key = (const gchar *) l->data;
value = g_hash_table_lookup (fields, key);
if (g_str_equal (key, GKM_SECRET_FIELD_SCHEMA)) if (g_str_equal (key, GKM_SECRET_FIELD_SCHEMA))
saw_schema = TRUE; saw_schema = TRUE;
g_string_append (result, key); g_string_append (result, key);
...@@ -261,6 +268,7 @@ gkm_secret_fields_serialize (CK_ATTRIBUTE_PTR attr, ...@@ -261,6 +268,7 @@ gkm_secret_fields_serialize (CK_ATTRIBUTE_PTR attr,
rv = gkm_attribute_set_data (attr, result->str, result->len); rv = gkm_attribute_set_data (attr, result->str, result->len);
g_string_free (result, TRUE); g_string_free (result, TRUE);
g_list_free (keys);
return rv; return rv;
} }
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment