NeoMutt  2020-06-26-89-g172cd3
Teaching an old dog new tricks
DOXYGEN
pattern.h File Reference

Match patterns to emails. More...

#include "config.h"
#include <stdbool.h>
#include <stdint.h>
#include "mutt/lib.h"
#include "mutt.h"
+ Include dependency graph for pattern.h:
+ This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  Pattern
 A simple (non-regex) pattern. More...
 
struct  PatternCache
 Cache commonly-used patterns. More...
 

Macros

#define MUTT_PC_NO_FLAGS   0
 No flags are set. More...
 
#define MUTT_PC_FULL_MSG   (1<<0)
 Enable body and header matching. More...
 
#define MUTT_PC_PATTERN_DYNAMIC   (1<<1)
 Enable runtime date range evaluation. More...
 
#define MUTT_PC_SEND_MODE_SEARCH   (1<<2)
 Allow send-mode body searching. More...
 
#define MUTT_PAT_EXEC_NO_FLAGS   0
 No flags are set. More...
 
#define MUTT_MATCH_FULL_ADDRESS   (1 << 0)
 Match the full address. More...
 

Typedefs

typedef uint8_t PatternCompFlags
 Flags for mutt_pattern_comp(), e.g. MUTT_PC_FULL_MSG. More...
 
typedef uint8_t PatternExecFlags
 Flags for mutt_pattern_exec(), e.g. MUTT_MATCH_FULL_ADDRESS. More...
 

Enumerations

enum  PatternType {
  MUTT_PAT_AND = MUTT_MT_MAX, MUTT_PAT_OR, MUTT_PAT_THREAD, MUTT_PAT_PARENT,
  MUTT_PAT_CHILDREN, MUTT_PAT_TO, MUTT_PAT_CC, MUTT_PAT_COLLAPSED,
  MUTT_PAT_SUBJECT, MUTT_PAT_FROM, MUTT_PAT_DATE, MUTT_PAT_DATE_RECEIVED,
  MUTT_PAT_DUPLICATED, MUTT_PAT_UNREFERENCED, MUTT_PAT_BROKEN, MUTT_PAT_ID,
  MUTT_PAT_ID_EXTERNAL, MUTT_PAT_BODY, MUTT_PAT_HEADER, MUTT_PAT_HORMEL,
  MUTT_PAT_WHOLE_MSG, MUTT_PAT_SENDER, MUTT_PAT_MESSAGE, MUTT_PAT_SCORE,
  MUTT_PAT_SIZE, MUTT_PAT_REFERENCE, MUTT_PAT_RECIPIENT, MUTT_PAT_LIST,
  MUTT_PAT_SUBSCRIBED_LIST, MUTT_PAT_PERSONAL_RECIP, MUTT_PAT_PERSONAL_FROM, MUTT_PAT_ADDRESS,
  MUTT_PAT_CRYPT_SIGN, MUTT_PAT_CRYPT_VERIFIED, MUTT_PAT_CRYPT_ENCRYPT, MUTT_PAT_PGP_KEY,
  MUTT_PAT_XLABEL, MUTT_PAT_SERVERSEARCH, MUTT_PAT_DRIVER_TAGS, MUTT_PAT_MIMEATTACH,
  MUTT_PAT_MIMETYPE, MUTT_PAT_NEWSGROUPS, MUTT_PAT_MAX
}
 Types of pattern to match. More...
 

Functions

 SLIST_HEAD (PatternList, Pattern)
 
int mutt_pattern_exec (struct Pattern *pat, PatternExecFlags flags, struct Mailbox *m, struct Email *e, struct PatternCache *cache)
 Match a pattern against an email header. More...
 
struct PatternList * mutt_pattern_comp (const char *s, PatternCompFlags flags, struct Buffer *err)
 Create a Pattern. More...
 
void mutt_check_simple (struct Buffer *s, const char *simple)
 Convert a simple search into a real request. More...
 
void mutt_pattern_free (struct PatternList **pat)
 Free a Pattern. More...
 
int mutt_which_case (const char *s)
 
int mutt_is_list_recipient (bool all_addr, struct Envelope *e)
 Matches known mailing lists. More...
 
int mutt_is_subscribed_list_recipient (bool all_addr, struct Envelope *e)
 Matches subscribed mailing lists. More...
 
int mutt_pattern_func (int op, char *prompt)
 Perform some Pattern matching. More...
 
int mutt_search_command (int cur, int op)
 Perform a search. More...
 
bool mutt_limit_current_thread (struct Email *e)
 Limit the email view to the current thread. More...
 

Variables

bool C_ThoroughSearch
 Config: Decode headers and messages before searching them. More...
 

Detailed Description

Match patterns to emails.

Authors
  • Richard Russon
  • Pietro Cerutti

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

You should have received a copy of the GNU General Public License along with this program. If not, see http://www.gnu.org/licenses/.

Definition in file pattern.h.

Macro Definition Documentation

◆ MUTT_PC_NO_FLAGS

#define MUTT_PC_NO_FLAGS   0

No flags are set.

Definition at line 41 of file pattern.h.

◆ MUTT_PC_FULL_MSG

#define MUTT_PC_FULL_MSG   (1<<0)

Enable body and header matching.

Definition at line 42 of file pattern.h.

◆ MUTT_PC_PATTERN_DYNAMIC

#define MUTT_PC_PATTERN_DYNAMIC   (1<<1)

Enable runtime date range evaluation.

Definition at line 43 of file pattern.h.

◆ MUTT_PC_SEND_MODE_SEARCH

#define MUTT_PC_SEND_MODE_SEARCH   (1<<2)

Allow send-mode body searching.

Definition at line 44 of file pattern.h.

◆ MUTT_PAT_EXEC_NO_FLAGS

#define MUTT_PAT_EXEC_NO_FLAGS   0

No flags are set.

Definition at line 75 of file pattern.h.

◆ MUTT_MATCH_FULL_ADDRESS

#define MUTT_MATCH_FULL_ADDRESS   (1 << 0)

Match the full address.

Definition at line 76 of file pattern.h.

Typedef Documentation

◆ PatternCompFlags

typedef uint8_t PatternCompFlags

Flags for mutt_pattern_comp(), e.g. MUTT_PC_FULL_MSG.

Definition at line 40 of file pattern.h.

◆ PatternExecFlags

typedef uint8_t PatternExecFlags

Flags for mutt_pattern_exec(), e.g. MUTT_MATCH_FULL_ADDRESS.

Definition at line 74 of file pattern.h.

Enumeration Type Documentation

◆ PatternType

Types of pattern to match.

Note
This enum piggy-backs on top of MessageType
See also
mutt_pattern_comp(), mutt_pattern_exec()
Enumerator
MUTT_PAT_AND 

Both patterns must match.

MUTT_PAT_OR 

Either pattern can match.

MUTT_PAT_THREAD 

Pattern matches email thread.

MUTT_PAT_PARENT 

Pattern matches parent.

MUTT_PAT_CHILDREN 

Pattern matches a child email.

MUTT_PAT_TO 

Pattern matches 'To:' field.

MUTT_PAT_CC 

Pattern matches 'Cc:' field.

MUTT_PAT_COLLAPSED 

Thread is collapsed.

MUTT_PAT_SUBJECT 

Pattern matches 'Subject:' field.

MUTT_PAT_FROM 

Pattern matches 'From:' field.

MUTT_PAT_DATE 

Pattern matches 'Date:' field.

MUTT_PAT_DATE_RECEIVED 

Pattern matches date received.

MUTT_PAT_DUPLICATED 

Duplicate message.

MUTT_PAT_UNREFERENCED 

Message is unreferenced in the thread.

MUTT_PAT_BROKEN 

Message is part of a broken thread.

MUTT_PAT_ID 

Pattern matches email's Message-Id.

MUTT_PAT_ID_EXTERNAL 

Message-Id is among results from an external query.

MUTT_PAT_BODY 

Pattern matches email's body.

MUTT_PAT_HEADER 

Pattern matches email's header.

MUTT_PAT_HORMEL 

Pattern matches email's spam score.

MUTT_PAT_WHOLE_MSG 

Pattern matches raw email text.

MUTT_PAT_SENDER 

Pattern matches sender.

MUTT_PAT_MESSAGE 

Pattern matches message number.

MUTT_PAT_SCORE 

Pattern matches email's score.

MUTT_PAT_SIZE 

Pattern matches email's size.

MUTT_PAT_REFERENCE 

Pattern matches 'References:' or 'In-Reply-To:' field.

MUTT_PAT_RECIPIENT 

User is a recipient of the email.

MUTT_PAT_LIST 

Email is on mailing list.

MUTT_PAT_SUBSCRIBED_LIST 

Email is on subscribed mailing list.

MUTT_PAT_PERSONAL_RECIP 

Email is addressed to the user.

MUTT_PAT_PERSONAL_FROM 

Email is from the user.

MUTT_PAT_ADDRESS 

Pattern matches any address field.

MUTT_PAT_CRYPT_SIGN 

Message is signed.

MUTT_PAT_CRYPT_VERIFIED 

Message is crypographically verified.

MUTT_PAT_CRYPT_ENCRYPT 

Message is encrypted.

MUTT_PAT_PGP_KEY 

Message has PGP key.

MUTT_PAT_XLABEL 

Pattern matches keyword/label.

MUTT_PAT_SERVERSEARCH 

Server-side pattern matches.

MUTT_PAT_DRIVER_TAGS 

Pattern matches message tags.

MUTT_PAT_MIMEATTACH 

Pattern matches number of attachments.

MUTT_PAT_MIMETYPE 

Pattern matches MIME type.

MUTT_PAT_NEWSGROUPS 

Pattern matches newsgroup.

