From 7f7ec82c7dc023b9ac7b985d1abe10e7bd3d908e Mon Sep 17 00:00:00 2001 From: Eduardo Chappa Date: Tue, 10 Jul 2018 17:38:51 -0600 Subject: * Several improvements to the OPENINGTEXT type of tokens, including: avoid memory leaks when trying to get the opening text a second time, and get the actual opening text for html messages that are part of a multipart/* text. In addition, Alpine caches this text, so that operations such as resizing, or marking a message deleted, does not make Alpine recompute this text. --- pith/mailindx.c | 35 +++++++++++++++++++++++++++++++---- pith/msgno.c | 3 +++ pith/pine.hlp | 2 +- pith/pineelt.h | 1 + 4 files changed, 36 insertions(+), 5 deletions(-) (limited to 'pith') diff --git a/pith/mailindx.c b/pith/mailindx.c index f9ec76dc..406a8552 100644 --- a/pith/mailindx.c +++ b/pith/mailindx.c @@ -17,6 +17,7 @@ static char rcsid[] = "$Id: mailindx.c 1266 2009-07-14 18:39:12Z hubert@u.washin #include "../pith/headers.h" #include "../pith/mailindx.h" +#include "../pith/pineelt.h" #include "../pith/mailview.h" #include "../pith/flag.h" #include "../pith/icache.h" @@ -2815,7 +2816,6 @@ format_index_index_line(INDEXDATA_S *idata) if(first_text){ strncpy(str, first_text, BIGWIDTH); str[BIGWIDTH] = '\0'; - fs_give((void **) &first_text); } } @@ -3734,12 +3734,32 @@ char * fetch_firsttext(INDEXDATA_S *idata, int delete_quotes) { ENVELOPE *env; - BODY *body = NULL; + BODY *body = NULL, *new_body = NULL; char *firsttext = NULL; STORE_S *so; gf_io_t pc; long partial_fetch_len = 0L; SEARCHSET *ss, **sset; + MESSAGECACHE *mc; + PINELT_S *pelt; + + /* we cache the result we get from this function, so that we do not have to + * refetch the text in case there is a change. We could cache in the envelope + * but c-client does not have a special field for that, nor we want to use the + * sparep pointer, since there could be other uses for sparep later, and even + * if we add a pointer to the ENVELOPE structure, we would be caching the same + * text twice (one in a private pointer, and the new pointer) and that would + * not make sense. Instead we will use an elt for this + */ + + if((mc = mail_elt(idata->stream, idata->rawno)) + && ((pelt = (PINELT_S *) mc->sparep) == NULL)){ + pelt = (PINELT_S *) fs_get(sizeof(PINELT_S)); + memset(pelt, 0, sizeof(PINELT_S)); + } + + if(pelt && pelt->firsttext != NULL) + return(pelt->firsttext); try_again: @@ -3748,7 +3768,7 @@ try_again: * Can we get this somehow in the overview call in build_header_work? */ ss = mail_newsearchset(); - ss->first = idata->rawno; + ss->first = ss->last = idata->rawno; sset = (SEARCHSET **) mail_parameters(idata->stream, GET_FETCHLOOKAHEAD, (void *) idata->stream); @@ -3794,6 +3814,7 @@ try_again: && (subtype=body->subtype) && ALLOWED_SUBTYPE(subtype)) || (body->type == TYPEMULTIPART && body->nested.part + && (new_body = &body->nested.part->body) != NULL && body->nested.part->body.type == TYPETEXT && (subtype=body->nested.part->body.subtype) && ALLOWED_SUBTYPE(subtype))) @@ -3802,7 +3823,8 @@ try_again: partno = "1.1"; gf_set_so_writec(&pc, so); - success = get_body_part_text(idata->stream, body, idata->rawno, + success = get_body_part_text(idata->stream, new_body ? new_body : body, + idata->rawno, partno, partial_fetch_len, pc, NULL, NULL, GBPT_NOINTR | GBPT_PEEK | @@ -3853,10 +3875,15 @@ try_again: if(firsttext) fs_give((void **) &firsttext); + if(ss) + mail_free_searchset(&ss); + partial_fetch_len = 4096L; goto try_again; } } + if(mc && pelt) + pelt->firsttext = firsttext; } } } diff --git a/pith/msgno.c b/pith/msgno.c index 972dcde9..c00f296b 100644 --- a/pith/msgno.c +++ b/pith/msgno.c @@ -937,6 +937,9 @@ free_pine_elt(void **sparep) if((*peltp)->pthrd) fs_give((void **) &(*peltp)->pthrd); + if((*peltp)->firsttext) + fs_give((void **) &(*peltp)->firsttext); + if((*peltp)->ice) free_ice(&(*peltp)->ice); diff --git a/pith/pine.hlp b/pith/pine.hlp index a28a0f12..486129cd 100644 --- a/pith/pine.hlp +++ b/pith/pine.hlp @@ -140,7 +140,7 @@ with help text for the config screen and the composer that didn't have any reasonable place to be called from. Dummy change to get revision in pine.hlp ============= h_revision ================= -Alpine Commit 296 2018-07-06 19:19:36 +Alpine Commit 298 2018-07-10 17:38:37 ============= h_news ================= diff --git a/pith/pineelt.h b/pith/pineelt.h index 2ed46aa1..54ab3811 100644 --- a/pith/pineelt.h +++ b/pith/pineelt.h @@ -41,6 +41,7 @@ typedef struct pine_elt { PINETHRD_S *pthrd; PARTEX_S *exceptions; ICE_S *ice; + char *firsttext; /* per-message pine state bits */ unsigned int hidden:1; unsigned int excluded:1; -- cgit v1.2.3-54-g00ecf