Package: trn4
Version: 4.0-test76-18
Tags: patch

If two articles have the same date but different subjects and
different article numbers, and the article numbers compare in the
opposite order to the subjects, it can be impossible to navigate to
some places in trn4's thread tree.  This is because the sibling
ordering of the articles in the tree is not stable, but depends on the
current article.  

So it can be that going "up" from B to its earlier sibling A causes
(after rethreading etc.) A to be rethreaded after B, so now you would
go "up" from A to B.  If there are even earlier siblings, they can be
unreachable (or at least difficult to reach).

It is IMO a bug that the thread tree capriciously rearranges itself
(at least, when all the articles are actually available etc. - there
are a lot of good reasons why rearranging the thread tree might be
necessary but it should be a convergent process and ideally should not
depend on the current article).

This patch fixes this particular rearrangement by extending the
partial order (on articles) implied by their dates into a complete
order by disambiguating on article number.  This ensures that the
articles, when rethreaded, are linked in in the same order each time.

I have chosen a single-line formatting of the if's in the comparison
function because IMO that makes the regularity easier to see.

Ian.

Only in ../trn4-4.0-test76: .config
Only in ../trn4-4.0-test76: .newsrc.test
Only in ../trn4-4.0-test76/HelpFiles/config: environment
Only in ../trn4-4.0-test76: Makefile
Only in ../trn4-4.0-test76: Pnews
Only in ../trn4-4.0-test76: Pnews.header
Only in ../trn4-4.0-test76: Policy.sh
Only in ../trn4-4.0-test76: Rnmail
Only in ../trn4-4.0-test76: Speller
Only in ../trn4-4.0-test76: access.def
Only in ../trn4-4.0-test76: all
Only in ../trn4-4.0-test76: config.h
Only in ../trn4-4.0-test76: config.sh
Only in ../trn4-4.0-test76/debian: trn4.debhelper.log
Only in ../trn4-4.0-test76: filexp
Only in ../trn4-4.0-test76: inews
Only in ../trn4-4.0-test76: makedepend
Only in ../trn4-4.0-test76: makedir
Only in ../trn4-4.0-test76: mbox.saver
Only in ../trn4-4.0-test76: mkpro
Only in ../trn4-4.0-test76: mktd
Only in ../trn4-4.0-test76: newsnews
Only in ../trn4-4.0-test76: nntplist
Only in ../trn4-4.0-test76: norm.saver
Only in ../trn4-4.0-test76: parsedate.c
diff '--exclude=*.o' -ru ../orig/trn4-4.0-test76/rt-process.c 
../trn4-4.0-test76/rt-process.c
--- ../orig/trn4-4.0-test76/rt-process.c        2000-06-04 09:33:17.000000000 
+0100
+++ ../trn4-4.0-test76/rt-process.c     2012-01-05 16:01:06.000000000 +0000
@@ -477,6 +477,25 @@
     }
 }
 
+/* Helper function for comparing article dates.  If the dates are
+** equal we compare article numbers.  This means that different
+** articles always compare as having different dates, and makes the
+** threading algorithm stable as to starting point.
+** Returns what Perl calls (left <=> right) ie -1 if left is before
+** right, +1 if after, 0 if same.
+*/
+static int
+compare_article_dates(left, right)
+register ARTICLE* left;
+register ARTICLE* right;
+{
+    if (left->date < right->date) return -1;
+    if (left->date > right->date) return +1;
+    if (left->num < right->num) return -1;
+    if (left->num > right->num) return +1;
+    return 0;
+}
+
 /* Link an article to its parent article.  If its parent pointer is zero,
 ** link it to its thread.  Sorts siblings by date.
 */
@@ -489,7 +508,7 @@
     if (!(ap = child->parent)) {
        register SUBJECT* sp = child->subj;
        ap = sp->thread;
-       if (!ap || child->date < ap->date) {
+       if (!ap || compare_article_dates(child, ap) < 0) {
            do {
                sp->thread = child;
                sp = sp->thread_link;
@@ -499,12 +518,13 @@
            goto sibling_search;
     } else {
        ap = ap->child1;
-       if (!ap || child->date < ap->date) {
+       if (!ap || compare_article_dates(child, ap) < 0) {
            child->sibling = ap;
            child->parent->child1 = child;
        } else {
          sibling_search:
-           while (ap->sibling && ap->sibling->date <= child->date)
+           while (ap->sibling &&
+                   compare_article_dates(ap->sibling, child) <= 0)
                ap = ap->sibling;
            child->sibling = ap->sibling;
            ap->sibling = child;
Only in ../trn4-4.0-test76: rt-process.c~
Only in ../trn4-4.0-test76: trn
Only in ../trn4-4.0-test76: trn-artchk
Only in ../trn4-4.0-test76: x.gdb
Only in ../trn4-4.0-test76: x.gdb~



-- 
To UNSUBSCRIBE, email to debian-bugs-dist-requ...@lists.debian.org
with a subject of "unsubscribe". Trouble? Contact listmas...@lists.debian.org

Reply via email to