about summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorJames Booth <boothj5@gmail.com>2016-05-08 03:04:36 +0100
committerJames Booth <boothj5@gmail.com>2016-05-08 03:04:36 +0100
commitac3ab39e233f4a0eb4c4b08086d3d17bea860248 (patch)
tree4d49cc7af60c25519a2b8651cea640e2260b6959
parent29380a39cdea36615aa97b5a8d79b42f9535aaee (diff)
downloadprofani-tty-ac3ab39e233f4a0eb4c4b08086d3d17bea860248.tar.gz
Use hash table for disco features
-rw-r--r--src/xmpp/connection.c81
-rw-r--r--src/xmpp/connection.h2
-rw-r--r--src/xmpp/iq.c6
-rw-r--r--src/xmpp/xmpp.h6
4 files changed, 37 insertions, 58 deletions
diff --git a/src/xmpp/connection.c b/src/xmpp/connection.c
index a9f77a23..0d456102 100644
--- a/src/xmpp/connection.c
+++ b/src/xmpp/connection.c
@@ -61,7 +61,7 @@ typedef struct prof_conn_t {
     int priority;
     char *domain;
     GHashTable *available_resources;
-    GSList *disco_infos;
+    GHashTable *features_by_jid;
 } ProfConnection;
 
 static ProfConnection conn;
@@ -85,7 +85,7 @@ void connection_init(void)
     conn.xmpp_conn = NULL;
     conn.xmpp_ctx = NULL;
     conn.domain = NULL;
-    conn.disco_infos = NULL;
+    conn.features_by_jid = g_hash_table_new_full(g_str_hash, g_str_equal, free, (GDestroyNotify)g_hash_table_destroy);
     conn.available_resources = g_hash_table_new_full(g_str_hash, g_str_equal, free, (GDestroyNotify)resource_destroy);
 }
 
@@ -203,19 +203,10 @@ connection_get_fulljid(void)
     return xmpp_conn_get_jid(conn.xmpp_conn);
 }
 
-DiscoInfo*
-connection_get_disco_info(const char *const jid)
+GHashTable*
+connection_get_features(const char *const jid)
 {
-    GSList *curr = conn.disco_infos;
-    while (curr) {
-        DiscoInfo *disco_info = curr->data;
-        if (g_strcmp0(disco_info->jid, jid) == 0) {
-            return disco_info;
-        }
-        curr = g_slist_next(curr);
-    }
-
-    return NULL;
+    return g_hash_table_lookup(conn.features_by_jid, jid);
 }
 
 GList*
@@ -365,54 +356,52 @@ connection_send_stanza(const char *const stanza)
     }
 }
 