MUTT_PAT_MAX 

Definition at line 105 of file pattern.h.

106 {
108  MUTT_PAT_OR,
112  MUTT_PAT_TO,
113  MUTT_PAT_CC,
116  MUTT_PAT_FROM,
117  MUTT_PAT_DATE,
122  MUTT_PAT_ID,
124  MUTT_PAT_BODY,
131  MUTT_PAT_SIZE,
134  MUTT_PAT_LIST,
148 #ifdef USE_NNTP
150 #endif
151  MUTT_PAT_MAX,
152 };
Pattern matches date received.
Definition: pattern.h:118
Pattern matches email&#39;s header.
Definition: pattern.h:125
Pattern matches MIME type.
Definition: pattern.h:147
Pattern matches &#39;Date:&#39; field.
Definition: pattern.h:117
Pattern matches newsgroup.
Definition: pattern.h:149
Pattern matches email&#39;s score.
Definition: pattern.h:130
Message is part of a broken thread.
Definition: pattern.h:121
Pattern matches email&#39;s size.
Definition: pattern.h:131
Pattern matches &#39;From:&#39; field.
Definition: pattern.h:116
Email is from the user.
Definition: pattern.h:137
Email is on mailing list.
Definition: pattern.h:134
Pattern matches a child email.
Definition: pattern.h:111
Pattern matches email&#39;s Message-Id.
Definition: pattern.h:122
Pattern matches message number.
Definition: pattern.h:129
Email is on subscribed mailing list.
Definition: pattern.h:135
Duplicate message.
Definition: pattern.h:119
Server-side pattern matches.
Definition: pattern.h:144
Pattern matches &#39;Cc:&#39; field.
Definition: pattern.h:113
Message is unreferenced in the thread.
Definition: pattern.h:120
Pattern matches keyword/label.
Definition: pattern.h:143
Either pattern can match.
Definition: pattern.h:108
Pattern matches email&#39;s spam score.
Definition: pattern.h:126
Message is encrypted.
Definition: pattern.h:141
Pattern matches &#39;Subject:&#39; field.
Definition: pattern.h:115
Email is addressed to the user.
Definition: pattern.h:136
Message has PGP key.
Definition: pattern.h:142
Pattern matches parent.
Definition: pattern.h:110
Pattern matches email&#39;s body.
Definition: pattern.h:124
Message is signed.
Definition: pattern.h:139
Thread is collapsed.
Definition: pattern.h:114
Pattern matches sender.
Definition: pattern.h:128
Both patterns must match.
Definition: pattern.h:107
Message is crypographically verified.
Definition: pattern.h:140
Pattern matches &#39;References:&#39; or &#39;In-Reply-To:&#39; field.
Definition: pattern.h:132
Pattern matches message tags.
Definition: pattern.h:145
Pattern matches any address field.
Definition: pattern.h:138
User is a recipient of the email.
Definition: pattern.h:133
Pattern matches email thread.
Definition: pattern.h:109
Pattern matches &#39;To:&#39; field.
Definition: pattern.h:112
Pattern matches raw email text.
Definition: pattern.h:127
Pattern matches number of attachments.
Definition: pattern.h:146
Message-Id is among results from an external query.
Definition: pattern.h:123

Function Documentation

◆ SLIST_HEAD()

SLIST_HEAD ( PatternList  ,
Pattern   
)

◆ mutt_pattern_exec()

int mutt_pattern_exec ( struct Pattern pat,
PatternExecFlags  flags,
struct Mailbox m,
struct Email e,
struct PatternCache cache 
)

Match a pattern against an email header.

Parameters
patPattern to match
flagsFlags, e.g. MUTT_MATCH_FULL_ADDRESS
mMailbox
eEmail
cacheCache for common Patterns
Return values
1Success, pattern matched
0Pattern did not match
-1Error

flags: MUTT_MATCH_FULL_ADDRESS - match both personal and machine address cache: For repeated matches against the same Header, passing in non-NULL will store some of the cacheable pattern matches in this structure.

Definition at line 2129 of file pattern.c.

