#include "mutt_crypt.h"
#include "mutt_curses.h"
+#include "group.h"
#ifdef USE_IMAP
#include "mx.h"
{ 'z', M_SIZE, 0, eat_range },
{ '=', M_DUPLICATED, 0, NULL },
{ '$', M_UNREFERENCED, 0, NULL },
- { 0 }
+ { 0, 0, 0, NULL }
};
static pattern_t *SearchPattern = NULL; /* current search pattern */
memset (&s, 0, sizeof (s));
s.fpin = msg->fp;
s.flags = M_CHARCONV;
- mutt_mktemp (tempfile);
+ mutt_mktemp (tempfile, sizeof (tempfile));
if ((s.fpout = safe_fopen (tempfile, "w+")) == NULL)
{
mutt_perror (tempfile);
mx_close_message (&msg);
if (s.fpout)
{
- fclose (s.fpout);
+ safe_fclose (&s.fpout);
unlink (tempfile);
}
return (0);
if (option (OPTTHOROUGHSRC))
{
- fclose (fp);
+ safe_fclose (&fp);
unlink (tempfile);
}
}
static int eat_regexp (pattern_t *pat, BUFFER *s, BUFFER *err)
{
BUFFER buf;
+ char errmsg[STRING];
int r;
memset (&buf, 0, sizeof (buf));
if (pat->stringmatch)
{
pat->p.str = safe_strdup (buf.data);
+ pat->ign_case = mutt_which_case (buf.data) == REG_ICASE;
FREE (&buf.data);
}
else if (pat->groupmatch)
{
pat->p.rx = safe_malloc (sizeof (regex_t));
r = REGCOMP (pat->p.rx, buf.data, REG_NEWLINE | REG_NOSUB | mutt_which_case (buf.data));
- FREE (&buf.data);
if (r)
{
- regerror (r, pat->p.rx, err->data, err->dsize);
- regfree (pat->p.rx);
+ regerror (r, pat->p.rx, errmsg, sizeof (errmsg));
+ mutt_buffer_printf (err, "'%s': %s", buf.data, errmsg);
+ FREE (&buf.data);
FREE (&pat->p.rx);
return (-1);
}
+ FREE (&buf.data);
}
return 0;
static int patmatch (const pattern_t* pat, const char* buf)
{
if (pat->stringmatch)
- return !strstr (buf, pat->p.str);
+ return pat->ign_case ? !strcasestr (buf, pat->p.str) :
+ !strstr (buf, pat->p.str);
else if (pat->groupmatch)
return !mutt_group_match (pat->p.g, buf);
else
case '%':
case '=':
case '~':
- if (*(ps.dptr + 1) == '(')
+ if (!*(ps.dptr + 1))
+ {
+ snprintf (err->data, err->dsize, _("missing pattern: %s"), ps.dptr);
+ mutt_pattern_free (&curlist);
+ return NULL;
+ }
+ if (*(ps.dptr + 1) == '(')
{
ps.dptr ++; /* skip ~ */
p = find_matching_paren (ps.dptr + 1);
case M_SIZE:
return (pat->not ^ (h->content->length >= pat->min && (pat->max == M_MAXRANGE || h->content->length <= pat->max)));
case M_REFERENCE:
- return (pat->not ^ match_reference (pat, h->env->references));
+ return (pat->not ^ (match_reference (pat, h->env->references) ||
+ match_reference (pat, h->env->in_reply_to)));
case M_ADDRESS:
return (pat->not ^ match_adrlist (pat, flags & M_MATCH_FULL_ADDRESS, 4,
h->env->from, h->env->sender,
simple = safe_strdup (buf);
mutt_check_simple (buf, sizeof (buf), NONULL (SimpleSearch));
+ memset (&err, 0, sizeof(err));
err.data = error;
err.dsize = sizeof (error);
if ((pat = mutt_pattern_comp (buf, M_FULL_MSG, &err)) == NULL)
char buf[STRING];
char temp[LONG_STRING];
char error[STRING];
- BUFFER err;
int incr;
HEADER *h;
progress_t progress;
const char* msg = NULL;
- if (op != OP_SEARCH_NEXT && op != OP_SEARCH_OPPOSITE)
+ if (!*LastSearch || (op != OP_SEARCH_NEXT && op != OP_SEARCH_OPPOSITE))
{
- strfcpy (buf, LastSearch, sizeof (buf));
- if (mutt_get_field ((op == OP_SEARCH) ? _("Search for: ") :
- _("Reverse search for: "), buf, sizeof (buf),
+ strfcpy (buf, *LastSearch ? LastSearch : "", sizeof (buf));
+ if (mutt_get_field ((op == OP_SEARCH || op == OP_SEARCH_NEXT) ?
+ _("Search for: ") : _("Reverse search for: "),
+ buf, sizeof (buf),
M_CLEAR | M_PATTERN) != 0 || !buf[0])
return (-1);
- if (op == OP_SEARCH)
+ if (op == OP_SEARCH || op == OP_SEARCH_NEXT)
unset_option (OPTSEARCHREVERSE);
else
set_option (OPTSEARCHREVERSE);
if (!SearchPattern || mutt_strcmp (temp, LastSearchExpn))
{
+ BUFFER err;
+ memset(&err, 0, sizeof(err));
set_option (OPTSEARCHINVALID);
strfcpy (LastSearch, buf, sizeof (LastSearch));
mutt_message _("Compiling search pattern...");
if ((SearchPattern = mutt_pattern_comp (temp, M_FULL_MSG, &err)) == NULL)
{
mutt_error ("%s", error);
+ LastSearch[0] = '\0';
return (-1);
}
mutt_clear_error ();
}
}
- else if (!SearchPattern)
- {
- mutt_error _("No search pattern.");
- return (-1);
- }
if (option (OPTSEARCHINVALID))
{