NeoMutt  2018-07-16 +952-a2da0a
Teaching an old dog new tricks
DOXYGEN
init.c File Reference

Config/command parsing. More...

#include "config.h"
#include <ctype.h>
#include <errno.h>
#include <inttypes.h>
#include <limits.h>
#include <pwd.h>
#include <regex.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/utsname.h>
#include <unistd.h>
#include <wchar.h>
#include "mutt/mutt.h"
#include "email/lib.h"
#include "mutt.h"
#include "init.h"
#include "alias.h"
#include "context.h"
#include "filter.h"
#include "group.h"
#include "hcache/hcache.h"
#include "keymap.h"
#include "menu.h"
#include "mutt_curses.h"
#include "mutt_window.h"
#include "mx.h"
#include "myvar.h"
#include "ncrypt/ncrypt.h"
#include "options.h"
#include "protos.h"
#include "sidebar.h"
#include "version.h"
#include "notmuch/mutt_notmuch.h"
#include "imap/imap.h"
#include <libintl.h>
+ Include dependency graph for init.c:

Go to the source code of this file.

Macros

#define MAXERRS   128
 
#define NUMVARS   mutt_array_size(MuttVars)
 
#define NUMCOMMANDS   mutt_array_size(Commands)
 

Enumerations

enum  GroupState { GS_NONE, GS_RX, GS_ADDR }
 Type of email address group. More...
 

Functions

static void add_to_stailq (struct ListHead *head, const char *str)
 Add a string to a list. More...
 
static void alternates_clean (void)
 Clear the recipient valid flag of all emails. More...
 
static void attachments_clean (void)
 always wise to do what someone else did before More...
 
static void matches_ensure_morespace (int current)
 Allocate more space for auto-completion. More...
 
static void candidate (char *try, const char *src, char *dest, size_t dlen)
 helper function for completion More...
 
static void clear_subject_mods (void)
 Clear out all modified email subjects. More...
 
static int complete_all_nm_tags (const char *pt)
 Pass a list of Notmuch tags to the completion code. More...
 
static int execute_commands (struct ListHead *p)
 Execute a set of NeoMutt commands. More...
 
static char * find_cfg (const char *home, const char *xdg_cfg_home)
 Find a config file. More...
 
static char * getmailname (void)
 Try to retrieve the FQDN from mailname files. More...
 
static bool get_hostname (void)
 Find the Fully-Qualified Domain Name. More...
 
static int parse_attach_list (struct Buffer *buf, struct Buffer *s, struct ListHead *head, struct Buffer *err)
 Parse the "attachments" command. More...
 