2131 {
2132  switch (pat->op)
2133  {
2134  case MUTT_PAT_AND:
2135  return pat->pat_not ^ (perform_and(pat->child, flags, m, e, cache) > 0);
2136  case MUTT_PAT_OR:
2137  return pat->pat_not ^ (perform_or(pat->child, flags, m, e, cache) > 0);
2138  case MUTT_PAT_THREAD:
2139  return pat->pat_not ^
2140  match_threadcomplete(pat->child, flags, m, e->thread, 1, 1, 1, 1);
2141  case MUTT_PAT_PARENT:
2142  return pat->pat_not ^ match_threadparent(pat->child, flags, m, e->thread);
2143  case MUTT_PAT_CHILDREN:
2144  return pat->pat_not ^ match_threadchildren(pat->child, flags, m, e->thread);
2145  case MUTT_ALL:
2146  return !pat->pat_not;
2147  case MUTT_EXPIRED:
2148  return pat->pat_not ^ e->expired;
2149  case MUTT_SUPERSEDED:
2150  return pat->pat_not ^ e->superseded;
2151  case MUTT_FLAG:
2152  return pat->pat_not ^ e->flagged;
2153  case MUTT_TAG:
2154  return pat->pat_not ^ e->tagged;
2155  case MUTT_NEW:
2156  return pat->pat_not ? e->old || e->read : !(e->old || e->read);
2157  case MUTT_UNREAD:
2158  return pat->pat_not ? e->read : !e->read;
2159  case MUTT_REPLIED:
2160  return pat->pat_not ^ e->replied;
2161  case MUTT_OLD:
2162  return pat->pat_not ? (!e->old || e->read) : (e->old && !e->read);
2163  case MUTT_READ:
2164  return pat->pat_not ^ e->read;
2165  case MUTT_DELETED:
2166  return pat->pat_not ^ e->deleted;
2167  case MUTT_PAT_MESSAGE:
2168  return pat->pat_not ^ ((EMSG(e) >= pat->min) && (EMSG(e) <= pat->max));
2169  case MUTT_PAT_DATE:
2170  if (pat->dynamic)
2172  return pat->pat_not ^ (e->date_sent >= pat->min && e->date_sent <= pat->max);
2174  if (pat->dynamic)
2176  return pat->pat_not ^ (e->received >= pat->min && e->received <= pat->max);
2177  case MUTT_PAT_BODY:
2178  case MUTT_PAT_HEADER:
2179  case MUTT_PAT_WHOLE_MSG:
2180  if (pat->sendmode)
2181  {
2182  if (!e->content || !e->content->filename)
2183  return 0;
2184  return pat->pat_not ^ msg_search_sendmode(e, pat);
2185  }
2186  /* m can be NULL in certain cases, such as when replying to a message
2187  * from the attachment menu and the user has a reply-hook using "~e".
2188  * This is also the case when message scoring. */
2189  if (!m)
2190  return 0;
2191 #ifdef USE_IMAP
2192  /* IMAP search sets e->matched at search compile time */
2193  if ((m->type == MUTT_IMAP) && pat->string_match)
2194  return e->matched;
2195 #endif
2196  return pat->pat_not ^ msg_search(m, pat, e->msgno);
2197  case MUTT_PAT_SERVERSEARCH:
2198 #ifdef USE_IMAP
2199  if (!m)
2200  return 0;
2201  if (m->type == MUTT_IMAP)
2202  {
2203  if (pat->string_match)
2204  return e->matched;
2205  return 0;
2206  }
2207  mutt_error(_("error: server custom search only supported with IMAP"));
2208  return 0;
2209 #else
2210  mutt_error(_("error: server custom search only supported with IMAP"));
2211  return -1;
2212 #endif
2213  case MUTT_PAT_SENDER:
2214  if (!e->env)
2215  return 0;
2216  return pat->pat_not ^ match_addrlist(pat, (flags & MUTT_MATCH_FULL_ADDRESS),
2217  1, &e->env->sender);
2218  case MUTT_PAT_FROM:
2219  if (!e->env)
2220  return 0;
2221  return pat->pat_not ^
2222  match_addrlist(pat, (flags & MUTT_MATCH_FULL_ADDRESS), 1, &e->env->from);
2223  case MUTT_PAT_TO:
2224  if (!e->env)
2225  return 0;
2226  return pat->pat_not ^
2227  match_addrlist(pat, (flags & MUTT_MATCH_FULL_ADDRESS), 1, &e->env->to);
2228  case MUTT_PAT_CC:
2229  if (!e->env)
2230  return 0;
2231  return pat->pat_not ^
2232  match_addrlist(pat, (flags & MUTT_MATCH_FULL_ADDRESS), 1, &e->env->cc);
2233  case MUTT_PAT_SUBJECT:
2234  if (!e->env)
2235  return 0;
2236  return pat->pat_not ^ (e->env->subject && patmatch(pat, e->env->subject));
2237  case MUTT_PAT_ID:
2238  case MUTT_PAT_ID_EXTERNAL:
2239  if (!e->env)
2240  return 0;
2241  return pat->pat_not ^ (e->env->message_id && patmatch(pat, e->env->message_id));
2242  case MUTT_PAT_SCORE:
2243  return pat->pat_not ^ (e->score >= pat->min &&
2244  (pat->max == MUTT_MAXRANGE || e->score <= pat->max));
2245  case MUTT_PAT_SIZE:
2246  return pat->pat_not ^
2247  (e->content->length >= pat->min &&
2248  (pat->max == MUTT_MAXRANGE || e->content->length <= pat->max));
2249  case MUTT_PAT_REFERENCE:
2250  if (!e->env)
2251  return 0;
2252  return pat->pat_not ^ (match_reference(pat, &e->env->references) ||
2253  match_reference(pat, &e->env->in_reply_to));
2254  case MUTT_PAT_ADDRESS:
2255  if (!e->env)
2256  return 0;
2257  return pat->pat_not ^ match_addrlist(pat, (flags & MUTT_MATCH_FULL_ADDRESS),
2258  4, &e->env->from, &e->env->sender,
2259  &e->env->to, &e->env->cc);
2260  case MUTT_PAT_RECIPIENT:
2261  if (!e->env)
2262  return 0;
2263  return pat->pat_not ^ match_addrlist(pat, (flags & MUTT_MATCH_FULL_ADDRESS),
2264  2, &e->env->to, &e->env->cc);
2265  case MUTT_PAT_LIST: /* known list, subscribed or not */
2266  {
2267  if (!e->env)
2268  return 0;
2269 
2270  int result;
2271  if (cache)
2272  {
2273  int *cache_entry = pat->all_addr ? &cache->list_all : &cache->list_one;
2274  if (!is_pattern_cache_set(*cache_entry))
2275  {
2276  set_pattern_cache_value(cache_entry,
2277  mutt_is_list_recipient(pat->all_addr, e->env));
2278  }
2279  result = get_pattern_cache_value(*cache_entry);
2280  }
2281  else
2282  result = mutt_is_list_recipient(pat->all_addr, e->env);
2283  return pat->pat_not ^ result;
2284  }
2286  {
2287  if (!e->env)
2288  return 0;
2289 
2290  int result;
2291  if (cache)
2292  {
2293  int *cache_entry = pat->all_addr ? &cache->sub_all : &cache->sub_one;
2294  if (!is_pattern_cache_set(*cache_entry))
2295  {
2297  cache_entry, mutt_is_subscribed_list_recipient(pat->all_addr, e->env));
2298  }
2299  result = get_pattern_cache_value(*cache_entry);
2300  }
2301  else
2302  result = mutt_is_subscribed_list_recipient(pat->all_addr, e->env);
2303  return pat->pat_not ^ result;
2304  }
2306  {
2307  if (!e->env)
2308  return 0;
2309 
2310  int result;
2311  if (cache)
2312  {
2313  int *cache_entry = pat->all_addr ? &cache->pers_recip_all : &cache->pers_recip_one;
2314  if (!is_pattern_cache_set(*cache_entry))
2315  {
2317  cache_entry, match_user(pat->all_addr, &e->env->to, &e->env->cc));
2318  }
2319  result = get_pattern_cache_value(*cache_entry);
2320  }
2321  else
2322  result = match_user(pat->all_addr, &e->env->to, &e->env->cc);
2323  return pat->pat_not ^ result;
2324  }
2326  {
2327  if (!e->env)
2328  return 0;
2329 
2330  int result;
2331  if (cache)
2332  {
2333  int *cache_entry = pat->all_addr ? &cache->pers_from_all : &cache->pers_from_one;
2334  if (!is_pattern_cache_set(*cache_entry))
2335  {
2336  set_pattern_cache_value(cache_entry,
2337  match_user(pat->all_addr, &e->env->from, NULL));
2338  }
2339  result = get_pattern_cache_value(*cache_entry);
2340  }
2341  else
2342  result = match_user(pat->all_addr, &e->env->from, NULL);
2343  return pat->pat_not ^ result;
2344  }
2345  case MUTT_PAT_COLLAPSED:
2346  return pat->pat_not ^ (e->collapsed && e->num_hidden > 1);
2347  case MUTT_PAT_CRYPT_SIGN:
2348  if (!WithCrypto)
2349  break;
2350  return pat->pat_not ^ ((e->security & SEC_SIGN) ? 1 : 0);
2352  if (!WithCrypto)
2353  break;
2354  return pat->pat_not ^ ((e->security & SEC_GOODSIGN) ? 1 : 0);
2356  if (!WithCrypto)
2357  break;
2358  return pat->pat_not ^ ((e->security & SEC_ENCRYPT) ? 1 : 0);
2359  case MUTT_PAT_PGP_KEY:
2360  if (!(WithCrypto & APPLICATION_PGP))
2361  break;
2362  return pat->pat_not ^ ((e->security & PGP_KEY) == PGP_KEY);
2363  case MUTT_PAT_XLABEL:
2364  if (!e->env)
2365  return 0;
2366  return pat->pat_not ^ (e->env->x_label && patmatch(pat, e->env->x_label));
2367  case MUTT_PAT_DRIVER_TAGS:
2368  {
2369  char *tags = driver_tags_get(&e->tags);
2370  bool rc = (pat->pat_not ^ (tags && patmatch(pat, tags)));
2371  FREE(&tags);
2372  return rc;
2373  }
2374  case MUTT_PAT_HORMEL:
2375  if (!e->env)
2376  return 0;
2377  return pat->pat_not ^ (e->env->spam.data && patmatch(pat, e->env->spam.data));
2378  case MUTT_PAT_DUPLICATED:
2379  return pat->pat_not ^ (e->thread && e->thread->duplicate_thread);
2380  case MUTT_PAT_MIMEATTACH:
2381  if (!m)
2382  return 0;
2383  {
2384  int count = mutt_count_body_parts(m, e);
2385  return pat->pat_not ^ (count >= pat->min &&
2386  (pat->max == MUTT_MAXRANGE || count <= pat->max));
2387  }
2388  case MUTT_PAT_MIMETYPE:
2389  if (!m)
2390  return 0;
2391  return pat->pat_not ^ match_mime_content_type(pat, m, e);
2392  case MUTT_PAT_UNREFERENCED:
2393  return pat->pat_not ^ (e->thread && !e->thread->child);
2394  case MUTT_PAT_BROKEN:
2395  return pat->pat_not ^ (e->thread && e->thread->fake_thread);
2396 #ifdef USE_NNTP
2397  case MUTT_PAT_NEWSGROUPS:
2398  if (!e->env)
2399  return 0;
2400  return pat->pat_not ^ (e->env->newsgroups && patmatch(pat, e->env->newsgroups));
2401 #endif
2402  }
2403  mutt_error(_("error: unknown op %d (report this error)"), pat->op);
2404  return -1;
2405 }
Pattern matches date received.
Definition: pattern.h:118
struct PatternList * child
Arguments to logical operation.
Definition: pattern.h:63
Deleted messages.
Definition: mutt.h:101
Pattern matches email&#39;s header.
Definition: pattern.h:125
Pattern matches MIME type.
Definition: pattern.h:147
char * filename
when sending a message, this is the file to which this structure refers
Definition: body.h:46
enum MailboxType type
Mailbox type.
Definition: mailbox.h:105
Pattern matches &#39;Date:&#39; field.
Definition: pattern.h:117
#define WithCrypto
Definition: lib.h:118
static bool match_reference(struct Pattern *pat, struct ListHead *refs)
Match references against a Pattern.
Definition: pattern.c:1772
static bool perform_and(struct PatternList *pat, PatternExecFlags flags, struct Mailbox *m, struct Email *e, struct PatternCache *cache)
Perform a logical AND on a set of Patterns.
Definition: pattern.c:1697
Pattern matches newsgroup.
Definition: pattern.h:149
Pattern matches email&#39;s score.
Definition: pattern.h:130
int pers_recip_all
^~p
Definition: pattern.h:92
struct MuttThread * thread
Thread of Emails.
Definition: email.h:94
static int match_threadchildren(struct PatternList *pat, PatternExecFlags flags, struct Mailbox *m, struct MuttThread *t)
Match Pattern against an email&#39;s children.
Definition: pattern.c:1938
static int match_addrlist(struct Pattern *pat, bool match_personal, int n,...)
Match a Pattern against and Address list.
Definition: pattern.c:1742
#define SEC_ENCRYPT
Email is encrypted.
Definition: lib.h:80
Message is part of a broken thread.
Definition: pattern.h:121
Pattern matches email&#39;s size.
Definition: pattern.h:131
struct Body * content
List of MIME parts.
Definition: email.h:90
Flagged messages.
Definition: mutt.h:102
Pattern matches &#39;From:&#39; field.
Definition: pattern.h:116
#define MUTT_MAXRANGE
Definition: pattern.c:99
Email is from the user.
Definition: pattern.h:137
#define _(a)
Definition: message.h:28
Email is on mailing list.
Definition: pattern.h:134
Pattern matches a child email.
Definition: pattern.h:111
static int match_user(int all_addr, struct AddressList *al1, struct AddressList *al2)
Matches the user&#39;s email Address.
Definition: pattern.c:1845
bool expired
Already expired?
Definition: email.h:52
Pattern matches email&#39;s Message-Id.
Definition: pattern.h:122
Messages that have been replied to.
Definition: mutt.h:95
int sub_all
^~u
Definition: pattern.h:90
Pattern matches message number.
Definition: pattern.h:129
static int match_threadcomplete(struct PatternList *pat, PatternExecFlags flags, struct Mailbox *m, struct MuttThread *t, int left, int up, int right, int down)
Match a Pattern against an email thread.
Definition: pattern.c:1881
Email is on subscribed mailing list.
Definition: pattern.h:135
static int msg_search_sendmode(struct Email *e, struct Pattern *pat)
Search in send-mode.
Definition: pattern.c:2047
static int is_pattern_cache_set(int cache_entry)
Is a given Pattern cached?
Definition: pattern.c:2034
All messages.
Definition: mutt.h:91
bool tagged
Email is tagged.
Definition: email.h:44
bool read
Email is read.
Definition: email.h:51
bool dynamic
Evaluate date ranges at run time.
Definition: pattern.h:58
struct ListHead in_reply_to
in-reply-to header content
Definition: envelope.h:82
char * message_id
Message ID.
Definition: envelope.h:69
bool all_addr
All Addresses in the list must match.
Definition: pattern.h:53
bool old
Email is seen, but unread.
Definition: email.h:50
struct AddressList from
Email&#39;s &#39;From&#39; list.
Definition: envelope.h:57
Duplicate message.
Definition: pattern.h:119
struct Envelope * env
Envelope information.
Definition: email.h:89
struct AddressList cc
Email&#39;s &#39;Cc&#39; list.
Definition: envelope.h:59
bool string_match
Check a string for a match.
Definition: pattern.h:54
bool pat_not
Pattern should be inverted (not)
Definition: pattern.h:52
bool superseded
Got superseded?
Definition: email.h:53
int min
Minimum for range checks.
Definition: pattern.h:61
struct TagList tags
For drivers that support server tagging.
Definition: email.h:102
int score
Message score.
Definition: email.h:88
time_t date_sent
Time when the message was sent (UTC)
Definition: email.h:81
Old messages.
Definition: mutt.h:94
int pers_from_one
~P
Definition: pattern.h:95
struct MuttThread * child
Child of this Thread.
Definition: thread.h:46
bool duplicate_thread
Duplicated Email in Thread.
Definition: thread.h:37
Server-side pattern matches.
Definition: pattern.h:144
Pattern matches &#39;Cc:&#39; field.
Definition: pattern.h:113
int pers_recip_one
~p
Definition: pattern.h:93
#define APPLICATION_PGP
Use PGP to encrypt/sign.
Definition: lib.h:92
Message is unreferenced in the thread.
Definition: pattern.h:120
LOFF_T length
length (in bytes) of attachment
Definition: body.h:45
bool fake_thread
Emails grouped by Subject.
Definition: thread.h:36
Pattern matches keyword/label.
Definition: pattern.h:143
Either pattern can match.
Definition: pattern.h:108
char * driver_tags_get(struct TagList *list)
Get tags.
Definition: tags.c:142
size_t num_hidden
Number of hidden messages in this view.
Definition: email.h:75
Pattern matches email&#39;s spam score.
Definition: pattern.h:126
Superseded messages.
Definition: mutt.h:107
Tagged messages.
Definition: mutt.h:103
Message is encrypted.
Definition: pattern.h:141
char * data
Pointer to data.
Definition: buffer.h:35
Pattern matches &#39;Subject:&#39; field.
Definition: pattern.h:115
int list_all
^~l
Definition: pattern.h:88
New messages.
Definition: mutt.h:93
Messages that have been read.
Definition: mutt.h:96
static int get_pattern_cache_value(int cache_entry)
Get pattern cache value.
Definition: pattern.c:2024
Email is addressed to the user.
Definition: pattern.h:136
Message has PGP key.
Definition: pattern.h:142
bool collapsed
Is this message part of a collapsed thread?
Definition: email.h:73
short op
Operation, e.g. MUTT_PAT_SCORE.
Definition: pattern.h:51
Pattern matches parent.
Definition: pattern.h:110
static int perform_or(struct PatternList *pat, PatternExecFlags flags, struct Mailbox *m, struct Email *e, struct PatternCache *cache)
Perform a logical OR on a set of Patterns.
Definition: pattern.c:1719
SecurityFlags security
bit 0-10: flags, bit 11,12: application, bit 13: traditional pgp See: ncrypt/lib.h pgplib...
Definition: email.h:39
#define MUTT_MATCH_FULL_ADDRESS
Match the full address.
Definition: pattern.h:76
Expired messages.
Definition: mutt.h:106
int pers_from_all
^~P
Definition: pattern.h:94
#define SEC_SIGN
Email is signed.
Definition: lib.h:81
Unread messages.
Definition: mutt.h:97
Pattern matches email&#39;s body.
Definition: pattern.h:124
static bool msg_search(struct Mailbox *m, struct Pattern *pat, int msgno)
Search an email.
Definition: pattern.c:1135
char * subject
Email&#39;s subject.
Definition: envelope.h:66
#define PGP_KEY
Definition: lib.h:101
bool flagged
Marked important?
Definition: email.h:43
char * newsgroups
List of newsgroups.
Definition: envelope.h:75
#define EMSG(e)
Definition: pattern.c:97
Message is signed.
Definition: pattern.h:139
bool deleted
Email is deleted.
Definition: email.h:45
bool sendmode
Evaluate searches in send-mode.
Definition: pattern.h:59
#define mutt_error(...)
Definition: logging.h:84
bool replied
Email has been replied to.
Definition: email.h:54
static int match_threadparent(struct PatternList *pat, PatternExecFlags flags, struct Mailbox *m, struct MuttThread *t)
Match Pattern against an email&#39;s parent.
Definition: pattern.c:1919
Thread is collapsed.
Definition: pattern.h:114
int mutt_is_subscribed_list_recipient(bool all_addr, struct Envelope *e)
Matches subscribed mailing lists.
Definition: pattern.c:1818
Pattern matches sender.
Definition: pattern.h:128
Both patterns must match.
Definition: pattern.h:107
#define FREE(x)
Definition: memory.h:40
Message is crypographically verified.
Definition: pattern.h:140
int max
Maximum for range checks.
Definition: pattern.h:62
Pattern matches &#39;References:&#39; or &#39;In-Reply-To:&#39; field.
Definition: pattern.h:132
static bool match_update_dynamic_date(struct Pattern *pat)
Update a dynamic date pattern.
Definition: pattern.c:1981
Pattern matches message tags.
Definition: pattern.h:145
struct AddressList to
Email&#39;s &#39;To&#39; list.
Definition: envelope.h:58
struct AddressList sender
Email&#39;s sender.
Definition: envelope.h:61
Pattern matches any address field.
Definition: pattern.h:138
User is a recipient of the email.
Definition: pattern.h:133
static bool match_mime_content_type(const struct Pattern *pat, struct Mailbox *m, struct Email *e)
Match a Pattern against an email&#39;s Content-Type.
Definition: pattern.c:1999
Pattern matches email thread.
Definition: pattern.h:109
int mutt_count_body_parts(struct Mailbox *m, struct Email *e)
Count the MIME Body parts.
Definition: mutt_parse.c:205
Pattern matches &#39;To:&#39; field.
Definition: pattern.h:112
static void set_pattern_cache_value(int *cache_entry, int value)
Sets a value in the PatternCache cache entry.
Definition: pattern.c:2013
Pattern matches raw email text.
Definition: pattern.h:127
struct ListHead references
message references (in reverse order)
Definition: envelope.h:81
&#39;IMAP&#39; Mailbox type
Definition: mailbox.h:53
char * x_label
X-Label.
Definition: envelope.h:72
int mutt_is_list_recipient(bool all_addr, struct Envelope *e)
Matches known mailing lists.
Definition: pattern.c:1831
Pattern matches number of attachments.
Definition: pattern.h:146
#define SEC_GOODSIGN
Email has a valid signature.
Definition: lib.h:82
int list_one
~l
Definition: pattern.h:89
time_t received
Time when the message was placed in the mailbox.
Definition: email.h:82
Message-Id is among results from an external query.
Definition: pattern.h:123
static bool patmatch(const struct Pattern *pat, const char *buf)
Compare a string to a Pattern.
Definition: pattern.c:1116
struct Buffer spam
Spam header.
Definition: envelope.h:80
bool matched
Search matches this Email.
Definition: email.h:68
int msgno
Number displayed to the user.
Definition: email.h:86
int sub_one
~u
Definition: pattern.h:91
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_pattern_comp()

