summaryrefslogtreecommitdiffabout
authorSergey Poznyakoff <gray@gnu.org>2020-10-01 15:51:06 (GMT)
committer Sergey Poznyakoff <gray@gnu.org>2020-10-01 15:56:48 (GMT)
commit3cab87f05d8a4bbb80198ecb24308f6d21642119 (patch) (side-by-side diff)
tree8e375afa88a653e2fe90debc3bc884dacfe60745
parent7ab9bfa2000ccf02449b12af4d3d8d383db9cab3 (diff)
downloadmailutils-3cab87f05d8a4bbb80198ecb24308f6d21642119.tar.gz
mailutils-3cab87f05d8a4bbb80198ecb24308f6d21642119.tar.bz2
Improve message comparison routine for maildir.
* libproto/maildir/mbox.c (maildir_message_cmp): Compare seconds, microseconds and number of deliveries, in that order. If all match (shouldn't happen), resort to lexicographical comparison.
Diffstat (more/less context) (ignore whitespace changes)
-rw-r--r--libproto/maildir/mbox.c68
1 files changed, 47 insertions, 21 deletions
diff --git a/libproto/maildir/mbox.c b/libproto/maildir/mbox.c
index bed89e9..a550e51 100644
--- a/libproto/maildir/mbox.c
+++ b/libproto/maildir/mbox.c
@@ -134,41 +134,67 @@ maildir_name_info_ptr (char *name)
return p + 3;
return NULL;
}
-
+/*
+ * Compare two maildir messages A and B. The purpose is to determine
+ * which one was delivered prior to another.
+ *
+ * Compare seconds, microseconds and number of deliveries, in that
+ * order. If all match (shouldn't happen), resort to lexicographical
+ * comparison.
+ */
static int
maildir_message_cmp (struct _amd_message *a, struct _amd_message *b)
{
- char *name_a, *name_b;
- unsigned long na = strtoul (((struct _maildir_message *) a)->file_name,
- &name_a, 10);
- unsigned long nb = strtoul (((struct _maildir_message *) b)->file_name,
- &name_b, 10);
- int rc;
+ char *name_a = ((struct _maildir_message *) a)->file_name;
+ char *name_b = ((struct _maildir_message *) b)->file_name;
+ char *pa, *pb;
+ unsigned long la, lb;
+ int d;
- if (na > nb)
+ la = strtoul (name_a, &name_a, 10);
+ lb = strtoul (name_b, &name_b, 10);
+
+ if (la > lb)
return 1;
- if (na < nb)
+ if (la < lb)
return -1;
- /* If timestamps are equal, compare rests of the filenames up to the
- info marker */
+ if ((d = (*name_a - *name_b)) != 0)
+ return d;
+
+ name_a++;
+ name_b++;
- if (name_a && !name_b)
- return 1;
- else if (!name_a)
+ if ((pa = strchr (name_a, 'M')) != 0 && (pb = strchr (name_b, 'M')) != 0)
{
- if (name_b)
+ la = strtoul (name_a, &name_a, 10);
+ lb = strtoul (name_b, &name_b, 10);
+
+ if (la > lb)
+ return 1;
+ if (la < lb)
return -1;
- else
- return 0;
}
-
+
+ if ((pa = strchr (name_a, 'Q')) != 0 && (pb = strchr (name_b, 'Q')) != 0)
+ {
+ la = strtoul (name_a, &name_a, 10);
+ lb = strtoul (name_b, &name_b, 10);
+
+ if (la > lb)
+ return 1;
+ if (la < lb)
+ return -1;
+ }
+
for (; *name_a && *name_a != ':' && *name_b && *name_b != ':';
name_a++, name_b++)
- if ((rc = (*name_a - *name_b)))
- return rc;
-
+ {
+ if ((d = (*name_a - *name_b)) != 0)
+ return d;
+ }
+
if ((*name_a == ':' || *name_a == 0) && (*name_b == ':' || *name_b == 0))
return 0;

Return to:

Send suggestions and report system problems to the System administrator.