-static void
-_disco_info_destroy(DiscoInfo *info)
-{
-    if (info) {
-        free(info->jid);
-        if (info->features) {
-            g_hash_table_destroy(info->features);
-        }
-        free(info);
-    }
-}
-
 void
 connection_disco_items_free(void)
 {
-    g_slist_free_full(conn.disco_infos, (GDestroyNotify)_disco_info_destroy);
-    conn.disco_infos = NULL;
+    g_hash_table_destroy(conn.features_by_jid);
+    conn.features_by_jid = NULL;
 }
 
 gboolean
 connection_supports(const char *const feature)
 {
-    DiscoInfo *disco_info;
-    GSList *curr = conn.disco_infos;
+    GList *jids = g_hash_table_get_keys(conn.features_by_jid);
+
+    GList *curr = jids;
     while (curr) {
-        disco_info = curr->data;
-        if (g_hash_table_lookup_extended(disco_info->features, feature, NULL, NULL)) {
+        char *jid = curr->data;
+        GHashTable *features = g_hash_table_lookup(conn.features_by_jid, jid);
+        if (features && g_hash_table_lookup(features, feature)) {
             return TRUE;
         }
-        curr = g_slist_next(curr);
+
+        curr = g_list_next(curr);
     }
 
+    g_list_free(jids);
+
     return FALSE;
 }
 
 char*
 connection_jid_for_feature(const char *const feature)
 {
-    DiscoInfo *disco_info;
-    GSList *curr = conn.disco_infos;
+    GList *jids = g_hash_table_get_keys(conn.features_by_jid);
+
+    GList *curr = jids;
     while (curr) {
-        disco_info = curr->data;
-        if (g_hash_table_lookup_extended(disco_info->features, feature, NULL, NULL)) {
-            return disco_info->jid;
+        char *jid = curr->data;
+        GHashTable *features = g_hash_table_lookup(conn.features_by_jid, jid);
+        if (features && g_hash_table_lookup(features, feature)) {
+            return jid;
         }
-        curr = g_slist_next(curr);
+
+        curr = g_list_next(curr);
     }
 
+    g_list_free(jids);
+
     return NULL;
 }
 
@@ -422,11 +411,10 @@ connection_set_disco_items(GSList *items)
     GSList *curr = items;
     while (curr) {
         DiscoItem *item = curr->data;
-        DiscoInfo *info = malloc(sizeof(struct disco_info_t));
-        info->jid = strdup(item->jid);
-        info->features = g_hash_table_new_full(g_str_hash, g_str_equal, free, NULL);
-        conn.disco_infos = g_slist_append(conn.disco_infos, info);
-        iq_disco_info_request_onconnect(info->jid);
+        g_hash_table_insert(conn.features_by_jid, strdup(item->jid),
+            g_hash_table_new_full(g_str_hash, g_str_equal, free, NULL));
+
+        iq_disco_info_request_onconnect(item->jid);
 
         curr = g_slist_next(curr);
     }
@@ -446,10 +434,7 @@ _connection_handler(xmpp_conn_t *const xmpp_conn, const xmpp_conn_event_t status
         conn.domain = strdup(my_jid->domainpart);
         jid_destroy(my_jid);
 
-        DiscoInfo *info = malloc(sizeof(struct disco_info_t));
-        info->jid = strdup(conn.domain);
-        info->features = g_hash_table_new_full(g_str_hash, g_str_equal, free, NULL);
-        conn.disco_infos = g_slist_append(conn.disco_infos, info);
+        g_hash_table_insert(conn.features_by_jid, strdup(conn.domain), g_hash_table_new_full(g_str_hash, g_str_equal, free, NULL));
 
         session_login_success(connection_is_secured());
 
diff --git a/src/xmpp/connection.h b/src/xmpp/connection.h
index 1c5a2a4f..75022975 100644
--- a/src/xmpp/connection.h
+++ b/src/xmpp/connection.h
@@ -58,7 +58,7 @@ xmpp_conn_t* connection_get_conn(void);
 xmpp_ctx_t* connection_get_ctx(void);
 char *connection_get_domain(void);
 char* connection_jid_for_feature(const char *const feature);
-DiscoInfo* connection_get_disco_info(const char *const jid);
+GHashTable* connection_get_features(const char *const jid);
 
 void connection_add_available_resource(Resource *resource);
 void connection_remove_available_resource(const char *const resource);
diff --git a/src/xmpp/iq.c b/src/xmpp/iq.c
index fef714e2..c87b45a4 100644
--- a/src/xmpp/iq.c
+++ b/src/xmpp/iq.c
@@ -1903,8 +1903,8 @@ _disco_info_response_id_handler_onconnect(xmpp_stanza_t *const stanza, void *con
     xmpp_stanza_t *query = xmpp_stanza_get_child_by_name(stanza, STANZA_NAME_QUERY);
 
     if (query) {
-        DiscoInfo *disco_info = connection_get_disco_info(from);
-        if (disco_info == NULL) {
+        GHashTable *features = connection_get_features(from);
+        if (features == NULL) {
             log_error("No matching disco item found for %s", from);
             return 1;
         }
@@ -1915,7 +1915,7 @@ _disco_info_response_id_handler_onconnect(xmpp_stanza_t *const stanza, void *con
             if (g_strcmp0(stanza_name, STANZA_NAME_FEATURE) == 0) {
                 const char *var = xmpp_stanza_get_attribute(child, STANZA_ATTR_VAR);
                 if (var) {
-                    g_hash_table_add(disco_info->features, strdup(var));
+                    g_hash_table_add(features, strdup(var));
                 }
             }
             child = xmpp_stanza_get_next(child);
diff --git a/src/xmpp/xmpp.h b/src/xmpp/xmpp.h
index 8fca8ab5..167a4bbf 100644
--- a/src/xmpp/xmpp.h
+++ b/src/xmpp/xmpp.h
@@ -105,11 +105,6 @@ typedef struct disco_identity_t {
     char *category;
 } DiscoIdentity;
 
-typedef struct disco_info_t {
-    char *jid;
-    GHashTable *features;
-} DiscoInfo;
-
 void session_init(void);
 jabber_conn_status_t session_connect_with_details(const char *const jid, const char *const passwd,
     const char *const altdomain, const int port, const char *const tls_policy);
@@ -119,7 +114,6 @@ void session_shutdown(void);
 void session_process_events(int millis);
 char* session_get_account_name(void);
 
-
 jabber_conn_status_t connection_get_status(void);
 char *connection_get_presence_msg(void);
 const char* connection_get_fulljid(void);