struct PatternList* mutt_pattern_comp ( const char *  s,
PatternCompFlags  flags,
struct Buffer err 
)

Create a Pattern.

Parameters
sPattern string
flagsFlags, e.g. MUTT_PC_FULL_MSG
errBuffer for error messages
Return values
ptrNewly allocated Pattern

Definition at line 1437 of file pattern.c.

1438 {
1439  /* curlist when assigned will always point to a list containing at least one node
1440  * with a Pattern value. */
1441  struct PatternList *curlist = NULL;
1442  struct PatternList *tmp = NULL, *tmp2 = NULL;
1443  struct PatternList *last = NULL;
1444  bool pat_not = false;
1445  bool all_addr = false;
1446  bool pat_or = false;
1447  bool implicit = true; /* used to detect logical AND operator */
1448  bool is_alias = false;
1449  short thread_op;
1450  const struct PatternFlags *entry = NULL;
1451  char *p = NULL;
1452  char *buf = NULL;
1453  struct Buffer ps;
1454 
1455  mutt_buffer_init(&ps);
1456  ps.dptr = (char *) s;
1457  ps.dsize = mutt_str_len(s);
1458 
1459  while (*ps.dptr)
1460  {
1461  SKIPWS(ps.dptr);
1462  switch (*ps.dptr)
1463  {
1464  case '^':
1465  ps.dptr++;
1466  all_addr = !all_addr;
1467  break;
1468  case '!':
1469  ps.dptr++;
1470  pat_not = !pat_not;
1471  break;
1472  case '@':
1473  ps.dptr++;
1474  is_alias = !is_alias;
1475  break;
1476  case '|':
1477  if (!pat_or)
1478  {
1479  if (!curlist)
1480  {
1481  mutt_buffer_printf(err, _("error in pattern at: %s"), ps.dptr);
1482  return NULL;
1483  }
1484 
1485  struct Pattern *pat = SLIST_FIRST(curlist);
1486 
1487  if (SLIST_NEXT(pat, entries))
1488  {
1489  /* A & B | C == (A & B) | C */
1490  tmp = mutt_pattern_node_new();
1491  pat = SLIST_FIRST(tmp);
1492  pat->op = MUTT_PAT_AND;
1493  pat->child = curlist;
1494 
1495  curlist = tmp;
1496  last = curlist;
1497  }
1498 
1499  pat_or = true;
1500  }
1501  ps.dptr++;
1502  implicit = false;
1503  pat_not = false;
1504  all_addr = false;
1505  is_alias = false;
1506  break;
1507  case '%':
1508  case '=':
1509  case '~':
1510  {
1511  struct Pattern *pat = NULL;
1512  if (ps.dptr[1] == '\0')
1513  {
1514  mutt_buffer_printf(err, _("missing pattern: %s"), ps.dptr);
1515  goto cleanup;
1516  }
1517  thread_op = 0;
1518  if (ps.dptr[1] == '(')
1519  thread_op = MUTT_PAT_THREAD;
1520  else if ((ps.dptr[1] == '<') && (ps.dptr[2] == '('))
1521  thread_op = MUTT_PAT_PARENT;
1522  else if ((ps.dptr[1] == '>') && (ps.dptr[2] == '('))
1523  thread_op = MUTT_PAT_CHILDREN;
1524  if (thread_op)
1525  {
1526  ps.dptr++; /* skip ~ */
1527  if ((thread_op == MUTT_PAT_PARENT) || (thread_op == MUTT_PAT_CHILDREN))
1528  ps.dptr++;
1529  p = find_matching_paren(ps.dptr + 1);
1530  if (p[0] != ')')
1531  {
1532  mutt_buffer_printf(err, _("mismatched parentheses: %s"), ps.dptr);
1533  goto cleanup;
1534  }
1535  tmp = mutt_pattern_node_new();
1536  pat = SLIST_FIRST(tmp);
1537  pat->op = thread_op;
1538  if (last)
1539  SLIST_NEXT(SLIST_FIRST(last), entries) = pat;
1540  else
1541  curlist = tmp;
1542  last = tmp;
1543  pat->pat_not ^= pat_not;
1544  pat->all_addr |= all_addr;
1545  pat->is_alias |= is_alias;
1546  pat_not = false;
1547  all_addr = false;
1548  is_alias = false;
1549  /* compile the sub-expression */
1550  buf = mutt_strn_dup(ps.dptr + 1, p - (ps.dptr + 1));
1551  tmp2 = mutt_pattern_comp(buf, flags, err);
1552  if (!tmp2)
1553  {
1554  FREE(&buf);
1555  goto cleanup;
1556  }
1557  FREE(&buf);
1558  pat->child = tmp2;
1559  ps.dptr = p + 1; /* restore location */
1560  break;
1561  }
1562  if (implicit && pat_or)
1563  {
1564  /* A | B & C == (A | B) & C */
1565  tmp = mutt_pattern_node_new();
1566  pat = SLIST_FIRST(tmp);
1567  pat->op = MUTT_PAT_OR;
1568  pat->child = curlist;
1569  curlist = tmp;
1570  last = tmp;
1571  pat_or = false;
1572  }
1573 
1574  tmp = mutt_pattern_node_new();
1575  pat = SLIST_FIRST(tmp);
1576  pat->pat_not = pat_not;
1577  pat->all_addr = all_addr;
1578  pat->is_alias = is_alias;
1579  pat->string_match = (ps.dptr[0] == '=');
1580  pat->group_match = (ps.dptr[0] == '%');
1581  pat_not = false;
1582  all_addr = false;
1583  is_alias = false;
1584 
1585  if (last)
1586  SLIST_NEXT(SLIST_FIRST(last), entries) = pat;
1587  else
1588  curlist = tmp;
1589  if (curlist != last)
1590  FREE(&last);
1591  last = tmp;
1592 
1593  ps.dptr++; /* move past the ~ */
1594  entry = lookup_tag(*ps.dptr);
1595  if (!entry)
1596  {
1597  mutt_buffer_printf(err, _("%c: invalid pattern modifier"), *ps.dptr);
1598  goto cleanup;
1599  }
1600  if (entry->flags && ((flags & entry->flags) == 0))
1601  {
1602  mutt_buffer_printf(err, _("%c: not supported in this mode"), *ps.dptr);
1603  goto cleanup;
1604  }
1605  if (flags & MUTT_PC_SEND_MODE_SEARCH)
1606  pat->sendmode = true;
1607 
1608  pat->op = entry->op;
1609 
1610  ps.dptr++; /* eat the operator and any optional whitespace */
1611  SKIPWS(ps.dptr);
1612 
1613  if (entry->eat_arg)
1614  {
1615  if (ps.dptr[0] == '\0')
1616  {
1617  mutt_buffer_printf(err, "%s", _("missing parameter"));
1618  goto cleanup;
1619  }
1620  if (!entry->eat_arg(pat, flags, &ps, err))
1621  {
1622  goto cleanup;
1623  }
1624  }
1625  implicit = true;
1626  break;
1627  }
1628 
1629  case '(':
1630  {
1631  p = find_matching_paren(ps.dptr + 1);
1632  if (p[0] != ')')
1633  {
1634  mutt_buffer_printf(err, _("mismatched parentheses: %s"), ps.dptr);
1635  goto cleanup;
1636  }
1637  /* compile the sub-expression */
1638  buf = mutt_strn_dup(ps.dptr + 1, p - (ps.dptr + 1));
1639  tmp = mutt_pattern_comp(buf, flags, err);
1640  FREE(&buf);
1641  if (!tmp)
1642  goto cleanup;
1643  struct Pattern *pat = SLIST_FIRST(tmp);
1644  if (last)
1645  SLIST_NEXT(SLIST_FIRST(last), entries) = pat;
1646  else
1647  curlist = tmp;
1648  last = tmp;
1649  pat = SLIST_FIRST(tmp);
1650  pat->pat_not ^= pat_not;
1651  pat->all_addr |= all_addr;
1652  pat->is_alias |= is_alias;
1653  pat_not = false;
1654  all_addr = false;
1655  is_alias = false;
1656  ps.dptr = p + 1; /* restore location */
1657  break;
1658  }
1659 
1660  default:
1661  mutt_buffer_printf(err, _("error in pattern at: %s"), ps.dptr);
1662  goto cleanup;
1663  }
1664  }
1665  if (!curlist)
1666  {
1667  mutt_buffer_strcpy(err, _("empty pattern"));
1668  return NULL;
1669  }
1670  if (curlist != tmp)
1671  FREE(&tmp);
1672  if (SLIST_NEXT(SLIST_FIRST(curlist), entries))
1673  {
1674  tmp = mutt_pattern_node_new();
1675  struct Pattern *pat = SLIST_FIRST(tmp);
1676  pat->op = pat_or ? MUTT_PAT_OR : MUTT_PAT_AND;
1677  pat->child = curlist;
1678  curlist = tmp;
1679  }
1680 
1681  return curlist;
1682 
1683 cleanup:
1684  mutt_pattern_free(&curlist);
1685  return NULL;
1686 }
struct PatternList * child
Arguments to logical operation.
Definition: pattern.h:63
int flags
Pattern flags, e.g. MUTT_PC_FULL_MSG.
Definition: pattern.c:171
bool group_match
Check a group of Addresses.
Definition: pattern.h:55
String manipulation buffer.
Definition: buffer.h:33
#define _(a)
Definition: message.h:28
static char * find_matching_paren(char *s)
Find the matching parenthesis.
Definition: pattern.c:1363
Pattern matches a child email.
Definition: pattern.h:111
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:160
A simple (non-regex) pattern.
Definition: pattern.h:49
bool is_alias
Is there an alias for this Address?
Definition: pattern.h:57
int op
Operation to perform, e.g. MUTT_PAT_SCORE.
Definition: pattern.c:170
bool all_addr
All Addresses in the list must match.
Definition: pattern.h:53
char * mutt_strn_dup(const char *begin, size_t len)
Duplicate a sub-string.
Definition: string.c:553
static const struct PatternFlags * lookup_tag(char tag)
Lookup a pattern modifier.
Definition: pattern.c:1348
#define SKIPWS(ch)
Definition: string2.h:46
bool string_match
Check a string for a match.
Definition: pattern.h:54
bool pat_not
Pattern should be inverted (not)
Definition: pattern.h:52
static struct PatternList * mutt_pattern_node_new(void)
Create a new list containing a Pattern.
Definition: pattern.c:1421
#define SLIST_NEXT(elm, field)
Definition: queue.h:269
struct PatternList * mutt_pattern_comp(const char *s, PatternCompFlags flags, struct Buffer *err)
Create a Pattern.
Definition: pattern.c:1437
#define SLIST_FIRST(head)
Definition: queue.h:228
Either pattern can match.
Definition: pattern.h:108
void mutt_pattern_free(struct PatternList **pat)
Free a Pattern.
Definition: pattern.c:1385
short op
Operation, e.g. MUTT_PAT_SCORE.
Definition: pattern.h:51
Pattern matches parent.
Definition: pattern.h:110
size_t mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:312
size_t mutt_str_len(const char *a)
Calculate the length of a string, safely.
Definition: string.c:636
bool sendmode
Evaluate searches in send-mode.
Definition: pattern.h:59
#define MUTT_PC_SEND_MODE_SEARCH
Allow send-mode body searching.
Definition: pattern.h:44
Both patterns must match.
Definition: pattern.h:107
#define FREE(x)
Definition: memory.h:40
Pattern matches email thread.
Definition: pattern.h:109
Mapping between user character and internal constant.
Definition: pattern.c:167
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:46
bool(* eat_arg)(struct Pattern *pat, int flags, struct Buffer *s, struct Buffer *err)
Function to parse a pattern.
Definition: pattern.c:181
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_check_simple()

