diff options
author | wiz <wiz@pkgsrc.org> | 2016-10-06 16:27:15 +0000 |
---|---|---|
committer | wiz <wiz@pkgsrc.org> | 2016-10-06 16:27:15 +0000 |
commit | 9eb0776e1451e7ecdc516b681e974444e984b60b (patch) | |
tree | 5839ffb9dec9dd8d2135e9157138ea47184e85a4 | |
parent | 6face2c96a2d1633afeb5249f28c72371db7a604 (diff) | |
download | pkgsrc-9eb0776e1451e7ecdc516b681e974444e984b60b.tar.gz |
Apply patch from upstream:
fix: crash handling keywords/labels
When an email is read by NeoMutt the labels are stored in linked list of
strings. These strings are used as keys in a hash table of all labels.
If NeoMutt reads another email with the same label, it's given a
reference to the same hash.
Now imagine that the first email is deleted -- the list of labels is
also deleted, so that hash now has invalid keys.
This commit maintains a linked list of all labels and uses that for the
hash table keys. It's not very efficient, but it avoids having to
change the hash table code.
Note: dgc (the keywords author) has created a new version which will
supplant this one, soon.
https://github.com/neomutt/neomutt/commit/f8160285f285c0bc3c93a2672ea1169af2f04481
Bump PKGREVISION.
-rw-r--r-- | mail/neomutt/Makefile | 4 | ||||
-rw-r--r-- | mail/neomutt/distinfo | 5 | ||||
-rw-r--r-- | mail/neomutt/patches/patch-hash.c | 28 | ||||
-rw-r--r-- | mail/neomutt/patches/patch-hash.h | 15 | ||||
-rw-r--r-- | mail/neomutt/patches/patch-headers.c | 139 |
5 files changed, 189 insertions, 2 deletions
diff --git a/mail/neomutt/Makefile b/mail/neomutt/Makefile index 917180c2134..bcb9fdfa6bb 100644 --- a/mail/neomutt/Makefile +++ b/mail/neomutt/Makefile @@ -1,6 +1,7 @@ -# $NetBSD: Makefile,v 1.12 2016/10/04 21:53:08 wiz Exp $ +# $NetBSD: Makefile,v 1.13 2016/10/06 16:27:15 wiz Exp $ DISTNAME= neomutt-20161003 +PKGREVISION= 1 CATEGORIES= mail MASTER_SITES= ${MASTER_SITE_GITHUB:=neomutt/} GITHUB_TAG= ${DISTNAME} @@ -19,6 +20,7 @@ CONFIGURE_ARGS+= --enable-external-dotlock CONFIGURE_ARGS+= --enable-imap CONFIGURE_ARGS+= --enable-notmuch CONFIGURE_ARGS+= --enable-pop +CONFIGURE_ARGS+= CFLAGS="-g -O0" EGDIR= ${PREFIX}/share/examples/mutt CONF_FILES= ${EGDIR}/Muttrc ${PKG_SYSCONFDIR}/Muttrc diff --git a/mail/neomutt/distinfo b/mail/neomutt/distinfo index 9062009a2db..f4698e8379a 100644 --- a/mail/neomutt/distinfo +++ b/mail/neomutt/distinfo @@ -1,6 +1,9 @@ -$NetBSD: distinfo,v 1.9 2016/10/04 11:05:06 wiz Exp $ +$NetBSD: distinfo,v 1.10 2016/10/06 16:27:15 wiz Exp $ SHA1 (neomutt-20161003.tar.gz) = d0849c7efaa7e099b17137d8f5f90b9a201142f1 RMD160 (neomutt-20161003.tar.gz) = c69fe3dba35c3341987b6eb21b4bc0a1eb546762 SHA512 (neomutt-20161003.tar.gz) = f3b42e0bf12038bfdce20db30d2ac4ee60a4ce317894ff035a4180a53d0899936aef6f809c52ef8786eab6b247e98ae244578d00a5dafb44e04f4b3ccc84b592 Size (neomutt-20161003.tar.gz) = 2656280 bytes +SHA1 (patch-hash.c) = 63df8e500d91f0dffb24801b84dc7155539d34a5 +SHA1 (patch-hash.h) = ddc94cfaeead9800f5f902de9f4255803122463d +SHA1 (patch-headers.c) = 8d985b9dfc717c5c30e9fb314c33b35d61dcaf56 diff --git a/mail/neomutt/patches/patch-hash.c b/mail/neomutt/patches/patch-hash.c new file mode 100644 index 00000000000..2daddd0d721 --- /dev/null +++ b/mail/neomutt/patches/patch-hash.c @@ -0,0 +1,28 @@ +$NetBSD: patch-hash.c,v 1.1 2016/10/06 16:27:15 wiz Exp $ + +Fix: crash handling keywords/labels +https://github.com/neomutt/neomutt/commit/f8160285f285c0bc3c93a2672ea1169af2f04481 + +--- hash.c.orig 2016-10-03 11:27:32.000000000 +0000 ++++ hash.c +@@ -153,6 +153,20 @@ void *hash_find_hash (const HASH * table + return NULL; + } + ++void hash_set_data (HASH *table, const char *key, void *data) ++{ ++ if (!table) ++ return; ++ ++ unsigned int hash = table->hash_string ((unsigned char *) key, table->nelem); ++ ++ struct hash_elem *ptr = table->table[hash]; ++ if (!ptr) ++ return; ++ ++ ptr->data = data; ++} ++ + void hash_delete_hash (HASH * table, int hash, const char *key, const void *data, + void (*destroy) (void *)) + { diff --git a/mail/neomutt/patches/patch-hash.h b/mail/neomutt/patches/patch-hash.h new file mode 100644 index 00000000000..1402e562f3d --- /dev/null +++ b/mail/neomutt/patches/patch-hash.h @@ -0,0 +1,15 @@ +$NetBSD: patch-hash.h,v 1.1 2016/10/06 16:27:15 wiz Exp $ + +Fix: crash handling keywords/labels +https://github.com/neomutt/neomutt/commit/f8160285f285c0bc3c93a2672ea1169af2f04481 + +--- hash.h.orig 2016-10-03 11:27:32.000000000 +0000 ++++ hash.h +@@ -46,6 +46,7 @@ void *hash_find_hash (const HASH * table + void hash_delete_hash (HASH * table, int hash, const char *key, const void *data, + void (*destroy) (void *)); + void hash_destroy (HASH ** hash, void (*destroy) (void *)); ++void hash_set_data (HASH *table, const char *key, void *data); + + struct hash_walk_state { + int index; diff --git a/mail/neomutt/patches/patch-headers.c b/mail/neomutt/patches/patch-headers.c new file mode 100644 index 00000000000..d0294001432 --- /dev/null +++ b/mail/neomutt/patches/patch-headers.c @@ -0,0 +1,139 @@ +$NetBSD: patch-headers.c,v 1.1 2016/10/06 16:27:15 wiz Exp $ + +Fix: crash handling keywords/labels +https://github.com/neomutt/neomutt/commit/f8160285f285c0bc3c93a2672ea1169af2f04481 + +--- headers.c.orig 2016-10-03 11:27:32.000000000 +0000 ++++ headers.c +@@ -28,6 +28,11 @@ + #include <string.h> + #include <ctype.h> + ++/* The labels are used as keys in the Labels hash. ++ * The keys must have a longer lifespan than the hash. ++ */ ++static LIST *LabelList = NULL; ++ + void mutt_edit_headers (const char *editor, + const char *body, + HEADER *msg, +@@ -215,6 +220,65 @@ void mutt_edit_headers (const char *edit + } + } + ++/** ++ * label_add - Add to a list of all labels ++ * @label: Label name to keep ++ * ++ * Add an item to our LIST of all labels. ++ * ++ * The keys in the Label HASH must have a longer lifespan than the HASH itself. ++ * We keep them in an (inefficient) linked list. ++ * ++ * Note: We don't check for duplicates. ++ * ++ * Returns: ++ * NULL on error ++ * LIST* new LIST item, on success ++ */ ++static LIST *label_add (const char *label) ++{ ++ if (!label) ++ return NULL; ++ ++ LIST *n = mutt_new_list(); ++ ++ /* Insert our new LIST item at the front */ ++ n->data = safe_strdup (label); ++ n->next = LabelList; ++ LabelList = n; ++ ++ return n; ++} ++ ++/** ++ * label_delete - Delete from a list of all labels ++ * @label: Label name to remove ++ * ++ * Delete an item from our LIST of all labels. ++ * ++ * The keys in the Label HASH must have a longer lifespan than the HASH itself. ++ * We keep them in an (inefficient) linked list. ++ */ ++static void label_delete (const char *label) ++{ ++ if (!label || !LabelList) ++ return; ++ ++ LIST *l; ++ LIST **prev; ++ ++ for (l = LabelList, prev = &LabelList; l; prev = &l->next, l = l->next) ++ { ++ if (mutt_strcmp (label, l->data) == 0) ++ { ++ *prev = l->next; ++ FREE(&l->data); ++ FREE(&l); ++ break; ++ } ++ } ++} ++ + void mutt_label_ref_dec(ENVELOPE *env) + { + uintptr_t count; +@@ -227,14 +291,21 @@ void mutt_label_ref_dec(ENVELOPE *env) + { + if (label->data == NULL) + continue; ++ + count = (uintptr_t)hash_find(Labels, label->data); +- if (count) ++ count--; ++ if (count > 0) + { ++ /* Existing label, decrease refcount */ ++ hash_set_data (Labels, label->data, (void*) count); ++ } ++ else ++ { ++ /* Old label */ + hash_delete(Labels, label->data, NULL, NULL); +- count--; +- if (count > 0) +- hash_insert(Labels, label->data, (void *)count, 0); ++ label_delete (label->data); + } ++ + dprint(1, (debugfile, "--label %s: %d\n", label->data, count)); + } + } +@@ -251,11 +322,22 @@ void mutt_label_ref_inc(ENVELOPE *env) + { + if (label->data == NULL) + continue; +- count = (uintptr_t)hash_find(Labels, label->data); +- if (count) +- hash_delete(Labels, label->data, NULL, NULL); +- count++; /* was zero if not found */ +- hash_insert(Labels, label->data, (void *)count, 0); ++ ++ count = (uintptr_t) hash_find(Labels, label->data); ++ count++; ++ if (count > 1) ++ { ++ /* Existing label, increase refcount */ ++ hash_set_data (Labels, label->data, (void*) count); ++ } ++ else ++ { ++ /* New label */ ++ const char *dup_label = safe_strdup (label->data); ++ label_add (dup_label); ++ hash_insert(Labels, dup_label, (void *) count, 0); ++ } ++ + dprint(1, (debugfile, "++label %s: %d\n", label->data, count)); + } + } |