static int parse_group_context (struct GroupContext **ctx, struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse a group context. More...
 
static int parse_replace_list (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse a string replacement rule - Implements command_t. More...
 
static int parse_unattach_list (struct Buffer *buf, struct Buffer *s, struct ListHead *head, struct Buffer *err)
 Parse the "unattachments" command. More...
 
static int parse_unreplace_list (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Remove a string replacement rule - Implements command_t. More...
 
static int print_attach_list (struct ListHead *h, const char op, const char *name)
 Print a list of attachments. More...
 
static void remove_from_stailq (struct ListHead *head, const char *str)
 Remove an item, matching a string, from a List. More...
 
static int source_rc (const char *rcfile_path, struct Buffer *err)
 Read an initialization file. More...
 
static int parse_alias (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'alias' command - Implements command_t. More...
 
static int parse_alternates (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'alternates' command - Implements command_t. More...
 
static int parse_attachments (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'attachments' command - Implements command_t. More...
 
static int parse_echo (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'echo' command - Implements command_t. More...
 
static int parse_finish (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'finish' command - Implements command_t. More...
 
static int parse_group (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'group' and 'ungroup' commands - Implements command_t. More...
 
static int parse_ifdef (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'ifdef' and 'ifndef' commands - Implements command_t. More...
 
static int parse_ignore (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'ignore' command - Implements command_t. More...
 
static int parse_lists (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'lists' command - Implements command_t. More...
 
static int parse_my_hdr (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'my_hdr' command - Implements command_t. More...
 
static int parse_path_list (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'sidebar_whitelist' command - Implements command_t. More...
 
static int parse_path_unlist (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unsidebar_whitelist' command - Implements command_t. More...
 
static int parse_set (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'set' family of commands - Implements command_t. More...
 
static int parse_setenv (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'setenv' and 'unsetenv' commands - Implements command_t. More...
 
static int parse_source (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'source' command - Implements command_t. More...
 
static int parse_spam_list (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'spam' and 'nospam' commands - Implements command_t. More...
 
static int parse_stailq (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse a list command - Implements command_t. More...
 
static int parse_subjectrx_list (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'subjectrx' command - Implements command_t. More...
 
static int parse_subscribe (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'subscribe' command - Implements command_t. More...
 
static int parse_subscribe_to (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'subscribe-to' command - Implements command_t. More...
 
static int parse_tag_formats (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'tag-formats' command - Implements command_t. More...
 
static int parse_tag_transforms (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'tag-transforms' command - Implements command_t. More...
 
static int parse_unalias (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unalias' command - Implements command_t. More...
 
static int parse_unalternates (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unalternates' command - Implements command_t. More...
 
static int parse_unattachments (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unattachments' command - Implements command_t. More...
 
static int parse_unignore (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unignore' command - Implements command_t. More...
 
static int parse_unlists (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unlists' command - Implements command_t. More...
 
static int parse_unmy_hdr (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unmy_hdr' command - Implements command_t. More...
 
static int parse_unstailq (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse an unlist command - Implements command_t. More...
 
static int parse_unsubjectrx_list (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unsubjectrx' command - Implements command_t. More...
 
static int parse_unsubscribe (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unsubscribe' command - Implements command_t. More...
 
static int parse_unsubscribe_from (struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
 Parse the 'unsubscribe-from' command - Implements command_t. More...
 
int mutt_dump_variables (bool hide_sensitive)
 Print a list of all variables with their values. More...
 
int mutt_extract_token (struct Buffer *dest, struct Buffer *tok, int flags)
 Extract one token from a string. More...
 
void mutt_free_attachmatch (struct AttachMatch **am)
 Free an AttachMatch - Implements list_free_t. More...
 
void mutt_free_opts (void)
 clean up before quitting More...
 
int mutt_get_hook_type (const char *name)
 Find a hook by name. More...
 
int mutt_init (bool skip_sys_rc, struct ListHead *commands)
 Initialise NeoMutt. More...
 
int mutt_parse_rc_line (char *line, struct Buffer *token, struct Buffer *err)
 Parse a line of user config. More...
 
int mutt_query_variables (struct ListHead *queries)
 Implement the -Q command line flag. More...
 
int query_quadoption (int opt, const char *prompt)
 Ask the user a quad-question. More...
 
int mutt_command_complete (char *buf, size_t buflen, int pos, int numtabs)
 Complete a command name. More...
 
int mutt_label_complete (char *buf, size_t buflen, int numtabs)
 Complete a label name. More...
 
bool mutt_nm_query_complete (char *buf, size_t buflen, int pos, int numtabs)
 Complete to the nearest notmuch tag. More...
 
bool mutt_nm_tag_complete (char *buf, size_t buflen, int numtabs)
 Complete to the nearest notmuch tag. More...
 
int mutt_var_value_complete (char *buf, size_t buflen, int pos)
 Complete a variable/value. More...
 
struct ConfigSetinit_config (size_t size)
 Initialise the config system. More...
 
int charset_validator (const struct ConfigSet *cs, const struct ConfigDef *cdef, intptr_t value, struct Buffer *err)
 Validate the "charset" config variable - Implements cs_validator() More...
 
int hcache_validator (const struct ConfigSet *cs, const struct ConfigDef *cdef, intptr_t value, struct Buffer *err)
 Validate the "header_cache_backend" config variable - Implements cs_validator() More...
 
int pager_validator (const struct ConfigSet *cs, const struct ConfigDef *cdef, intptr_t value, struct Buffer *err)
 Check for config variables that can't be set from the pager - Implements cs_validator() More...
 
int multipart_validator (const struct ConfigSet *cs, const struct ConfigDef *cdef, intptr_t value, struct Buffer *err)
 Validate the "show_multipart_alternative" config variable - Implements cs_validator() More...
 
int reply_validator (const struct ConfigSet *cs, const struct ConfigDef *cdef, intptr_t value, struct Buffer *err)
 Validate the "reply_regex" config variable - Implements cs_validator() More...
 

Variables

static struct ListHead MuttrcStack = STAILQ_HEAD_INITIALIZER(MuttrcStack)
 
static char UserTyped [LONG_STRING] = { 0 }
 
static int NumMatched = 0
 
static char Completed [STRING] = { 0 }
 
static const char ** Matches
 
static int MatchesListsize = MAX(NUMVARS, NUMCOMMANDS) + 10
 
static char ** nm_tags
 

Detailed Description

Config/command parsing.

Authors
  • Michael R. Elkins

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 init.c.

Macro Definition Documentation

#define MAXERRS   128

Definition at line 78 of file init.c.

#define NUMVARS   mutt_array_size(MuttVars)

Definition at line 80 of file init.c.

#define NUMCOMMANDS   mutt_array_size(Commands)

Definition at line 81 of file init.c.

Enumeration Type Documentation

enum GroupState

Type of email address group.

Enumerator
GS_NONE 

Group is missing an argument.

GS_RX 

Entry is a regular expression.

GS_ADDR 

Entry is an address.

Definition at line 101 of file init.c.

102 {
103  GS_NONE,
104  GS_RX,
105  GS_ADDR,
106 };
Group is missing an argument.
Definition: init.c:103
Entry is an address.
Definition: init.c:105
Entry is a regular expression.
Definition: init.c:104

Function Documentation

static void add_to_stailq ( struct ListHead *  head,
const char *  str 
)
static

Add a string to a list.

Parameters
headString list
strString to add
Note
Duplicate or empty strings will not be added

Definition at line 115 of file init.c.

116 {
117  /* don't add a NULL or empty string to the list */
118  if (!str || *str == '\0')
119  return;
120 
121  /* check to make sure the item is not already on this list */
122  struct ListNode *np = NULL;
123  STAILQ_FOREACH(np, head, entries)
124  {
125  if (mutt_str_strcasecmp(str, np->data) == 0)
126  {
127  return;
128  }
129  }
131 }
struct ListNode * mutt_list_insert_tail(struct ListHead *h, char *s)
Append a string to the end of a List.
Definition: list.c:58
#define STAILQ_FOREACH(var, head, field)
Definition: queue.h:350
char * data
Definition: list.h:35
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625
A List node for strings.
Definition: list.h:33

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static void alternates_clean ( void  )
static

Clear the recipient valid flag of all emails.

Definition at line 136 of file init.c.

137 {
138  if (!Context)
139  return;
140 
141  for (int i = 0; i < Context->mailbox->msg_count; i++)
142  Context->mailbox->hdrs[i]->recip_valid = false;
143 }
The "current" mailbox.
Definition: context.h:36
int msg_count
total number of messages
Definition: mailbox.h:86
struct Email ** hdrs
Definition: mailbox.h:93
struct Mailbox * mailbox
Definition: context.h:50
bool recip_valid
is_recipient is valid
Definition: email.h:56

+ Here is the caller graph for this function:

static void attachments_clean ( void  )
static

always wise to do what someone else did before

Definition at line 148 of file init.c.

149 {
150  if (!Context)
151  return;
152 
153  for (int i = 0; i < Context->mailbox->msg_count; i++)
154  Context->mailbox->hdrs[i]->attach_valid = false;
155 }
The "current" mailbox.
Definition: context.h:36
int msg_count
total number of messages
Definition: mailbox.h:86
struct Email ** hdrs
Definition: mailbox.h:93
struct Mailbox * mailbox
Definition: context.h:50
bool attach_valid
Definition: email.h:72

+ Here is the caller graph for this function:

static void matches_ensure_morespace ( int  current)
static

Allocate more space for auto-completion.

Parameters
currentCurrent allocation

Definition at line 161 of file init.c.

162 {
163  if (current <= (MatchesListsize - 2))
164  return;
165 
166  int base_space = MAX(NUMVARS, NUMCOMMANDS) + 1;
167  int extra_space = MatchesListsize - base_space;
168  extra_space *= 2;
169  const int space = base_space + extra_space;
170  mutt_mem_realloc(&Matches, space * sizeof(char *));
171  memset(&Matches[current + 1], 0, space - current);
172  MatchesListsize = space;
173 }
#define MAX(a, b)
Definition: memory.h:30
void mutt_mem_realloc(void *ptr, size_t size)
Resize a block of memory on the heap.
Definition: memory.c:124
static int MatchesListsize
Definition: init.c:91
#define NUMVARS
Definition: init.c:80
static const char ** Matches
Definition: init.c:89
#define NUMCOMMANDS
Definition: init.c:81

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static void candidate ( char *  try,
const char *  src,
char *  dest,
size_t  dlen 
)
static

helper function for completion

Parameters
tryUser entered data for completion
srcCandidate for completion
destCompletion result gets here
dlenLength of dest buffer

Changes the dest buffer if necessary/possible to aid completion.

Definition at line 184 of file init.c.

185 {
186  if (!dest || !try || !src)
187  return;
188 
189  if (strstr(src, try) != src)
190  return;
191 
193  Matches[NumMatched++] = src;
194  if (dest[0] == 0)
195  mutt_str_strfcpy(dest, src, dlen);
196  else
197  {
198  int l;
199  for (l = 0; src[l] && src[l] == dest[l]; l++)
200  ;
201  dest[l] = '\0';
202  }
203 }
static int NumMatched
Definition: init.c:87
static void matches_ensure_morespace(int current)
Allocate more space for auto-completion.
Definition: init.c:161
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
static const char ** Matches
Definition: init.c:89

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static void clear_subject_mods ( void  )
static

Clear out all modified email subjects.

Definition at line 208 of file init.c.

209 {
210  if (!Context)
211  return;
212 
213  for (int i = 0; i < Context->mailbox->msg_count; i++)
215 }
The "current" mailbox.
Definition: context.h:36
int msg_count
total number of messages
Definition: mailbox.h:86
char * disp_subj
display subject (modified copy of subject)
Definition: envelope.h:46
struct Email ** hdrs
Definition: mailbox.h:93
struct Mailbox * mailbox
Definition: context.h:50
struct Envelope * env
envelope information
Definition: email.h:91
#define FREE(x)
Definition: memory.h:46

+ Here is the caller graph for this function:

static int complete_all_nm_tags ( const char *  pt)
static

Pass a list of Notmuch tags to the completion code.

Parameters
ptList of all Notmuch tags
Return values
0Success
-1Error

Definition at line 224 of file init.c.

225 {
226  int tag_count_1 = 0;
227  int tag_count_2 = 0;
228 
229  NumMatched = 0;
230  mutt_str_strfcpy(UserTyped, pt, sizeof(UserTyped));
231  memset(Matches, 0, MatchesListsize);
232  memset(Completed, 0, sizeof(Completed));
233 
235 
236  /* Work out how many tags there are. */
237  if (nm_get_all_tags(Context->mailbox, NULL, &tag_count_1) || tag_count_1 == 0)
238  goto done;
239 
240  /* Free the old list, if any. */
241  if (nm_tags)
242  {
243  for (int i = 0; nm_tags[i]; i++)
244  FREE(&nm_tags[i]);
245  FREE(&nm_tags);
246  }
247  /* Allocate a new list, with sentinel. */
248  nm_tags = mutt_mem_malloc((tag_count_1 + 1) * sizeof(char *));
249  nm_tags[tag_count_1] = NULL;
250 
251  /* Get all the tags. */
252  if (nm_get_all_tags(Context->mailbox, nm_tags, &tag_count_2) || tag_count_1 != tag_count_2)
253  {
254  FREE(&nm_tags);
255  nm_tags = NULL;
257  return -1;
258  }
259 
260  /* Put them into the completion machinery. */
261  for (int num = 0; num < tag_count_1; num++)
262  {
263  candidate(UserTyped, nm_tags[num], Completed, sizeof(Completed));
264  }
265 
268 
269 done:
271  return 0;
272 }
The "current" mailbox.
Definition: context.h:36
static int NumMatched
Definition: init.c:87
static char ** nm_tags
Definition: init.c:95
static void candidate(char *try, const char *src, char *dest, size_t dlen)
helper function for completion
Definition: init.c:184
struct Mailbox * mailbox
Definition: context.h:50
void nm_db_longrun_done(struct Mailbox *m)
Finish a long transaction.
Definition: nm_db.c:301
static int MatchesListsize
Definition: init.c:91
static void matches_ensure_morespace(int current)
Allocate more space for auto-completion.
Definition: init.c:161
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:99
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
int nm_get_all_tags(struct Mailbox *m, char **tag_list, int *tag_count)
Fill a list with all notmuch tags.
static char UserTyped[LONG_STRING]
Definition: init.c:85
static const char ** Matches
Definition: init.c:89
#define FREE(x)
Definition: memory.h:46
void nm_db_longrun_init(struct Mailbox *m, bool writable)
Start a long transaction.
Definition: nm_db.c:286
static char Completed[STRING]
Definition: init.c:88

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int execute_commands ( struct ListHead *  p)
static

Execute a set of NeoMutt commands.

Parameters
pList of command strings
Return values
0Success, all the commands succeeded
-1Error

Definition at line 281 of file init.c.

282 {
283  struct Buffer err, token;
284 
285  mutt_buffer_init(&err);
286  err.dsize = STRING;
287  err.data = mutt_mem_malloc(err.dsize);
288  mutt_buffer_init(&token);
289  struct ListNode *np = NULL;
290  STAILQ_FOREACH(np, p, entries)
291  {
292  if (mutt_parse_rc_line(np->data, &token, &err) == -1)
293  {
294  mutt_error(_("Error in command line: %s"), err.data);
295  FREE(&token.data);
296  FREE(&err.data);
297 
298  return -1;
299  }
300  }
301  FREE(&token.data);
302  FREE(&err.data);
303 
304  return 0;
305 }
int mutt_parse_rc_line(char *line, struct Buffer *token, struct Buffer *err)
Parse a line of user config.
Definition: init.c:3119
String manipulation buffer.
Definition: buffer.h:33
#define _(a)
Definition: message.h:28
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:99
#define STAILQ_FOREACH(var, head, field)
Definition: queue.h:350
char * data
Definition: list.h:35
#define STRING
Definition: string2.h:35
#define mutt_error(...)
Definition: logging.h:88
#define FREE(x)
Definition: memory.h:46
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:66
A List node for strings.
Definition: list.h:33

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static char* find_cfg ( const char *  home,
const char *  xdg_cfg_home 
)
static

Find a config file.

Parameters
homeUser's home directory
xdg_cfg_homeXDG home directory
Return values
ptrSuccess, first matching directory
NULLError, no matching directories

Definition at line 314 of file init.c.

315 {
316  const char *names[] = {
317  "neomuttrc",
318  "muttrc",
319  NULL,
320  };
321 
322  const char *locations[][2] = {
323  { xdg_cfg_home, "neomutt/" },
324  { xdg_cfg_home, "mutt/" },
325  { home, ".neomutt/" },
326  { home, ".mutt/" },
327  { home, "." },
328  { NULL, NULL },
329  };
330 
331  for (int i = 0; locations[i][0] || locations[i][1]; i++)
332  {
333  if (!locations[i][0])
334  continue;
335 
336  for (int j = 0; names[j]; j++)
337  {
338  char buffer[STRING];
339 
340  snprintf(buffer, sizeof(buffer), "%s/%s%s", locations[i][0],
341  locations[i][1], names[j]);
342  if (access(buffer, F_OK) == 0)
343  return mutt_str_strdup(buffer);
344  }
345  }
346 
347  return NULL;
348 }
#define STRING
Definition: string2.h:35
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static char* getmailname ( void  )
static

Try to retrieve the FQDN from mailname files.

Return values
ptrHeap allocated string with the FQDN
NULLif no valid mailname file could be read

Definition at line 356 of file init.c.

357 {
358  char *mailname = NULL;
359  static const char *mn_files[] = { "/etc/mailname", "/etc/mail/mailname" };
360 
361  for (size_t i = 0; i < mutt_array_size(mn_files); i++)
362  {
363  FILE *f = mutt_file_fopen(mn_files[i], "r");
364  if (!f)
365  continue;
366 
367  size_t len = 0;
368  mailname = mutt_file_read_line(NULL, &len, f, NULL, 0);
369  mutt_file_fclose(&f);
370  if (mailname && *mailname)
371  break;
372 
373  FREE(&mailname);
374  }
375 
376  return mailname;
377 }
char * mutt_file_read_line(char *line, size_t *size, FILE *fp, int *line_num, int flags)
Read a line from a file.
Definition: file.c:632
#define mutt_array_size(x)
Definition: memory.h:33
FILE * mutt_file_fopen(const char *path, const char *mode)
Call fopen() safely.
Definition: file.c:548
int mutt_file_fclose(FILE **f)
Close a FILE handle (and NULL the pointer)
Definition: file.c:149
#define FREE(x)
Definition: memory.h:46

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static bool get_hostname ( void  )
static

Find the Fully-Qualified Domain Name.

Return values
trueSuccess
falseError, failed to find any name

Use several methods to try to find the Fully-Qualified domain name of this host. If the user has already configured a hostname, this function will use it.

Definition at line 388 of file init.c.

389 {
390  char *str = NULL;
391  struct utsname utsname;
392 
393  if (Hostname)
394  {
395  str = Hostname;
396  }
397  else
398  {
399  /* The call to uname() shouldn't fail, but if it does, the system is horribly
400  * broken, and the system's networking configuration is in an unreliable
401  * state. We should bail. */
402  if ((uname(&utsname)) == -1)
403  {
404  mutt_perror(_("unable to determine nodename via uname()"));
405  return false; // TEST09: can't test
406  }
407 
408  str = utsname.nodename;
409  }
410 
411  /* some systems report the FQDN instead of just the hostname */
412  char *dot = strchr(str, '.');
413  if (dot)
415  else
417 
418  if (!Hostname)
419  {
420  /* now get FQDN. Use configured domain first, DNS next, then uname */
421 #ifdef DOMAIN
422  /* we have a compile-time domain name, use that for Hostname */
423  Hostname =
425  sprintf((char *) Hostname, "%s.%s", NONULL(ShortHostname), DOMAIN);
426 #else
427  Hostname = getmailname();
428  if (!Hostname)
429  {
430  char buffer[LONG_STRING];
431  if (getdnsdomainname(buffer, sizeof(buffer)) == 0)
432  {
435  sprintf((char *) Hostname, "%s.%s", NONULL(ShortHostname), buffer);
436  }
437  else
438  {
439  /* DNS failed, use the nodename. Whether or not the nodename had a '.'
440  * in it, we can use the nodename as the FQDN. On hosts where DNS is
441  * not being used, e.g. small network that relies on hosts files, a
442  * short host name is all that is required for SMTP to work correctly.
443  * It could be wrong, but we've done the best we can, at this point the
444  * onus is on the user to provide the correct hostname if the nodename
445  * won't work in their network. */
446  Hostname = mutt_str_strdup(utsname.nodename);
447  }
448  }
449 #endif
450  }
451  if (Hostname)
452  cs_str_initial_set(Config, "hostname", Hostname, NULL);
453 
454  return true;
455 }
#define NONULL(x)
Definition: string2.h:39
#define mutt_perror(...)
Definition: logging.h:89
static char * getmailname(void)
Try to retrieve the FQDN from mailname files.
Definition: init.c:356
#define _(a)
Definition: message.h:28
WHERE struct ConfigSet * Config
Wrapper around the user&#39;s config settings.
Definition: globals.h:39
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:663
#define LONG_STRING
Definition: string2.h:36
int getdnsdomainname(char *buf, size_t buflen)
Lookup the host&#39;s name using DNS.
Definition: getdomain.c:44
int cs_str_initial_set(const struct ConfigSet *cs, const char *name, const char *value, struct Buffer *err)
Set the initial value of a config item.
Definition: set.c:513
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:99
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
WHERE char * ShortHostname
Short version of the hostname.
Definition: globals.h:48
WHERE char * Hostname
Config: Fully-qualified domain name of this machine.
Definition: globals.h:111
char * mutt_str_substr_dup(const char *begin, const char *end)
Duplicate a sub-string.
Definition: string.c:576

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int parse_attach_list ( struct Buffer buf,
struct Buffer s,
struct ListHead *  head,
struct Buffer err 
)
static

Parse the "attachments" command.

Parameters
bufBuffer for temporary storage
sBuffer containing the attachments command
headList of AttachMatch to add to
errBuffer for error messages
Return values
0Success
-1Error

Definition at line 466 of file init.c.

468 {
469  struct AttachMatch *a = NULL;
470  char *p = NULL;
471  char *tmpminor = NULL;
472  size_t len;
473  int ret;
474 
475  do
476  {
477  mutt_extract_token(buf, s, 0);
478 
479  if (!buf->data || *buf->data == '\0')
480  continue;
481 
482  a = mutt_mem_malloc(sizeof(struct AttachMatch));
483 
484  /* some cheap hacks that I expect to remove */
485  if (mutt_str_strcasecmp(buf->data, "any") == 0)
486  a->major = mutt_str_strdup("*/.*");
487  else if (mutt_str_strcasecmp(buf->data, "none") == 0)
488  a->major = mutt_str_strdup("cheap_hack/this_should_never_match");
489  else
490  a->major = mutt_str_strdup(buf->data);
491 
492  p = strchr(a->major, '/');
493  if (p)
494  {
495  *p = '\0';
496  p++;
497  a->minor = p;
498  }
499  else
500  {
501  a->minor = "unknown";
502  }
503 
504  len = strlen(a->minor);
505  tmpminor = mutt_mem_malloc(len + 3);
506  strcpy(&tmpminor[1], a->minor);
507  tmpminor[0] = '^';
508  tmpminor[len + 1] = '$';
509  tmpminor[len + 2] = '\0';
510 
512  ret = REGCOMP(&a->minor_regex, tmpminor, REG_ICASE);
513 
514  FREE(&tmpminor);
515 
516  if (ret != 0)
517  {
518  regerror(ret, &a->minor_regex, err->data, err->dsize);
519  FREE(&a->major);
520  FREE(&a);
521  return -1;
522  }
523 
524  mutt_debug(5, "added %s/%s [%d]\n", a->major, a->minor, a->major_int);
525 
526  mutt_list_insert_tail(head, (char *) a);
527  } while (MoreArgs(s));
528 
530  return 0;
531 }
int major_int
Definition: mutt.h:200
size_t dsize
length of data
Definition: buffer.h:37
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
const char * major
Definition: mutt.h:199
struct ListNode * mutt_list_insert_tail(struct ListHead *h, char *s)
Append a string to the end of a List.
Definition: list.c:58
static void attachments_clean(void)
always wise to do what someone else did before
Definition: init.c:148
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:99
char * data
pointer to data
Definition: buffer.h:35
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
regex_t minor_regex
Definition: mutt.h:202
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625
int mutt_check_mime_type(const char *s)
Check a MIME type string.
Definition: parse.c:255
#define FREE(x)
Definition: memory.h:46
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
An attachment matching a regex.
Definition: mutt.h:197
const char * minor
Definition: mutt.h:201
#define REGCOMP(X, Y, Z)
Compile a regular expression.
Definition: regex3.h:52

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int parse_group_context ( struct GroupContext **  ctx,
struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse a group context.

Parameters
ctxGroupContext to add to
bufTemporary Buffer space
sBuffer containing string to be parsed
dataFlags associated with the command
errBuffer for error messages
Return values
0Success
-1Error

Definition at line 543 of file init.c.

545 {
546  while (mutt_str_strcasecmp(buf->data, "-group") == 0)
547  {
548  if (!MoreArgs(s))
549  {
550  mutt_buffer_strcpy(err, _("-group: no group name"));
551  goto bail;
552  }
553 
554  mutt_extract_token(buf, s, 0);
555 
557 
558  if (!MoreArgs(s))
559  {
560  mutt_buffer_strcpy(err, _("out of arguments"));
561  goto bail;
562  }
563 
564  mutt_extract_token(buf, s, 0);
565  }
566 
567  return 0;
568 
569 bail:
571  return -1;
572 }
struct Group * mutt_pattern_group(const char *k)
Match a pattern to a Group.
Definition: group.c:45
#define _(a)
Definition: message.h:28
void mutt_group_context_destroy(struct GroupContext **ctx)
Destroy a Group List.
Definition: group.c:130
void mutt_group_context_add(struct GroupContext **ctx, struct Group *group)
Add a Group to a List.
Definition: group.c:114
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
void mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:316
char * data
pointer to data
Definition: buffer.h:35
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int parse_replace_list ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse a string replacement rule - Implements command_t.

Definition at line 577 of file init.c.

579 {
580  struct ReplaceList *list = (struct ReplaceList *) data;
581  struct Buffer templ = { 0 };
582 
583  /* First token is a regex. */
584  if (!MoreArgs(s))
585  {
586  mutt_buffer_printf(err, _("%s: too few arguments"), "subjectrx");
587  return -1;
588  }
589  mutt_extract_token(buf, s, 0);
590 
591  /* Second token is a replacement template */
592  if (!MoreArgs(s))
593  {
594  mutt_buffer_printf(err, _("%s: too few arguments"), "subjectrx");
595  return -1;
596  }
597  mutt_extract_token(&templ, s, 0);
598 
599  if (mutt_replacelist_add(list, buf->data, templ.data, err) != 0)
600  {
601  FREE(&templ.data);
602  return -1;
603  }
604  FREE(&templ.data);
605 
606  return 0;
607 }
int mutt_replacelist_add(struct ReplaceList *rl, const char *pat, const char *templ, struct Buffer *err)
Add a pattern and a template to a list.
Definition: regex.c:260
String manipulation buffer.
Definition: buffer.h:33
#define _(a)
Definition: message.h:28
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
char * data
pointer to data
Definition: buffer.h:35
#define FREE(x)
Definition: memory.h:46

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int parse_unattach_list ( struct Buffer buf,
struct Buffer s,
struct ListHead *  head,
struct Buffer err 
)
static

Parse the "unattachments" command.

Parameters
bufBuffer for temporary storage
sBuffer containing the unattachments command
headList of AttachMatch to remove from
errBuffer for error messages
Return values
0Always

Definition at line 617 of file init.c.

619 {
620  struct AttachMatch *a = NULL;
621  char *tmp = NULL;
622  char *minor = NULL;
623 
624  do
625  {
626  mutt_extract_token(buf, s, 0);
627  FREE(&tmp);
628 
629  if (mutt_str_strcasecmp(buf->data, "any") == 0)
630  tmp = mutt_str_strdup("*/.*");
631  else if (mutt_str_strcasecmp(buf->data, "none") == 0)
632  tmp = mutt_str_strdup("cheap_hack/this_should_never_match");
633  else
634  tmp = mutt_str_strdup(buf->data);
635 
636  minor = strchr(tmp, '/');
637  if (minor)
638  {
639  *minor = '\0';
640  minor++;
641  }
642  else
643  {
644  minor = "unknown";
645  }
646  const int major = mutt_check_mime_type(tmp);
647 
648  struct ListNode *np, *tmp2;
649  STAILQ_FOREACH_SAFE(np, head, entries, tmp2)
650  {
651  a = (struct AttachMatch *) np->data;
652  mutt_debug(5, "check %s/%s [%d] : %s/%s [%d]\n", a->major, a->minor,
653  a->major_int, tmp, minor, major);
654  if (a->major_int == major && (mutt_str_strcasecmp(minor, a->minor) == 0))
655  {
656  mutt_debug(5, "removed %s/%s [%d]\n", a->major, a->minor, a->major_int);
657  regfree(&a->minor_regex);
658  FREE(&a->major);
659  STAILQ_REMOVE(head, np, ListNode, entries);
660  FREE(&np->data);
661  FREE(&np);
662  }
663  }
664 
665  } while (MoreArgs(s));
666 
667  FREE(&tmp);
669  return 0;
670 }
int major_int
Definition: mutt.h:200
#define STAILQ_REMOVE(head, elm, type, field)
Definition: queue.h:400
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
const char * major
Definition: mutt.h:199
#define STAILQ_FOREACH_SAFE(var, head, field, tvar)
Definition: queue.h:360
static void attachments_clean(void)
always wise to do what someone else did before
Definition: init.c:148
char * data
pointer to data
Definition: buffer.h:35
char * data
Definition: list.h:35
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
regex_t minor_regex
Definition: mutt.h:202
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625
int mutt_check_mime_type(const char *s)
Check a MIME type string.
Definition: parse.c:255
#define FREE(x)
Definition: memory.h:46
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
An attachment matching a regex.
Definition: mutt.h:197
A List node for strings.
Definition: list.h:33
const char * minor
Definition: mutt.h:201

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int parse_unreplace_list ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Remove a string replacement rule - Implements command_t.

Definition at line 675 of file init.c.

677 {
678  struct ReplaceList *list = (struct ReplaceList *) data;
679 
680  /* First token is a regex. */
681  if (!MoreArgs(s))
682  {
683  mutt_buffer_printf(err, _("%s: too few arguments"), "unsubjectrx");
684  return -1;
685  }
686 
687  mutt_extract_token(buf, s, 0);
688 
689  /* "*" is a special case. */
690  if (mutt_str_strcmp(buf->data, "*") == 0)
691  {
692  mutt_replacelist_free(list);
693  return 0;
694  }
695 
696  mutt_replacelist_remove(list, buf->data);
697  return 0;
698 }
#define _(a)
Definition: message.h:28
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
void mutt_replacelist_free(struct ReplaceList *rl)
Free a ReplaceList object.
Definition: regex.c:444
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
char * data
pointer to data
Definition: buffer.h:35
int mutt_replacelist_remove(struct ReplaceList *rl, const char *pat)
Remove a pattern from a list.
Definition: regex.c:561
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int print_attach_list ( struct ListHead *  h,
const char  op,
const char *  name 
)
static

Print a list of attachments.

Parameters
hList of attachments
opOperation, e.g. '+', '-'
nameAttached/Inline, 'A', 'I'
Return values
0Always

Definition at line 707 of file init.c.

708 {
709  struct ListNode *np = NULL;
710  STAILQ_FOREACH(np, h, entries)
711  {
712  printf("attachments %c%s %s/%s\n", op, name,
713  ((struct AttachMatch *) np->data)->major,
714  ((struct AttachMatch *) np->data)->minor);
715  }
716 
717  return 0;
718 }
const char * name
Definition: pgpmicalg.c:42
#define STAILQ_FOREACH(var, head, field)
Definition: queue.h:350
char * data
Definition: list.h:35
An attachment matching a regex.
Definition: mutt.h:197
A List node for strings.
Definition: list.h:33

+ Here is the caller graph for this function:

static void remove_from_stailq ( struct ListHead *  head,
const char *  str 
)
static

Remove an item, matching a string, from a List.

Parameters
headHead of the List
strString to match
Note
The string comparison is case-insensitive

Definition at line 727 of file init.c.

728 {
729  if (mutt_str_strcmp("*", str) == 0)
730  mutt_list_free(head); /* ``unCMD *'' means delete all current entries */
731  else
732  {
733  struct ListNode *np, *tmp;
734  STAILQ_FOREACH_SAFE(np, head, entries, tmp)
735  {
736  if (mutt_str_strcasecmp(str, np->data) == 0)
737  {
738  STAILQ_REMOVE(head, np, ListNode, entries);
739  FREE(&np->data);
740  FREE(&np);
741  break;
742  }
743  }
744  }
745 }
#define STAILQ_REMOVE(head, elm, type, field)
Definition: queue.h:400
void mutt_list_free(struct ListHead *h)
Free a List AND its strings.
Definition: list.c:105
#define STAILQ_FOREACH_SAFE(var, head, field, tvar)
Definition: queue.h:360
char * data
Definition: list.h:35
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625
#define FREE(x)
Definition: memory.h:46
A List node for strings.
Definition: list.h:33
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int source_rc ( const char *  rcfile_path,
struct Buffer err 
)
static

Read an initialization file.

Parameters
rcfile_pathPath to initialization file
errBuffer for error messages
Return values
<0if neomutt should pause to let the user know

Definition at line 753 of file init.c.

754 {
755  FILE *f = NULL;
756  int line = 0, rc = 0, line_rc, warnings = 0;
757  struct Buffer token;
758  char *linebuf = NULL;
759  char *currentline = NULL;
760  char rcfile[PATH_MAX];
761  size_t buflen;
762  size_t rcfilelen;
763  bool ispipe;
764 
765  pid_t pid;
766 
767  mutt_str_strfcpy(rcfile, rcfile_path, sizeof(rcfile));
768 
769  rcfilelen = mutt_str_strlen(rcfile);
770  if (rcfilelen == 0)
771  return -1;
772 
773  ispipe = rcfile[rcfilelen - 1] == '|';
774 
775  if (!ispipe)
776  {
777  struct ListNode *np = STAILQ_FIRST(&MuttrcStack);
778  if (!mutt_path_to_absolute(rcfile, np ? NONULL(np->data) : ""))
779  {
780  mutt_error(_("Error: impossible to build path of '%s'"), rcfile_path);
781  return -1;
782  }
783 
784  STAILQ_FOREACH(np, &MuttrcStack, entries)
785  {
786  if (mutt_str_strcmp(np->data, rcfile) == 0)
787  {
788  break;
789  }
790  }
791  if (!np)
792  {
794  }
795  else
796  {
797  mutt_error(_("Error: Cyclic sourcing of configuration file '%s'"), rcfile);
798  return -1;
799  }
800  }
801 
802  mutt_debug(2, "Reading configuration file '%s'.\n", rcfile);
803 
804  f = mutt_open_read(rcfile, &pid);
805  if (!f)
806  {
807  mutt_buffer_printf(err, "%s: %s", rcfile, strerror(errno));
808  return -1;
809  }
810 
811  mutt_buffer_init(&token);
812  while ((linebuf = mutt_file_read_line(linebuf, &buflen, f, &line, MUTT_CONT)))
813  {
814  const int conv = ConfigCharset && (*ConfigCharset) && Charset;
815  if (conv)
816  {
817  currentline = mutt_str_strdup(linebuf);
818  if (!currentline)
819  continue;
820  mutt_ch_convert_string(&currentline, ConfigCharset, Charset, 0);
821  }
822  else
823  currentline = linebuf;
824  mutt_buffer_reset(err);
825  line_rc = mutt_parse_rc_line(currentline, &token, err);
826  if (line_rc == -1)
827  {
828  mutt_error(_("Error in %s, line %d: %s"), rcfile, line, err->data);
829  if (--rc < -MAXERRS)
830  {
831  if (conv)
832  FREE(&currentline);
833  break;
834  }
835  }
836  else if (line_rc == -2)
837  {
838  /* Warning */
839  mutt_error(_("Warning in %s, line %d: %s"), rcfile, line, err->data);
840  warnings++;
841  }
842  else if (line_rc == 1)
843  {
844  break; /* Found "finish" command */
845  }
846  else
847  {
848  if (rc < 0)
849  rc = -1;
850  }
851  if (conv)
852  FREE(&currentline);
853  }
854  FREE(&token.data);
855  FREE(&linebuf);
856  mutt_file_fclose(&f);
857  if (pid != -1)
858  mutt_wait_filter(pid);
859  if (rc)
860  {
861  /* the neomuttrc source keyword */
862  mutt_buffer_reset(err);
863  mutt_buffer_printf(err, (rc >= -MAXERRS) ? _("source: errors in %s") : _("source: reading aborted due to too many errors in %s"),
864  rcfile);
865  rc = -1;
866  }
867  else
868  {
869  /* Don't alias errors with warnings */
870  if (warnings > 0)
871  {
872  mutt_buffer_printf(err, ngettext("source: %d warning in %s", "source: %d warnings in %s", warnings),
873  warnings, rcfile);
874  rc = -2;
875  }
876  }
877 
878  if (!ispipe && !STAILQ_EMPTY(&MuttrcStack))
879  {
880  struct ListNode *np = STAILQ_FIRST(&MuttrcStack);
881  STAILQ_REMOVE_HEAD(&MuttrcStack, entries);
882  FREE(&np->data);
883  FREE(&np);
884  }
885 
886  return rc;
887 }
#define NONULL(x)
Definition: string2.h:39
int mutt_ch_convert_string(char **ps, const char *from, const char *to, int flags)
Convert a string between encodings.
Definition: charset.c:715
void mutt_buffer_reset(struct Buffer *buf)
Reset an existing Buffer.
Definition: buffer.c:81
char * mutt_file_read_line(char *line, size_t *size, FILE *fp, int *line_num, int flags)
Read a line from a file.
Definition: file.c:632
static struct ListHead MuttrcStack
Definition: init.c:76
char * Charset
Config: Default character set for displaying text on screen.
Definition: charset.c:52
int mutt_parse_rc_line(char *line, struct Buffer *token, struct Buffer *err)
Parse a line of user config.
Definition: init.c:3119
String manipulation buffer.
Definition: buffer.h:33
#define _(a)
Definition: message.h:28
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:663
WHERE char * ConfigCharset
Config: Character set that the config files are in.
Definition: globals.h:106
#define STAILQ_REMOVE_HEAD(head, field)
Definition: queue.h:420
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
#define MUTT_CONT
-continuation
Definition: file.h:36
const char * line
Definition: common.c:35
#define PATH_MAX
Definition: mutt.h:46
char * data
pointer to data
Definition: buffer.h:35
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
#define MAXERRS
Definition: init.c:78
struct ListNode * mutt_list_insert_head(struct ListHead *h, char *s)
Insert a string at the beginning of a List.
Definition: list.c:44
#define STAILQ_FOREACH(var, head, field)
Definition: queue.h:350
int mutt_path_to_absolute(char *path, const char *reference)
Convert relative filepath to an absolute path.
Definition: path.c:416
char * data
Definition: list.h:35
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
int mutt_file_fclose(FILE **f)
Close a FILE handle (and NULL the pointer)
Definition: file.c:149
#define mutt_error(...)
Definition: logging.h:88
#define FREE(x)
Definition: memory.h:46
#define STAILQ_EMPTY(head)
Definition: queue.h:346
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:66
int mutt_wait_filter(pid_t pid)
Wait for the exit of a process and return its status.
Definition: filter.c:227
A List node for strings.
Definition: list.h:33
FILE * mutt_open_read(const char *path, pid_t *thepid)
Run a command to read from.
Definition: muttlib.c:1338
#define STAILQ_FIRST(head)
Definition: queue.h:348
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int parse_alias ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'alias' command - Implements command_t.

Definition at line 892 of file init.c.

894 {
895  struct Alias *tmp = NULL;
896  char *estr = NULL;
897  struct GroupContext *gc = NULL;
898 
899  if (!MoreArgs(s))
900  {
901  mutt_buffer_strcpy(err, _("alias: no address"));
902  return -1;
903  }
904 
905  mutt_extract_token(buf, s, 0);
906 
907  if (parse_group_context(&gc, buf, s, data, err) == -1)
908  return -1;
909 
910  /* check to see if an alias with this name already exists */
911  TAILQ_FOREACH(tmp, &Aliases, entries)
912  {
913  if (mutt_str_strcasecmp(tmp->name, buf->data) == 0)
914  break;
915  }
916 
917  if (!tmp)
918  {
919  /* create a new alias */
920  tmp = mutt_mem_calloc(1, sizeof(struct Alias));
921  tmp->name = mutt_str_strdup(buf->data);
922  TAILQ_INSERT_TAIL(&Aliases, tmp, entries);
923  /* give the main addressbook code a chance */
924  if (CurrentMenu == MENU_ALIAS)
925  OptMenuCaller = true;
926  }
927  else
928  {
930  /* override the previous value */
931  mutt_addr_free(&tmp->addr);
932  if (CurrentMenu == MENU_ALIAS)
934  }
935 
937  mutt_debug(3, "Second token is '%s'.\n", buf->data);
938 
939  tmp->addr = mutt_addr_parse_list2(tmp->addr, buf->data);
940 
941  if (mutt_addrlist_to_intl(tmp->addr, &estr))
942  {
943  mutt_buffer_printf(err, _("Warning: Bad IDN '%s' in alias '%s'"), estr, tmp->name);
944  FREE(&estr);
945  goto bail;
946  }
947 
950 
951  if (DebugLevel > 2)
952  {
953  /* A group is terminated with an empty address, so check a->mailbox */
954  for (struct Address *a = tmp->addr; a && a->mailbox; a = a->next)
955  {
956  if (!a->group)
957  mutt_debug(3, " %s\n", a->mailbox);
958  else
959  mutt_debug(3, " Group %s\n", a->mailbox);
960  }
961  }
963  return 0;
964 
965 bail:
967  return -1;
968 }
void mutt_alias_delete_reverse(struct Alias *t)
Remove an email address lookup for an Alias.
Definition: alias.c:569
A shortcut for an email address.
Definition: alias.h:36
char * name
Definition: alias.h:38
struct Address * mutt_addr_parse_list2(struct Address *p, const char *s)
Parse a list of email addresses.
Definition: address.c:630
void * mutt_mem_calloc(size_t nmemb, size_t size)
Allocate zeroed memory on the heap.
Definition: memory.c:51
#define TAILQ_FOREACH(var, head, field)
Definition: queue.h:719
WHERE bool OptMenuCaller
(pseudo) tell menu to give caller a take
Definition: options.h:37
short DebugLevel
Config: Logging level for debug logs.
Definition: mutt_logging.c:48
#define _(a)
Definition: message.h:28
void mutt_group_context_destroy(struct GroupContext **ctx)
Destroy a Group List.
Definition: group.c:130
An email address.
Definition: address.h:32
char * mailbox
mailbox and host address
Definition: address.h:35
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
Select an email address by its alias.
Definition: keymap.h:67
A set of Groups.
Definition: group.h:48
int mutt_addrlist_to_intl(struct Address *a, char **err)
Convert an Address list to Punycode.
Definition: address.c:1208
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
void mutt_group_context_add_addrlist(struct GroupContext *ctx, struct Address *a)
Add an Address List to a Group List.
Definition: group.c:215
#define MUTT_TOKEN_QUOTE
don&#39;t interpret quotes
Definition: mutt.h:74
void mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:316
#define MUTT_TOKEN_SPACE
don&#39;t treat whitespace as a term
Definition: mutt.h:73
char * data
pointer to data
Definition: buffer.h:35
#define TAILQ_INSERT_TAIL(head, elm, field)
Definition: queue.h:803
#define MUTT_TOKEN_SEMICOLON
don&#39;t treat ; as special
Definition: mutt.h:77
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625
void mutt_alias_add_reverse(struct Alias *t)
Add an email address lookup for an Alias.
Definition: alias.c:547
#define FREE(x)
Definition: memory.h:46
struct Address * addr
Definition: alias.h:39
WHERE int CurrentMenu
Current Menu, e.g. MENU_PAGER.
Definition: globals.h:93
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
static int parse_group_context(struct GroupContext **ctx, struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
Parse a group context.
Definition: init.c:543
void mutt_addr_free(struct Address **p)
Free a list of Addresses.
Definition: address.c:446

+ Here is the call graph for this function:

static int parse_alternates ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'alternates' command - Implements command_t.

Definition at line 973 of file init.c.

975 {
976  struct GroupContext *gc = NULL;
977 
979 
980  do
981  {
982  mutt_extract_token(buf, s, 0);
983 
984  if (parse_group_context(&gc, buf, s, data, err) == -1)
985  goto bail;
986 
987  mutt_regexlist_remove(&UnAlternates, buf->data);
988 
989  if (mutt_regexlist_add(&Alternates, buf->data, REG_ICASE, err) != 0)
990  goto bail;
991 
992  if (mutt_group_context_add_regex(gc, buf->data, REG_ICASE, err) != 0)
993  goto bail;
994  } while (MoreArgs(s));
995 
997  return 0;
998 
999 bail:
1001  return -1;
1002 }
int mutt_regexlist_remove(struct RegexList *rl, const char *str)
Remove a Regex from a list.
Definition: regex.c:224
static void alternates_clean(void)
Clear the recipient valid flag of all emails.
Definition: init.c:136
void mutt_group_context_destroy(struct GroupContext **ctx)
Destroy a Group List.
Definition: group.c:130
A set of Groups.
Definition: group.h:48
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
int mutt_regexlist_add(struct RegexList *rl, const char *str, int flags, struct Buffer *err)
Compile a regex string and add it to a list.
Definition: regex.c:128
char * data
pointer to data
Definition: buffer.h:35
int mutt_group_context_add_regex(struct GroupContext *ctx, const char *s, int flags, struct Buffer *err)
Add a Regex to a Group List.
Definition: group.c:251
static int parse_group_context(struct GroupContext **ctx, struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
Parse a group context.
Definition: init.c:543

+ Here is the call graph for this function:

static int parse_attachments ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'attachments' command - Implements command_t.

Definition at line 1007 of file init.c.

1009 {
1010  char op, *category = NULL;
1011  struct ListHead *head = NULL;
1012 
1013  mutt_extract_token(buf, s, 0);
1014  if (!buf->data || *buf->data == '\0')
1015  {
1016  mutt_buffer_strcpy(err, _("attachments: no disposition"));
1017  return -1;
1018  }
1019 
1020  category = buf->data;
1021  op = *category++;
1022 
1023  if (op == '?')
1024  {
1025  mutt_endwin();
1026  fflush(stdout);
1027  printf("\n%s\n\n", _("Current attachments settings:"));
1028  print_attach_list(&AttachAllow, '+', "A");
1029  print_attach_list(&AttachExclude, '-', "A");
1030  print_attach_list(&InlineAllow, '+', "I");
1031  print_attach_list(&InlineExclude, '-', "I");
1033  return 0;
1034  }
1035 
1036  if (op != '+' && op != '-')
1037  {
1038  op = '+';
1039  category--;
1040  }
1041  if (mutt_str_startswith("attachment", category, CASE_IGNORE))
1042  {
1043  if (op == '+')
1044  head = &AttachAllow;
1045  else
1046  head = &AttachExclude;
1047  }
1048  else if (mutt_str_startswith("inline", category, CASE_IGNORE))
1049  {
1050  if (op == '+')
1051  head = &InlineAllow;
1052  else
1053  head = &InlineExclude;
1054  }
1055  else
1056  {
1057  mutt_buffer_strcpy(err, _("attachments: invalid disposition"));
1058  return -1;
1059  }
1060 
1061  return parse_attach_list(buf, s, head, err);
1062 }
#define _(a)
Definition: message.h:28
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
void mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:316
void mutt_endwin(void)
Shutdown curses/slang.
Definition: curs_lib.c:498
char * data
pointer to data
Definition: buffer.h:35
Ignore case when comparing strings.
Definition: string2.h:70
size_t mutt_str_startswith(const char *str, const char *prefix, enum CaseSensitivity cs)
Check whether a string starts with a prefix.
Definition: string.c:166
int mutt_any_key_to_continue(const char *s)
Prompt the user to &#39;press any key&#39; and wait.
Definition: curs_lib.c:531
static int parse_attach_list(struct Buffer *buf, struct Buffer *s, struct ListHead *head, struct Buffer *err)
Parse the "attachments" command.
Definition: init.c:466
static int print_attach_list(struct ListHead *h, const char op, const char *name)
Print a list of attachments.
Definition: init.c:707

+ Here is the call graph for this function:

static int parse_echo ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'echo' command - Implements command_t.

Definition at line 1067 of file init.c.

1069 {
1070  if (!MoreArgs(s))
1071  {
1072  mutt_buffer_printf(err, _("%s: too few arguments"), "echo");
1073  return -1;
1074  }
1075  mutt_extract_token(buf, s, 0);
1076  OptForceRefresh = true;
1077  mutt_message("%s", buf->data);
1078  OptForceRefresh = false;
1079  mutt_sleep(0);
1080 
1081  return 0;
1082 }
#define mutt_message(...)
Definition: logging.h:87
#define _(a)
Definition: message.h:28
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
void mutt_sleep(short s)
Sleep for a while.
Definition: muttlib.c:1478
WHERE bool OptForceRefresh
(pseudo) refresh even during macros
Definition: options.h:34
char * data
pointer to data
Definition: buffer.h:35

+ Here is the call graph for this function:

static int parse_finish ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'finish' command - Implements command_t.

Return values
1Stop processing the current file
-1Failed

If the 'finish' command is found, we should stop reading the current file.

Definition at line 1091 of file init.c.

1093 {
1094  if (MoreArgs(s))
1095  {
1096  mutt_buffer_printf(err, _("%s: too many arguments"), "finish");
1097  return -1;
1098  }
1099 
1100  return 1;
1101 }
#define _(a)
Definition: message.h:28
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
#define MoreArgs(buf)
Definition: buffer.h:44

+ Here is the call graph for this function:

static int parse_group ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'group' and 'ungroup' commands - Implements command_t.

Definition at line 1106 of file init.c.

1108 {
1109  struct GroupContext *gc = NULL;
1110  enum GroupState state = GS_NONE;
1111  struct Address *addr = NULL;
1112  char *estr = NULL;
1113 
1114  do
1115  {
1116  mutt_extract_token(buf, s, 0);
1117  if (parse_group_context(&gc, buf, s, data, err) == -1)
1118  goto bail;
1119 
1120  if (data == MUTT_UNGROUP && (mutt_str_strcasecmp(buf->data, "*") == 0))
1121  {
1122  if (mutt_group_context_clear(&gc) < 0)
1123  goto bail;
1124  goto out;
1125  }
1126 
1127  if (mutt_str_strcasecmp(buf->data, "-rx") == 0)
1128  state = GS_RX;
1129  else if (mutt_str_strcasecmp(buf->data, "-addr") == 0)
1130  state = GS_ADDR;
1131  else
1132  {
1133  switch (state)
1134  {
1135  case GS_NONE:
1136  mutt_buffer_printf(err, _("%sgroup: missing -rx or -addr"),
1137  (data == MUTT_UNGROUP) ? "un" : "");
1138  goto bail;
1139 
1140  case GS_RX:
1141  if (data == MUTT_GROUP &&
1142  mutt_group_context_add_regex(gc, buf->data, REG_ICASE, err) != 0)
1143  {
1144  goto bail;
1145  }
1146  else if (data == MUTT_UNGROUP &&
1147  mutt_group_context_remove_regex(gc, buf->data) < 0)
1148  {
1149  goto bail;
1150  }
1151  break;
1152 
1153  case GS_ADDR:
1154  addr = mutt_addr_parse_list2(NULL, buf->data);
1155  if (!addr)
1156  goto bail;
1157  if (mutt_addrlist_to_intl(addr, &estr))
1158  {
1159  mutt_buffer_printf(err, _("%sgroup: warning: bad IDN '%s'"),
1160  data == 1 ? "un" : "", estr);
1161  mutt_addr_free(&addr);
1162  FREE(&estr);
1163  goto bail;
1164  }
1165  if (data == MUTT_GROUP)
1167  else if (data == MUTT_UNGROUP)
1169  mutt_addr_free(&addr);
1170  break;
1171  }
1172  }
1173  } while (MoreArgs(s));
1174 
1175 out:
1177  return 0;
1178 
1179 bail:
1181  return -1;
1182 }
struct Address * mutt_addr_parse_list2(struct Address *p, const char *s)
Parse a list of email addresses.
Definition: address.c:630
int mutt_group_context_remove_regex(struct GroupContext *ctx, const char *s)
Remove a Regex from a Group List.
Definition: group.c:269
#define MUTT_UNGROUP
Definition: group.h:33
#define _(a)
Definition: message.h:28
void mutt_group_context_destroy(struct GroupContext **ctx)
Destroy a Group List.
Definition: group.c:130
An email address.
Definition: address.h:32
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
A set of Groups.
Definition: group.h:48
int mutt_addrlist_to_intl(struct Address *a, char **err)
Convert an Address list to Punycode.
Definition: address.c:1208
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
void mutt_group_context_add_addrlist(struct GroupContext *ctx, struct Address *a)
Add an Address List to a Group List.
Definition: group.c:215
char * data
pointer to data
Definition: buffer.h:35
Group is missing an argument.
Definition: init.c:103
int mutt_group_context_remove_addrlist(struct GroupContext *ctx, struct Address *a)
Remove an Address List from a Group List.
Definition: group.c:228
GroupState
Type of email address group.
Definition: init.c:101
int mutt_group_context_add_regex(struct GroupContext *ctx, const char *s, int flags, struct Buffer *err)
Add a Regex to a Group List.
Definition: group.c:251
Entry is an address.
Definition: init.c:105
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625
#define FREE(x)
Definition: memory.h:46
Entry is a regular expression.
Definition: init.c:104
static int parse_group_context(struct GroupContext **ctx, struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
Parse a group context.
Definition: init.c:543
void mutt_addr_free(struct Address **p)
Free a list of Addresses.
Definition: address.c:446
int mutt_group_context_clear(struct GroupContext **ctx)
Empty a Group List.
Definition: group.c:85
#define MUTT_GROUP
Definition: group.h:32

+ Here is the call graph for this function:

static int parse_ifdef ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'ifdef' and 'ifndef' commands - Implements command_t.

The 'ifdef' command allows conditional elements in the config file. If a given variable, function, command or compile-time symbol exists, then read the rest of the line of config commands. e.g. ifdef sidebar source ~/.neomutt/sidebar.rc

If (data == 1) then it means use the 'ifndef' (if-not-defined) command. e.g. ifndef imap finish

Definition at line 1197 of file init.c.

1199 {
1200  struct Buffer token = { 0 };
1201 
1202  mutt_extract_token(buf, s, 0);
1203 
1204  /* is the item defined as a variable? */
1205  struct HashElem *he = cs_get_elem(Config, buf->data);
1206  bool res = (he != NULL);
1207 
1208  /* is the item a compiled-in feature? */
1209  if (!res)
1210  {
1211  res = feature_enabled(buf->data);
1212  }
1213 
1214  /* or a function? */
1215  if (!res)
1216  {
1217  for (int i = 0; !res && (i < MENU_MAX); i++)
1218  {
1219  const struct Binding *b = km_get_table(Menus[i].value);
1220  if (!b)
1221  continue;
1222 
1223  for (int j = 0; b[j].name; j++)
1224  {
1225  if (mutt_str_strcmp(buf->data, b[j].name) == 0)
1226  {
1227  res = true;
1228  break;
1229  }
1230  }
1231  }
1232  }
1233 
1234  /* or a command? */
1235  if (!res)
1236  {
1237  for (int i = 0; Commands[i].name; i++)
1238  {
1239  if (mutt_str_strcmp(buf->data, Commands[i].name) == 0)
1240  {
1241  res = true;
1242  break;
1243  }
1244  }
1245  }
1246 
1247  /* or a my_ var? */
1248  if (!res)
1249  {
1250  res = !!myvar_get(buf->data);
1251  }
1252 
1253  if (!MoreArgs(s))
1254  {
1255  mutt_buffer_printf(err, _("%s: too few arguments"), (data ? "ifndef" : "ifdef"));
1256  return -1;
1257  }
1259 
1260  /* ifdef KNOWN_SYMBOL or ifndef UNKNOWN_SYMBOL */
1261  if ((res && (data == 0)) || (!res && (data == 1)))
1262  {
1263  int rc = mutt_parse_rc_line(buf->data, &token, err);
1264  if (rc == -1)
1265  {
1266  mutt_error(_("Error: %s"), err->data);
1267  FREE(&token.data);
1268  return -1;
1269  }
1270  FREE(&token.data);
1271  return rc;
1272  }
1273  return 0;
1274 }
bool feature_enabled(const char *name)
Test if a compile-time feature is enabled.
Definition: version.c:469
int mutt_parse_rc_line(char *line, struct Buffer *token, struct Buffer *err)
Parse a line of user config.
Definition: init.c:3119
String manipulation buffer.
Definition: buffer.h:33
#define _(a)
Definition: message.h:28
WHERE struct ConfigSet * Config
Wrapper around the user&#39;s config settings.
Definition: globals.h:39
const char * name
Name of the command.
Definition: mutt_commands.h:45
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
const struct Command Commands[]
Definition: init.h:4685
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
const char * name
name of the function
Definition: keymap.h:100
struct HashElem * cs_get_elem(const struct ConfigSet *cs, const char *name)
Get the HashElem representing a config item.
Definition: set.c:192
const struct Mapping Menus[]
Menu name lookup table.
Definition: keymap.c:59
const struct Binding * km_get_table(int menu)
Lookup a menu&#39;s keybindings.
Definition: keymap.c:1209
#define MUTT_TOKEN_SPACE
don&#39;t treat whitespace as a term
Definition: mutt.h:73
char * data
pointer to data
Definition: buffer.h:35
const char * myvar_get(const char *var)
Get the value of a "my_" variable.
Definition: myvar.c:42
#define mutt_error(...)
Definition: logging.h:88
#define FREE(x)
Definition: memory.h:46
The item stored in a Hash Table.
Definition: hash.h:42
Mapping between a user key and a function.
Definition: keymap.h:98
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

static int parse_ignore ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'ignore' command - Implements command_t.

Definition at line 1279 of file init.c.

1281 {
1282  do
1283  {
1284  mutt_extract_token(buf, s, 0);
1286  add_to_stailq(&Ignore, buf->data);
1287  } while (MoreArgs(s));
1288 
1289  return 0;
1290 }
static void remove_from_stailq(struct ListHead *head, const char *str)
Remove an item, matching a string, from a List.
Definition: init.c:727
struct ListHead UnIgnore
List of header patterns to unignore (see)
Definition: email_globals.c:44
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
char * data
pointer to data
Definition: buffer.h:35
struct ListHead Ignore
List of header patterns to ignore.
Definition: email_globals.c:43
static void add_to_stailq(struct ListHead *head, const char *str)
Add a string to a list.
Definition: init.c:115

+ Here is the call graph for this function:

static int parse_lists ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'lists' command - Implements command_t.

Definition at line 1295 of file init.c.

1297 {
1298  struct GroupContext *gc = NULL;
1299 
1300  do
1301  {
1302  mutt_extract_token(buf, s, 0);
1303 
1304  if (parse_group_context(&gc, buf, s, data, err) == -1)
1305  goto bail;
1306 
1307  mutt_regexlist_remove(&UnMailLists, buf->data);
1308 
1309  if (mutt_regexlist_add(&MailLists, buf->data, REG_ICASE, err) != 0)
1310  goto bail;
1311 
1312  if (mutt_group_context_add_regex(gc, buf->data, REG_ICASE, err) != 0)
1313  goto bail;
1314  } while (MoreArgs(s));
1315 
1317  return 0;
1318 
1319 bail:
1321  return -1;
1322 }
int mutt_regexlist_remove(struct RegexList *rl, const char *str)
Remove a Regex from a list.
Definition: regex.c:224
void mutt_group_context_destroy(struct GroupContext **ctx)
Destroy a Group List.
Definition: group.c:130
A set of Groups.
Definition: group.h:48
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
int mutt_regexlist_add(struct RegexList *rl, const char *str, int flags, struct Buffer *err)
Compile a regex string and add it to a list.
Definition: regex.c:128
char * data
pointer to data
Definition: buffer.h:35
int mutt_group_context_add_regex(struct GroupContext *ctx, const char *s, int flags, struct Buffer *err)
Add a Regex to a Group List.
Definition: group.c:251
static int parse_group_context(struct GroupContext **ctx, struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
Parse a group context.
Definition: init.c:543

+ Here is the call graph for this function:

static int parse_my_hdr ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'my_hdr' command - Implements command_t.

Definition at line 1327 of file init.c.

1329 {
1330  struct ListNode *n = NULL;
1331  size_t keylen;
1332 
1334  char *p = strpbrk(buf->data, ": \t");
1335  if (!p || (*p != ':'))
1336  {
1337  mutt_buffer_strcpy(err, _("invalid header field"));
1338  return -1;
1339  }
1340  keylen = p - buf->data + 1;
1341 
1342  STAILQ_FOREACH(n, &UserHeader, entries)
1343  {
1344  /* see if there is already a field by this name */
1345  if (mutt_str_strncasecmp(buf->data, n->data, keylen) == 0)
1346  {
1347  break;
1348  }
1349  }
1350 
1351  if (!n)
1352  {
1353  /* not found, allocate memory for a new node and add it to the list */
1354  n = mutt_list_insert_tail(&UserHeader, NULL);
1355  }
1356  else
1357  {
1358  /* found, free the existing data */
1359  FREE(&n->data);
1360  }
1361 
1362  n->data = buf->data;
1363  mutt_buffer_init(buf);
1364 
1365  return 0;
1366 }
#define _(a)
Definition: message.h:28
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
struct ListNode * mutt_list_insert_tail(struct ListHead *h, char *s)
Append a string to the end of a List.
Definition: list.c:58
#define MUTT_TOKEN_QUOTE
don&#39;t interpret quotes
Definition: mutt.h:74
void mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:316
int mutt_str_strncasecmp(const char *a, const char *b, size_t l)
Compare two strings ignoring case (to a maximum), safely.
Definition: string.c:653
#define MUTT_TOKEN_SPACE
don&#39;t treat whitespace as a term
Definition: mutt.h:73
char * data
pointer to data
Definition: buffer.h:35
#define STAILQ_FOREACH(var, head, field)
Definition: queue.h:350
char * data
Definition: list.h:35
#define FREE(x)
Definition: memory.h:46
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:66
A List node for strings.
Definition: list.h:33

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

static int parse_path_list ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'sidebar_whitelist' command - Implements command_t.

Definition at line 1372 of file init.c.

1374 {
1375  char path[PATH_MAX];
1376 
1377  do
1378  {
1379  mutt_extract_token(buf, s, 0);
1380  mutt_str_strfcpy(path, buf->data, sizeof(path));
1381  mutt_expand_path(path, sizeof(path));
1382  add_to_stailq((struct ListHead *) data, path);
1383  } while (MoreArgs(s));
1384 
1385  return 0;
1386 }
char * mutt_expand_path(char *buf, size_t buflen)
Create the canonical path.
Definition: muttlib.c:157
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
#define PATH_MAX
Definition: mutt.h:46
char * data
pointer to data
Definition: buffer.h:35
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
char * data
Definition: list.h:35
static void add_to_stailq(struct ListHead *head, const char *str)
Add a string to a list.
Definition: init.c:115

+ Here is the call graph for this function:

static int parse_path_unlist ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unsidebar_whitelist' command - Implements command_t.

Definition at line 1393 of file init.c.

1395 {
1396  char path[PATH_MAX];
1397 
1398  do
1399  {
1400  mutt_extract_token(buf, s, 0);
1401  /* Check for deletion of entire list */
1402  if (mutt_str_strcmp(buf->data, "*") == 0)
1403  {
1404  mutt_list_free((struct ListHead *) data);
1405  break;
1406  }
1407  mutt_str_strfcpy(path, buf->data, sizeof(path));
1408  mutt_expand_path(path, sizeof(path));
1409  remove_from_stailq((struct ListHead *) data, path);
1410  } while (MoreArgs(s));
1411 
1412  return 0;
1413 }
static void remove_from_stailq(struct ListHead *head, const char *str)
Remove an item, matching a string, from a List.
Definition: init.c:727
void mutt_list_free(struct ListHead *h)
Free a List AND its strings.
Definition: list.c:105
char * mutt_expand_path(char *buf, size_t buflen)
Create the canonical path.
Definition: muttlib.c:157
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
#define PATH_MAX
Definition: mutt.h:46
char * data
pointer to data
Definition: buffer.h:35
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
char * data
Definition: list.h:35
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

static int parse_set ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'set' family of commands - Implements command_t.

This is used by 'reset', 'set', 'toggle' and 'unset'.

Definition at line 1421 of file init.c.

1423 {
1424  /* The order must match `enum MuttSetCommand` */
1425  static const char *set_commands[] = { "set", "toggle", "unset", "reset" };
1426 
1427  int rc = 0;
1428 
1429  while (MoreArgs(s))
1430  {
1431  bool prefix = false;
1432  bool query = false;
1433  bool inv = (data == MUTT_SET_INV);
1434  bool reset = (data == MUTT_SET_RESET);
1435  bool unset = (data == MUTT_SET_UNSET);
1436 
1437  if (*s->dptr == '?')
1438  {
1439  prefix = true;
1440  query = true;
1441  s->dptr++;
1442  }
1443  else if (mutt_str_startswith(s->dptr, "no", CASE_MATCH))
1444  {
1445  prefix = true;
1446  unset = !unset;
1447  s->dptr += 2;
1448  }
1449  else if (mutt_str_startswith(s->dptr, "inv", CASE_MATCH))
1450  {
1451  prefix = true;
1452  inv = !inv;
1453  s->dptr += 3;
1454  }
1455  else if (*s->dptr == '&')
1456  {
1457  prefix = true;
1458  reset = true;
1459  s->dptr++;
1460  }
1461 
1462  if (prefix && (data != MUTT_SET_SET))
1463  {
1464  mutt_buffer_printf(err, "ERR22 cannot use 'inv', 'no', '&' or '?' with the '%s' command",
1465  set_commands[data]);
1466  return -1;
1467  }
1468 
1469  /* get the variable name */
1471 
1472  bool bq = false;
1473  bool equals = false;
1474 
1475  struct HashElem *he = NULL;
1476  bool my = mutt_str_startswith(buf->data, "my_", CASE_MATCH);
1477  if (!my)
1478  {
1479  he = cs_get_elem(Config, buf->data);
1480  if (!he)
1481  {
1482  if (reset && (mutt_str_strcmp(buf->data, "all") == 0))
1483  {
1484  struct HashElem **list = get_elem_list(Config);
1485  if (!list)
1486  return -1;
1487 
1488  for (size_t i = 0; list[i]; i++)
1489  cs_he_reset(Config, list[i], NULL);
1490 
1491  FREE(&list);
1492  break;
1493  }
1494  else
1495  {
1496  mutt_buffer_printf(err, "ERR01 unknown variable: %s", buf->data);
1497  return -1;
1498  }
1499  }
1500 
1501  bq = ((DTYPE(he->type) == DT_BOOL) || (DTYPE(he->type) == DT_QUAD));
1502  }
1503 
1504  if (*s->dptr == '?')
1505  {
1506  if (prefix)
1507  {
1509  err, "ERR02 cannot use a prefix when querying a variable");
1510  return -1;
1511  }
1512 
1513  if (reset || unset || inv)
1514  {
1515  mutt_buffer_printf(err, "ERR03 cannot query a variable with the '%s' command",
1516  set_commands[data]);
1517  return -1;
1518  }
1519 
1520  query = true;
1521  s->dptr++;
1522  }
1523  else if (*s->dptr == '=')
1524  {
1525  if (prefix)
1526  {
1527  mutt_buffer_printf(err,
1528  "ERR04 cannot use prefix when setting a variable");
1529  return -1;
1530  }
1531 
1532  if (reset || unset || inv)
1533  {
1534  mutt_buffer_printf(err, "ERR05 cannot set a variable with the '%s' command",
1535  set_commands[data]);
1536  return -1;
1537  }
1538 
1539  equals = true;
1540  s->dptr++;
1541  }
1542 
1543  if (!bq && (inv || (unset && prefix)))
1544  {
1545  if (data == MUTT_SET_SET)
1546  {
1547  mutt_buffer_printf(err, "ERR06 prefixes 'no' and 'inv' may only be "
1548  "used with bool/quad variables");
1549  }
1550  else
1551  {
1552  mutt_buffer_printf(err, "ERR07 command '%s' can only be used with bool/quad variables",
1553  set_commands[data]);
1554  }
1555  return -1;
1556  }
1557 
1558  if (reset)
1559  {
1560  // mutt_buffer_printf(err, "ACT24 reset variable %s", buf->data);
1561  if (he)
1562  {
1563  rc = cs_he_reset(Config, he, err);
1564  if (CSR_RESULT(rc) != CSR_SUCCESS)
1565  return -1;
1566  }
1567  else
1568  {
1569  myvar_del(buf->data);
1570  }
1571  continue;
1572  }
1573 
1574  if ((data == MUTT_SET_SET) && !inv && !unset)
1575  {
1576  if (query)
1577  {
1578  // mutt_buffer_printf(err, "ACT08 query variable %s", buf->data);
1579  if (he)
1580  {
1581  mutt_buffer_addstr(err, buf->data);
1582  mutt_buffer_addch(err, '=');
1583  mutt_buffer_reset(buf);
1584  rc = cs_he_string_get(Config, he, buf);
1585  if (CSR_RESULT(rc) != CSR_SUCCESS)
1586  {
1587  mutt_buffer_addstr(err, buf->data);
1588  return -1;
1589  }
1590  pretty_var(buf->data, err);
1591  }
1592  else
1593  {
1594  const char *val = myvar_get(buf->data);
1595  if (val)
1596  {
1597  mutt_buffer_addstr(err, buf->data);
1598  mutt_buffer_addch(err, '=');
1599  pretty_var(val, err);
1600  }
1601  else
1602  {
1603  mutt_buffer_printf(err, _("%s: unknown variable"), buf->data);
1604  return -1;
1605  }
1606  }
1607  break;
1608  }
1609  else if (equals)
1610  {
1611  // mutt_buffer_printf(err, "ACT11 set variable %s to ", buf->data);
1612  const char *name = NULL;
1613  if (my)
1614  {
1615  name = mutt_str_strdup(buf->data);
1616  }
1618  if (my)
1619  {
1620  myvar_set(name, buf->data);
1621  FREE(&name);
1622  }
1623  else
1624  {
1625  if (DTYPE(he->type) == DT_PATH)
1626  {
1627  mutt_expand_path(buf->data, buf->dsize);
1628  char scratch[PATH_MAX];
1629  mutt_str_strfcpy(scratch, buf->data, sizeof(scratch));
1630  size_t scratchlen = mutt_str_strlen(scratch);
1631  if (!(he->type & DT_MAILBOX) && (scratchlen != 0))
1632  {
1633  if ((scratch[scratchlen - 1] != '|') && /* not a command */
1634  (url_check_scheme(scratch) == U_UNKNOWN)) /* probably a local file */
1635  {
1636  struct ListNode *np = STAILQ_FIRST(&MuttrcStack);
1637  if (mutt_path_to_absolute(scratch, np ? NONULL(np->data) : "./"))
1638  {
1639  mutt_buffer_reset(buf);
1640  mutt_buffer_addstr(buf, scratch);
1641  }
1642  else
1643  {
1644  mutt_error(_("Error: impossible to build path of '%s'"), scratch);
1645  }
1646  }
1647  }
1648  }
1649  else if (DTYPE(he->type) == DT_COMMAND)
1650  {
1651  char scratch[PATH_MAX];
1652  mutt_str_strfcpy(scratch, buf->data, sizeof(scratch));
1653 
1654  if (mutt_str_strcmp(buf->data, "builtin") != 0)
1655  {
1656  mutt_expand_path(scratch, sizeof(scratch));
1657  }
1658  mutt_buffer_reset(buf);
1659  mutt_buffer_addstr(buf, scratch);
1660  }
1661 
1662  rc = cs_he_string_set(Config, he, buf->data, err);
1663  if (CSR_RESULT(rc) != CSR_SUCCESS)
1664  return -1;
1665  }
1666  continue;
1667  }
1668  else
1669  {
1670  if (bq)
1671  {
1672  // mutt_buffer_printf(err, "ACT23 set variable %s to 'yes'", buf->data);
1673  rc = cs_he_native_set(Config, he, true, err);
1674  if (CSR_RESULT(rc) != CSR_SUCCESS)
1675  return -1;
1676  continue;
1677  }
1678  else
1679  {
1680  // mutt_buffer_printf(err, "ACT10 query variable %s", buf->data);
1681  if (he)
1682  {
1683  mutt_buffer_addstr(err, buf->data);
1684  mutt_buffer_addch(err, '=');
1685  mutt_buffer_reset(buf);
1686  rc = cs_he_string_get(Config, he, buf);
1687  if (CSR_RESULT(rc) != CSR_SUCCESS)
1688  {
1689  mutt_buffer_addstr(err, buf->data);
1690  return -1;
1691  }
1692  pretty_var(buf->data, err);
1693  }
1694  else
1695  {
1696  const char *val = myvar_get(buf->data);
1697  if (val)
1698  {
1699  mutt_buffer_addstr(err, buf->data);
1700  mutt_buffer_addch(err, '=');
1701  pretty_var(val, err);
1702  }
1703  else
1704  {
1705  mutt_buffer_printf(err, _("%s: unknown variable"), buf->data);
1706  return -1;
1707  }
1708  }
1709  break;
1710  }
1711  }
1712  }
1713 
1714  if (my)
1715  {
1716  myvar_del(buf->data);
1717  }
1718  else if (bq)
1719  {
1720  if (inv)
1721  {
1722  // mutt_buffer_printf(err, "ACT25 TOGGLE bool/quad variable %s", buf->data);
1723  if (DTYPE(he->type) == DT_BOOL)
1724  bool_he_toggle(Config, he, err);
1725  else
1726  quad_he_toggle(Config, he, err);
1727  }
1728  else
1729  {
1730  // mutt_buffer_printf(err, "ACT26 UNSET bool/quad variable %s", buf->data);
1731  rc = cs_he_native_set(Config, he, false, err);
1732  if (CSR_RESULT(rc) != CSR_SUCCESS)
1733  return -1;
1734  }
1735  continue;
1736  }
1737  else
1738  {
1739  rc = cs_he_string_set(Config, he, NULL, err);
1740  if (CSR_RESULT(rc) != CSR_SUCCESS)
1741  return -1;
1742  }
1743  }
1744 
1745  return 0;
1746 }
#define NONULL(x)
Definition: string2.h:39
void mutt_buffer_reset(struct Buffer *buf)
Reset an existing Buffer.
Definition: buffer.c:81
#define CSR_RESULT(x)
Definition: set.h:61
static struct ListHead MuttrcStack
Definition: init.c:76
size_t pretty_var(const char *str, struct Buffer *buf)
Escape and stringify a config item value.
Definition: dump.c:85
Url wasn&#39;t recognised.
Definition: url.h:34
#define _(a)
Definition: message.h:28
WHERE struct ConfigSet * Config
Wrapper around the user&#39;s config settings.
Definition: globals.h:39
Match case when comparing strings.
Definition: string2.h:69
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:663
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
int bool_he_toggle(struct ConfigSet *cs, struct HashElem *he, struct Buffer *err)
Toggle the value of a bool.
Definition: bool.c:216
#define DT_QUAD
quad-option (no/yes/ask-no/ask-yes)
Definition: types.h:36
#define DTYPE(x)
Mask for the Data Type.
Definition: types.h:42
size_t dsize
length of data
Definition: buffer.h:37
char * mutt_expand_path(char *buf, size_t buflen)
Create the canonical path.
Definition: muttlib.c:157
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
const char * name
Definition: pgpmicalg.c:42
int cs_he_reset(const struct ConfigSet *cs, struct HashElem *he, struct Buffer *err)
Reset a config item to its initial value.
Definition: set.c:402
default is to invert all vars
Definition: init.h:101
int cs_he_native_set(const struct ConfigSet *cs, struct HashElem *he, intptr_t value, struct Buffer *err)
Natively set the value of a HashElem config item.
Definition: set.c:750
enum UrlScheme url_check_scheme(const char *s)
Check the protocol of a URL.
Definition: url.c:133
default is to set all vars
Definition: init.h:100
struct HashElem * cs_get_elem(const struct ConfigSet *cs, const char *name)
Get the HashElem representing a config item.
Definition: set.c:192
void myvar_del(const char *var)
Unset the value of a "my_" variable.
Definition: myvar.c:83
size_t mutt_buffer_addstr(struct Buffer *buf, const char *s)
Add a string to a Buffer.
Definition: buffer.c:258
#define CSR_SUCCESS
Action completed successfully.
Definition: set.h:45
void myvar_set(const char *var, const char *val)
Set the value of a "my_" variable.
Definition: myvar.c:60
#define DT_PATH
a pathname
Definition: types.h:35
#define PATH_MAX
Definition: mutt.h:46
#define DT_MAILBOX
DT_PATH: Don&#39;t perform path expansions.
Definition: types.h:46
char * dptr
current read/write position
Definition: buffer.h:36
char * data
pointer to data
Definition: buffer.h:35
#define DT_COMMAND
a command
Definition: types.h:29
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
size_t mutt_buffer_addch(struct Buffer *buf, char c)
Add a single character to a Buffer.
Definition: buffer.c:273
default is to reset all vars to default
Definition: init.h:103
int mutt_path_to_absolute(char *path, const char *reference)
Convert relative filepath to an absolute path.
Definition: path.c:416
const char * myvar_get(const char *var)
Get the value of a "my_" variable.
Definition: myvar.c:42
size_t mutt_str_startswith(const char *str, const char *prefix, enum CaseSensitivity cs)
Check whether a string starts with a prefix.
Definition: string.c:166
int cs_he_string_get(const struct ConfigSet *cs, struct HashElem *he, struct Buffer *result)
Get a config item as a string.
Definition: set.c:680
void * data
Definition: hash.h:46
default is to unset all vars
Definition: init.h:102
char * data
Definition: list.h:35
int quad_he_toggle(struct ConfigSet *cs, struct HashElem *he, struct Buffer *err)
Toggle the value of a quad.
Definition: quad.c:229
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
#define mutt_error(...)
Definition: logging.h:88
#define MUTT_TOKEN_BACKTICK_VARS
expand variables within backticks
Definition: mutt.h:78
int type
Definition: hash.h:44
#define FREE(x)
Definition: memory.h:46
The item stored in a Hash Table.
Definition: hash.h:42
#define MUTT_TOKEN_EQUAL
treat &#39;=&#39; as a special
Definition: mutt.h:71
A List node for strings.
Definition: list.h:33
struct HashElem ** get_elem_list(struct ConfigSet *cs)
Create a sorted list of all config items.
Definition: dump.c:120
#define STAILQ_FIRST(head)
Definition: queue.h:348
#define DT_BOOL
boolean option
Definition: types.h:28
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612
int cs_he_string_set(const struct ConfigSet *cs, struct HashElem *he, const char *value, struct Buffer *err)
Set a config item by string.
Definition: set.c:602
#define MUTT_TOKEN_QUESTION
treat &#39;?&#39; as a special
Definition: mutt.h:80

+ Here is the call graph for this function:

static int parse_setenv ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'setenv' and 'unsetenv' commands - Implements command_t.

Definition at line 1751 of file init.c.

1753 {
1754  char **envp = mutt_envlist_getlist();
1755 
1756  bool query = false;
1757  bool unset = (data == MUTT_SET_UNSET);
1758 
1759  if (!MoreArgs(s))
1760  {
1761  mutt_buffer_printf(err, _("%s: too few arguments"), "setenv");
1762  return -1;
1763  }
1764 
1765  if (*s->dptr == '?')
1766  {
1767  query = true;
1768  s->dptr++;
1769  }
1770 
1771  /* get variable name */
1773 
1774  if (query)
1775  {
1776  bool found = false;
1777  while (envp && *envp)
1778  {
1779  /* This will display all matches for "^QUERY" */
1780  if (mutt_str_startswith(*envp, buf->data, CASE_MATCH))
1781  {
1782  if (!found)
1783  {
1784  mutt_endwin();
1785  found = true;
1786  }
1787  puts(*envp);
1788  }
1789  envp++;
1790  }
1791 
1792  if (found)
1793  {
1795  return 0;
1796  }
1797 
1798  mutt_buffer_printf(err, _("%s is unset"), buf->data);
1799  return -1;
1800  }
1801 
1802  if (unset)
1803  {
1804  if (mutt_envlist_unset(buf->data))
1805  return 0;
1806  return -1;
1807  }
1808 
1809  /* set variable */
1810 
1811  if (*s->dptr == '=')
1812  {
1813  s->dptr++;
1814  SKIPWS(s->dptr);
1815  }
1816 
1817  if (!MoreArgs(s))
1818  {
1819  mutt_buffer_printf(err, _("%s: too few arguments"), "setenv");
1820  return -1;
1821  }
1822 
1823  char *name = mutt_str_strdup(buf->data);
1824  mutt_extract_token(buf, s, 0);
1825  mutt_envlist_set(name, buf->data, true);
1826  FREE(&name);
1827 
1828  return 0;
1829 }
#define _(a)
Definition: message.h:28
Match case when comparing strings.
Definition: string2.h:69
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
const char * name
Definition: pgpmicalg.c:42
void mutt_endwin(void)
Shutdown curses/slang.
Definition: curs_lib.c:498
bool mutt_envlist_unset(const char *name)
Unset an environment variable.
Definition: envlist.c:129
char * dptr
current read/write position
Definition: buffer.h:36
char * data
pointer to data
Definition: buffer.h:35
size_t mutt_str_startswith(const char *str, const char *prefix, enum CaseSensitivity cs)
Check whether a string starts with a prefix.
Definition: string.c:166
int mutt_any_key_to_continue(const char *s)
Prompt the user to &#39;press any key&#39; and wait.
Definition: curs_lib.c:531
default is to unset all vars
Definition: init.h:102
char * data
Definition: list.h:35
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
#define FREE(x)
Definition: memory.h:46
bool mutt_envlist_set(const char *name, const char *value, bool overwrite)
Set an environment variable.
Definition: envlist.c:84
#define MUTT_TOKEN_EQUAL
treat &#39;=&#39; as a special
Definition: mutt.h:71
char ** mutt_envlist_getlist(void)
Get the private environment.
Definition: envlist.c:165
#define SKIPWS(c)
Definition: string2.h:49

+ Here is the call graph for this function:

static int parse_source ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'source' command - Implements command_t.

Definition at line 1834 of file init.c.

1836 {
1837  char path[PATH_MAX];
1838 
1839  do
1840  {
1841  if (mutt_extract_token(buf, s, 0) != 0)
1842  {
1843  mutt_buffer_printf(err, _("source: error at %s"), s->dptr);
1844  return -1;
1845  }
1846  mutt_str_strfcpy(path, buf->data, sizeof(path));
1847  mutt_expand_path(path, sizeof(path));
1848 
1849  if (source_rc(path, err) < 0)
1850  {
1851  mutt_buffer_printf(err, _("source: file %s could not be sourced"), path);
1852  return -1;
1853  }
1854 
1855  } while (MoreArgs(s));
1856 
1857  return 0;
1858 }
static int source_rc(const char *rcfile_path, struct Buffer *err)
Read an initialization file.
Definition: init.c:753
#define _(a)
Definition: message.h:28
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
char * mutt_expand_path(char *buf, size_t buflen)
Create the canonical path.
Definition: muttlib.c:157
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
#define PATH_MAX
Definition: mutt.h:46
char * dptr
current read/write position
Definition: buffer.h:36
char * data
pointer to data
Definition: buffer.h:35
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742

+ Here is the call graph for this function:

static int parse_spam_list ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'spam' and 'nospam' commands - Implements command_t.

Definition at line 1863 of file init.c.

1865 {
1866  struct Buffer templ;
1867 
1868  mutt_buffer_init(&templ);
1869 
1870  /* Insist on at least one parameter */
1871  if (!MoreArgs(s))
1872  {
1873  if (data == MUTT_SPAM)
1874  mutt_buffer_strcpy(err, _("spam: no matching pattern"));
1875  else
1876  mutt_buffer_strcpy(err, _("nospam: no matching pattern"));
1877  return -1;
1878  }
1879 
1880  /* Extract the first token, a regex */
1881  mutt_extract_token(buf, s, 0);
1882 
1883  /* data should be either MUTT_SPAM or MUTT_NOSPAM. MUTT_SPAM is for spam commands. */
1884  if (data == MUTT_SPAM)
1885  {
1886  /* If there's a second parameter, it's a template for the spam tag. */
1887  if (MoreArgs(s))
1888  {
1889  mutt_extract_token(&templ, s, 0);
1890 
1891  /* Add to the spam list. */
1892  if (mutt_replacelist_add(&SpamList, buf->data, templ.data, err) != 0)
1893  {
1894  FREE(&templ.data);
1895  return -1;
1896  }
1897  FREE(&templ.data);
1898  }
1899  /* If not, try to remove from the nospam list. */
1900  else
1901  {
1903  }
1904 
1905  return 0;
1906  }
1907  /* MUTT_NOSPAM is for nospam commands. */
1908  else if (data == MUTT_NOSPAM)
1909  {
1910  /* nospam only ever has one parameter. */
1911 
1912  /* "*" is a special case. */
1913  if (mutt_str_strcmp(buf->data, "*") == 0)
1914  {
1917  return 0;
1918  }
1919 
1920  /* If it's on the spam list, just remove it. */
1921  if (mutt_replacelist_remove(&SpamList, buf->data) != 0)
1922  return 0;
1923 
1924  /* Otherwise, add it to the nospam list. */
1925  if (mutt_regexlist_add(&NoSpamList, buf->data, REG_ICASE, err) != 0)
1926  return -1;
1927 
1928  return 0;
1929  }
1930 
1931  /* This should not happen. */
1932  mutt_buffer_strcpy(err, "This is no good at all.");
1933  return -1;
1934 }
int mutt_replacelist_add(struct ReplaceList *rl, const char *pat, const char *templ, struct Buffer *err)
Add a pattern and a template to a list.
Definition: regex.c:260
int mutt_regexlist_remove(struct RegexList *rl, const char *str)
Remove a Regex from a list.
Definition: regex.c:224
#define MUTT_NOSPAM
Definition: mutt.h:187
struct ReplaceList SpamList
List of regexes and patterns to match spam emails.
Definition: email_globals.c:42
String manipulation buffer.
Definition: buffer.h:33
#define _(a)
Definition: message.h:28
void mutt_replacelist_free(struct ReplaceList *rl)
Free a ReplaceList object.
Definition: regex.c:444
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
#define MUTT_SPAM
Definition: mutt.h:186
int mutt_regexlist_add(struct RegexList *rl, const char *str, int flags, struct Buffer *err)
Compile a regex string and add it to a list.
Definition: regex.c:128
void mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:316
char * data
pointer to data
Definition: buffer.h:35
int mutt_replacelist_remove(struct ReplaceList *rl, const char *pat)
Remove a pattern from a list.
Definition: regex.c:561
#define FREE(x)
Definition: memory.h:46
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:66
struct RegexList NoSpamList
List of regexes to whitelist non-spam emails.
Definition: email_globals.c:41
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612
void mutt_regexlist_free(struct RegexList *rl)
Free a RegexList object.
Definition: regex.c:166

+ Here is the call graph for this function:

static int parse_stailq ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse a list command - Implements command_t.

This is used by 'alternative_order', 'auto_view' and several others.

Definition at line 1941 of file init.c.

1943 {
1944  do
1945  {
1946  mutt_extract_token(buf, s, 0);
1947  add_to_stailq((struct ListHead *) data, buf->data);
1948  } while (MoreArgs(s));
1949 
1950  return 0;
1951 }
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
char * data
pointer to data
Definition: buffer.h:35
static void add_to_stailq(struct ListHead *head, const char *str)
Add a string to a list.
Definition: init.c:115

+ Here is the call graph for this function:

static int parse_subjectrx_list ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'subjectrx' command - Implements command_t.

Definition at line 1956 of file init.c.

1958 {
1959  int rc;
1960 
1961  rc = parse_replace_list(buf, s, data, err);
1962  if (rc == 0)
1964  return rc;
1965 }
static void clear_subject_mods(void)
Clear out all modified email subjects.
Definition: init.c:208
char * data
pointer to data
Definition: buffer.h:35
static int parse_replace_list(struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
Parse a string replacement rule - Implements command_t.
Definition: init.c:577

+ Here is the call graph for this function:

static int parse_subscribe ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'subscribe' command - Implements command_t.

Definition at line 1970 of file init.c.

1972 {
1973  struct GroupContext *gc = NULL;
1974 
1975  do
1976  {
1977  mutt_extract_token(buf, s, 0);
1978 
1979  if (parse_group_context(&gc, buf, s, data, err) == -1)
1980  goto bail;
1981 
1982  mutt_regexlist_remove(&UnMailLists, buf->data);
1983  mutt_regexlist_remove(&UnSubscribedLists, buf->data);
1984 
1985  if (mutt_regexlist_add(&MailLists, buf->data, REG_ICASE, err) != 0)
1986  goto bail;
1987  if (mutt_regexlist_add(&SubscribedLists, buf->data, REG_ICASE, err) != 0)
1988  goto bail;
1989  if (mutt_group_context_add_regex(gc, buf->data, REG_ICASE, err) != 0)
1990  goto bail;
1991  } while (MoreArgs(s));
1992 
1994  return 0;
1995 
1996 bail:
1998  return -1;
1999 }
int mutt_regexlist_remove(struct RegexList *rl, const char *str)
Remove a Regex from a list.
Definition: regex.c:224
void mutt_group_context_destroy(struct GroupContext **ctx)
Destroy a Group List.
Definition: group.c:130
A set of Groups.
Definition: group.h:48
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
int mutt_regexlist_add(struct RegexList *rl, const char *str, int flags, struct Buffer *err)
Compile a regex string and add it to a list.
Definition: regex.c:128
char * data
pointer to data
Definition: buffer.h:35
int mutt_group_context_add_regex(struct GroupContext *ctx, const char *s, int flags, struct Buffer *err)
Add a Regex to a Group List.
Definition: group.c:251
static int parse_group_context(struct GroupContext **ctx, struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
Parse a group context.
Definition: init.c:543

+ Here is the call graph for this function:

static int parse_subscribe_to ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'subscribe-to' command - Implements command_t.

The 'subscribe-to' command allows to subscribe to an IMAP-Mailbox. Patterns are not supported. Use it as follows: subscribe-to =folder

Definition at line 2009 of file init.c.

2011 {
2012  if (!buf || !s || !err)
2013  return -1;
2014 
2015  mutt_buffer_reset(err);
2016 
2017  if (MoreArgs(s))
2018  {
2019  mutt_extract_token(buf, s, 0);
2020 
2021  if (MoreArgs(s))
2022  {
2023  mutt_buffer_printf(err, _("%s: too many arguments"), "subscribe-to");
2024  return -1;
2025  }
2026 
2027  if (buf->data && *buf->data)
2028  {
2029  /* Expand and subscribe */
2030  if (imap_subscribe(mutt_expand_path(buf->data, buf->dsize), true) != 0)
2031  {
2032  mutt_buffer_printf(err, _("Could not subscribe to %s"), buf->data);
2033  return -1;
2034  }
2035  else
2036  {
2037  mutt_message(_("Subscribed to %s"), buf->data);
2038  return 0;
2039  }
2040  }
2041  else
2042  {
2043  mutt_debug(5, "Corrupted buffer");
2044  return -1;
2045  }
2046  }
2047 
2048  mutt_buffer_addstr(err, _("No folder specified"));
2049  return -1;
2050 }
void mutt_buffer_reset(struct Buffer *buf)
Reset an existing Buffer.
Definition: buffer.c:81
#define mutt_message(...)
Definition: logging.h:87
#define _(a)
Definition: message.h:28
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
size_t dsize
length of data
Definition: buffer.h:37
char * mutt_expand_path(char *buf, size_t buflen)
Create the canonical path.
Definition: muttlib.c:157
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
size_t mutt_buffer_addstr(struct Buffer *buf, const char *s)
Add a string to a Buffer.
Definition: buffer.c:258
char * data
pointer to data
Definition: buffer.h:35
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
int imap_subscribe(char *path, bool subscribe)
Subscribe to a mailbox.
Definition: imap.c:1391

+ Here is the call graph for this function:

static int parse_tag_formats ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'tag-formats' command - Implements command_t.

Definition at line 2056 of file init.c.

2058 {
2059  if (!buf || !s)
2060  return -1;
2061 
2062  char *tmp = NULL;
2063 
2064  while (MoreArgs(s))
2065  {
2066  char *tag = NULL, *format = NULL;
2067 
2068  mutt_extract_token(buf, s, 0);
2069  if (buf->data && *buf->data)
2070  tag = mutt_str_strdup(buf->data);
2071  else
2072  continue;
2073 
2074  mutt_extract_token(buf, s, 0);
2075  format = mutt_str_strdup(buf->data);
2076 
2077  /* avoid duplicates */
2078  tmp = mutt_hash_find(TagFormats, format);
2079  if (tmp)
2080  {
2081  mutt_debug(3, "tag format '%s' already registered as '%s'\n", format, tmp);
2082  FREE(&tag);
2083  FREE(&format);
2084  continue;
2085  }
2086 
2087  mutt_hash_insert(TagFormats, format, tag);
2088  }
2089  return 0;
2090 }
void * mutt_hash_find(const struct Hash *table, const char *strkey)
Find the HashElem data in a Hash table element using a key.
Definition: hash.c:374
WHERE struct Hash * TagFormats
Hash table of tag-formats (tag -> format string)
Definition: globals.h:59
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
char * data
pointer to data
Definition: buffer.h:35
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
#define FREE(x)
Definition: memory.h:46
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
struct HashElem * mutt_hash_insert(struct Hash *table, const char *strkey, void *data)
Add a new element to the Hash table (with string keys)
Definition: hash.c:349

+ Here is the call graph for this function:

static int parse_tag_transforms ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'tag-transforms' command - Implements command_t.

Definition at line 2095 of file init.c.

2097 {
2098  if (!buf || !s)
2099  return -1;
2100 
2101  char *tmp = NULL;
2102 
2103  while (MoreArgs(s))
2104  {
2105  char *tag = NULL, *transform = NULL;
2106 
2107  mutt_extract_token(buf, s, 0);
2108  if (buf->data && *buf->data)
2109  tag = mutt_str_strdup(buf->data);
2110  else
2111  continue;
2112 
2113  mutt_extract_token(buf, s, 0);
2114  transform = mutt_str_strdup(buf->data);
2115 
2116  /* avoid duplicates */
2117  tmp = mutt_hash_find(TagTransforms, tag);
2118  if (tmp)
2119  {
2120  mutt_debug(3, "tag transform '%s' already registered as '%s'\n", tag, tmp);
2121  FREE(&tag);
2122  FREE(&transform);
2123  continue;
2124  }
2125 
2126  mutt_hash_insert(TagTransforms, tag, transform);
2127  }
2128  return 0;
2129 }
struct Hash * TagTransforms
Lookup table of alternative tag names.
Definition: tags.c:39
void * mutt_hash_find(const struct Hash *table, const char *strkey)
Find the HashElem data in a Hash table element using a key.
Definition: hash.c:374
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
char * data
pointer to data
Definition: buffer.h:35
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
#define FREE(x)
Definition: memory.h:46
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
struct HashElem * mutt_hash_insert(struct Hash *table, const char *strkey, void *data)
Add a new element to the Hash table (with string keys)
Definition: hash.c:349

+ Here is the call graph for this function:

static int parse_unalias ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unalias' command - Implements command_t.

Definition at line 2134 of file init.c.

2136 {
2137  struct Alias *a = NULL;
2138 
2139  do
2140  {
2141  mutt_extract_token(buf, s, 0);
2142 
2143  if (mutt_str_strcmp("*", buf->data) == 0)
2144  {
2145  if (CurrentMenu == MENU_ALIAS)
2146  {
2147  TAILQ_FOREACH(a, &Aliases, entries)
2148  {
2149  a->del = true;
2150  }
2152  }
2153  else
2154  mutt_aliaslist_free(&Aliases);
2155  break;
2156  }
2157  else
2158  {
2159  TAILQ_FOREACH(a, &Aliases, entries)
2160  {
2161  if (mutt_str_strcasecmp(buf->data, a->name) == 0)
2162  {
2163  if (CurrentMenu == MENU_ALIAS)
2164  {
2165  a->del = true;
2167  }
2168  else
2169  {
2170  TAILQ_REMOVE(&Aliases, a, entries);
2171  mutt_alias_free(&a);
2172  }
2173  break;
2174  }
2175  }
2176  }
2177  } while (MoreArgs(s));
2178  return 0;
2179 }
A shortcut for an email address.
Definition: alias.h:36
char * name
Definition: alias.h:38
void mutt_aliaslist_free(struct AliasList *a_list)
Free a List of Aliases.
Definition: alias.c:753
#define TAILQ_FOREACH(var, head, field)
Definition: queue.h:719
Select an email address by its alias.
Definition: keymap.h:67
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
bool del
Definition: alias.h:41
#define TAILQ_REMOVE(head, elm, field)
Definition: queue.h:821
char * data
pointer to data
Definition: buffer.h:35
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625
void mutt_alias_free(struct Alias **p)
Free an Alias.
Definition: alias.c:738
WHERE int CurrentMenu
Current Menu, e.g. MENU_PAGER.
Definition: globals.h:93
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

static int parse_unalternates ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unalternates' command - Implements command_t.

Definition at line 2184 of file init.c.

2186 {
2187  alternates_clean();
2188  do
2189  {
2190  mutt_extract_token(buf, s, 0);
2191  mutt_regexlist_remove(&Alternates, buf->data);
2192 
2193  if ((mutt_str_strcmp(buf->data, "*") != 0) &&
2194  mutt_regexlist_add(&UnAlternates, buf->data, REG_ICASE, err) != 0)
2195  {
2196  return -1;
2197  }
2198 
2199  } while (MoreArgs(s));
2200 
2201  return 0;
2202 }
int mutt_regexlist_remove(struct RegexList *rl, const char *str)
Remove a Regex from a list.
Definition: regex.c:224
static void alternates_clean(void)
Clear the recipient valid flag of all emails.
Definition: init.c:136
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
int mutt_regexlist_add(struct RegexList *rl, const char *str, int flags, struct Buffer *err)
Compile a regex string and add it to a list.
Definition: regex.c:128
char * data
pointer to data
Definition: buffer.h:35
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

static int parse_unattachments ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unattachments' command - Implements command_t.

Definition at line 2207 of file init.c.

2209 {
2210  char op, *p = NULL;
2211  struct ListHead *head = NULL;
2212 
2213  mutt_extract_token(buf, s, 0);
2214  if (!buf->data || *buf->data == '\0')
2215  {
2216  mutt_buffer_strcpy(err, _("unattachments: no disposition"));
2217  return -1;
2218  }
2219 
2220  p = buf->data;
2221  op = *p++;
2222  if (op != '+' && op != '-')
2223  {
2224  op = '+';
2225  p--;
2226  }
2227  if (mutt_str_startswith("attachment", p, CASE_IGNORE))
2228  {
2229  if (op == '+')
2230  head = &AttachAllow;
2231  else
2232  head = &AttachExclude;
2233  }
2234  else if (mutt_str_startswith("inline", p, CASE_IGNORE))
2235  {
2236  if (op == '+')
2237  head = &InlineAllow;
2238  else
2239  head = &InlineExclude;
2240  }
2241  else
2242  {
2243  mutt_buffer_strcpy(err, _("unattachments: invalid disposition"));
2244  return -1;
2245  }
2246 
2247  return parse_unattach_list(buf, s, head, err);
2248 }
#define _(a)
Definition: message.h:28
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
void mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:316
char * data
pointer to data
Definition: buffer.h:35
Ignore case when comparing strings.
Definition: string2.h:70
size_t mutt_str_startswith(const char *str, const char *prefix, enum CaseSensitivity cs)
Check whether a string starts with a prefix.
Definition: string.c:166
static int parse_unattach_list(struct Buffer *buf, struct Buffer *s, struct ListHead *head, struct Buffer *err)
Parse the "unattachments" command.
Definition: init.c:617

+ Here is the call graph for this function:

static int parse_unignore ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unignore' command - Implements command_t.

Definition at line 2253 of file init.c.

2255 {
2256  do
2257  {
2258  mutt_extract_token(buf, s, 0);
2259 
2260  /* don't add "*" to the unignore list */
2261  if (strcmp(buf->data, "*") != 0)
2262  add_to_stailq(&UnIgnore, buf->data);
2263 
2264  remove_from_stailq(&Ignore, buf->data);
2265  } while (MoreArgs(s));
2266 
2267  return 0;
2268 }
static void remove_from_stailq(struct ListHead *head, const char *str)
Remove an item, matching a string, from a List.
Definition: init.c:727
struct ListHead UnIgnore
List of header patterns to unignore (see)
Definition: email_globals.c:44
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
char * data
pointer to data
Definition: buffer.h:35
struct ListHead Ignore
List of header patterns to ignore.
Definition: email_globals.c:43
static void add_to_stailq(struct ListHead *head, const char *str)
Add a string to a list.
Definition: init.c:115

+ Here is the call graph for this function:

static int parse_unlists ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unlists' command - Implements command_t.

Definition at line 2273 of file init.c.

2275 {
2276  do
2277  {
2278  mutt_extract_token(buf, s, 0);
2279  mutt_regexlist_remove(&SubscribedLists, buf->data);
2280  mutt_regexlist_remove(&MailLists, buf->data);
2281 
2282  if ((mutt_str_strcmp(buf->data, "*") != 0) &&
2283  mutt_regexlist_add(&UnMailLists, buf->data, REG_ICASE, err) != 0)
2284  {
2285  return -1;
2286  }
2287  } while (MoreArgs(s));
2288 
2289  return 0;
2290 }
int mutt_regexlist_remove(struct RegexList *rl, const char *str)
Remove a Regex from a list.
Definition: regex.c:224
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
int mutt_regexlist_add(struct RegexList *rl, const char *str, int flags, struct Buffer *err)
Compile a regex string and add it to a list.
Definition: regex.c:128
char * data
pointer to data
Definition: buffer.h:35
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

static int parse_unmy_hdr ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unmy_hdr' command - Implements command_t.

Definition at line 2295 of file init.c.

2297 {
2298  struct ListNode *np, *tmp;
2299  size_t l;
2300 
2301  do
2302  {
2303  mutt_extract_token(buf, s, 0);
2304  if (mutt_str_strcmp("*", buf->data) == 0)
2305  {
2306  mutt_list_free(&UserHeader);
2307  continue;
2308  }
2309 
2310  l = mutt_str_strlen(buf->data);
2311  if (buf->data[l - 1] == ':')
2312  l--;
2313 
2314  STAILQ_FOREACH_SAFE(np, &UserHeader, entries, tmp)
2315  {
2316  if ((mutt_str_strncasecmp(buf->data, np->data, l) == 0) && np->data[l] == ':')
2317  {
2318  STAILQ_REMOVE(&UserHeader, np, ListNode, entries);
2319  FREE(&np->data);
2320  FREE(&np);
2321  }
2322  }
2323  } while (MoreArgs(s));
2324  return 0;
2325 }
#define STAILQ_REMOVE(head, elm, type, field)
Definition: queue.h:400
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:663
void mutt_list_free(struct ListHead *h)
Free a List AND its strings.
Definition: list.c:105
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
#define STAILQ_FOREACH_SAFE(var, head, field, tvar)
Definition: queue.h:360
int mutt_str_strncasecmp(const char *a, const char *b, size_t l)
Compare two strings ignoring case (to a maximum), safely.
Definition: string.c:653
char * data
pointer to data
Definition: buffer.h:35
char * data
Definition: list.h:35
#define FREE(x)
Definition: memory.h:46
A List node for strings.
Definition: list.h:33
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

static int parse_unstailq ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse an unlist command - Implements command_t.

This is used by 'unalternative_order', 'unauto_view' and several others.

Definition at line 2332 of file init.c.

2334 {
2335  do
2336  {
2337  mutt_extract_token(buf, s, 0);
2338  /* Check for deletion of entire list */
2339  if (mutt_str_strcmp(buf->data, "*") == 0)
2340  {
2341  mutt_list_free((struct ListHead *) data);
2342  break;
2343  }
2344  remove_from_stailq((struct ListHead *) data, buf->data);
2345  } while (MoreArgs(s));
2346 
2347  return 0;
2348 }
static void remove_from_stailq(struct ListHead *head, const char *str)
Remove an item, matching a string, from a List.
Definition: init.c:727
void mutt_list_free(struct ListHead *h)
Free a List AND its strings.
Definition: list.c:105
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
char * data
pointer to data
Definition: buffer.h:35
char * data
Definition: list.h:35
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

static int parse_unsubjectrx_list ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unsubjectrx' command - Implements command_t.

Definition at line 2353 of file init.c.

2355 {
2356  int rc;
2357 
2358  rc = parse_unreplace_list(buf, s, data, err);
2359  if (rc == 0)
2361  return rc;
2362 }
static void clear_subject_mods(void)
Clear out all modified email subjects.
Definition: init.c:208
char * data
Definition: list.h:35
static int parse_unreplace_list(struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
Remove a string replacement rule - Implements command_t.
Definition: init.c:675

+ Here is the call graph for this function:

static int parse_unsubscribe ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unsubscribe' command - Implements command_t.

Definition at line 2367 of file init.c.

2369 {
2370  do
2371  {
2372  mutt_extract_token(buf, s, 0);
2373  mutt_regexlist_remove(&SubscribedLists, buf->data);
2374 
2375  if ((mutt_str_strcmp(buf->data, "*") != 0) &&
2376  mutt_regexlist_add(&UnSubscribedLists, buf->data, REG_ICASE, err) != 0)
2377  {
2378  return -1;
2379  }
2380  } while (MoreArgs(s));
2381 
2382  return 0;
2383 }
int mutt_regexlist_remove(struct RegexList *rl, const char *str)
Remove a Regex from a list.
Definition: regex.c:224
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
int mutt_regexlist_add(struct RegexList *rl, const char *str, int flags, struct Buffer *err)
Compile a regex string and add it to a list.
Definition: regex.c:128
char * data
pointer to data
Definition: buffer.h:35
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612

+ Here is the call graph for this function:

static int parse_unsubscribe_from ( struct Buffer buf,
struct Buffer s,
unsigned long  data,
struct Buffer err 
)
static

Parse the 'unsubscribe-from' command - Implements command_t.

The 'unsubscribe-from' command allows to unsubscribe from an IMAP-Mailbox. Patterns are not supported. Use it as follows: unsubscribe-from =folder

Definition at line 2393 of file init.c.

2395 {
2396  if (!buf || !s || !err)
2397  return -1;
2398 
2399  if (MoreArgs(s))
2400  {
2401  mutt_extract_token(buf, s, 0);
2402 
2403  if (MoreArgs(s))
2404  {
2405  mutt_buffer_printf(err, _("%s: too many arguments"), "unsubscribe-from");
2406  return -1;
2407  }
2408 
2409  if (buf->data && *buf->data)
2410  {
2411  /* Expand and subscribe */
2412  if (imap_subscribe(mutt_expand_path(buf->data, buf->dsize), false) != 0)
2413  {
2414  mutt_buffer_printf(err, _("Could not unsubscribe from %s"), buf->data);
2415  return -1;
2416  }
2417  else
2418  {
2419  mutt_message(_("Unsubscribed from %s"), buf->data);
2420  return 0;
2421  }
2422  }
2423  else
2424  {
2425  mutt_debug(5, "Corrupted buffer");
2426  return -1;
2427  }
2428  }
2429 
2430  mutt_buffer_addstr(err, _("No folder specified"));
2431  return -1;
2432 }
#define mutt_message(...)
Definition: logging.h:87
#define _(a)
Definition: message.h:28
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
size_t dsize
length of data
Definition: buffer.h:37
char * mutt_expand_path(char *buf, size_t buflen)
Create the canonical path.
Definition: muttlib.c:157
#define MoreArgs(buf)
Definition: buffer.h:44
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
size_t mutt_buffer_addstr(struct Buffer *buf, const char *s)
Add a string to a Buffer.
Definition: buffer.c:258
char * data
pointer to data
Definition: buffer.h:35
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
int imap_subscribe(char *path, bool subscribe)
Subscribe to a mailbox.
Definition: imap.c:1391

+ Here is the call graph for this function:

int mutt_dump_variables ( bool  hide_sensitive)

Print a list of all variables with their values.

Parameters
hide_sensitiveDon't display the values of private config items
Return values
0Success
1Error

Definition at line 2472 of file init.c.

2473 {
2474  char command[STRING];
2475 
2476  struct Buffer err, token;
2477 
2478  mutt_buffer_init(&err);
2479  mutt_buffer_init(&token);
2480 
2481  err.dsize = STRING;
2482  err.data = mutt_mem_malloc(err.dsize);
2483 
2484  for (int i = 0; MuttVars[i].name; i++)
2485  {
2486  if (MuttVars[i].type == DT_SYNONYM)
2487  continue;
2488 
2489  if (hide_sensitive && IS_SENSITIVE(MuttVars[i]))
2490  {
2491  mutt_message("%s='***'", MuttVars[i].name);
2492  continue;
2493  }
2494  snprintf(command, sizeof(command), "set ?%s\n", MuttVars[i].name);
2495  if (mutt_parse_rc_line(command, &token, &err) == -1)
2496  {
2497  mutt_message("%s", err.data);
2498  FREE(&token.data);
2499  FREE(&err.data);
2500 
2501  return 1; // TEST17: can't test
2502  }
2503  mutt_message("%s", err.data);
2504  }
2505 
2506  FREE(&token.data);
2507  FREE(&err.data);
2508 
2509  return 0;
2510 }
#define mutt_message(...)
Definition: logging.h:87
int mutt_parse_rc_line(char *line, struct Buffer *token, struct Buffer *err)
Parse a line of user config.
Definition: init.c:3119
String manipulation buffer.
Definition: buffer.h:33
#define IS_SENSITIVE(x)
Definition: types.h:74
const char * name
Definition: pgpmicalg.c:42
const char * name
User-visible name.
Definition: set.h:162
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:99
#define DT_SYNONYM
synonym for another variable
Definition: types.h:40
#define STRING
Definition: string2.h:35
struct ConfigDef MuttVars[]
Definition: init.h:123
#define FREE(x)
Definition: memory.h:46
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:66

+ Here is the call graph for this function:

int mutt_extract_token ( struct Buffer dest,
struct Buffer tok,
int  flags 
)

Extract one token from a string.

Parameters
destBuffer for the result
tokBuffer containing tokens
flagsFlags, e.g. MUTT_TOKEN_SPACE
Return values
0Success
-1Error

Definition at line 2520 of file init.c.

2521 {
2522  if (!dest || !tok)
2523  return -1;
2524 
2525  char ch;
2526  char qc = 0; /* quote char */
2527  char *pc = NULL;
2528 
2529  /* reset the destination pointer to the beginning of the buffer */
2530  dest->dptr = dest->data;
2531 
2532  SKIPWS(tok->dptr);
2533  while ((ch = *tok->dptr))
2534  {
2535  if (!qc)
2536  {
2537  if ((ISSPACE(ch) && !(flags & MUTT_TOKEN_SPACE)) ||
2538  (ch == '#' && !(flags & MUTT_TOKEN_COMMENT)) ||
2539  (ch == '=' && (flags & MUTT_TOKEN_EQUAL)) ||
2540  (ch == '?' && (flags & MUTT_TOKEN_QUESTION)) ||
2541  (ch == ';' && !(flags & MUTT_TOKEN_SEMICOLON)) ||
2542  ((flags & MUTT_TOKEN_PATTERN) && strchr("~%=!|", ch)))
2543  {
2544  break;
2545  }
2546  }
2547 
2548  tok->dptr++;
2549 
2550  if (ch == qc)
2551  qc = 0; /* end of quote */
2552  else if (!qc && (ch == '\'' || ch == '"') && !(flags & MUTT_TOKEN_QUOTE))
2553  qc = ch;
2554  else if (ch == '\\' && qc != '\'')
2555  {
2556  if (!*tok->dptr)
2557  return -1; /* premature end of token */
2558  switch (ch = *tok->dptr++)
2559  {
2560  case 'c':
2561  case 'C':
2562  if (!*tok->dptr)
2563  return -1; /* premature end of token */
2564  mutt_buffer_addch(dest, (toupper((unsigned char) *tok->dptr) - '@') & 0x7f);
2565  tok->dptr++;
2566  break;
2567  case 'e':
2568  mutt_buffer_addch(dest, '\033');
2569  break;
2570  case 'f':
2571  mutt_buffer_addch(dest, '\f');
2572  break;
2573  case 'n':
2574  mutt_buffer_addch(dest, '\n');
2575  break;
2576  case 'r':
2577  mutt_buffer_addch(dest, '\r');
2578  break;
2579  case 't':
2580  mutt_buffer_addch(dest, '\t');
2581  break;
2582  default:
2583  if (isdigit((unsigned char) ch) && isdigit((unsigned char) *tok->dptr) &&
2584  isdigit((unsigned char) *(tok->dptr + 1)))
2585  {
2586  mutt_buffer_addch(dest, (ch << 6) + (*tok->dptr << 3) + *(tok->dptr + 1) - 3504);
2587  tok->dptr += 2;
2588  }
2589  else
2590  mutt_buffer_addch(dest, ch);
2591  }
2592  }
2593  else if (ch == '^' && (flags & MUTT_TOKEN_CONDENSE))
2594  {
2595  if (!*tok->dptr)
2596  return -1; /* premature end of token */
2597  ch = *tok->dptr++;
2598  if (ch == '^')
2599  mutt_buffer_addch(dest, ch);
2600  else if (ch == '[')
2601  mutt_buffer_addch(dest, '\033');
2602  else if (isalpha((unsigned char) ch))
2603  mutt_buffer_addch(dest, toupper((unsigned char) ch) - '@');
2604  else
2605  {
2606  mutt_buffer_addch(dest, '^');
2607  mutt_buffer_addch(dest, ch);
2608  }
2609  }
2610  else if (ch == '`' && (!qc || qc == '"'))
2611  {
2612  FILE *fp = NULL;
2613  pid_t pid;
2614  char *ptr = NULL;
2615  size_t expnlen;
2616  struct Buffer expn;
2617  int line = 0;
2618 
2619  pc = tok->dptr;
2620  do
2621  {
2622  pc = strpbrk(pc, "\\`");
2623  if (pc)
2624  {
2625  /* skip any quoted chars */
2626  if (*pc == '\\')
2627  pc += 2;
2628  }
2629  } while (pc && *pc != '`');
2630  if (!pc)
2631  {
2632  mutt_debug(1, "mismatched backticks\n");
2633  return -1;
2634  }
2635  struct Buffer cmd;
2636  mutt_buffer_init(&cmd);
2637  *pc = '\0';
2638  if (flags & MUTT_TOKEN_BACKTICK_VARS)
2639  {
2640  /* recursively extract tokens to interpolate variables */
2641  mutt_extract_token(&cmd, tok,
2642  MUTT_TOKEN_QUOTE | MUTT_TOKEN_SPACE | MUTT_TOKEN_COMMENT |
2643  MUTT_TOKEN_SEMICOLON | MUTT_TOKEN_NOSHELL);
2644  }
2645  else
2646  {
2647  cmd.data = mutt_str_strdup(tok->dptr);
2648  }
2649  *pc = '`';
2650  pid = mutt_create_filter(cmd.data, NULL, &fp, NULL);
2651  if (pid < 0)
2652  {
2653  mutt_debug(1, "unable to fork command: %s\n", cmd);
2654  FREE(&cmd.data);
2655  return -1;
2656  }
2657  FREE(&cmd.data);
2658 
2659  tok->dptr = pc + 1;
2660 
2661  /* read line */
2662  mutt_buffer_init(&expn);
2663  expn.data = mutt_file_read_line(NULL, &expn.dsize, fp, &line, 0);
2664  mutt_file_fclose(&fp);
2665  mutt_wait_filter(pid);
2666 
2667  /* if we got output, make a new string consisting of the shell output
2668  plus whatever else was left on the original line */
2669  /* BUT: If this is inside a quoted string, directly add output to
2670  * the token */
2671  if (expn.data && qc)
2672  {
2673  mutt_buffer_addstr(dest, expn.data);
2674  FREE(&expn.data);
2675  }
2676  else if (expn.data)
2677  {
2678  expnlen = mutt_str_strlen(expn.data);
2679  tok->dsize = expnlen + mutt_str_strlen(tok->dptr) + 1;
2680  ptr = mutt_mem_malloc(tok->dsize);
2681  memcpy(ptr, expn.data, expnlen);
2682  strcpy(ptr + expnlen, tok->dptr);
2683  if (tok->destroy)
2684  FREE(&tok->data);
2685  tok->data = ptr;
2686  tok->dptr = ptr;
2687  tok->destroy = 1; /* mark that the caller should destroy this data */
2688  ptr = NULL;
2689  FREE(&expn.data);
2690  }
2691  }
2692  else if (ch == '$' && (!qc || qc == '"') &&
2693  (*tok->dptr == '{' || isalpha((unsigned char) *tok->dptr)))
2694  {
2695  const char *env = NULL;
2696  char *var = NULL;
2697 
2698  if (*tok->dptr == '{')
2699  {
2700  pc = strchr(tok->dptr, '}');
2701  if (pc)
2702  {
2703  var = mutt_str_substr_dup(tok->dptr + 1, pc);
2704  tok->dptr = pc + 1;
2705 
2706  if ((flags & MUTT_TOKEN_NOSHELL))
2707  {
2708  mutt_buffer_addch(dest, ch);
2709  mutt_buffer_addch(dest, '{');
2710  mutt_buffer_addstr(dest, var);
2711  mutt_buffer_addch(dest, '}');
2712  FREE(&var);
2713  }
2714  }
2715  }
2716  else
2717  {
2718  for (pc = tok->dptr; isalnum((unsigned char) *pc) || *pc == '_'; pc++)
2719  ;
2720  var = mutt_str_substr_dup(tok->dptr, pc);
2721  tok->dptr = pc;
2722  }
2723  if (var)
2724  {
2725  struct Buffer result;
2726  mutt_buffer_init(&result);
2727  int rc = cs_str_string_get(Config, var, &result);
2728 
2729  if (CSR_RESULT(rc) == CSR_SUCCESS)
2730  {
2731  mutt_buffer_addstr(dest, result.data);
2732  FREE(&result.data);
2733  }
2734  else if ((env = myvar_get(var)))
2735  {
2736  mutt_buffer_addstr(dest, env);
2737  }
2738  else if (!(flags & MUTT_TOKEN_NOSHELL) && (env = mutt_str_getenv(var)))
2739  {
2740  mutt_buffer_addstr(dest, env);
2741  }
2742  else
2743  {
2744  mutt_buffer_addch(dest, ch);
2745  mutt_buffer_addstr(dest, var);
2746  }
2747  FREE(&var);
2748  }
2749  }
2750  else
2751  mutt_buffer_addch(dest, ch);
2752  }
2753  mutt_buffer_addch(dest, 0); /* terminate the string */
2754  SKIPWS(tok->dptr);
2755  return 0;
2756 }
#define CSR_RESULT(x)
Definition: set.h:61
char * mutt_file_read_line(char *line, size_t *size, FILE *fp, int *line_num, int flags)
Read a line from a file.
Definition: file.c:632
#define MUTT_TOKEN_COMMENT
don&#39;t reap comments
Definition: mutt.h:76
String manipulation buffer.
Definition: buffer.h:33
WHERE struct ConfigSet * Config
Wrapper around the user&#39;s config settings.
Definition: globals.h:39
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:663
const char * mutt_str_getenv(const char *name)
Get an environment variable.
Definition: string.c:1049
int destroy
destroy &#39;data&#39; when done?
Definition: buffer.h:38
size_t dsize
length of data
Definition: buffer.h:37
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
#define ISSPACE(c)
Definition: string2.h:40
int cs_str_string_get(const struct ConfigSet *cs, const char *name, struct Buffer *result)
Get a config item as a string.
Definition: set.c:727
#define MUTT_TOKEN_NOSHELL
don&#39;t expand environment variables
Definition: mutt.h:79
const char * line
Definition: common.c:35
size_t mutt_buffer_addstr(struct Buffer *buf, const char *s)
Add a string to a Buffer.
Definition: buffer.c:258
#define CSR_SUCCESS
Action completed successfully.
Definition: set.h:45
#define MUTT_TOKEN_QUOTE
don&#39;t interpret quotes
Definition: mutt.h:74
#define MUTT_TOKEN_CONDENSE
^(char) to control chars (macros)
Definition: mutt.h:72
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:99
char * dptr
current read/write position
Definition: buffer.h:36
#define MUTT_TOKEN_SPACE
don&#39;t treat whitespace as a term
Definition: mutt.h:73
char * data
pointer to data
Definition: buffer.h:35
size_t mutt_buffer_addch(struct Buffer *buf, char c)
Add a single character to a Buffer.
Definition: buffer.c:273
const char * myvar_get(const char *var)
Get the value of a "my_" variable.
Definition: myvar.c:42
#define MUTT_TOKEN_SEMICOLON
don&#39;t treat ; as special
Definition: mutt.h:77
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
int mutt_file_fclose(FILE **f)
Close a FILE handle (and NULL the pointer)
Definition: file.c:149
#define MUTT_TOKEN_BACKTICK_VARS
expand variables within backticks
Definition: mutt.h:78
#define FREE(x)
Definition: memory.h:46
pid_t mutt_create_filter(const char *s, FILE **in, FILE **out, FILE **err)
Set up filter program.
Definition: filter.c:216
#define MUTT_TOKEN_EQUAL
treat &#39;=&#39; as a special
Definition: mutt.h:71
#define mutt_debug(LEVEL,...)
Definition: logging.h:85
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:66
int mutt_wait_filter(pid_t pid)
Wait for the exit of a process and return its status.
Definition: filter.c:227
char * mutt_str_substr_dup(const char *begin, const char *end)
Duplicate a sub-string.
Definition: string.c:576
#define MUTT_TOKEN_PATTERN
!)|~ are terms (for patterns)
Definition: mutt.h:75
#define MUTT_TOKEN_QUESTION
treat &#39;?&#39; as a special
Definition: mutt.h:80
#define SKIPWS(c)
Definition: string2.h:49

+ Here is the call graph for this function:

void mutt_free_attachmatch ( struct AttachMatch **  am)

Free an AttachMatch - Implements list_free_t.

Note
We don't free minor because it is either a pointer into major, or a static string.

Definition at line 2764 of file init.c.

2765 {
2766  if (!am || !*am)
2767  return;
2768 
2769  regfree(&(*am)->minor_regex);
2770  FREE(&(*am)->major);
2771  FREE(am);
2772 }
#define FREE(x)
Definition: memory.h:46

+ Here is the caller graph for this function:

void mutt_free_opts ( void  )

clean up before quitting

Definition at line 2777 of file init.c.

2778 {
2780 
2781  FREE(&Matches);
2782 
2783  mutt_aliaslist_free(&Aliases);
2784 
2785  mutt_regexlist_free(&Alternates);
2786  mutt_regexlist_free(&MailLists);
2788  mutt_regexlist_free(&SubscribedLists);
2789  mutt_regexlist_free(&UnAlternates);
2790  mutt_regexlist_free(&UnMailLists);
2791  mutt_regexlist_free(&UnSubscribedLists);
2792 
2797 
2798  /* Lists of strings */
2799  mutt_list_free(&AlternativeOrderList);
2800  mutt_list_free(&AutoViewList);
2801  mutt_list_free(&HeaderOrderList);
2803  mutt_list_free(&MailToAllow);
2804  mutt_list_free(&MimeLookupList);
2805  mutt_list_free(&Muttrc);
2807 #ifdef USE_SIDEBAR
2808  mutt_list_free(&SidebarWhitelist);
2809 #endif
2811  mutt_list_free(&UserHeader);
2812 
2813  /* Lists of AttachMatch */
2818 
2819  mutt_free_colors();
2820 
2821  FREE(&CurrentFolder);
2822  FREE(&HomeDir);
2823  FREE(&LastFolder);
2824  FREE(&ShortHostname);
2825  FREE(&Username);
2826 
2828  mutt_replacelist_free(&SubjectRegexList);
2829 
2830  mutt_delete_hooks(0);
2831 
2832  mutt_hist_free();
2833  mutt_free_keys();
2834 
2836 }
WHERE char * Username
User&#39;s login name.
Definition: globals.h:50
void mutt_aliaslist_free(struct AliasList *a_list)
Free a List of Aliases.
Definition: alias.c:753
WHERE struct Hash * Groups
Hash table of alias groups (name -> Group)
Definition: globals.h:57
struct Hash * TagTransforms
Lookup table of alternative tag names.
Definition: tags.c:39
static struct ListHead MuttrcStack
Definition: init.c:76
struct ReplaceList SpamList
List of regexes and patterns to match spam emails.
Definition: email_globals.c:42
void mutt_list_free_type(struct ListHead *h, list_free_t fn)
Free a List of type.
Definition: list.c:123
WHERE struct Hash * TagFormats
Hash table of tag-formats (tag -> format string)
Definition: globals.h:59
WHERE char * LastFolder
Previously selected mailbox.
Definition: globals.h:53
void mutt_hash_destroy(struct Hash **ptr)
Destroy a hash table.
Definition: hash.c:458
struct ListHead UnIgnore
List of header patterns to unignore (see)
Definition: email_globals.c:44
void mutt_replacelist_free(struct ReplaceList *rl)
Free a ReplaceList object.
Definition: regex.c:444
void mutt_list_free(struct ListHead *h)
Free a List AND its strings.
Definition: list.c:105
WHERE char * HomeDir
User&#39;s home directory.
Definition: globals.h:47
WHERE char * CurrentFolder
Currently selected mailbox.
Definition: globals.h:52
void mutt_delete_hooks(int type)
Delete matching hooks.
Definition: hook.c:307
WHERE struct Hash * ReverseAliases
Hash table of aliases (email address -> alias)
Definition: globals.h:58
static const char ** Matches
Definition: init.c:89
void mutt_free_colors(void)
Free all the colours (on shutdown)
Definition: color.c:1191
WHERE char * ShortHostname
Short version of the hostname.
Definition: globals.h:48
#define FREE(x)
Definition: memory.h:46
void mutt_free_keys(void)
Free the key maps.
Definition: keymap.c:1431
struct RegexList NoSpamList
List of regexes to whitelist non-spam emails.
Definition: email_globals.c:41
void mutt_free_attachmatch(struct AttachMatch **am)
Free an AttachMatch - Implements list_free_t.
Definition: init.c:2764
void mutt_hist_free(void)
Free all the history lists.
Definition: history.c:439
struct ListHead Ignore
List of header patterns to ignore.
Definition: email_globals.c:43
void mutt_regexlist_free(struct RegexList *rl)
Free a RegexList object.
Definition: regex.c:166
void(* list_free_t)(void **ptr)
typedef list_free_t - Prototype for a function to free List data
Definition: list.h:51

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int mutt_get_hook_type ( const char *  name)

Find a hook by name.

Parameters
nameName to find
Return values
numData associated with the hook
0Error, no matching hook

Definition at line 2844 of file init.c.

2845 {
2846  for (const struct Command *c = Commands; c->name; c++)
2847  if (c->func == mutt_parse_hook && (mutt_str_strcasecmp(c->name, name) == 0))
2848  return c->data;
2849  return 0;
2850 }
A user-callable command.
Definition: mutt_commands.h:43
const char * name
Name of the command.
Definition: mutt_commands.h:45
int mutt_parse_hook(struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
const struct Command Commands[]
Definition: init.h:4685
const char * name
Definition: pgpmicalg.c:42
int mutt_str_strcasecmp(const char *a, const char *b)
Compare two strings ignoring case, safely.
Definition: string.c:625

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int mutt_init ( bool  skip_sys_rc,
struct ListHead *  commands 
)

Initialise NeoMutt.

Parameters
skip_sys_rcIf true, don't read the system config file
commandsList of config commands to execute
Return values
0Success
1Error

Definition at line 2859 of file init.c.

2860 {
2861  char buffer[LONG_STRING];
2862  int need_pause = 0;
2863  struct Buffer err;
2864 
2865  mutt_buffer_init(&err);
2866  err.dsize = STRING;
2867  err.data = mutt_mem_malloc(err.dsize);
2868  err.dptr = err.data;
2869 
2870  Groups = mutt_hash_new(1031, 0);
2871  /* reverse alias keys need to be strdup'ed because of idna conversions */
2875  TagFormats = mutt_hash_new(64, 0);
2876 
2877  mutt_menu_init();
2879 
2880  snprintf(AttachmentMarker, sizeof(AttachmentMarker), "\033]9;%" PRIu64 "\a",
2881  mutt_rand64());
2882 
2883  /* "$spoolfile" precedence: config file, environment */
2884  const char *p = mutt_str_getenv("MAIL");
2885  if (!p)
2886  p = mutt_str_getenv("MAILDIR");
2887  if (!p)
2888  {
2889 #ifdef HOMESPOOL
2890  mutt_path_concat(buffer, NONULL(HomeDir), MAILPATH, sizeof(buffer));
2891 #else
2892  mutt_path_concat(buffer, MAILPATH, NONULL(Username), sizeof(buffer));
2893 #endif
2894  p = buffer;
2895  }
2896  cs_str_initial_set(Config, "spoolfile", p, NULL);
2897  cs_str_reset(Config, "spoolfile", NULL);
2898 
2899  p = mutt_str_getenv("REPLYTO");
2900  if (p)
2901  {
2902  struct Buffer buf, token;
2903 
2904  snprintf(buffer, sizeof(buffer), "Reply-To: %s", p);
2905 
2906  mutt_buffer_init(&buf);
2907  buf.data = buffer;
2908  buf.dptr = buffer;
2909  buf.dsize = mutt_str_strlen(buffer);
2910 
2911  mutt_buffer_init(&token);
2912  parse_my_hdr(&token, &buf, 0, &err); /* adds to UserHeader */
2913  FREE(&token.data);
2914  }
2915 
2916  p = mutt_str_getenv("EMAIL");
2917  if (p)
2918  {
2919  cs_str_initial_set(Config, "from", p, NULL);
2920  cs_str_reset(Config, "from", NULL);
2921  }
2922 
2923  /* "$mailcap_path" precedence: config file, environment, code */
2924  const char *env_mc = mutt_str_getenv("MAILCAPS");
2925  if (env_mc)
2926  cs_str_string_set(Config, "mailcap_path", env_mc, NULL);
2927 
2928  /* "$tmpdir" precedence: config file, environment, code */
2929  const char *env_tmp = mutt_str_getenv("TMPDIR");
2930  if (env_tmp)
2931  cs_str_string_set(Config, "tmpdir", env_tmp, NULL);
2932 
2933  /* "$visual", "$editor" precedence: config file, environment, code */
2934  const char *env_ed = mutt_str_getenv("VISUAL");
2935  if (!env_ed)
2936  env_ed = mutt_str_getenv("EDITOR");
2937  if (env_ed)
2938  {
2939  cs_str_string_set(Config, "editor", env_ed, NULL);
2940  cs_str_string_set(Config, "visual", env_ed, NULL);
2941  }
2942 
2945 
2946  Matches = mutt_mem_calloc(MatchesListsize, sizeof(char *));
2947 
2949 
2950 #ifdef HAVE_GETSID
2951  /* Unset suspend by default if we're the session leader */
2952  if (getsid(0) == getpid())
2953  Suspend = false;
2954 #endif
2955 
2956  /* RFC2368, "4. Unsafe headers"
2957  * The creator of a mailto URL cannot expect the resolver of a URL to
2958  * understand more than the "subject" and "body" headers. Clients that
2959  * resolve mailto URLs into mail messages should be able to correctly
2960  * create RFC822-compliant mail messages using the "subject" and "body"
2961  * headers.
2962  */
2963  add_to_stailq(&MailToAllow, "body");
2964  add_to_stailq(&MailToAllow, "subject");
2965  /* Cc, In-Reply-To, and References help with not breaking threading on
2966  * mailing lists, see https://github.com/neomutt/neomutt/issues/115 */
2967  add_to_stailq(&MailToAllow, "cc");
2968  add_to_stailq(&MailToAllow, "in-reply-to");
2969  add_to_stailq(&MailToAllow, "references");
2970 
2971  if (STAILQ_EMPTY(&Muttrc))
2972  {
2973  const char *xdg_cfg_home = mutt_str_getenv("XDG_CONFIG_HOME");
2974 
2975  if (!xdg_cfg_home && HomeDir)
2976  {
2977  snprintf(buffer, sizeof(buffer), "%s/.config", HomeDir);
2978  xdg_cfg_home = buffer;
2979  }
2980 
2981  char *config = find_cfg(HomeDir, xdg_cfg_home);
2982  if (config)
2983  {
2984  mutt_list_insert_tail(&Muttrc, config);
2985  }
2986  }
2987  else
2988  {
2989  struct ListNode *np = NULL;
2990  STAILQ_FOREACH(np, &Muttrc, entries)
2991  {
2992  mutt_str_strfcpy(buffer, np->data, sizeof(buffer));
2993  FREE(&np->data);
2994  mutt_expand_path(buffer, sizeof(buffer));
2995  np->data = mutt_str_strdup(buffer);
2996  if (access(np->data, F_OK))
2997  {
2998  mutt_perror(np->data);
2999  return 1; // TEST10: neomutt -F missing
3000  }
3001  }
3002  }
3003 
3004  if (!STAILQ_EMPTY(&Muttrc))
3005  {
3006  cs_str_string_set(Config, "alias_file", STAILQ_FIRST(&Muttrc)->data, NULL);
3007  }
3008 
3009  /* Process the global rc file if it exists and the user hasn't explicitly
3010  requested not to via "-n". */
3011  if (!skip_sys_rc)
3012  {
3013  do
3014  {
3015  if (mutt_set_xdg_path(XDG_CONFIG_DIRS, buffer, sizeof(buffer)))
3016  break;
3017 
3018  snprintf(buffer, sizeof(buffer), "%s/neomuttrc", SYSCONFDIR);
3019  if (access(buffer, F_OK) == 0)
3020  break;
3021 
3022  snprintf(buffer, sizeof(buffer), "%s/Muttrc", SYSCONFDIR);
3023  if (access(buffer, F_OK) == 0)
3024  break;
3025 
3026  snprintf(buffer, sizeof(buffer), "%s/neomuttrc", PKGDATADIR);
3027  if (access(buffer, F_OK) == 0)
3028  break;
3029 
3030  snprintf(buffer, sizeof(buffer), "%s/Muttrc", PKGDATADIR);
3031  } while (false);
3032 
3033  if (access(buffer, F_OK) == 0)
3034  {
3035  if (source_rc(buffer, &err) != 0)
3036  {
3037  mutt_error("%s", err.data);
3038  need_pause = 1; // TEST11: neomutt (error in /etc/neomuttrc)
3039  }
3040  }
3041  }
3042 
3043  /* Read the user's initialization file. */
3044  struct ListNode *np = NULL;
3045  STAILQ_FOREACH(np, &Muttrc, entries)
3046  {
3047  if (np->data)
3048  {
3049  if (source_rc(np->data, &err) != 0)
3050  {
3051  mutt_error("%s", err.data);
3052  need_pause = 1; // TEST12: neomutt (error in ~/.neomuttrc)
3053  }
3054  }
3055  }
3056 
3057  if (execute_commands(commands) != 0)
3058  need_pause = 1; // TEST13: neomutt -e broken
3059 
3060  if (!get_hostname())
3061  return 1;
3062 
3063  if (!Realname)
3064  {
3065  struct passwd *pw = getpwuid(getuid());
3066  if (pw)
3067  {
3068  char buf[STRING];
3069  Realname = mutt_str_strdup(mutt_gecos_name(buf, sizeof(buf), pw));
3070  }
3071  }
3072  cs_str_initial_set(Config, "realname", Realname, NULL);
3073 
3074  if (need_pause && !OptNoCurses)
3075  {
3077  if (mutt_any_key_to_continue(NULL) == 'q')
3078  return 1; // TEST14: neomutt -e broken (press 'q')
3079  }
3080 
3081  mutt_file_mkdir(Tmpdir, S_IRWXU);
3082 
3083  mutt_hist_init();
3085 
3086 #ifdef USE_NOTMUCH
3087  if (VirtualSpoolfile)
3088  {
3089  /* Find the first virtual folder and open it */
3090  struct MailboxNode *mp = NULL;
3091  STAILQ_FOREACH(mp, &AllMailboxes, entries)
3092  {
3093  if (mp->m->magic == MUTT_NOTMUCH)
3094  {
3095  cs_str_string_set(Config, "spoolfile", mp->m->path, NULL);
3096  break;
3097  }
3098  }
3099  }
3100 #endif
3101 
3102  FREE(&err.data);
3103  return 0;
3104 }
struct Hash * mutt_hash_new(size_t nelem, int flags)
Create a new Hash table (with string keys)
Definition: hash.c:278
WHERE char * Username
User&#39;s login name.
Definition: globals.h:50
&#39;Notmuch&#39; (virtual) Mailbox type
Definition: magic.h:43
#define NONULL(x)
Definition: string2.h:39
void * mutt_mem_calloc(size_t nmemb, size_t size)
Allocate zeroed memory on the heap.
Definition: memory.c:51
#define mutt_perror(...)
Definition: logging.h:89
WHERE struct Hash * Groups
Hash table of alias groups (name -> Group)
Definition: globals.h:57
struct Hash * TagTransforms
Lookup table of alternative tag names.
Definition: tags.c:39
int cs_str_string_set(const struct ConfigSet *cs, const char *name, const char *value, struct Buffer *err)
Set a config item by string.
Definition: set.c:657
char * Charset
Config: Default character set for displaying text on screen.
Definition: charset.c:52
String manipulation buffer.
Definition: buffer.h:33
static int execute_commands(struct ListHead *p)
Execute a set of NeoMutt commands.
Definition: init.c:281
static int source_rc(const char *rcfile_path, struct Buffer *err)
Read an initialization file.
Definition: init.c:753
WHERE struct Hash * TagFormats
Hash table of tag-formats (tag -> format string)
Definition: globals.h:59
WHERE struct ConfigSet * Config
Wrapper around the user&#39;s config settings.
Definition: globals.h:39
WHERE bool OptNoCurses
(pseudo) when sending in batch mode
Definition: options.h:45
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:663
void mutt_ch_set_charset(const char *charset)
Update the records for a new character set.
Definition: charset.c:954
#define LONG_STRING
Definition: string2.h:36
void log_queue_flush(log_dispatcher_t disp)
Replay the log queue.
Definition: logging.c:349
static char * find_cfg(const char *home, const char *xdg_cfg_home)
Find a config file.
Definition: init.c:314
const char * mutt_str_getenv(const char *name)
Get an environment variable.
Definition: string.c:1049
struct Mailbox * m
Definition: mailbox.h:139
int cs_str_initial_set(const struct ConfigSet *cs, const char *name, const char *value, struct Buffer *err)
Set the initial value of a config item.
Definition: set.c:513
#define MUTT_HASH_STRCASECMP
use strcasecmp() to compare keys
Definition: hash.h:74
char * mutt_expand_path(char *buf, size_t buflen)
Create the canonical path.
Definition: muttlib.c:157
void mutt_hist_read_file(void)
Read the History from a file.
Definition: history.c:588
enum MailboxType magic
mailbox type
Definition: mailbox.h:99
WHERE char * HomeDir
User&#39;s home directory.
Definition: globals.h:47
static int parse_my_hdr(struct Buffer *buf, struct Buffer *s, unsigned long data, struct Buffer *err)
Parse the &#39;my_hdr&#39; command - Implements command_t.
Definition: init.c:1327
void mutt_buffer_pool_init(void)
Initialise the Buffer pool.
Definition: buffer.c:362
struct ListNode * mutt_list_insert_tail(struct ListHead *h, char *s)
Append a string to the end of a List.
Definition: list.c:58
#define MUTT_HASH_ALLOW_DUPS
allow duplicate keys to be inserted
Definition: hash.h:76
static int MatchesListsize
Definition: init.c:91
WHERE char * Realname
Config: Real name of the user.
Definition: globals.h:141
void * mutt_mem_malloc(size_t size)
Allocate memory on the heap.
Definition: memory.c:99
int mutt_file_mkdir(const char *path, mode_t mode)
Recursively create directories.
Definition: file.c:796
WHERE bool Suspend
Config: Allow the user to suspend NeoMutt using &#39;^Z&#39;.
Definition: globals.h:258
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
char * mutt_ch_get_langinfo_charset(void)
Get the user&#39;s choice of character set.
Definition: charset.c:421
char * Tmpdir
Config: Directory for temporary files.
Definition: file.c:50
#define STAILQ_FOREACH(var, head, field)
Definition: queue.h:350
WHERE bool VirtualSpoolfile
Config: (notmuch) Use the first virtual mailbox as a spool file.
Definition: globals.h:286
void mutt_hist_init(void)
Create a set of empty History ring buffers.
Definition: history.c:462
uint64_t mutt_rand64(void)
Create a 64-bit random number.
Definition: muttlib.c:536
int mutt_set_xdg_path(enum XdgType type, char *buf, size_t bufsize)
Find an XDG path or its fallback.
Definition: muttlib.c:1534
struct MailboxList AllMailboxes
List of all Mailboxes.
Definition: mailbox.c:85
char path[PATH_MAX]
Definition: mailbox.h:78
int cs_str_reset(const struct ConfigSet *cs, const char *name, struct Buffer *err)
Reset a config item to its initial value.
Definition: set.c:449
WHERE struct Hash * ReverseAliases
Hash table of aliases (email address -> alias)
Definition: globals.h:58
int mutt_any_key_to_continue(const char *s)
Prompt the user to &#39;press any key&#39; and wait.
Definition: curs_lib.c:531
char * data
Definition: list.h:35
#define STRING
Definition: string2.h:35
char * mutt_gecos_name(char *dest, size_t destlen, struct passwd *pw)
Lookup a user&#39;s real name in /etc/passwd.
Definition: muttlib.c:355
char * mutt_str_strdup(const char *str)
Copy a string, safely.
Definition: string.c:384
#define mutt_error(...)
Definition: logging.h:88
WHERE char AttachmentMarker[STRING]
Unique ANSI string to mark PGP messages in an email.
Definition: globals.h:45
static const char ** Matches
Definition: init.c:89
#define FREE(x)
Definition: memory.h:46
#define STAILQ_EMPTY(head)
Definition: queue.h:346
char * mutt_path_concat(char *d, const char *dir, const char *fname, size_t l)
Join a directory name and a filename.
Definition: path.c:323
List of Mailboxes.
Definition: mailbox.h:137
WHERE int CurrentMenu
Current Menu, e.g. MENU_PAGER.
Definition: globals.h:93
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:66
#define MUTT_HASH_STRDUP_KEYS
make a copy of the keys
Definition: hash.h:75
A List node for strings.
Definition: list.h:33
static bool get_hostname(void)
Find the Fully-Qualified Domain Name.
Definition: init.c:388
XDG system dir: /etc/xdg.
Definition: protos.h:45
#define STAILQ_FIRST(head)
Definition: queue.h:348
int log_disp_terminal(time_t stamp, const char *file, int line, const char *function, int level,...)
Save a log line to the terminal - Implements log_dispatcher_t.
Definition: logging.c:442
Index panel (list of emails)
Definition: keymap.h:73
static void add_to_stailq(struct ListHead *head, const char *str)
Add a string to a list.
Definition: init.c:115

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int mutt_parse_rc_line ( char *  line,
struct Buffer token,
struct Buffer err 
)

Parse a line of user config.

Parameters
lineconfig line to read
tokenscratch buffer to be used by parser
errwhere to write error messages
Return values
0Success
-1Failure

Caller should free token->data when finished. the reason for this variable is to avoid having to allocate and deallocate a lot of memory if we are parsing many lines. the caller can pass in the memory to use, which avoids having to create new space for every call to this function.

Definition at line 3119 of file init.c.

3120 {
3121  int i, r = 0;
3122  struct Buffer expn;
3123 
3124  if (!line || !*line)
3125  return 0;
3126 
3127  mutt_buffer_init(&expn);
3128  expn.data = line;
3129  expn.dptr = line;
3130  expn.dsize = mutt_str_strlen(line);
3131 
3132  *err->data = 0;
3133 
3134  SKIPWS(expn.dptr);
3135  while (*expn.dptr)
3136  {
3137  if (*expn.dptr == '#')
3138  break; /* rest of line is a comment */
3139  if (*expn.dptr == ';')
3140  {
3141  expn.dptr++;
3142  continue;
3143  }
3144  mutt_extract_token(token, &expn, 0);
3145  for (i = 0; Commands[i].name; i++)
3146  {
3147  if (mutt_str_strcmp(token->data, Commands[i].name) == 0)
3148  {
3149  r = Commands[i].func(token, &expn, Commands[i].data, err);
3150  if (r != 0)
3151  { /* -1 Error, +1 Finish */
3152  goto finish; /* Propagate return code */
3153  }
3154  break; /* Continue with next command */
3155  }
3156  }
3157  if (!Commands[i].name)
3158  {
3159  mutt_buffer_printf(err, _("%s: unknown command"), NONULL(token->data));
3160  r = -1;
3161  break; /* Ignore the rest of the line */
3162  }
3163  }
3164 finish:
3165  if (expn.destroy)
3166  FREE(&expn.data);
3167  return r;
3168 }
#define NONULL(x)
Definition: string2.h:39
command_t func
Function to parse the command.
Definition: mutt_commands.h:46
String manipulation buffer.
Definition: buffer.h:33
#define _(a)
Definition: message.h:28
const char * name
Name of the command.
Definition: mutt_commands.h:45
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:663
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:200
const struct Command Commands[]
Definition: init.h:4685
int mutt_extract_token(struct Buffer *dest, struct Buffer *tok, int flags)
Extract one token from a string.
Definition: init.c:2520
const char * name
Definition: pgpmicalg.c:42
const char * line
Definition: common.c:35
char * data
pointer to data
Definition: buffer.h:35
#define FREE(x)
Definition: memory.h:46
struct Buffer * mutt_buffer_init(struct Buffer *buf)
Initialise a new Buffer.
Definition: buffer.c:66
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:612
#define SKIPWS(c)
Definition: string2.h:49

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int mutt_query_variables ( struct ListHead *  queries)

Implement the -Q command line flag.

Parameters
queriesList of query strings
Return values
0Success, all queries exist
1Error

Definition at line 3176 of file init.c.

3177 {
3178  struct Buffer *value = mutt_buffer_alloc(STRING);
3179  struct Buffer *tmp = mutt_buffer_alloc(STRING);
3180  int rc = 0;
3181 
3182  struct ListNode *np = NULL;
3183  STAILQ_FOREACH(np, queries, entries)
3184  {
3185  mutt_buffer_reset(value);
3186 
3187  struct HashElem *he = cs_get_elem(Config, np->data);
3188  if (!he)
3189  {
3190  rc = 1;
3191  continue;
3192  }
3193 
3194  int rv = cs_he_string_get(Config, he, value);
3195  if (CSR_RESULT(rv) != CSR_SUCCESS)
3196  {
3197  rc = 1;
3198  continue;
3199  }
3200 
3201  int type = DTYPE(he->type);
3202  if ((type == DT_PATH) && !(he->type & DT_MAILBOX))
3203  mutt_pretty_mailbox(value->data, value->dsize);
3204 
3205  if ((type != DT_BOOL) && (type != DT_NUMBER) && (type != DT_LONG) && (type != DT_QUAD))
3206  {
3207  mutt_buffer_reset(tmp);
3208  pretty_var(value->data, tmp);
3209  mutt_buffer_strcpy(value, tmp->data);
3210  }
3211 
3212  dump_config_neo(Config, he, value, NULL, 0);
3213  }
3214 
3215  mutt_buffer_free(&value);
3216  mutt_buffer_free(&tmp);
3217 
3218  return rc; // TEST16: neomutt -Q charset
3219 }
void mutt_buffer_reset(struct Buffer *buf)
Reset an existing Buffer.
Definition: buffer.c:81
#define DT_LONG
a number (long)
Definition: types.h:31
#define CSR_RESULT(x)
Definition: set.h:61
void mutt_pretty_mailbox(char *s, size_t buflen)
Shorten a mailbox path using &#39;~&#39; or &#39;=&#39;.
Definition: muttlib.c:606
size_t pretty_var(const char *str, struct Buffer *buf)
Escape and stringify a config item value.
Definition: dump.c:85
String manipulation buffer.
Definition: buffer.h:33
WHERE struct ConfigSet * Config
Wrapper around the user&#39;s config settings.
Definition: globals.h:39
#define DT_QUAD
quad-option (no/yes/ask-no/ask-yes)
Definition: types.h:36
#define DTYPE(x)
Mask for the Data Type.
Definition: types.h:42
struct Buffer * mutt_buffer_alloc(size_t size)
Create a new Buffer.
Definition: buffer.c:298
size_t dsize
length of data
Definition: buffer.h:37
void mutt_buffer_free(struct Buffer **p)
Release a Buffer and its contents.
Definition: buffer.c:138
struct HashElem * cs_get_elem(const struct ConfigSet *cs, const char *name)
Get the HashElem representing a config item.
Definition: set.c:192
#define CSR_SUCCESS
Action completed successfully.
Definition: set.h:45
void mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:316
#define DT_PATH
a pathname
Definition: types.h:35
#define DT_MAILBOX
DT_PATH: Don&#39;t perform path expansions.
Definition: types.h:46
char * data
pointer to data
Definition: buffer.h:35
#define STAILQ_FOREACH(var, head, field)
Definition: queue.h:350
int cs_he_string_get(const struct ConfigSet *cs, struct HashElem *he, struct Buffer *result)
Get a config item as a string.
Definition: set.c:680
char * data
Definition: list.h:35
#define STRING
Definition: string2.h:35
int type
Definition: hash.h:44
The item stored in a Hash Table.
Definition: hash.h:42
A List node for strings.
Definition: list.h:33
#define DT_NUMBER
a number
Definition: types.h:34
#define DT_BOOL
boolean option
Definition: types.h:28
void dump_config_neo(struct ConfigSet *cs, struct HashElem *he, struct Buffer *value, struct Buffer *initial, int flags)
Dump the config in the style of NeoMutt.
Definition: dump.c:185

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int query_quadoption ( int  opt,
const char *  prompt 
)

Ask the user a quad-question.

Parameters
optOption to use
promptMessage to show to the user
Return values
numResult, e.g. MUTT_YES

Definition at line 3227 of file init.c.

3228 {
3229  switch (opt)
3230  {
3231  case MUTT_YES:
3232  case MUTT_NO:
3233  return opt;
3234 
3235  default:
3236  opt = mutt_yesorno(prompt, (opt == MUTT_ASKYES));
3238  return opt;
3239  }
3240 
3241  /* not reached */
3242 }
User answered &#39;Yes&#39;, or assume &#39;Yes&#39;.
Definition: quad.h:39
int mutt_yesorno(const char *msg, int def)
Ask the user a Yes/No question.
Definition: curs_lib.c:330
Ask the user, defaulting to &#39;Yes&#39;.
Definition: quad.h:41
void mutt_window_clearline(struct MuttWindow *win, int row)
Clear a row of a Window.
Definition: mutt_window.c:69
User answered &#39;No&#39;, or assume &#39;No&#39;.
Definition: quad.h:38
struct MuttWindow * MuttMessageWindow
Message Window.
Definition: mutt_window.c:41

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int mutt_command_complete ( char *  buf,
size_t  buflen,
int  pos,
int  numtabs 
)

Complete a command name.

Parameters
bufBuffer for the result
buflenLength of the buffer
posCursor position in the buffer
numtabsNumber of times the user has hit 'tab'
Return values
1Success, a match
0Error, no match

Definition at line 3253 of file init.c.

3254 {
3255  char *pt = buf;
3256  int num;
3257  int spaces; /* keep track of the number of leading spaces on the line */
3258  struct MyVar *myv = NULL;
3259 
3260  SKIPWS(buf);
3261  spaces = buf - pt;
3262 
3263  pt = buf + pos - spaces;
3264  while ((pt > buf) && !isspace((unsigned char) *pt))
3265  pt--;
3266 
3267  if (pt == buf) /* complete cmd */
3268  {
3269  /* first TAB. Collect all the matches */
3270  if (numtabs == 1)
3271  {
3272  NumMatched = 0;
3273  mutt_str_strfcpy(UserTyped, pt, sizeof(UserTyped));
3274  memset(Matches, 0, MatchesListsize);
3275  memset(Completed, 0, sizeof(Completed));
3276  for (num = 0; Commands[num].name; num++)
3280 
3281  /* All matches are stored. Longest non-ambiguous string is ""
3282  * i.e. don't change 'buf'. Fake successful return this time */
3283  if (UserTyped[0] == 0)
3284  return 1;
3285  }
3286 
3287  if (Completed[0] == 0 && UserTyped[0])
3288  return 0;
3289 
3290  /* NumMatched will _always_ be at least 1 since the initial
3291  * user-typed string is always stored */
3292  if (numtabs == 1 && NumMatched == 2)
3293  snprintf(Completed, sizeof(Completed), "%s", Matches[0]);
3294  else if (numtabs > 1 && NumMatched > 2)
3295  {
3296  /* cycle through all the matches */
3297  snprintf(Completed, sizeof(Completed), "%s", Matches[(numtabs - 2) % NumMatched]);
3298  }
3299 
3300  /* return the completed command */
3301  strncpy(buf, Completed, buflen - spaces);
3302  }
3303  else if (mutt_str_startswith(buf, "set", CASE_MATCH) ||
3304  mutt_str_startswith(buf, "unset", CASE_MATCH) ||
3305  mutt_str_startswith(buf, "reset", CASE_MATCH) ||
3306  mutt_str_startswith(buf, "toggle", CASE_MATCH))
3307  { /* complete variables */
3308  static const char *const prefixes[] = { "no", "inv", "?", "&", 0 };
3309 
3310  pt++;
3311  /* loop through all the possible prefixes (no, inv, ...) */
3312  if (mutt_str_startswith(buf, "set", CASE_MATCH))
3313  {
3314  for (num = 0; prefixes[num]; num++)
3315  {
3316  if (mutt_str_startswith(pt, prefixes[num], CASE_MATCH))
3317  {
3318  pt += mutt_str_strlen(prefixes[num]);
3319  break;
3320  }
3321  }
3322  }
3323 
3324  /* first TAB. Collect all the matches */
3325  if (numtabs == 1)
3326  {
3327  NumMatched = 0;
3328  mutt_str_strfcpy(UserTyped, pt, sizeof(UserTyped));
3329  memset(Matches, 0, MatchesListsize);
3330  memset(Completed, 0, sizeof(Completed));
3331  for (num = 0; MuttVars[num].name; num++)
3332  candidate(UserTyped, MuttVars[num].name, Completed, sizeof(Completed));
3333  TAILQ_FOREACH(myv, &MyVars, entries)
3334  {
3335  candidate(UserTyped, myv->name, Completed, sizeof(Completed));
3336  }
3339 
3340  /* All matches are stored. Longest non-ambiguous string is ""
3341  * i.e. don't change 'buf'. Fake successful return this time */
3342  if (UserTyped[0] == 0)
3343  return 1;
3344  }
3345 
3346  if (Completed[0] == 0 && UserTyped[0])
3347  return 0;
3348 
3349  /* NumMatched will _always_ be at least 1 since the initial
3350  * user-typed string is always stored */
3351  if (numtabs == 1 && NumMatched == 2)
3352  snprintf(Completed, sizeof(Completed), "%s", Matches[0]);
3353  else if (numtabs > 1 && NumMatched > 2)
3354  {
3355  /* cycle through all the matches */
3356  snprintf(Completed, sizeof(Completed), "%s", Matches[(numtabs - 2) % NumMatched]);
3357  }
3358 
3359  strncpy(pt, Completed, buf + buflen - pt - spaces);
3360  }
3361  else if (mutt_str_startswith(buf, "exec", CASE_MATCH))
3362  {
3363  const struct Binding *menu = km_get_table(CurrentMenu);
3364 
3365  if (!menu && CurrentMenu != MENU_PAGER)
3366  menu = OpGeneric;
3367 
3368  pt++;
3369  /* first TAB. Collect all the matches */
3370  if (numtabs == 1)
3371  {
3372  NumMatched = 0;
3373  mutt_str_strfcpy(UserTyped, pt, sizeof(UserTyped));
3374  memset(Matches, 0, MatchesListsize);
3375  memset(Completed, 0, sizeof(Completed));
3376  for (num = 0; menu[num].name; num++)
3377  candidate(UserTyped, menu[num].name, Completed, sizeof(Completed));
3378  /* try the generic menu */
3379  if (Completed[0] == 0 && CurrentMenu != MENU_PAGER)
3380  {
3381  menu = OpGeneric;
3382  for (num = 0; menu[num].name; num++)
3383  candidate(UserTyped, menu[num].name, Completed, sizeof(Completed));
3384  }
3387 
3388  /* All matches are stored. Longest non-ambiguous string is ""
3389  * i.e. don't change 'buf'. Fake successful return this time */
3390  if (UserTyped[0] == 0)
3391  return 1;
3392  }
3393 
3394  if (Completed[0] == 0 && UserTyped[0])
3395  return 0;
3396 
3397  /* NumMatched will _always_ be at least 1 since the initial
3398  * user-typed string is always stored */
3399  if (numtabs == 1 && NumMatched == 2)
3400  snprintf(Completed, sizeof(Completed), "%s", Matches[0]);
3401  else if (numtabs > 1 && NumMatched > 2)
3402  {
3403  /* cycle through all the matches */
3404  snprintf(Completed, sizeof(Completed), "%s", Matches[(numtabs - 2) % NumMatched]);
3405  }
3406 
3407  strncpy(pt, Completed, buf + buflen - pt - spaces);
3408  }
3409  else
3410  return 0;
3411 
3412  return 1;
3413 }
#define TAILQ_FOREACH(var, head, field)
Definition: queue.h:719
static int NumMatched
Definition: init.c:87
const char * name
Name of the command.
Definition: mutt_commands.h:45
Match case when comparing strings.
Definition: string2.h:69
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:663
char * name
Definition: myvar.h:33
static void candidate(char *try, const char *src, char *dest, size_t dlen)
helper function for completion
Definition: init.c:184
const struct Command Commands[]
Definition: init.h:4685
const char * name
Definition: pgpmicalg.c:42
A user-set variable.
Definition: myvar.h:31
const char * name
name of the function
Definition: keymap.h:100
const char * name
User-visible name.
Definition: set.h:162
const struct Binding * km_get_table(int menu)
Lookup a menu&#39;s keybindings.
Definition: keymap.c:1209
static int MatchesListsize
Definition: init.c:91
static void matches_ensure_morespace(int current)
Allocate more space for auto-completion.
Definition: init.c:161
const struct Binding OpGeneric[]
Key bindings for the generic menu.
Definition: functions.h:52
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
struct MyVarHead MyVars
List of all the user&#39;s custom config variables.
Definition: myvar.c:34
size_t mutt_str_startswith(const char *str, const char *prefix, enum CaseSensitivity cs)
Check whether a string starts with a prefix.
Definition: string.c:166
static char UserTyped[LONG_STRING]
Definition: init.c:85
struct ConfigDef MuttVars[]
Definition: init.h:123
static const char ** Matches
Definition: init.c:89
WHERE int CurrentMenu
Current Menu, e.g. MENU_PAGER.
Definition: globals.h:93
static char Completed[STRING]
Definition: init.c:88
Mapping between a user key and a function.
Definition: keymap.h:98
Pager pager (email viewer)
Definition: keymap.h:74
#define SKIPWS(c)
Definition: string2.h:49

+ Here is the call graph for this function:

+ Here is the caller graph for this function:

int mutt_label_complete ( char *  buf,
size_t  buflen,
int  numtabs 
)

Complete a label name.

Parameters
bufBuffer for the result
buflenLength of the buffer
numtabsNumber of times the user has hit 'tab'
Return values
1Success, a match
0Error, no match

Definition at line 3423 of file init.c.

3424 {
3425  char *pt = buf;
3426  int spaces; /* keep track of the number of leading spaces on the line */
3427 
3428  if (!Context || !Context->mailbox->label_hash)
3429  return 0;
3430 
3431  SKIPWS(buf);
3432  spaces = buf - pt;
3433 
3434  /* first TAB. Collect all the matches */
3435  if (numtabs == 1)
3436  {
3437  struct HashElem *entry = NULL;
3438  struct HashWalkState state = { 0 };
3439 
3440  NumMatched = 0;
3441  mutt_str_strfcpy(UserTyped, buf, sizeof(UserTyped));
3442  memset(Matches, 0, MatchesListsize);
3443  memset(Completed, 0, sizeof(Completed));
3444  while ((entry = mutt_hash_walk(Context->mailbox->label_hash, &state)))
3445  candidate(UserTyped, entry->key.strkey, Completed, sizeof(Completed));
3447  qsort(Matches, NumMatched, sizeof(char *), (sort_t *) mutt_str_strcasecmp);
3449 
3450  /* All matches are stored. Longest non-ambiguous string is ""
3451  * i.e. don't change 'buf'. Fake successful return this time */
3452  if (UserTyped[0] == 0)
3453  return 1;
3454  }
3455 
3456  if (Completed[0] == 0 && UserTyped[0])
3457  return 0;
3458 
3459  /* NumMatched will _always_ be at least 1 since the initial
3460  * user-typed string is always stored */
3461  if (numtabs == 1 && NumMatched == 2)
3462  snprintf(Completed, sizeof(Completed), "%s", Matches[0]);
3463  else if (numtabs > 1 && NumMatched > 2)
3464  {
3465  /* cycle through all the matches */
3466  snprintf(Completed, sizeof(Completed), "%s", Matches[(numtabs - 2) % NumMatched]);
3467  }
3468 
3469  /* return the completed label */
3470  strncpy(buf, Completed, buflen - spaces);
3471 
3472  return 1;
3473 }
The "current" mailbox.
Definition: context.h:36
union HashKey key
Definition: hash.h:45
int sort_t(const void *a, const void *b)
typedef sort_t - Prototype for a function to compare two emails
Definition: sort.h:48
static int NumMatched
Definition: init.c:87
Cursor to iterate through a Hash Table.
Definition: hash.h:95
static void candidate(char *try, const char *src, char *dest, size_t dlen)
helper function for completion
Definition: init.c:184
struct Mailbox * mailbox
Definition: context.h:50
static int MatchesListsize
Definition: init.c:91
static void matches_ensure_morespace(int current)
Allocate more space for auto-completion.
Definition: init.c:161
size_t mutt_str_strfcpy(char *dest, const char *src, size_t dsize)
Copy a string into a buffer (guaranteeing NUL-termination)
Definition: string.c:742
struct HashElem * mutt_hash_walk(const struct Hash *table, struct HashWalkState *state)
Iterate through all the HashElem&#39;s in a Hash table.
Definition: hash.c:491
static char UserTyped[LONG_STRING]
Definition: init.c:85