void mutt_check_simple ( struct Buffer buf,
const char *  simple 
)

Convert a simple search into a real request.

Parameters
bufBuffer for the result
simpleSearch string to convert

Definition at line 2430 of file pattern.c.

2431 {
2432  bool do_simple = true;
2433 
2434  for (const char *p = mutt_b2s(buf); p && (p[0] != '\0'); p++)
2435  {
2436  if ((p[0] == '\\') && (p[1] != '\0'))
2437  p++;
2438  else if ((p[0] == '~') || (p[0] == '=') || (p[0] == '%'))
2439  {
2440  do_simple = false;
2441  break;
2442  }
2443  }
2444 
2445  /* XXX - is mutt_istr_cmp() right here, or should we use locale's
2446  * equivalences? */
2447 
2448  if (do_simple) /* yup, so spoof a real request */
2449  {
2450  /* convert old tokens into the new format */
2451  if (mutt_istr_equal("all", mutt_b2s(buf)) || mutt_str_equal("^", mutt_b2s(buf)) ||
2452  mutt_str_equal(".", mutt_b2s(buf))) /* ~A is more efficient */
2453  {
2454  mutt_buffer_strcpy(buf, "~A");
2455  }
2456  else if (mutt_istr_equal("del", mutt_b2s(buf)))
2457  mutt_buffer_strcpy(buf, "~D");
2458  else if (mutt_istr_equal("flag", mutt_b2s(buf)))
2459  mutt_buffer_strcpy(buf, "~F");
2460  else if (mutt_istr_equal("new", mutt_b2s(buf)))
2461  mutt_buffer_strcpy(buf, "~N");
2462  else if (mutt_istr_equal("old", mutt_b2s(buf)))
2463  mutt_buffer_strcpy(buf, "~O");
2464  else if (mutt_istr_equal("repl", mutt_b2s(buf)))
2465  mutt_buffer_strcpy(buf, "~Q");
2466  else if (mutt_istr_equal("read", mutt_b2s(buf)))
2467  mutt_buffer_strcpy(buf, "~R");
2468  else if (mutt_istr_equal("tag", mutt_b2s(buf)))
2469  mutt_buffer_strcpy(buf, "~T");
2470  else if (mutt_istr_equal("unread", mutt_b2s(buf)))
2471  mutt_buffer_strcpy(buf, "~U");
2472  else
2473  {
2474  struct Buffer *tmp = mutt_buffer_pool_get();
2475  quote_simple(mutt_b2s(buf), tmp);
2476  mutt_file_expand_fmt(buf, simple, mutt_b2s(tmp));
2478  }
2479  }
2480 }
bool mutt_str_equal(const char *a, const char *b)
Compare two strings.
Definition: string.c:876
struct Buffer * mutt_buffer_pool_get(void)
Get a Buffer from the pool.
Definition: pool.c:101
static void quote_simple(const char *str, struct Buffer *buf)
Apply simple quoting to a string.
Definition: pattern.c:2412
void mutt_buffer_pool_release(struct Buffer **pbuf)
Free a Buffer from the pool.
Definition: pool.c:112
String manipulation buffer.
Definition: buffer.h:33
bool mutt_istr_equal(const char *a, const char *b)
Compare two strings, ignoring case.
Definition: string.c:888
#define mutt_b2s(buf)
Definition: buffer.h:41
union Pattern::@1 p
void mutt_file_expand_fmt(struct Buffer *dest, const char *fmt, const char *src)
Replace s in a string with a filename.
Definition: file.c:1440
size_t mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:312
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_pattern_free()

