mirror of
https://git.jabber.space/devs/cproof.git
synced 2026-08-01 14:16:21 +00:00
fix(export): hash stanza_id with content instead of trusting it as sole dedup key
This commit is contained in:
@@ -90,18 +90,21 @@ _close_temp_sqlite(int opened)
|
|||||||
// =========================================================================
|
// =========================================================================
|
||||||
|
|
||||||
// Returns a g_strdup'd key — callers free with g_free (gchar* convention).
|
// Returns a g_strdup'd key — callers free with g_free (gchar* convention).
|
||||||
|
//
|
||||||
|
// stanza_id is mixed into the hash but is NOT used as the sole key, since
|
||||||
|
// some clients (older Pidgin, Adium) reuse incremental ids per session and
|
||||||
|
// servers echo them back unchanged. Trusting stanza_id alone silently drops
|
||||||
|
// legitimate distinct messages on collision. By hashing id + timestamp +
|
||||||
|
// from_jid + body together we preserve id as a disambiguator without making
|
||||||
|
// it a single point of failure: true exact duplicates still dedup, but two
|
||||||
|
// messages that share an id with different content (or different timestamps)
|
||||||
|
// stay distinct.
|
||||||
static gchar*
|
static gchar*
|
||||||
_make_dedup_key(const char* stanza_id, const char* timestamp, const char* from_jid, const char* body)
|
_make_dedup_key(const char* stanza_id, const char* timestamp, const char* from_jid, const char* body)
|
||||||
{
|
{
|
||||||
if (stanza_id && stanza_id[0] != '\0')
|
|
||||||
return g_strdup(stanza_id);
|
|
||||||
|
|
||||||
// Fallback for messages without stanza-id: SHA-256 over the FULL body,
|
|
||||||
// not the first 256 bytes. The previous prefix-only hash collided on
|
|
||||||
// legitimate near-identical templates (signatures, code blocks, paste-
|
|
||||||
// bombs) — second occurrence was silently dropped on import. Hashing
|
|
||||||
// whole body is microseconds of extra work per row.
|
|
||||||
GChecksum* sum = g_checksum_new(G_CHECKSUM_SHA256);
|
GChecksum* sum = g_checksum_new(G_CHECKSUM_SHA256);
|
||||||
|
g_checksum_update(sum, (const guchar*)(stanza_id ? stanza_id : ""), -1);
|
||||||
|
g_checksum_update(sum, (const guchar*)"|", 1);
|
||||||
g_checksum_update(sum, (const guchar*)(timestamp ? timestamp : ""), -1);
|
g_checksum_update(sum, (const guchar*)(timestamp ? timestamp : ""), -1);
|
||||||
g_checksum_update(sum, (const guchar*)"|", 1);
|
g_checksum_update(sum, (const guchar*)"|", 1);
|
||||||
g_checksum_update(sum, (const guchar*)(from_jid ? from_jid : ""), -1);
|
g_checksum_update(sum, (const guchar*)(from_jid ? from_jid : ""), -1);
|
||||||
|
|||||||
Reference in New Issue
Block a user