refactor: optimize hash table iterations and fix security issues #58
All checks were successful
CI Code / Check spelling (pull_request) Successful in 21s
CI Code / Check coding style (pull_request) Successful in 36s
CI Code / Linux (arch) (pull_request) Successful in 10m15s
CI Code / Linux (ubuntu) (pull_request) Successful in 13m57s
CI Code / Linux (debian) (pull_request) Successful in 16m17s

- refactor(core): replace g_hash_table_get_keys with g_hash_table_iter_init
  * Eliminates temporary GList allocations
  * Improves iteration performance
  * Affected: connection.c, cmd_defs.c, cmd_funcs.c, omemo.c, gpg.c,
    disco.c, form.c, autocompleters.c, capabilities.c, callbacks.c

- fix(xmpp): correct queued_messages loop in connection.c:1031
  * Remove incorrect NULL check that prevented message storage
  * calloc zeros array, causing loop to skip immediately
  * Fixes dropped messages during reconnection with SM enabled

- fix(ui): prevent format string vulnerabilities in cons_show calls
  * Replace cons_show(variable) with cons_show("%s", variable)
  * Protects against format string attacks if variables contain %
  * Updated instances across cmd_funcs.c, connection.c, ox.c,
    console.c, core.c
This commit is contained in:
2025-11-10 18:51:16 +03:00
parent 33952c1331
commit b7a38f1e34
13 changed files with 143 additions and 177 deletions

View File

@@ -148,7 +148,7 @@ connection_init(void)
if (string_to_verbosity(v, &verbosity, &err_msg)) {
xmpp_ctx_set_verbosity(conn.xmpp_ctx, verbosity);
} else {
cons_show(err_msg);
cons_show("%s", err_msg);
}
conn.xmpp_conn = xmpp_conn_new(conn.xmpp_ctx);
@@ -635,22 +635,18 @@ gboolean
connection_supports(const char* const feature)
{
gboolean ret = FALSE;
GList* jids = g_hash_table_get_keys(conn.features_by_jid);
GHashTableIter iter;
gpointer key, value;
GList* curr = jids;
while (curr) {
char* jid = curr->data;
GHashTable* features = g_hash_table_lookup(conn.features_by_jid, jid);
g_hash_table_iter_init(&iter, conn.features_by_jid);
while (g_hash_table_iter_next(&iter, &key, &value)) {
GHashTable* features = (GHashTable*)value;
if (features && g_hash_table_lookup(features, feature)) {
ret = TRUE;
break;
}
curr = g_list_next(curr);
}
g_list_free(jids);
return ret;
}
@@ -661,22 +657,17 @@ connection_jid_for_feature(const char* const feature)
return NULL;
}
GList* jids = g_hash_table_get_keys(conn.features_by_jid);
GHashTableIter iter;
gpointer key, value;
GList* curr = jids;
while (curr) {
char* jid = curr->data;
GHashTable* features = g_hash_table_lookup(conn.features_by_jid, jid);
g_hash_table_iter_init(&iter, conn.features_by_jid);
while (g_hash_table_iter_next(&iter, &key, &value)) {
GHashTable* features = (GHashTable*)value;
if (features && g_hash_table_lookup(features, feature)) {
g_list_free(jids);
return jid;
return (const char*)key;
}
curr = g_list_next(curr);
}
g_list_free(jids);
return NULL;
}
@@ -1028,7 +1019,7 @@ _connection_handler(xmpp_conn_t* const xmpp_conn, const xmpp_conn_event_t status
conn.sm_state = xmpp_conn_get_sm_state(conn.xmpp_conn);
if (send_queue_len > 0 && prefs_get_boolean(PREF_STROPHE_SM_RESEND)) {
conn.queued_messages = calloc(send_queue_len + 1, sizeof(*conn.queued_messages));
for (int n = 0; n < send_queue_len && conn.queued_messages[n]; ++n) {
for (int n = 0; n < send_queue_len; ++n) {
conn.queued_messages[n] = xmpp_conn_send_queue_drop_element(conn.xmpp_conn, XMPP_QUEUE_OLDEST);
}
} else if (send_queue_len > 0) {
@@ -1183,12 +1174,13 @@ connection_debug_print_features()
continue;
}
GList* feature_keys = g_hash_table_get_keys(features);
for (GList* l = feature_keys; l != NULL; l = l->next) {
const char* feature = (const char*)l->data;
GHashTableIter feature_iter;
gpointer feature_key, feature_value;
g_hash_table_iter_init(&feature_iter, features);
while (g_hash_table_iter_next(&feature_iter, &feature_key, &feature_value)) {
const char* feature = (const char*)feature_key;
log_debug("%s:\t%s", jid, feature);
}
g_list_free(feature_keys);
}
log_debug("=== End of Features ===");