void mutt_pattern_free ( struct PatternList **  pat)

Free a Pattern.

Parameters
[out]patPattern to free

Definition at line 1385 of file pattern.c.

1386 {
1387  if (!pat || !*pat)
1388  return;
1389 
1390  struct Pattern *np = SLIST_FIRST(*pat), *next = NULL;
1391 
1392  while (np)
1393  {
1394  next = SLIST_NEXT(np, entries);
1395 
1396  if (np->is_multi)
1398  else if (np->string_match || np->dynamic)
1399  FREE(&np->p.str);
1400  else if (np->group_match)
1401  np->p.group = NULL;
1402  else if (np->p.regex)
1403  {
1404  regfree(np->p.regex);
1405  FREE(&np->p.regex);
1406  }
1407 
1408  mutt_pattern_free(&np->child);
1409  FREE(&np);
1410 
1411  np = next;
1412  }
1413 
1414  FREE(pat);
1415 }
struct PatternList * child
Arguments to logical operation.
Definition: pattern.h:63
regex_t * regex
Compiled regex, for non-pattern matching.
Definition: pattern.h:65
bool group_match
Check a group of Addresses.
Definition: pattern.h:55
bool is_multi
Multiple case (only for ~I pattern now)
Definition: pattern.h:60
void mutt_list_free(struct ListHead *h)
Free a List AND its strings.
Definition: list.c:122
A simple (non-regex) pattern.
Definition: pattern.h:49
bool dynamic
Evaluate date ranges at run time.
Definition: pattern.h:58
bool string_match
Check a string for a match.
Definition: pattern.h:54
#define SLIST_NEXT(elm, field)
Definition: queue.h:269
#define SLIST_FIRST(head)
Definition: queue.h:228
union Pattern::@1 p
void mutt_pattern_free(struct PatternList **pat)
Free a Pattern.
Definition: pattern.c:1385
char * str
String, if string_match is set.
Definition: pattern.h:67
struct Group * group
Address group if group_match is set.
Definition: pattern.h:66
#define FREE(x)
Definition: memory.h:40
struct ListHead multi_cases
Multiple strings for ~I pattern.
Definition: pattern.h:68
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_which_case()

int mutt_which_case ( const char *  s)

◆ mutt_is_list_recipient()

int mutt_is_list_recipient ( bool  all_addr,
struct Envelope e 
)

Matches known mailing lists.

Parameters
all_addrIf true, ALL Addresses must be mailing lists
eEnvelope
Return values
true
  • One Address is a mailing list (all_addr is false)
  • All the Addresses are mailing lists (all_addr is true)

Definition at line 1831 of file pattern.c.

1832 {
1834 }
bool mutt_is_mail_list(const struct Address *addr)
Is this the email address of a mailing list? - Implements addr_predicate_t.
Definition: maillist.c:45
bool all_addr
All Addresses in the list must match.
Definition: pattern.h:53
static int mutt_is_predicate_recipient(bool all_addr, struct Envelope *e, addr_predicate_t p)
Test an Envelopes Addresses using a predicate function.
Definition: pattern.c:1794
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_is_subscribed_list_recipient()

int mutt_is_subscribed_list_recipient ( bool  all_addr,
struct Envelope e 
)

Matches subscribed mailing lists.

Parameters
all_addrIf true, ALL Addresses must be on the subscribed list
eEnvelope
Return values
true
  • One Address is subscribed (all_addr is false)
  • All the Addresses are subscribed (all_addr is true)

Definition at line 1818 of file pattern.c.

1819 {
1821 }
bool mutt_is_subscribed_list(const struct Address *addr)
Is this the email address of a user-subscribed mailing list? - Implements addr_predicate_t.
Definition: maillist.c:57
bool all_addr
All Addresses in the list must match.
Definition: pattern.h:53
static int mutt_is_predicate_recipient(bool all_addr, struct Envelope *e, addr_predicate_t p)
Test an Envelopes Addresses using a predicate function.
Definition: pattern.c:1794
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_pattern_func()

int mutt_pattern_func ( int  op,
char *  prompt 
)

Perform some Pattern matching.

Parameters
opOperation to perform, e.g. MUTT_LIMIT
promptPrompt to show the user
Return values
0Success
-1Failure

Definition at line 2554 of file pattern.c.

