From cbbb23c13fc9af4db366dc2799a3287e349dc852 Mon Sep 17 00:00:00 2001 From: djcb Date: Sun, 9 Dec 2012 13:48:22 +0200 Subject: [PATCH] =?UTF-8?q?*=20Fixes=20for=20the=20threading=20algorithm?= =?UTF-8?q?=20(thanks=20to=20Abd=C3=B3=20Roig)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The problem was that once a container got a parent, it did not change it anymore due to the child_elligible condition, but the parent might have been assigned from an incomplete References sequence. Now, we make sure the last reference gets to be the message's parent (following the JWZ's algorithm), reparenting the message if necessary. This makes sense, as the last parent-child relationship (between last ref and the message) is the most reliable piece of info here. Instead of child_elligible, we now only check that the new parent is not a descendant of the current message, to prevent making a loop. Everything else is fine, as it only moves a subtree around. --- lib/mu-container.c | 4 ++-- lib/mu-threader.c | 12 +++++++++++- 2 files changed, 13 insertions(+), 3 deletions(-) diff --git a/lib/mu-container.c b/lib/mu-container.c index 73587c92..c2a676a3 100644 --- a/lib/mu-container.c +++ b/lib/mu-container.c @@ -200,8 +200,8 @@ mu_container_remove_child (MuContainer *c, MuContainer *child) g_return_val_if_fail (c, NULL); g_return_val_if_fail (child, NULL); - g_assert (!child->child); - g_return_val_if_fail (!child->child, NULL); + /* g_assert (!child->child); */ + /* g_return_val_if_fail (!child->child, NULL); */ g_return_val_if_fail (c != child, NULL); c->child = mu_container_remove_sibling (c->child, child); diff --git a/lib/mu-threader.c b/lib/mu-threader.c index 5efc962f..46660831 100644 --- a/lib/mu-threader.c +++ b/lib/mu-threader.c @@ -285,8 +285,18 @@ handle_references (GHashTable *id_table, MuContainer *c) /* optimization: if the the message was newly added, it's by * definition not reachable yet */ - if (child_elligible (parent, c, created)) + + if (parent && c && !(c->child && mu_container_reachable (c->child, parent))) { + + /* if c already has a parent, remove c from its parent children + and reparent it, as now we know who is c's parent reliably */ + if (c->parent) { + mu_container_remove_child(c->parent, c); + c->next = c->last = c->parent = NULL; + } + parent = mu_container_append_children (parent, c); + } }