2555 {
2556  if (!Context || !Context->mailbox)
2557  return -1;
2558 
2559  struct Buffer err;
2560  int rc = -1;
2561  struct Progress progress;
2562  struct Buffer *buf = mutt_buffer_pool_get();
2563  struct Mailbox *m = Context->mailbox;
2564 
2566  if (prompt || (op != MUTT_LIMIT))
2567  {
2568  if ((mutt_buffer_get_field(prompt, buf, MUTT_PATTERN | MUTT_CLEAR) != 0) ||
2569  mutt_buffer_is_empty(buf))
2570  {
2572  return -1;
2573  }
2574  }
2575 
2576  mutt_message(_("Compiling search pattern..."));
2577 
2578  char *simple = mutt_buffer_strdup(buf);
2580 
2581  mutt_buffer_init(&err);
2582  err.dsize = 256;
2583  err.data = mutt_mem_malloc(err.dsize);
2584  struct PatternList *pat = mutt_pattern_comp(buf->data, MUTT_PC_FULL_MSG, &err);
2585  if (!pat)
2586  {
2587  mutt_error("%s", err.data);
2588  goto bail;
2589  }
2590 
2591 #ifdef USE_IMAP
2592  if ((m->type == MUTT_IMAP) && (!imap_search(m, pat)))
2593  goto bail;
2594 #endif
2595 
2596  mutt_progress_init(&progress, _("Executing command on matching messages..."),
2597  MUTT_PROGRESS_READ, (op == MUTT_LIMIT) ? m->msg_count : m->vcount);
2598 
2599  if (op == MUTT_LIMIT)
2600  {
2601  m->vcount = 0;
2602  Context->vsize = 0;
2603  Context->collapsed = false;
2604  int padding = mx_msg_padding_size(m);
2605 
2606  for (int i = 0; i < m->msg_count; i++)
2607  {
2608  struct Email *e = m->emails[i];
2609  if (!e)
2610  break;
2611 
2612  mutt_progress_update(&progress, i, -1);
2613  /* new limit pattern implicitly uncollapses all threads */
2614  e->vnum = -1;
2615  e->limited = false;
2616  e->collapsed = false;
2617  e->num_hidden = 0;
2618  if (mutt_pattern_exec(SLIST_FIRST(pat), MUTT_MATCH_FULL_ADDRESS, m, e, NULL))
2619  {
2620  e->vnum = m->vcount;
2621  e->limited = true;
2622  m->v2r[m->vcount] = i;
2623  m->vcount++;
2624  struct Body *b = e->content;
2625  Context->vsize += b->length + b->offset - b->hdr_offset + padding;
2626  }
2627  }
2628  }
2629  else
2630  {
2631  for (int i = 0; i < m->vcount; i++)
2632  {
2633  struct Email *e = mutt_get_virt_email(Context->mailbox, i);
2634  if (!e)
2635  continue;
2636  mutt_progress_update(&progress, i, -1);
2637  if (mutt_pattern_exec(SLIST_FIRST(pat), MUTT_MATCH_FULL_ADDRESS, m, e, NULL))
2638  {
2639  switch (op)
2640  {
2641  case MUTT_UNDELETE:
2642  mutt_set_flag(m, e, MUTT_PURGE, false);
2643  /* fallthrough */
2644  case MUTT_DELETE:
2645  mutt_set_flag(m, e, MUTT_DELETE, (op == MUTT_DELETE));
2646  break;
2647  case MUTT_TAG:
2648  case MUTT_UNTAG:
2649  mutt_set_flag(m, e, MUTT_TAG, (op == MUTT_TAG));
2650  break;
2651  }
2652  }
2653  }
2654  }
2655 
2656  mutt_clear_error();
2657 
2658  if (op == MUTT_LIMIT)
2659  {
2660  /* drop previous limit pattern */
2661  FREE(&Context->pattern);
2663 
2664  if (m->msg_count && !m->vcount)
2665  mutt_error(_("No messages matched criteria"));
2666 
2667  /* record new limit pattern, unless match all */
2668  const char *pbuf = buf->data;
2669  while (*pbuf == ' ')
2670  pbuf++;
2671  if (!mutt_str_equal(pbuf, "~A"))
2672  {
2673  Context->pattern = simple;
2674  simple = NULL; /* don't clobber it */
2676  }
2677  }
2678 
2679  rc = 0;
2680 
2681 bail:
2683  FREE(&simple);
2684  mutt_pattern_free(&pat);
2685  FREE(&err.data);
2686 
2687  return rc;
2688 }
bool mutt_str_equal(const char *a, const char *b)
Compare two strings.
Definition: string.c:876
struct Email ** emails
Array of Emails.
Definition: mailbox.h:99
bool imap_search(struct Mailbox *m, const struct PatternList *pat)
Find messages in mailbox matching a pattern.
Definition: search.c:226
The "current" mailbox.
Definition: context.h:37
enum MailboxType type
Mailbox type.
Definition: mailbox.h:105
#define NONULL(x)
Definition: string2.h:37
int msg_count
Total number of messages.
Definition: mailbox.h:91
#define mutt_set_flag(m, e, flag, bf)
Definition: protos.h:68
The envelope/body of an email.
Definition: email.h:37
#define MUTT_CLEAR
Clear input if printable character is pressed.
Definition: mutt.h:62
struct Buffer * mutt_buffer_pool_get(void)
Get a Buffer from the pool.
Definition: pool.c:101
struct Email * mutt_get_virt_email(struct Mailbox *m, int vnum)
Get a virtual Email.
Definition: context.c:406
#define mutt_message(...)
Definition: logging.h:83
void mutt_check_simple(struct Buffer *buf, const char *simple)
Convert a simple search into a real request.
Definition: pattern.c:2430
Messages in limited view.
Definition: mutt.h:105
void mutt_buffer_pool_release(struct Buffer **pbuf)
Free a Buffer from the pool.
Definition: pool.c:112
struct Body * content
List of MIME parts.
Definition: email.h:90
char * mutt_buffer_strdup(struct Buffer *buf)
Copy a Buffer&#39;s string.
Definition: buffer.c:432
String manipulation buffer.
Definition: buffer.h:33
Messages to be un-deleted.
Definition: mutt.h:99
LOFF_T offset
offset where the actual data begins
Definition: body.h:44
#define _(a)
Definition: message.h:28
Messages to be purged (bypass trash)
Definition: mutt.h:100
A progress bar.
Definition: progress.h:50
#define MUTT_PATTERN
Pattern mode - only used for history classes.
Definition: mutt.h:64
int vcount
The number of virtual messages.
Definition: mailbox.h:102
The body of an email.
Definition: body.h:34
void mutt_progress_update(struct Progress *progress, size_t pos, int percent)
Update the state of the progress bar.
Definition: progress.c:212
struct Mailbox * mailbox
Definition: context.h:50
Progress tracks elements, according to C_ReadInc.
Definition: progress.h:42
bool limited
Is this message in a limited view?
Definition: email.h:74
void mutt_clear_error(void)
Clear the message line (bottom line of screen)
Definition: mutt_logging.c:113
off_t vsize
Definition: context.h:39
int mutt_pattern_exec(struct Pattern *pat, PatternExecFlags flags, struct Mailbox *m, struct Email *e, struct PatternCache *cache)
Match a pattern against an email header.
Definition: pattern.c:2129
struct PatternList * mutt_pattern_comp(const char *s, PatternCompFlags flags, struct Buffer *err)
Create a Pattern.
Definition: pattern.c:1437
#define SLIST_FIRST(head)
Definition: queue.h:228
LOFF_T length
length (in bytes) of attachment
Definition: body.h:45
Messages to be deleted.
Definition: mutt.h:98
A mailbox.
Definition: mailbox.h:81
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:90
size_t num_hidden
Number of hidden messages in this view.
Definition: email.h:75
struct PatternList * limit_pattern
Compiled limit pattern.
Definition: context.h:41
Tagged messages.
Definition: mutt.h:103
char * data
Pointer to data.
Definition: buffer.h:35
void mutt_pattern_free(struct PatternList **pat)
Free a Pattern.
Definition: pattern.c:1385
bool collapsed
Is this message part of a collapsed thread?
Definition: email.h:73
int vnum
Virtual message number.
Definition: email.h:87
void mutt_progress_init(struct Progress *progress, const char *msg, enum ProgressType type, size_t size)
Set up a progress bar.
Definition: progress.c:153
#define MUTT_MATCH_FULL_ADDRESS
Match the full address.
Definition: pattern.h:76
size_t mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:312
WHERE char * C_SimpleSearch
Config: Pattern to search for when search doesn&#39;t contain ~&#39;s.
Definition: mutt_globals.h:110
#define mutt_buffer_get_field(field, buf, complete)
Definition: curs_lib.h:85
int * v2r
Mapping from virtual to real msgno.
Definition: mailbox.h:101
bool collapsed
Are all threads collapsed?
Definition: context.h:48
#define mutt_error(...)
Definition: logging.h:84
#define FREE(x)
Definition: memory.h:40
#define MUTT_PC_FULL_MSG
Enable body and header matching.
Definition: pattern.h:42
Messages to be un-tagged.
Definition: mutt.h:104
int mx_msg_padding_size(struct Mailbox *m)
Bytes of padding between messages - Wrapper for MxOps::msg_padding_size()
Definition: mx.c:1543
long hdr_offset
Offset in stream where the headers begin.
Definition: body.h:42
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:46
bool mutt_buffer_is_empty(const struct Buffer *buf)
Is the Buffer empty?
Definition: buffer.c:252
&#39;IMAP&#39; Mailbox type
Definition: mailbox.h:53
char * pattern
Limit pattern string.
Definition: context.h:40
static unsigned char * pbuf
Cache PGP data packet.
Definition: pgppacket.c:38
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_search_command()

int mutt_search_command ( int  cur,
int  op 
)

Perform a search.

Parameters
curIndex number of current email
opOperation to perform, e.g. OP_SEARCH_NEXT
Return values
>=0 Index of matching email
-1No match, or error

Definition at line 2697 of file pattern.c.

2698 {
2699  struct Progress progress;
2700 
2701  if ((*LastSearch == '\0') || ((op != OP_SEARCH_NEXT) && (op != OP_SEARCH_OPPOSITE)))
2702  {
2703  char buf[256];
2704  mutt_str_copy(buf, (LastSearch[0] != '\0') ? LastSearch : "", sizeof(buf));
2705  if ((mutt_get_field(((op == OP_SEARCH) || (op == OP_SEARCH_NEXT)) ?
2706  _("Search for: ") :
2707  _("Reverse search for: "),
2708  buf, sizeof(buf), MUTT_CLEAR | MUTT_PATTERN) != 0) ||
2709  (buf[0] == '\0'))
2710  {
2711  return -1;
2712  }
2713 
2714  if ((op == OP_SEARCH) || (op == OP_SEARCH_NEXT))
2715  OptSearchReverse = false;
2716  else
2717  OptSearchReverse = true;
2718 
2719  /* compare the *expanded* version of the search pattern in case
2720  * $simple_search has changed while we were searching */
2721  struct Buffer *tmp = mutt_buffer_pool_get();
2722  mutt_buffer_strcpy(tmp, buf);
2724 
2726  {
2727  struct Buffer err;
2728  mutt_buffer_init(&err);
2729  OptSearchInvalid = true;
2730  mutt_str_copy(LastSearch, buf, sizeof(LastSearch));
2732  mutt_message(_("Compiling search pattern..."));
2734  err.dsize = 256;
2735  err.data = mutt_mem_malloc(err.dsize);
2737  if (!SearchPattern)
2738  {
2740  mutt_error("%s", err.data);
2741  FREE(&err.data);
2742  LastSearch[0] = '\0';
2743  LastSearchExpn[0] = '\0';
2744  return -1;
2745  }
2746  FREE(&err.data);
2747  mutt_clear_error();
2748  }
2749 
2751  }
2752 
2753  if (OptSearchInvalid)
2754  {
2755  for (int i = 0; i < Context->mailbox->msg_count; i++)
2756  Context->mailbox->emails[i]->searched = false;
2757 #ifdef USE_IMAP
2758  if ((Context->mailbox->type == MUTT_IMAP) &&
2760  return -1;
2761 #endif
2762  OptSearchInvalid = false;
2763  }
2764 
2765  int incr = OptSearchReverse ? -1 : 1;
2766  if (op == OP_SEARCH_OPPOSITE)
2767  incr = -incr;
2768 
2769  mutt_progress_init(&progress, _("Searching..."), MUTT_PROGRESS_READ,
2770  Context->mailbox->vcount);
2771 
2772  for (int i = cur + incr, j = 0; j != Context->mailbox->vcount; j++)
2773  {
2774  const char *msg = NULL;
2775  mutt_progress_update(&progress, j, -1);
2776  if (i > Context->mailbox->vcount - 1)
2777  {
2778  i = 0;
2779  if (C_WrapSearch)
2780  msg = _("Search wrapped to top");
2781  else
2782  {
2783  mutt_message(_("Search hit bottom without finding match"));
2784  return -1;
2785  }
2786  }
2787  else if (i < 0)
2788  {
2789  i = Context->mailbox->vcount - 1;
2790  if (C_WrapSearch)
2791  msg = _("Search wrapped to bottom");
2792  else
2793  {
2794  mutt_message(_("Search hit top without finding match"));
2795  return -1;
2796  }
2797  }
2798 
2799  struct Email *e = mutt_get_virt_email(Context->mailbox, i);
2800  if (e->searched)
2801  {
2802  /* if we've already evaluated this message, use the cached value */
2803  if (e->matched)
2804  {
2805  mutt_clear_error();
2806  if (msg && *msg)
2807  mutt_message(msg);
2808  return i;
2809  }
2810  }
2811  else
2812  {
2813  /* remember that we've already searched this message */
2814  e->searched = true;
2816  Context->mailbox, e, NULL);
2817  if (e->matched > 0)
2818  {
2819  mutt_clear_error();
2820  if (msg && *msg)
2821  mutt_message(msg);
2822  return i;
2823  }
2824  }
2825 
2826  if (SigInt)
2827  {
2828  mutt_error(_("Search interrupted"));
2829  SigInt = 0;
2830  return -1;
2831  }
2832 
2833  i += incr;
2834  }
2835 
2836  mutt_error(_("Not found"));
2837  return -1;
2838 }
bool mutt_str_equal(const char *a, const char *b)
Compare two strings.
Definition: string.c:876
struct Email ** emails
Array of Emails.
Definition: mailbox.h:99
bool imap_search(struct Mailbox *m, const struct PatternList *pat)
Find messages in mailbox matching a pattern.
Definition: search.c:226
The "current" mailbox.
Definition: context.h:37
enum MailboxType type
Mailbox type.
Definition: mailbox.h:105
#define NONULL(x)
Definition: string2.h:37
int msg_count
Total number of messages.
Definition: mailbox.h:91
The envelope/body of an email.
Definition: email.h:37
#define MUTT_CLEAR
Clear input if printable character is pressed.
Definition: mutt.h:62
struct Buffer * mutt_buffer_pool_get(void)
Get a Buffer from the pool.
Definition: pool.c:101
struct Email * mutt_get_virt_email(struct Mailbox *m, int vnum)
Get a virtual Email.
Definition: context.c:406
if(!test_colorize_)
Definition: acutest.h:499
#define mutt_message(...)
Definition: logging.h:83
WHERE SIG_ATOMIC_VOLATILE_T SigInt
true after SIGINT is received
Definition: mutt_globals.h:75
void mutt_check_simple(struct Buffer *buf, const char *simple)
Convert a simple search into a real request.
Definition: pattern.c:2430
void mutt_buffer_pool_release(struct Buffer **pbuf)
Free a Buffer from the pool.
Definition: pool.c:112
String manipulation buffer.
Definition: buffer.h:33
#define _(a)
Definition: message.h:28
static char LastSearch[256]
last pattern searched for
Definition: pattern.c:200
bool searched
Email has been searched.
Definition: email.h:67
A progress bar.
Definition: progress.h:50
#define MUTT_PATTERN
Pattern mode - only used for history classes.
Definition: mutt.h:64
#define mutt_get_field(field, buf, buflen, complete)
Definition: curs_lib.h:91
int vcount
The number of virtual messages.
Definition: mailbox.h:102
void mutt_progress_update(struct Progress *progress, size_t pos, int percent)
Update the state of the progress bar.
Definition: progress.c:212
struct Mailbox * mailbox
Definition: context.h:50
Progress tracks elements, according to C_ReadInc.
Definition: progress.h:42
void mutt_clear_error(void)
Clear the message line (bottom line of screen)
Definition: mutt_logging.c:113
#define mutt_b2s(buf)
Definition: buffer.h:41
int mutt_pattern_exec(struct Pattern *pat, PatternExecFlags flags, struct Mailbox *m, struct Email *e, struct PatternCache *cache)
Match a pattern against an email header.
Definition: pattern.c:2129
struct PatternList * mutt_pattern_comp(const char *s, PatternCompFlags flags, struct Buffer *err)
Create a Pattern.
Definition: pattern.c:1437
static char LastSearchExpn[1024]
expanded version of LastSearch
Definition: pattern.c:201
#define SLIST_FIRST(head)
Definition: queue.h:228
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:90
char * data
Pointer to data.
Definition: buffer.h:35
void mutt_pattern_free(struct PatternList **pat)
Free a Pattern.
Definition: pattern.c:1385
WHERE bool OptSearchInvalid
(pseudo) used to invalidate the search pattern
Definition: options.h:52
void mutt_progress_init(struct Progress *progress, const char *msg, enum ProgressType type, size_t size)
Set up a progress bar.
Definition: progress.c:153
#define MUTT_MATCH_FULL_ADDRESS
Match the full address.
Definition: pattern.h:76
WHERE bool C_WrapSearch
Config: Wrap around when the search hits the end.
Definition: mutt_globals.h:172
size_t mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:312
WHERE char * C_SimpleSearch
Config: Pattern to search for when search doesn&#39;t contain ~&#39;s.
Definition: mutt_globals.h:110
static struct PatternList * SearchPattern
current search pattern
Definition: pattern.c:199
size_t mutt_str_copy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:721
#define mutt_error(...)
Definition: logging.h:84
#define FREE(x)
Definition: memory.h:40
#define MUTT_PC_FULL_MSG
Enable body and header matching.
Definition: pattern.h:42
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:46
&#39;IMAP&#39; Mailbox type
Definition: mailbox.h:53
WHERE bool OptSearchReverse
(pseudo) used by ci_search_command
Definition: options.h:53
bool matched
Search matches this Email.
Definition: email.h:68
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_limit_current_thread()

bool mutt_limit_current_thread ( struct Email e)

Limit the email view to the current thread.

Parameters
eCurrent Email
Return values
trueSuccess
falseFailure

Definition at line 2507 of file pattern.c.

2508 {
2509  if (!e || !Context || !Context->mailbox)
2510  return false;
2511 
2512  struct MuttThread *me = top_of_thread(e);
2513  if (!me)
2514  return false;
2515 
2516  struct Mailbox *m = Context->mailbox;
2517 
2518  m->vcount = 0;
2519  Context->vsize = 0;
2520  Context->collapsed = false;
2521 
2522  for (int i = 0; i < m->msg_count; i++)
2523  {
2524  e = m->emails[i];
2525  if (!e)
2526  break;
2527 
2528  e->vnum = -1;
2529  e->limited = false;
2530  e->collapsed = false;
2531  e->num_hidden = 0;
2532 
2533  if (top_of_thread(e) == me)
2534  {
2535  struct Body *body = e->content;
2536 
2537  e->vnum = m->vcount;
2538  e->limited = true;
2539  m->v2r[m->vcount] = i;
2540  m->vcount++;
2541  Context->vsize += (body->length + body->offset - body->hdr_offset);
2542  }
2543  }
2544  return true;
2545 }
struct Email ** emails
Array of Emails.
Definition: mailbox.h:99
The "current" mailbox.
Definition: context.h:37
int msg_count
Total number of messages.
Definition: mailbox.h:91
struct Body * content
List of MIME parts.
Definition: email.h:90
LOFF_T offset
offset where the actual data begins
Definition: body.h:44
int vcount
The number of virtual messages.
Definition: mailbox.h:102
The body of an email.
Definition: body.h:34
struct Mailbox * mailbox
Definition: context.h:50
bool limited
Is this message in a limited view?
Definition: email.h:74
off_t vsize
Definition: context.h:39
LOFF_T length
length (in bytes) of attachment
Definition: body.h:45
A mailbox.
Definition: mailbox.h:81
static struct MuttThread * top_of_thread(struct Email *e)
Find the first email in the current thread.
Definition: pattern.c:2488
size_t num_hidden
Number of hidden messages in this view.
Definition: email.h:75
bool collapsed
Is this message part of a collapsed thread?
Definition: email.h:73
int vnum
Virtual message number.
Definition: email.h:87
An Email conversation.
Definition: thread.h:34
int * v2r
Mapping from virtual to real msgno.
Definition: mailbox.h:101
bool collapsed
Are all threads collapsed?
Definition: context.h:48
long hdr_offset
Offset in stream where the headers begin.
Definition: body.h:42
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

Variable Documentation

◆ C_ThoroughSearch

bool C_ThoroughSearch

Config: Decode headers and messages before searching them.

Definition at line 75 of file pattern.c.