NeoMutt  2019-12-07-60-g0cfa53
Teaching an old dog new tricks
DOXYGEN
mx.c File Reference

Mailbox multiplexor. More...

#include "config.h"
#include <errno.h>
#include <limits.h>
#include <stdbool.h>
#include <string.h>
#include <sys/stat.h>
#include <unistd.h>
#include "mutt/mutt.h"
#include "address/lib.h"
#include "email/lib.h"
#include "core/lib.h"
#include "mutt.h"
#include "mx.h"
#include "alias.h"
#include "context.h"
#include "copy.h"
#include "globals.h"
#include "hook.h"
#include "keymap.h"
#include "maildir/lib.h"
#include "mbox/mbox.h"
#include "mutt_header.h"
#include "mutt_logging.h"
#include "mutt_mailbox.h"
#include "muttlib.h"
#include "opcodes.h"
#include "options.h"
#include "protos.h"
#include "sort.h"
#include "compress.h"
#include "imap/imap.h"
#include "pop/pop.h"
#include "nntp/nntp.h"
#include "notmuch/mutt_notmuch.h"
#include <libintl.h>
+ Include dependency graph for mx.c:

Go to the source code of this file.

Functions

const struct MxOpsmx_get_ops (enum MailboxType magic)
 Get mailbox operations. More...
 
static bool mutt_is_spool (const char *str)
 Is this the spoolfile? More...
 
int mx_access (const char *path, int flags)
 Wrapper for access, checks permissions on a given mailbox. More...
 
static int mx_open_mailbox_append (struct Mailbox *m, OpenMailboxFlags flags)
 Open a mailbox for appending. More...
 
struct Contextmx_mbox_open (struct Mailbox *m, OpenMailboxFlags flags)
 Open a mailbox and parse it. More...
 
void mx_fastclose_mailbox (struct Mailbox *m)
 free up memory associated with the Mailbox More...
 
static int sync_mailbox (struct Mailbox *m, int *index_hint)
 save changes to disk More...
 
static int trash_append (struct Mailbox *m)
 move deleted mails to the trash folder More...
 
int mx_mbox_close (struct Context **ptr)
 Save changes and close mailbox. More...
 
int mx_mbox_sync (struct Mailbox *m, int *index_hint)
 Save changes to mailbox. More...
 
struct Messagemx_msg_open_new (struct Mailbox *m, struct Email *e, MsgOpenFlags flags)
 Open a new message. More...
 
int mx_mbox_check (struct Mailbox *m, int *index_hint)
 Check for new mail - Wrapper for MxOps::mbox_check() More...
 
struct Messagemx_msg_open (struct Mailbox *m, int msgno)
 return a stream pointer for a message More...
 
int mx_msg_commit (struct Mailbox *m, struct Message *msg)
 Commit a message to a folder - Wrapper for MxOps::msg_commit() More...
 
int mx_msg_close (struct Mailbox *m, struct Message **msg)
 Close a message. More...
 
void mx_alloc_memory (struct Mailbox *m)
 Create storage for the emails. More...
 
int mx_check_empty (const char *path)
 Is the mailbox empty. More...
 
int mx_tags_edit (struct Mailbox *m, const char *tags, char *buf, size_t buflen)
 start the tag editor of the mailbox More...
 
int mx_tags_commit (struct Mailbox *m, struct Email *e, char *tags)
 Save tags to the Mailbox - Wrapper for MxOps::tags_commit() More...
 
bool mx_tags_is_supported (struct Mailbox *m)
 return true if mailbox support tagging More...
 
enum MailboxType mx_path_probe (const char *path, struct stat *st)
 Find a mailbox that understands a path. More...
 
int mx_path_canon (char *buf, size_t buflen, const char *folder, enum MailboxType *magic)
 Canonicalise a mailbox path - Wrapper for MxOps::path_canon() More...
 
int mx_path_canon2 (struct Mailbox *m, const char *folder)
 Canonicalise the path to realpath. More...
 
int mx_path_pretty (char *buf, size_t buflen, const char *folder)
 Abbreviate a mailbox path - Wrapper for MxOps::path_pretty() More...
 
int mx_path_parent (char *buf, size_t buflen)
 Find the parent of a mailbox path - Wrapper for MxOps::path_parent() More...
 
int mx_msg_padding_size (struct Mailbox *m)
 Bytes of padding between messages - Wrapper for MxOps::msg_padding_size() More...
 
struct Accountmx_ac_find (struct Mailbox *m)
 Find the Account owning a Mailbox. More...
 
struct Mailboxmx_mbox_find (struct Account *a, const char *path)
 Find a Mailbox on an Account. More...
 
struct Mailboxmx_mbox_find2 (const char *path)
 Find a Mailbox on an Account. More...
 
struct Mailboxmx_path_resolve (const char *path)
 Get a Mailbox for a path. More...
 
int mx_ac_add (struct Account *a, struct Mailbox *m)
 Add a Mailbox to an Account - Wrapper for MxOps::ac_add() More...
 
int mx_ac_remove (struct Mailbox *m)
 Remove a Mailbox from an Account and delete Account if empty. More...
 
int mx_mbox_check_stats (struct Mailbox *m, int flags)
 Check the statistics for a mailbox - Wrapper for MxOps::mbox_check_stats() More...
 
int mx_save_hcache (struct Mailbox *m, struct Email *e)
 Save message to the header cache - Wrapper for MxOps::msg_save_hcache() More...
 

Variables

unsigned char C_CatchupNewsgroup
 Config: (nntp) Mark all articles as read when leaving a newsgroup. More...
 
bool C_KeepFlagged
 Config: Don't move flagged messages from C_Spoolfile to C_Mbox. More...
 
unsigned char C_MboxType
 Config: Default type for creating new mailboxes. More...
 
unsigned char C_Move
 Config: Move emails from C_Spoolfile to C_Mbox when read. More...
 
char * C_Trash
 Config: Folder to put deleted emails. More...
 
static struct Mapping MagicMap []
 
struct EnumDef MagicDef
 
static const struct MxOpsmx_ops []
 All the Mailbox backends. More...
 

Detailed Description

Mailbox multiplexor.

Authors
  • Michael R. Elkins
  • Thomas Roessler
  • Richard Russon
  • Pietro Cerutti

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

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

Definition in file mx.c.

Function Documentation

◆ mx_get_ops()

const struct MxOps* mx_get_ops ( enum MailboxType  magic)

Get mailbox operations.

Parameters
magicMailbox magic number
Return values
ptrMailbox function
NULLError

Definition at line 140 of file mx.c.

141 {
142  for (const struct MxOps **ops = mx_ops; *ops; ops++)
143  if ((*ops)->magic == magic)
144  return *ops;
145 
146  return NULL;
147 }
static const struct MxOps * mx_ops[]
All the Mailbox backends.
Definition: mx.c:106
The Mailbox API.
Definition: mx.h:103
+ Here is the caller graph for this function:

◆ mutt_is_spool()

static bool mutt_is_spool ( const char *  str)
static

Is this the spoolfile?

Parameters
strName to check
Return values
trueIt is the spoolfile

Definition at line 154 of file mx.c.

155 {
156  return mutt_str_strcmp(C_Spoolfile, str) == 0;
157 }
WHERE char * C_Spoolfile
Config: Inbox.
Definition: globals.h:144
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:615
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_access()

int mx_access ( const char *  path,
int  flags 
)

Wrapper for access, checks permissions on a given mailbox.

Parameters
pathPath of mailbox
flagsFlags, e.g. W_OK
Return values
0Success, allowed
<0Failure, not allowed

We may be interested in using ACL-style flags at some point, currently we use the normal access() flags.

Definition at line 169 of file mx.c.

170 {
171 #ifdef USE_IMAP
172  if (imap_path_probe(path, NULL) == MUTT_IMAP)
173  return imap_access(path);
174 #endif
175 
176  return access(path, flags);
177 }
enum MailboxType imap_path_probe(const char *path, const struct stat *st)
Is this an IMAP Mailbox? - Implements MxOps::path_probe()
Definition: imap.c:2474
int imap_access(const char *path)
Check permissions on an IMAP mailbox with a new connection.
Definition: imap.c:601
&#39;IMAP&#39; Mailbox type
Definition: mailbox.h:52
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_open_mailbox_append()

static int mx_open_mailbox_append ( struct Mailbox m,
OpenMailboxFlags  flags 
)
static

Open a mailbox for appending.

Parameters
mMailbox
flagsFlags, see OpenMailboxFlags
Return values
0Success
-1Failure

Definition at line 186 of file mx.c.

187 {
188  if (!m)
189  return -1;
190 
191  struct stat sb;
192 
193  m->append = true;
194  if ((m->magic == MUTT_UNKNOWN) || (m->magic == MUTT_MAILBOX_ERROR))
195  {
196  m->magic = mx_path_probe(mailbox_path(m), NULL);
197 
198  if (m->magic == MUTT_UNKNOWN)
199  {
200  if (flags & (MUTT_APPEND | MUTT_NEWFOLDER))
201  {
203  }
204  else
205  {
206  mutt_error(_("%s is not a mailbox"), mailbox_path(m));
207  return -1;
208  }
209  }
210 
211  if (m->magic == MUTT_MAILBOX_ERROR)
212  {
213  if (stat(mailbox_path(m), &sb) == -1)
214  {
215  if (errno == ENOENT)
216  {
217 #ifdef USE_COMPRESSED
218  if (mutt_comp_can_append(m))
219  m->magic = MUTT_COMPRESSED;
220  else
221 #endif
222  m->magic = C_MboxType;
223  flags |= MUTT_APPENDNEW;
224  }
225  else
226  {
228  return -1;
229  }
230  }
231  else
232  return -1;
233  }
234 
235  m->mx_ops = mx_get_ops(m->magic);
236  }
237 
238  if (!m->mx_ops || !m->mx_ops->mbox_open_append)
239  return -1;
240 
241  int rc = m->mx_ops->mbox_open_append(m, flags);
242  m->opened++;
243  return rc;
244 }
#define MUTT_APPEND
Open mailbox for appending messages.
Definition: mx.h:52
static const char * mailbox_path(const struct Mailbox *m)
Get the Mailbox&#39;s path string.
Definition: mailbox.h:191
#define MUTT_APPENDNEW
Set in mx_open_mailbox_append if the mailbox doesn&#39;t exist.
Definition: mx.h:59
#define mutt_perror(...)
Definition: logging.h:85
#define _(a)
Definition: message.h:28
Mailbox wasn&#39;t recognised.
Definition: mailbox.h:46
Error occurred examining Mailbox.
Definition: mailbox.h:45
int(* mbox_open_append)(struct Mailbox *m, OpenMailboxFlags flags)
Open a Mailbox for appending.
Definition: mx.h:139
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
int opened
Number of times mailbox is opened.
Definition: mailbox.h:131
Compressed file Mailbox type.
Definition: mailbox.h:55
bool append
Mailbox is opened in append mode.
Definition: mailbox.h:112
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
unsigned char C_MboxType
Config: Default type for creating new mailboxes.
Definition: mx.c:83
bool mutt_comp_can_append(struct Mailbox *m)
Can we append to this path?
Definition: compress.c:339
const struct MxOps * mx_get_ops(enum MailboxType magic)
Get mailbox operations.
Definition: mx.c:140
#define mutt_error(...)
Definition: logging.h:84
#define MUTT_NEWFOLDER
Create a new folder - same as MUTT_APPEND,.
Definition: mx.h:55
enum MailboxType mx_path_probe(const char *path, struct stat *st)
Find a mailbox that understands a path.
Definition: mx.c:1288
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_mbox_open()

struct Context* mx_mbox_open ( struct Mailbox m,
OpenMailboxFlags  flags 
)

Open a mailbox and parse it.

Parameters
mMailbox to open
flagsFlags, see OpenMailboxFlags
Return values
ptrMailbox context
NULLError

Definition at line 253 of file mx.c.

254 {
255  if (!m)
256  return NULL;
257 
258  struct Context *ctx = ctx_new();
259  ctx->mailbox = m;
260 
261  struct EventContext ev_ctx = { ctx };
262  notify_send(ctx->notify, NT_CONTEXT, NT_CONTEXT_OPEN, &ev_ctx);
263 
264  // If the Mailbox is closed, Context->mailbox must be set to NULL
266 
267  if ((m->magic == MUTT_UNKNOWN) && (flags & (MUTT_NEWFOLDER | MUTT_APPEND)))
268  {
269  m->magic = C_MboxType;
270  m->mx_ops = mx_get_ops(m->magic);
271  }
272 
273  const bool newly_linked_account = !m->account;
274  if (newly_linked_account)
275  {
276  struct Account *a = mx_ac_find(m);
277  bool new_account = false;
278  if (!a)
279  {
280  a = account_new(NULL, NeoMutt->sub);
281  a->magic = m->magic;
282  new_account = true;
283  }
284  if (mx_ac_add(a, m) < 0)
285  {
286  ctx_free(&ctx);
287  if (new_account)
288  {
289  FREE(&a);
290  }
291  return NULL;
292  }
293  if (new_account)
294  {
296  }
297  }
298 
299  ctx->msg_not_read_yet = -1;
300  ctx->collapsed = false;
301 
302  m->quiet = (flags & MUTT_QUIET);
303  if (flags & MUTT_READONLY)
304  m->readonly = true;
305  m->peekonly = (flags & MUTT_PEEK);
306 
307  if (flags & (MUTT_APPEND | MUTT_NEWFOLDER))
308  {
309  if (mx_open_mailbox_append(ctx->mailbox, flags) != 0)
310  {
311  goto error;
312  }
313  return ctx;
314  }
315 
316  if (m->opened > 0)
317  {
318  m->opened++;
319  return ctx;
320  }
321 
322  m->size = 0;
323  m->msg_unread = 0;
324  m->msg_flagged = 0;
325  m->rights = MUTT_ACL_ALL;
326 
327  if (m->magic == MUTT_UNKNOWN)
328  {
329  m->magic = mx_path_probe(mailbox_path(m), NULL);
330  m->mx_ops = mx_get_ops(m->magic);
331  }
332 
333  if ((m->magic == MUTT_UNKNOWN) || (m->magic == MUTT_MAILBOX_ERROR) || !m->mx_ops)
334  {
335  if (m->magic == MUTT_MAILBOX_ERROR)
337  else if ((m->magic == MUTT_UNKNOWN) || !m->mx_ops)
338  mutt_error(_("%s is not a mailbox"), mailbox_path(m));
339  goto error;
340  }
341 
343 
344  /* if the user has a 'push' command in their .neomuttrc, or in a folder-hook,
345  * it will cause the progress messages not to be displayed because
346  * mutt_refresh() will think we are in the middle of a macro. so set a
347  * flag to indicate that we should really refresh the screen. */
348  OptForceRefresh = true;
349 
350  if (!m->quiet)
351  mutt_message(_("Reading %s..."), mailbox_path(m));
352 
353  // Clear out any existing emails
354  for (int i = 0; i < m->email_max; i++)
355  {
356  email_free(&m->emails[i]);
357  }
358 
359  m->msg_count = 0;
360  m->msg_unread = 0;
361  m->msg_flagged = 0;
362  m->msg_new = 0;
363  m->msg_deleted = 0;
364  m->msg_tagged = 0;
365  m->vcount = 0;
366 
367  int rc = m->mx_ops->mbox_open(ctx->mailbox);
368  m->opened++;
369  if (rc == 0)
370  ctx_update(ctx);
371 
372  if ((rc == 0) || (rc == -2))
373  {
374  if ((flags & MUTT_NOSORT) == 0)
375  {
376  /* avoid unnecessary work since the mailbox is completely unthreaded
377  * to begin with */
378  OptSortSubthreads = false;
379  OptNeedRescore = false;
380  }
381  if (!m->quiet)
383  if (rc == -2)
384  {
385  mutt_error(_("Reading from %s interrupted..."), mailbox_path(m));
386  mutt_sort_headers(ctx, true);
387  }
388  }
389  else
390  {
391  goto error;
392  }
393 
394  if (!m->peekonly)
395  m->has_new = false;
396  OptForceRefresh = false;
397 
398  return ctx;
399 
400 error:
402  if (newly_linked_account)
404  ctx_free(&ctx);
405  return NULL;
406 }
#define MUTT_APPEND
Open mailbox for appending messages.
Definition: mx.h:52
struct Email ** emails
Array of Emails.
Definition: mailbox.h:98
The "current" mailbox.
Definition: context.h:36
static const char * mailbox_path(const struct Mailbox *m)
Get the Mailbox&#39;s path string.
Definition: mailbox.h:191
int ctx_mailbox_observer(struct NotifyCallback *nc)
Watch for changes affecting the Context - Implements observer_t.
Definition: context.c:295
#define MUTT_ACL_ALL
Definition: mailbox.h:75
int msg_count
Total number of messages.
Definition: mailbox.h:90
off_t size
Size of the Mailbox.
Definition: mailbox.h:86
#define mutt_perror(...)
Definition: logging.h:85
int msg_deleted
Number of deleted messages.
Definition: mailbox.h:95
int msg_unread
Number of unread messages.
Definition: mailbox.h:91
int mx_ac_add(struct Account *a, struct Mailbox *m)
Add a Mailbox to an Account - Wrapper for MxOps::ac_add()
Definition: mx.c:1623
#define mutt_message(...)
Definition: logging.h:83
int msg_flagged
Number of flagged messages.
Definition: mailbox.h:92
bool peekonly
Just taking a glance, revert atime.
Definition: mailbox.h:116
A group of associated Mailboxes.
Definition: account.h:36
#define _(a)
Definition: message.h:28
Mailbox wasn&#39;t recognised.
Definition: mailbox.h:46
Error occurred examining Mailbox.
Definition: mailbox.h:45
#define MUTT_READONLY
Open in read-only mode.
Definition: mx.h:53
WHERE bool OptNeedRescore
(pseudo) set when the &#39;score&#39; command is used
Definition: options.h:40
struct Account * mx_ac_find(struct Mailbox *m)
Find the Account owning a Mailbox.
Definition: mx.c:1531
Container for Accounts, Notifications.
Definition: neomutt.h:35
struct Context * ctx_new(void)
Create a new Context.
Definition: context.c:72
bool notify_observer_add(struct Notify *notify, observer_t callback, void *global_data)
Add an observer to an object.
Definition: notify.c:154
int vcount
The number of virtual messages.
Definition: mailbox.h:101
int(* mbox_open)(struct Mailbox *m)
Open a Mailbox.
Definition: mx.h:131
bool has_new
Mailbox has new mail.
Definition: mailbox.h:87
struct Mailbox * mailbox
Definition: context.h:50
#define MUTT_PEEK
Revert atime back after taking a look (if applicable)
Definition: mx.h:58
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
bool readonly
Don&#39;t allow changes to the mailbox.
Definition: mailbox.h:118
The Context has been opened.
Definition: context.h:67
struct Notify * notify
Notifications handler.
Definition: context.h:51
void mx_fastclose_mailbox(struct Mailbox *m)
free up memory associated with the Mailbox
Definition: mx.c:412
int opened
Number of times mailbox is opened.
Definition: mailbox.h:131
void mutt_clear_error(void)
Clear the message line (bottom line of screen)
Definition: mutt_logging.c:113
struct Account * account_new(const char *name, struct ConfigSubset *sub)
Create a new Account.
Definition: account.c:43
int msg_not_read_yet
Which msg "new" in pager, -1 if none.
Definition: context.h:44
WHERE bool OptForceRefresh
(pseudo) refresh even during macros
Definition: options.h:35
void mutt_sort_headers(struct Context *ctx, bool init)
Sort emails by their headers.
Definition: sort.c:362
int email_max
Number of pointers in emails.
Definition: mailbox.h:99
void ctx_update(struct Context *ctx)
Update the Context&#39;s message counts.
Definition: context.c:106
enum MailboxType magic
Type of Mailboxes this Account contains.
Definition: account.h:38
#define MUTT_NOSORT
Do not sort the mailbox after opening it.
Definition: mx.h:51
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
bool quiet
Inhibit status messages?
Definition: mailbox.h:117
unsigned char C_MboxType
Config: Default type for creating new mailboxes.
Definition: mx.c:83
int msg_tagged
How many messages are tagged?
Definition: mailbox.h:96
#define MUTT_QUIET
Do not print any messages.
Definition: mx.h:54
AclFlags rights
ACL bits, see AclFlags.
Definition: mailbox.h:120
bool notify_send(struct Notify *notify, enum NotifyType event_type, int event_subtype, void *event_data)
Send out a notification message.
Definition: notify.c:138
void mutt_make_label_hash(struct Mailbox *m)
Create a Hash Table to store the labels.
Definition: mutt_header.c:359
Context has changed.
Definition: notify_type.h:35
struct Account * account
Account that owns this Mailbox.
Definition: mailbox.h:130
static int mx_open_mailbox_append(struct Mailbox *m, OpenMailboxFlags flags)
Open a mailbox for appending.
Definition: mx.c:186
int msg_new
Number of new messages.
Definition: mailbox.h:94
const struct MxOps * mx_get_ops(enum MailboxType magic)
Get mailbox operations.
Definition: mx.c:140
bool collapsed
Are all threads collapsed?
Definition: context.h:48
bool account_mailbox_remove(struct Account *a, struct Mailbox *m)
Remove a Mailbox from an Account.
Definition: account.c:95
#define mutt_error(...)
Definition: logging.h:84
#define FREE(x)
Definition: memory.h:40
WHERE bool OptSortSubthreads
(pseudo) used when $sort_aux changes
Definition: options.h:52
void ctx_free(struct Context **ptr)
Free a Context.
Definition: context.c:49
struct ConfigSubset * sub
Inherited config items.
Definition: neomutt.h:38
struct Notify * notify
Notifications handler.
Definition: mailbox.h:138
An Event that happened to an Context.
Definition: context.h:57
#define MUTT_NEWFOLDER
Create a new folder - same as MUTT_APPEND,.
Definition: mx.h:55
bool neomutt_account_add(struct NeoMutt *n, struct Account *a)
Add an Account to the global list.
Definition: neomutt.c:84
void email_free(struct Email **ptr)
Free an Email.
Definition: email.c:41
enum MailboxType mx_path_probe(const char *path, struct stat *st)
Find a mailbox that understands a path.
Definition: mx.c:1288
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_fastclose_mailbox()

void mx_fastclose_mailbox ( struct Mailbox m)

free up memory associated with the Mailbox

Parameters
mMailbox

Definition at line 412 of file mx.c.

413 {
414  if (!m)
415  return;
416 
417  m->opened--;
418  if (m->opened != 0)
419  return;
420 
421  /* never announce that a mailbox we've just left has new mail.
422  * TODO: really belongs in mx_mbox_close, but this is a nice hook point */
423  if (!m->peekonly)
425 
426  if (m->mx_ops)
427  m->mx_ops->mbox_close(m);
428 
430  mutt_hash_free(&m->id_hash);
432 
433  if (m->emails)
434  {
435  for (int i = 0; i < m->msg_count; i++)
436  {
437  if (!m->emails[i])
438  break;
439  email_free(&m->emails[i]);
440  }
441  }
442 }
struct Email ** emails
Array of Emails.
Definition: mailbox.h:98
int msg_count
Total number of messages.
Definition: mailbox.h:90
bool peekonly
Just taking a glance, revert atime.
Definition: mailbox.h:116
int opened
Number of times mailbox is opened.
Definition: mailbox.h:131
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
int(* mbox_close)(struct Mailbox *m)
Close a Mailbox.
Definition: mx.h:171
struct Hash * subj_hash
Hash table by subject.
Definition: mailbox.h:127
void mutt_mailbox_set_notified(struct Mailbox *m)
Note when the user was last notified of new mail.
Definition: mutt_mailbox.c:270
void mutt_hash_free(struct Hash **ptr)
Free a hash table.
Definition: hash.c:471
void email_free(struct Email **ptr)
Free an Email.
Definition: email.c:41
struct Hash * label_hash
Hash table for x-labels.
Definition: mailbox.h:128
struct Hash * id_hash
Hash table by msg id.
Definition: mailbox.h:126
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ sync_mailbox()

static int sync_mailbox ( struct Mailbox m,
int *  index_hint 
)
static

save changes to disk

Parameters
mMailbox
index_hintCurrent email
Return values
0Success
-1Failure

Definition at line 451 of file mx.c.

452 {
453  if (!m || !m->mx_ops || !m->mx_ops->mbox_sync)
454  return -1;
455 
456  if (!m->quiet)
457  {
458  /* L10N: Displayed before/as a mailbox is being synced */
459  mutt_message(_("Writing %s..."), mailbox_path(m));
460  }
461 
462  int rc = m->mx_ops->mbox_sync(m, index_hint);
463  if ((rc != 0) && !m->quiet)
464  {
465  /* L10N: Displayed if a mailbox sync fails */
466  mutt_error(_("Unable to write %s"), mailbox_path(m));
467  }
468 
469  return rc;
470 }
static const char * mailbox_path(const struct Mailbox *m)
Get the Mailbox&#39;s path string.
Definition: mailbox.h:191
int(* mbox_sync)(struct Mailbox *m, int *index_hint)
Save changes to the Mailbox.
Definition: mx.h:164
#define mutt_message(...)
Definition: logging.h:83
#define _(a)
Definition: message.h:28
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
bool quiet
Inhibit status messages?
Definition: mailbox.h:117
#define mutt_error(...)
Definition: logging.h:84
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ trash_append()

static int trash_append ( struct Mailbox m)
static

move deleted mails to the trash folder

Parameters
mMailbox
Return values
0Success
-1Failure

Definition at line 478 of file mx.c.

479 {
480  if (!m)
481  return -1;
482 
483  struct stat st, stc;
484  int opt_confappend, rc;
485 
486  if (!C_Trash || (m->msg_deleted == 0) || ((m->magic == MUTT_MAILDIR) && C_MaildirTrash))
487  {
488  return 0;
489  }
490 
491  int delmsgcount = 0;
492  int first_del = -1;
493  for (int i = 0; i < m->msg_count; i++)
494  {
495  struct Email *e = m->emails[i];
496  if (!e)
497  break;
498 
499  if (e->deleted && !e->purge)
500  {
501  if (first_del < 0)
502  first_del = i;
503  delmsgcount++;
504  }
505  }
506 
507  if (delmsgcount == 0)
508  return 0; /* nothing to be done */
509 
510  /* avoid the "append messages" prompt */
511  opt_confappend = C_Confirmappend;
512  if (opt_confappend)
513  C_Confirmappend = false;
514  rc = mutt_save_confirm(C_Trash, &st);
515  if (opt_confappend)
516  C_Confirmappend = true;
517  if (rc != 0)
518  {
519  /* L10N: Although we know the precise number of messages, we do not show it to the user.
520  So feel free to use a "generic plural" as plural translation if your language has one. */
521  mutt_error(ngettext("message not deleted", "messages not deleted", delmsgcount));
522  return -1;
523  }
524 
525  if ((lstat(mailbox_path(m), &stc) == 0) && (stc.st_ino == st.st_ino) &&
526  (stc.st_dev == st.st_dev) && (stc.st_rdev == st.st_rdev))
527  {
528  return 0; /* we are in the trash folder: simple sync */
529  }
530 
531 #ifdef USE_IMAP
532  if ((m->magic == MUTT_IMAP) && (imap_path_probe(C_Trash, NULL) == MUTT_IMAP))
533  {
534  if (imap_fast_trash(m, C_Trash) == 0)
535  return 0;
536  }
537 #endif
538 
539  struct Mailbox *m_trash = mx_path_resolve(C_Trash);
540  const bool old_append = m_trash->append;
541  struct Context *ctx_trash = mx_mbox_open(m_trash, MUTT_APPEND);
542  if (ctx_trash)
543  {
544  /* continue from initial scan above */
545  for (int i = first_del; i < m->msg_count; i++)
546  {
547  struct Email *e = m->emails[i];
548  if (!e)
549  break;
550 
551  if (e->deleted && !e->purge)
552  {
553  if (mutt_append_message(ctx_trash->mailbox, m, e, MUTT_CM_NO_FLAGS, CH_NO_FLAGS) == -1)
554  {
555  m_trash->append = old_append;
556  mx_mbox_close(&ctx_trash);
557  return -1;
558  }
559  }
560  }
561 
562  m_trash->append = old_append;
563  mx_mbox_close(&ctx_trash);
564  }
565  else
566  {
567  mutt_error(_("Can't open trash folder"));
568  mailbox_free(&m_trash);
569  return -1;
570  }
571 
572  return 0;
573 }
#define MUTT_APPEND
Open mailbox for appending messages.
Definition: mx.h:52
struct Email ** emails
Array of Emails.
Definition: mailbox.h:98
The "current" mailbox.
Definition: context.h:36
static const char * mailbox_path(const struct Mailbox *m)
Get the Mailbox&#39;s path string.
Definition: mailbox.h:191
int msg_count
Total number of messages.
Definition: mailbox.h:90
The envelope/body of an email.
Definition: email.h:37
enum MailboxType imap_path_probe(const char *path, const struct stat *st)
Is this an IMAP Mailbox? - Implements MxOps::path_probe()
Definition: imap.c:2474
int msg_deleted
Number of deleted messages.
Definition: mailbox.h:95
int mx_mbox_close(struct Context **ptr)
Save changes and close mailbox.
Definition: mx.c:583
WHERE bool C_Confirmappend
Config: Confirm before appending emails to a mailbox.
Definition: globals.h:207
#define _(a)
Definition: message.h:28
struct Context * mx_mbox_open(struct Mailbox *m, OpenMailboxFlags flags)
Open a mailbox and parse it.
Definition: mx.c:253
#define MUTT_CM_NO_FLAGS
No flags are set.
Definition: copy.h:34
int mutt_save_confirm(const char *s, struct stat *st)
Ask the user to save.
Definition: muttlib.c:1448
char * C_Trash
Config: Folder to put deleted emails.
Definition: mx.c:85
struct Mailbox * mailbox
Definition: context.h:50
void mailbox_free(struct Mailbox **ptr)
Free a Mailbox.
Definition: mailbox.c:60
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
&#39;Maildir&#39; Mailbox type
Definition: mailbox.h:50
A mailbox.
Definition: mailbox.h:80
#define CH_NO_FLAGS
No flags are set.
Definition: copy.h:50
WHERE bool C_MaildirTrash
Config: Use the maildir &#39;trashed&#39; flag, rather than deleting.
Definition: globals.h:240
bool append
Mailbox is opened in append mode.
Definition: mailbox.h:112
bool purge
Skip trash folder when deleting.
Definition: email.h:46
bool deleted
Email is deleted.
Definition: email.h:45
#define mutt_error(...)
Definition: logging.h:84
int mutt_append_message(struct Mailbox *dest, struct Mailbox *src, struct Email *e, CopyMessageFlags cmflags, CopyHeaderFlags chflags)
Append a message.
Definition: copy.c:880
struct Mailbox * mx_path_resolve(const char *path)
Get a Mailbox for a path.
Definition: mx.c:1603
&#39;IMAP&#39; Mailbox type
Definition: mailbox.h:52
int imap_fast_trash(struct Mailbox *m, char *dest)
Use server COPY command to copy deleted messages to trash.
Definition: imap.c:1526
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_mbox_close()

int mx_mbox_close ( struct Context **  ptr)

Save changes and close mailbox.

Parameters
[out]ptrMailbox
Return values
0Success
-1Failure
Note
Context will be freed after it's closed

Definition at line 583 of file mx.c.

584 {
585  if (!ptr || !*ptr)
586  return 0;
587 
588  struct Context *ctx = *ptr;
589  if (!ctx || !ctx->mailbox)
590  return -1;
591 
592  struct Mailbox *m = ctx->mailbox;
593 
594  if (C_MailCheckRecent && !m->peekonly)
595  m->has_new = false;
596 
597  if (m->readonly || m->dontwrite || m->append || m->peekonly)
598  {
600  ctx_free(ptr);
601  return 0;
602  }
603 
604  int i, read_msgs = 0;
605  int rc = -1;
606  enum QuadOption move_messages = MUTT_NO;
607  enum QuadOption purge = MUTT_YES;
608  struct Buffer *mbox = NULL;
609  struct Buffer *buf = mutt_buffer_pool_get();
610 
611 #ifdef USE_NNTP
612  if ((m->msg_unread != 0) && (m->magic == MUTT_NNTP))
613  {
614  struct NntpMboxData *mdata = m->mdata;
615 
616  if (mdata && mdata->adata && mdata->group)
617  {
618  enum QuadOption ans =
619  query_quadoption(C_CatchupNewsgroup, _("Mark all articles read?"));
620  if (ans == MUTT_ABORT)
621  goto cleanup;
622  if (ans == MUTT_YES)
623  mutt_newsgroup_catchup(m, mdata->adata, mdata->group);
624  }
625  }
626 #endif
627 
628  for (i = 0; i < m->msg_count; i++)
629  {
630  struct Email *e = m->emails[i];
631  if (!e)
632  break;
633 
634  if (!e->deleted && e->read && !(e->flagged && C_KeepFlagged))
635  read_msgs++;
636  }
637 
638 #ifdef USE_NNTP
639  /* don't need to move articles from newsgroup */
640  if (m->magic == MUTT_NNTP)
641  read_msgs = 0;
642 #endif
643 
644  if ((read_msgs != 0) && (C_Move != MUTT_NO))
645  {
646  bool is_spool;
647  mbox = mutt_buffer_pool_get();
648 
650  if (p)
651  {
652  is_spool = true;
653  mutt_buffer_strcpy(mbox, p);
654  }
655  else
656  {
657  mutt_buffer_strcpy(mbox, C_Mbox);
658  is_spool = mutt_is_spool(mailbox_path(m)) && !mutt_is_spool(mutt_b2s(mbox));
659  }
660 
661  if (is_spool && !mutt_buffer_is_empty(mbox))
662  {
664  mutt_buffer_printf(buf,
665  /* L10N: The first argument is the number of read messages to be
666  moved, the second argument is the target mailbox. */
667  ngettext("Move %d read message to %s?",
668  "Move %d read messages to %s?", read_msgs),
669  read_msgs, mutt_b2s(mbox));
670  move_messages = query_quadoption(C_Move, mutt_b2s(buf));
671  if (move_messages == MUTT_ABORT)
672  goto cleanup;
673  }
674  }
675 
676  /* There is no point in asking whether or not to purge if we are
677  * just marking messages as "trash". */
678  if ((m->msg_deleted != 0) && !((m->magic == MUTT_MAILDIR) && C_MaildirTrash))
679  {
680  mutt_buffer_printf(buf,
681  ngettext("Purge %d deleted message?",
682  "Purge %d deleted messages?", m->msg_deleted),
683  m->msg_deleted);
684  purge = query_quadoption(C_Delete, mutt_b2s(buf));
685  if (purge == MUTT_ABORT)
686  goto cleanup;
687  }
688 
689  if (C_MarkOld && !m->peekonly)
690  {
691  for (i = 0; i < m->msg_count; i++)
692  {
693  struct Email *e = m->emails[i];
694  if (!e)
695  break;
696  if (!e->deleted && !e->old && !e->read)
697  mutt_set_flag(m, e, MUTT_OLD, true);
698  }
699  }
700 
701  if (move_messages)
702  {
703  if (!m->quiet)
704  mutt_message(_("Moving read messages to %s..."), mutt_b2s(mbox));
705 
706 #ifdef USE_IMAP
707  /* try to use server-side copy first */
708  i = 1;
709 
710  if ((m->magic == MUTT_IMAP) && (imap_path_probe(mutt_b2s(mbox), NULL) == MUTT_IMAP))
711  {
712  /* tag messages for moving, and clear old tags, if any */
713  for (i = 0; i < m->msg_count; i++)
714  {
715  struct Email *e = m->emails[i];
716  if (!e)
717  break;
718 
719  if (e->read && !e->deleted && !(e->flagged && C_KeepFlagged))
720  e->tagged = true;
721  else
722  e->tagged = false;
723  }
724 
725  i = imap_copy_messages(ctx->mailbox, NULL, mutt_b2s(mbox), true);
726  }
727 
728  if (i == 0) /* success */
730  else if (i == -1) /* horrible error, bail */
731  goto cleanup;
732  else /* use regular append-copy mode */
733 #endif
734  {
735  struct Mailbox *m_read = mx_path_resolve(mutt_b2s(mbox));
736  struct Context *ctx_read = mx_mbox_open(m_read, MUTT_APPEND);
737  if (!ctx_read)
738  {
739  mailbox_free(&m_read);
740  goto cleanup;
741  }
742 
743  for (i = 0; i < m->msg_count; i++)
744  {
745  struct Email *e = m->emails[i];
746  if (!e)
747  break;
748  if (e->read && !e->deleted && !(e->flagged && C_KeepFlagged))
749  {
750  if (mutt_append_message(ctx_read->mailbox, ctx->mailbox, e,
752  {
753  mutt_set_flag(m, e, MUTT_DELETE, true);
754  mutt_set_flag(m, e, MUTT_PURGE, true);
755  }
756  else
757  {
758  mx_mbox_close(&ctx_read);
759  goto cleanup;
760  }
761  }
762  }
763 
764  mx_mbox_close(&ctx_read);
765  }
766  }
767  else if (!m->changed && (m->msg_deleted == 0))
768  {
769  if (!m->quiet)
770  mutt_message(_("Mailbox is unchanged"));
771  if ((m->magic == MUTT_MBOX) || (m->magic == MUTT_MMDF))
772  mbox_reset_atime(m, NULL);
774  ctx_free(ptr);
775  rc = 0;
776  goto cleanup;
777  }
778 
779  /* copy mails to the trash before expunging */
780  if (purge && (m->msg_deleted != 0) && (mutt_str_strcmp(mailbox_path(m), C_Trash) != 0))
781  {
782  if (trash_append(ctx->mailbox) != 0)
783  goto cleanup;
784  }
785 
786 #ifdef USE_IMAP
787  /* allow IMAP to preserve the deleted flag across sessions */
788  if (m->magic == MUTT_IMAP)
789  {
790  int check = imap_sync_mailbox(ctx->mailbox, (purge != MUTT_NO), true);
791  if (check != 0)
792  goto cleanup;
793  }
794  else
795 #endif
796  {
797  if (purge == MUTT_NO)
798  {
799  for (i = 0; i < m->msg_count; i++)
800  {
801  struct Email *e = m->emails[i];
802  if (!e)
803  break;
804 
805  e->deleted = false;
806  e->purge = false;
807  }
808  m->msg_deleted = 0;
809  }
810 
811  if (m->changed || (m->msg_deleted != 0))
812  {
813  int check = sync_mailbox(ctx->mailbox, NULL);
814  if (check != 0)
815  goto cleanup;
816  }
817  }
818 
819  if (!m->quiet)
820  {
821  if (move_messages)
822  {
823  mutt_message(_("%d kept, %d moved, %d deleted"),
824  m->msg_count - m->msg_deleted, read_msgs, m->msg_deleted);
825  }
826  else
827  mutt_message(_("%d kept, %d deleted"), m->msg_count - m->msg_deleted, m->msg_deleted);
828  }
829 
830  if ((m->msg_count == m->msg_deleted) &&
831  ((m->magic == MUTT_MMDF) || (m->magic == MUTT_MBOX)) &&
833  {
835  }
836 
837 #ifdef USE_SIDEBAR
838  if ((purge == MUTT_YES) && (m->msg_deleted != 0))
839  {
840  for (i = 0; i < m->msg_count; i++)
841  {
842  struct Email *e = m->emails[i];
843  if (!e)
844  break;
845  if (e->deleted && !e->read)
846  {
847  m->msg_unread--;
848  if (!e->old)
849  m->msg_new--;
850  }
851  if (e->deleted && e->flagged)
852  m->msg_flagged--;
853  }
854  }
855 #endif
856 
858  ctx_free(ptr);
859 
860  rc = 0;
861 
862 cleanup:
865  return rc;
866 }
#define MUTT_APPEND
Open mailbox for appending messages.
Definition: mx.h:52
struct Email ** emails
Array of Emails.
Definition: mailbox.h:98
The "current" mailbox.
Definition: context.h:36
static const char * mailbox_path(const struct Mailbox *m)
Get the Mailbox&#39;s path string.
Definition: mailbox.h:191
int msg_count
Total number of messages.
Definition: mailbox.h:90
#define mutt_set_flag(m, e, flag, bf)
Definition: protos.h:70
WHERE bool C_MailCheckRecent
Config: Notify the user about new mail since the last time the mailbox was opened.
Definition: globals.h:239
The envelope/body of an email.
Definition: email.h:37
struct Buffer * mutt_buffer_pool_get(void)
Get a Buffer from the pool.
Definition: pool.c:101
struct NntpMboxData * mutt_newsgroup_catchup(struct Mailbox *m, struct NntpAccountData *adata, char *group)
Catchup newsgroup.
Definition: newsrc.c:1268
enum MailboxType imap_path_probe(const char *path, const struct stat *st)
Is this an IMAP Mailbox? - Implements MxOps::path_probe()
Definition: imap.c:2474
int msg_deleted
Number of deleted messages.
Definition: mailbox.h:95
int msg_unread
Number of unread messages.
Definition: mailbox.h:91
&#39;NNTP&#39; (Usenet) Mailbox type
Definition: mailbox.h:51
int mx_mbox_close(struct Context **ptr)
Save changes and close mailbox.
Definition: mx.c:583
User aborted the question (with Ctrl-G)
Definition: quad.h:38
enum QuadOption query_quadoption(enum QuadOption opt, const char *prompt)
Ask the user a quad-question.
Definition: init.c:3360
#define mutt_message(...)
Definition: logging.h:83
int msg_flagged
Number of flagged messages.
Definition: mailbox.h:92
User answered &#39;Yes&#39;, or assume &#39;Yes&#39;.
Definition: quad.h:40
static int trash_append(struct Mailbox *m)
move deleted mails to the trash folder
Definition: mx.c:478
bool peekonly
Just taking a glance, revert atime.
Definition: mailbox.h:116
struct NntpAccountData * adata
Definition: nntp.h:153
unsigned char C_Move
Config: Move emails from C_Spoolfile to C_Mbox when read.
Definition: mx.c:84
void mutt_buffer_pool_release(struct Buffer **pbuf)
Free a Buffer from the pool.
Definition: pool.c:112
WHERE unsigned char C_Delete
Config: Really delete messages, when the mailbox is closed.
Definition: globals.h:180
String manipulation buffer.
Definition: buffer.h:33
WHERE bool C_SaveEmpty
Config: (mbox,mmdf) Preserve empty mailboxes.
Definition: globals.h:249
#define _(a)
Definition: message.h:28
struct Context * mx_mbox_open(struct Mailbox *m, OpenMailboxFlags flags)
Open a mailbox and parse it.
Definition: mx.c:253
Messages to be purged (bypass trash)
Definition: mutt.h:104
int mutt_buffer_printf(struct Buffer *buf, const char *fmt,...)
Format a string overwriting a Buffer.
Definition: buffer.c:160
#define MUTT_CM_NO_FLAGS
No flags are set.
Definition: copy.h:34
int imap_sync_mailbox(struct Mailbox *m, bool expunge, bool close)
Sync all the changes to the server.
Definition: imap.c:1634
bool has_new
Mailbox has new mail.
Definition: mailbox.h:87
char * C_Trash
Config: Folder to put deleted emails.
Definition: mx.c:85
bool tagged
Email is tagged.
Definition: email.h:44
bool read
Email is read.
Definition: email.h:51
struct Mailbox * mailbox
Definition: context.h:50
bool old
Email is seen, but unread.
Definition: email.h:50
void mailbox_free(struct Mailbox **ptr)
Free a Mailbox.
Definition: mailbox.c:60
void mutt_file_unlink_empty(const char *path)
Delete a file if it&#39;s empty.
Definition: file.c:1302
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
bool readonly
Don&#39;t allow changes to the mailbox.
Definition: mailbox.h:118
WHERE char * C_Mbox
Config: Folder that receives read emails (see Move)
Definition: globals.h:117
void mx_fastclose_mailbox(struct Mailbox *m)
free up memory associated with the Mailbox
Definition: mx.c:412
char * group
Definition: nntp.h:140
void mutt_clear_error(void)
Clear the message line (bottom line of screen)
Definition: mutt_logging.c:113
void * mdata
Driver specific data.
Definition: mailbox.h:135
#define MUTT_MBOX_HOOK
mbox-hook: move messages after reading them
Definition: hook.h:46
&#39;Maildir&#39; Mailbox type
Definition: mailbox.h:50
Old messages.
Definition: mutt.h:98
#define mutt_b2s(buf)
Definition: buffer.h:41
unsigned char C_CatchupNewsgroup
Config: (nntp) Mark all articles as read when leaving a newsgroup.
Definition: mx.c:81
Messages to be deleted.
Definition: mutt.h:102
A mailbox.
Definition: mailbox.h:80
char * mutt_find_hook(HookFlags type, const char *pat)
Find a matching hook.
Definition: hook.c:552
User answered &#39;No&#39;, or assume &#39;No&#39;.
Definition: quad.h:39
WHERE bool C_MaildirTrash
Config: Use the maildir &#39;trashed&#39; flag, rather than deleting.
Definition: globals.h:240
bool dontwrite
Don&#39;t write the mailbox on close.
Definition: mailbox.h:114
&#39;mmdf&#39; Mailbox type
Definition: mailbox.h:48
bool append
Mailbox is opened in append mode.
Definition: mailbox.h:112
bool quiet
Inhibit status messages?
Definition: mailbox.h:117
int imap_copy_messages(struct Mailbox *m, struct EmailList *el, const char *dest, bool delete_original)
Server COPY messages to another folder.
Definition: message.c:1587
bool purge
Skip trash folder when deleting.
Definition: email.h:46
#define CH_UPDATE_LEN
Update Lines: and Content-Length:
Definition: copy.h:61
NNTP-specific Mailbox data -.
Definition: nntp.h:138
size_t mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:312
&#39;mbox&#39; Mailbox type
Definition: mailbox.h:47
bool C_MarkOld
Config: Mark new emails as old when leaving the mailbox.
Definition: email_globals.c:36
void mutt_buffer_expand_path(struct Buffer *buf)
Create the canonical path.
Definition: muttlib.c:342
static int sync_mailbox(struct Mailbox *m, int *index_hint)
save changes to disk
Definition: mx.c:451
bool flagged
Marked important?
Definition: email.h:43
int msg_new
Number of new messages.
Definition: mailbox.h:94
bool deleted
Email is deleted.
Definition: email.h:45
void mbox_reset_atime(struct Mailbox *m, struct stat *st)
Reset the access time on the mailbox file.
Definition: mbox.c:843
int mutt_append_message(struct Mailbox *dest, struct Mailbox *src, struct Email *e, CopyMessageFlags cmflags, CopyHeaderFlags chflags)
Append a message.
Definition: copy.c:880
struct Mailbox * mx_path_resolve(const char *path)
Get a Mailbox for a path.
Definition: mx.c:1603
bool changed
Mailbox has been modified.
Definition: mailbox.h:113
void ctx_free(struct Context **ptr)
Free a Context.
Definition: context.c:49
bool C_KeepFlagged
Config: Don&#39;t move flagged messages from C_Spoolfile to C_Mbox.
Definition: mx.c:82
bool mutt_buffer_is_empty(const struct Buffer *buf)
Is the Buffer empty?
Definition: buffer.c:252
&#39;IMAP&#39; Mailbox type
Definition: mailbox.h:52
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:615
static bool mutt_is_spool(const char *str)
Is this the spoolfile?
Definition: mx.c:154
QuadOption
Possible values for a quad-option.
Definition: quad.h:36
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_mbox_sync()

int mx_mbox_sync ( struct Mailbox m,
int *  index_hint 
)

Save changes to mailbox.

Parameters
[in]mMailbox
[out]index_hintCurrently selected Email
Return values
0Success
-1Error

Definition at line 875 of file mx.c.

876 {
877  if (!m)
878  return -1;
879 
880  int rc;
881  int purge = 1;
882  int msgcount, deleted;
883 
884  if (m->dontwrite)
885  {
886  char buf[256], tmp[256];
887  if (km_expand_key(buf, sizeof(buf), km_find_func(MENU_MAIN, OP_TOGGLE_WRITE)))
888  snprintf(tmp, sizeof(tmp), _(" Press '%s' to toggle write"), buf);
889  else
890  mutt_str_strfcpy(tmp, _("Use 'toggle-write' to re-enable write"), sizeof(tmp));
891 
892  mutt_error(_("Mailbox is marked unwritable. %s"), tmp);
893  return -1;
894  }
895  else if (m->readonly)
896  {
897  mutt_error(_("Mailbox is read-only"));
898  return -1;
899  }
900 
901  if (!m->changed && (m->msg_deleted == 0))
902  {
903  if (!m->quiet)
904  mutt_message(_("Mailbox is unchanged"));
905  return 0;
906  }
907 
908  if (m->msg_deleted != 0)
909  {
910  char buf[128];
911 
912  snprintf(buf, sizeof(buf),
913  ngettext("Purge %d deleted message?", "Purge %d deleted messages?", m->msg_deleted),
914  m->msg_deleted);
915  purge = query_quadoption(C_Delete, buf);
916  if (purge == MUTT_ABORT)
917  return -1;
918  if (purge == MUTT_NO)
919  {
920  if (!m->changed)
921  return 0; /* nothing to do! */
922  /* let IMAP servers hold on to D flags */
923  if (m->magic != MUTT_IMAP)
924  {
925  for (int i = 0; i < m->msg_count; i++)
926  {
927  struct Email *e = m->emails[i];
928  if (!e)
929  break;
930  e->deleted = false;
931  e->purge = false;
932  }
933  m->msg_deleted = 0;
934  }
935  }
937  }
938 
939  /* really only for IMAP - imap_sync_mailbox results in a call to
940  * ctx_update_tables, so m->msg_deleted is 0 when it comes back */
941  msgcount = m->msg_count;
942  deleted = m->msg_deleted;
943 
944  if (purge && (m->msg_deleted != 0) && (mutt_str_strcmp(mailbox_path(m), C_Trash) != 0))
945  {
946  if (trash_append(m) != 0)
947  return -1;
948  }
949 
950 #ifdef USE_IMAP
951  if (m->magic == MUTT_IMAP)
952  rc = imap_sync_mailbox(m, purge, false);
953  else
954 #endif
955  rc = sync_mailbox(m, index_hint);
956  if (rc == 0)
957  {
958 #ifdef USE_IMAP
959  if ((m->magic == MUTT_IMAP) && !purge)
960  {
961  if (!m->quiet)
962  mutt_message(_("Mailbox checkpointed"));
963  }
964  else
965 #endif
966  {
967  if (!m->quiet)
968  mutt_message(_("%d kept, %d deleted"), msgcount - deleted, deleted);
969  }
970 
971  mutt_sleep(0);
972 
973  if ((m->msg_count == m->msg_deleted) &&
974  ((m->magic == MUTT_MBOX) || (m->magic == MUTT_MMDF)) &&
976  {
977  unlink(mailbox_path(m));
979  return 0;
980  }
981 
982  /* if we haven't deleted any messages, we don't need to resort */
983  /* ... except for certain folder formats which need "unsorted"
984  * sort order in order to synchronize folders.
985  *
986  * MH and maildir are safe. mbox-style seems to need re-sorting,
987  * at least with the new threading code. */
988  if (purge || ((m->magic != MUTT_MAILDIR) && (m->magic != MUTT_MH)))
989  {
990  /* IMAP does this automatically after handling EXPUNGE */
991  if (m->magic != MUTT_IMAP)
992  {
995  }
996  }
997  }
998 
999  return rc;
1000 }
struct Email ** emails
Array of Emails.
Definition: mailbox.h:98
static const char * mailbox_path(const struct Mailbox *m)
Get the Mailbox&#39;s path string.
Definition: mailbox.h:191
int msg_count
Total number of messages.
Definition: mailbox.h:90
The envelope/body of an email.
Definition: email.h:37
Clear the &#39;last-tagged&#39; pointer.
Definition: mailbox.h:173
Update internal tables.
Definition: mailbox.h:172
int msg_deleted
Number of deleted messages.
Definition: mailbox.h:95
User aborted the question (with Ctrl-G)
Definition: quad.h:38
enum QuadOption query_quadoption(enum QuadOption opt, const char *prompt)
Ask the user a quad-question.
Definition: init.c:3360
#define mutt_message(...)
Definition: logging.h:83
static int trash_append(struct Mailbox *m)
move deleted mails to the trash folder
Definition: mx.c:478
WHERE unsigned char C_Delete
Config: Really delete messages, when the mailbox is closed.
Definition: globals.h:180
WHERE bool C_SaveEmpty
Config: (mbox,mmdf) Preserve empty mailboxes.
Definition: globals.h:249
#define _(a)
Definition: message.h:28
Index panel (list of emails)
Definition: keymap.h:77
int imap_sync_mailbox(struct Mailbox *m, bool expunge, bool close)
Sync all the changes to the server.
Definition: imap.c:1634
char * C_Trash
Config: Folder to put deleted emails.
Definition: mx.c:85
void mutt_sleep(short s)
Sleep for a while.
Definition: muttlib.c:1545
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
bool readonly
Don&#39;t allow changes to the mailbox.
Definition: mailbox.h:118
void mx_fastclose_mailbox(struct Mailbox *m)
free up memory associated with the Mailbox
Definition: mx.c:412
&#39;Maildir&#39; Mailbox type
Definition: mailbox.h:50
struct Keymap * km_find_func(enum MenuType menu, int func)
Find a function&#39;s mapping in a Menu.
Definition: keymap.c:854
Email list needs resorting.
Definition: mailbox.h:171
User answered &#39;No&#39;, or assume &#39;No&#39;.
Definition: quad.h:39
int km_expand_key(char *s, size_t len, struct Keymap *map)
Get the key string bound to a Keymap.
Definition: keymap.c:826
bool dontwrite
Don&#39;t write the mailbox on close.
Definition: mailbox.h:114
&#39;mmdf&#39; Mailbox type
Definition: mailbox.h:48
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:750
&#39;MH&#39; Mailbox type
Definition: mailbox.h:49
bool quiet
Inhibit status messages?
Definition: mailbox.h:117
bool purge
Skip trash folder when deleting.
Definition: email.h:46
&#39;mbox&#39; Mailbox type
Definition: mailbox.h:47
static int sync_mailbox(struct Mailbox *m, int *index_hint)
save changes to disk
Definition: mx.c:451
bool deleted
Email is deleted.
Definition: email.h:45
#define mutt_error(...)
Definition: logging.h:84
bool changed
Mailbox has been modified.
Definition: mailbox.h:113
&#39;IMAP&#39; Mailbox type
Definition: mailbox.h:52
void mailbox_changed(struct Mailbox *m, enum NotifyMailbox action)
Notify observers of a change to a Mailbox.
Definition: mailbox.c:171
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:615
static bool mutt_is_spool(const char *str)
Is this the spoolfile?
Definition: mx.c:154
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_msg_open_new()

struct Message* mx_msg_open_new ( struct Mailbox m,
struct Email e,
MsgOpenFlags  flags 
)

Open a new message.

Parameters
mDestination mailbox
eMessage being copied (required for maildir support, because the filename depends on the message flags)
flagsFlags, see MsgOpenFlags
Return values
ptrNew Message

Definition at line 1009 of file mx.c.

1010 {
1011  if (!m)
1012  return NULL;
1013 
1014  struct Address *p = NULL;
1015  struct Message *msg = NULL;
1016 
1017  if (!m->mx_ops || !m->mx_ops->msg_open_new)
1018  {
1019  mutt_debug(LL_DEBUG1, "function unimplemented for mailbox type %d\n", m->magic);
1020  return NULL;
1021  }
1022 
1023  msg = mutt_mem_calloc(1, sizeof(struct Message));
1024  msg->write = true;
1025 
1026  if (e)
1027  {
1028  msg->flags.flagged = e->flagged;
1029  msg->flags.replied = e->replied;
1030  msg->flags.read = e->read;
1031  msg->flags.draft = (flags & MUTT_SET_DRAFT);
1032  msg->received = e->received;
1033  }
1034 
1035  if (msg->received == 0)
1036  msg->received = mutt_date_epoch();
1037 
1038  if (m->mx_ops->msg_open_new(m, msg, e) == 0)
1039  {
1040  if (m->magic == MUTT_MMDF)
1041  fputs(MMDF_SEP, msg->fp);
1042 
1043  if (((m->magic == MUTT_MBOX) || (m->magic == MUTT_MMDF)) && (flags & MUTT_ADD_FROM))
1044  {
1045  if (e)
1046  {
1047  p = TAILQ_FIRST(&e->env->return_path);
1048  if (!p)
1049  p = TAILQ_FIRST(&e->env->sender);
1050  if (!p)
1051  p = TAILQ_FIRST(&e->env->from);
1052  }
1053 
1054  char buf[64] = { 0 };
1055  mutt_date_localtime_format(buf, sizeof(buf), "%a %b %e %H:%M:%S %Y\n", msg->received);
1056  fprintf(msg->fp, "From %s %s", p ? p->mailbox : NONULL(Username), buf);
1057  }
1058  }
1059  else
1060  FREE(&msg);
1061 
1062  return msg;
1063 }
time_t mutt_date_epoch(void)
Return the number of seconds since the Unix epoch.
Definition: date.c:411
WHERE char * Username
User&#39;s login name.
Definition: globals.h:52
#define NONULL(x)
Definition: string2.h:37
void * mutt_mem_calloc(size_t nmemb, size_t size)
Allocate zeroed memory on the heap.
Definition: memory.c:50
size_t mutt_date_localtime_format(char *buf, size_t buflen, const char *format, time_t t)
Format localtime.
Definition: date.c:774
#define TAILQ_FIRST(head)
Definition: queue.h:716
bool replied
Definition: mx.h:91
An email address.
Definition: address.h:34
char * mailbox
Mailbox and host address.
Definition: address.h:37
#define MUTT_SET_DRAFT
set the message draft flag
Definition: mx.h:65
int(* msg_open_new)(struct Mailbox *m, struct Message *msg, struct Email *e)
Open a new message in a Mailbox.
Definition: mx.h:189
bool read
Email is read.
Definition: email.h:51
struct AddressList from
Email&#39;s &#39;From&#39; list.
Definition: envelope.h:57
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
struct Envelope * env
Envelope information.
Definition: email.h:89
bool flagged
Definition: mx.h:90
A local copy of an email.
Definition: mx.h:81
struct Message::@0 flags
&#39;mmdf&#39; Mailbox type
Definition: mailbox.h:48
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
bool draft
Definition: mx.h:92
&#39;mbox&#39; Mailbox type
Definition: mailbox.h:47
bool write
nonzero if message is open for writing
Definition: mx.h:86
struct AddressList return_path
Return path for the Email.
Definition: envelope.h:56
Log at debug level 1.
Definition: logging.h:40
bool flagged
Marked important?
Definition: email.h:43
bool replied
Email has been replied to.
Definition: email.h:54
FILE * fp
pointer to the message data
Definition: mx.h:83
#define FREE(x)
Definition: memory.h:40
time_t received
the time at which this message was received
Definition: mx.h:94
struct AddressList sender
Email&#39;s sender.
Definition: envelope.h:61
#define mutt_debug(LEVEL,...)
Definition: logging.h:81
bool read
Definition: mx.h:89
#define MUTT_ADD_FROM
add a From_ line
Definition: mx.h:64
time_t received
Time when the message was placed in the mailbox.
Definition: email.h:82
#define MMDF_SEP
Definition: mbox.h:60
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_mbox_check()

int mx_mbox_check ( struct Mailbox m,
int *  index_hint 
)

Check for new mail - Wrapper for MxOps::mbox_check()

Parameters
mMailbox
index_hintCurrent email
Return values
>0Success, e.g. MUTT_NEW_MAIL
0Success, no change
-1Failure

Definition at line 1073 of file mx.c.

1074 {
1075  if (!m || !m->mx_ops)
1076  return -1;
1077 
1078  int rc = m->mx_ops->mbox_check(m, index_hint);
1079  if ((rc == MUTT_NEW_MAIL) || (rc == MUTT_REOPENED))
1081 
1082  return rc;
1083 }
Email list was changed.
Definition: mailbox.h:170
int(* mbox_check)(struct Mailbox *m, int *index_hint)
Check for new mail.
Definition: mx.h:147
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
New mail received in Mailbox.
Definition: mx.h:72
Mailbox was reopened.
Definition: mx.h:74
void mailbox_changed(struct Mailbox *m, enum NotifyMailbox action)
Notify observers of a change to a Mailbox.
Definition: mailbox.c:171
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_msg_open()

struct Message* mx_msg_open ( struct Mailbox m,
int  msgno 
)

return a stream pointer for a message

Parameters
mMailbox
msgnoMessage number
Return values
ptrMessage
NULLError

Definition at line 1092 of file mx.c.

1093 {
1094  if (!m)
1095  return NULL;
1096 
1097  struct Message *msg = NULL;
1098 
1099  if (!m->mx_ops || !m->mx_ops->msg_open)
1100  {
1101  mutt_debug(LL_DEBUG1, "function not implemented for mailbox type %d\n", m->magic);
1102  return NULL;
1103  }
1104 
1105  msg = mutt_mem_calloc(1, sizeof(struct Message));
1106  if (m->mx_ops->msg_open(m, msg, msgno) < 0)
1107  FREE(&msg);
1108 
1109  return msg;
1110 }
void * mutt_mem_calloc(size_t nmemb, size_t size)
Allocate zeroed memory on the heap.
Definition: memory.c:50
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
A local copy of an email.
Definition: mx.h:81
int(* msg_open)(struct Mailbox *m, struct Message *msg, int msgno)
Open an email message in a Mailbox.
Definition: mx.h:180
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
Log at debug level 1.
Definition: logging.h:40
#define FREE(x)
Definition: memory.h:40
#define mutt_debug(LEVEL,...)
Definition: logging.h:81
+ Here is the caller graph for this function:

◆ mx_msg_commit()

int mx_msg_commit ( struct Mailbox m,
struct Message msg 
)

Commit a message to a folder - Wrapper for MxOps::msg_commit()

Parameters
mMailbox
msgMessage to commit
Return values
0Success
-1Failure

Definition at line 1119 of file mx.c.

1120 {
1121  if (!m || !m->mx_ops || !m->mx_ops->msg_commit)
1122  return -1;
1123 
1124  if (!(msg->write && m->append))
1125  {
1126  mutt_debug(LL_DEBUG1, "msg->write = %d, m->append = %d\n", msg->write, m->append);
1127  return -1;
1128  }
1129 
1130  return m->mx_ops->msg_commit(m, msg);
1131 }
int(* msg_commit)(struct Mailbox *m, struct Message *msg)
Save changes to an email.
Definition: mx.h:197
bool append
Mailbox is opened in append mode.
Definition: mailbox.h:112
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
bool write
nonzero if message is open for writing
Definition: mx.h:86
Log at debug level 1.
Definition: logging.h:40
#define mutt_debug(LEVEL,...)
Definition: logging.h:81
+ Here is the caller graph for this function:

◆ mx_msg_close()

int mx_msg_close ( struct Mailbox m,
struct Message **  msg 
)

Close a message.

Parameters
[in]mMailbox
[out]msgMessage to close
Return values
0Success
-1Failure

Definition at line 1140 of file mx.c.

1141 {
1142  if (!m || !msg || !*msg)
1143  return 0;
1144 
1145  int rc = 0;
1146 
1147  if (m->mx_ops && m->mx_ops->msg_close)
1148  rc = m->mx_ops->msg_close(m, *msg);
1149 
1150  if ((*msg)->path)
1151  {
1152  mutt_debug(LL_DEBUG1, "unlinking %s\n", (*msg)->path);
1153  unlink((*msg)->path);
1154  FREE(&(*msg)->path);
1155  }
1156 
1157  FREE(&(*msg)->committed_path);
1158  FREE(msg);
1159  return rc;
1160 }
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
Log at debug level 1.
Definition: logging.h:40
#define FREE(x)
Definition: memory.h:40
int(* msg_close)(struct Mailbox *m, struct Message *msg)
Close an email.
Definition: mx.h:205
#define mutt_debug(LEVEL,...)
Definition: logging.h:81
+ Here is the caller graph for this function:

◆ mx_alloc_memory()

void mx_alloc_memory ( struct Mailbox m)

Create storage for the emails.

Parameters
mMailbox

Definition at line 1166 of file mx.c.

1167 {
1168  size_t s = MAX(sizeof(struct Email *), sizeof(int));
1169 
1170  if ((m->email_max + 25) * s < m->email_max * s)
1171  {
1172  mutt_error(_("Out of memory"));
1173  mutt_exit(1);
1174  }
1175 
1176  m->email_max += 25;
1177  if (m->emails)
1178  {
1179  mutt_mem_realloc(&m->emails, sizeof(struct Email *) * m->email_max);
1180  mutt_mem_realloc(&m->v2r, sizeof(int) * m->email_max);
1181  }
1182  else
1183  {
1184  m->emails = mutt_mem_calloc(m->email_max, sizeof(struct Email *));
1185  m->v2r = mutt_mem_calloc(m->email_max, sizeof(int));
1186  }
1187  for (int i = m->email_max - 25; i < m->email_max; i++)
1188  {
1189  m->emails[i] = NULL;
1190  m->v2r[i] = -1;
1191  }
1192 }
struct Email ** emails
Array of Emails.
Definition: mailbox.h:98
void * mutt_mem_calloc(size_t nmemb, size_t size)
Allocate zeroed memory on the heap.
Definition: memory.c:50
The envelope/body of an email.
Definition: email.h:37
#define _(a)
Definition: message.h:28
#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:114
int email_max
Number of pointers in emails.
Definition: mailbox.h:99
void mutt_exit(int code)
Leave NeoMutt NOW.
Definition: main.c:207
int * v2r
Mapping from virtual to real msgno.
Definition: mailbox.h:100
#define mutt_error(...)
Definition: logging.h:84
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_check_empty()

int mx_check_empty ( const char *  path)

Is the mailbox empty.

Parameters
pathMailbox to check
Return values
1Mailbox is empty
0Mailbox contains mail
-1Error

Definition at line 1201 of file mx.c.

1202 {
1203  switch (mx_path_probe(path, NULL))
1204  {
1205  case MUTT_MBOX:
1206  case MUTT_MMDF:
1207  return mutt_file_check_empty(path);
1208  case MUTT_MH:
1209  return mh_check_empty(path);
1210  case MUTT_MAILDIR:
1211  return maildir_check_empty(path);
1212 #ifdef USE_IMAP
1213  case MUTT_IMAP:
1214  {
1215  int rc = imap_path_status(path, false);
1216  if (rc < 0)
1217  return -1;
1218  if (rc == 0)
1219  return 1;
1220  return 0;
1221  }
1222 #endif
1223  default:
1224  errno = EINVAL;
1225  return -1;
1226  }
1227  /* not reached */
1228 }
int imap_path_status(const char *path, bool queue)
Refresh the number of total and new messages.
Definition: imap.c:1310
&#39;Maildir&#39; Mailbox type
Definition: mailbox.h:50
&#39;mmdf&#39; Mailbox type
Definition: mailbox.h:48
&#39;MH&#39; Mailbox type
Definition: mailbox.h:49
&#39;mbox&#39; Mailbox type
Definition: mailbox.h:47
int maildir_check_empty(const char *path)
Is the mailbox empty.
Definition: shared.c:1564
int mutt_file_check_empty(const char *path)
Is the mailbox empty.
Definition: file.c:1403
enum MailboxType mx_path_probe(const char *path, struct stat *st)
Find a mailbox that understands a path.
Definition: mx.c:1288
&#39;IMAP&#39; Mailbox type
Definition: mailbox.h:52
char * path
path to temp file
Definition: mx.h:84
int mh_check_empty(const char *path)
Is mailbox empty.
Definition: shared.c:1604
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_tags_edit()

int mx_tags_edit ( struct Mailbox m,
const char *  tags,
char *  buf,
size_t  buflen 
)

start the tag editor of the mailbox

Parameters
mMailbox
tagsExisting tags
bufBuffer for the results
buflenLength of the buffer
Return values
-1Error
0No valid user input
1Buffer set

Definition at line 1240 of file mx.c.

1241 {
1242  if (!m)
1243  return -1;
1244 
1245  if (m->mx_ops->tags_edit)
1246  return m->mx_ops->tags_edit(m, tags, buf, buflen);
1247 
1248  mutt_message(_("Folder doesn't support tagging, aborting"));
1249  return -1;
1250 }
#define mutt_message(...)
Definition: logging.h:83
#define _(a)
Definition: message.h:28
int(* tags_edit)(struct Mailbox *m, const char *tags, char *buf, size_t buflen)
Prompt and validate new messages tags.
Definition: mx.h:230
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
+ Here is the caller graph for this function:

◆ mx_tags_commit()

int mx_tags_commit ( struct Mailbox m,
struct Email e,
char *  tags 
)

Save tags to the Mailbox - Wrapper for MxOps::tags_commit()

Parameters
mMailbox
eEmail
tagsTags to save
Return values
0Success
-1Failure

Definition at line 1260 of file mx.c.

1261 {
1262  if (!m)
1263  return -1;
1264 
1265  if (m->mx_ops->tags_commit)
1266  return m->mx_ops->tags_commit(m, e, tags);
1267 
1268  mutt_message(_("Folder doesn't support tagging, aborting"));
1269  return -1;
1270 }
#define mutt_message(...)
Definition: logging.h:83
#define _(a)
Definition: message.h:28
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
int(* tags_commit)(struct Mailbox *m, struct Email *e, char *buf)
Save the tags to a message.
Definition: mx.h:239
+ Here is the caller graph for this function:

◆ mx_tags_is_supported()

bool mx_tags_is_supported ( struct Mailbox m)

return true if mailbox support tagging

Parameters
mMailbox
Return values
trueTagging is supported

Definition at line 1277 of file mx.c.

1278 {
1279  return m && m->mx_ops->tags_commit && m->mx_ops->tags_edit;
1280 }
int(* tags_edit)(struct Mailbox *m, const char *tags, char *buf, size_t buflen)
Prompt and validate new messages tags.
Definition: mx.h:230
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
int(* tags_commit)(struct Mailbox *m, struct Email *e, char *buf)
Save the tags to a message.
Definition: mx.h:239
+ Here is the caller graph for this function:

◆ mx_path_probe()

enum MailboxType mx_path_probe ( const char *  path,
struct stat *  st 
)

Find a mailbox that understands a path.

Parameters
[in]pathPath to examine
[out]ststat buffer (OPTIONAL, for local mailboxes)
Return values
numType, e.g. MUTT_IMAP

Definition at line 1288 of file mx.c.

1289 {
1290  if (!path)
1291  return MUTT_UNKNOWN;
1292 
1293  static const struct MxOps *no_stat[] = {
1294 #ifdef USE_IMAP
1295  &MxImapOps,
1296 #endif
1297 #ifdef USE_NOTMUCH
1298  &MxNotmuchOps,
1299 #endif
1300 #ifdef USE_POP
1301  &MxPopOps,
1302 #endif
1303 #ifdef USE_NNTP
1304  &MxNntpOps,
1305 #endif
1306  };
1307 
1308  static const struct MxOps *with_stat[] = {
1310 #ifdef USE_COMPRESSED
1311  &MxCompOps,
1312 #endif
1313  };
1314 
1315  enum MailboxType rc;
1316 
1317  for (size_t i = 0; i < mutt_array_size(no_stat); i++)
1318  {
1319  rc = no_stat[i]->path_probe(path, NULL);
1320  if (rc != MUTT_UNKNOWN)
1321  return rc;
1322  }
1323 
1324  struct stat st2 = { 0 };
1325  if (!st)
1326  st = &st2;
1327 
1328  if (stat(path, st) != 0)
1329  {
1330  mutt_debug(LL_DEBUG1, "unable to stat %s: %s (errno %d)\n", path, strerror(errno), errno);
1331  return MUTT_UNKNOWN;
1332  }
1333 
1334  for (size_t i = 0; i < mutt_array_size(with_stat); i++)
1335  {
1336  rc = with_stat[i]->path_probe(path, st);
1337  if (rc != MUTT_UNKNOWN)
1338  return rc;
1339  }
1340 
1341  return rc;
1342 }
struct MxOps MxMhOps
MH Mailbox - Implements MxOps.
Definition: mh.c:814
enum MailboxType(* path_probe)(const char *path, const struct stat *st)
Does this Mailbox type recognise this path?
Definition: mx.h:246
struct MxOps MxMaildirOps
Maildir Mailbox - Implements MxOps.
Definition: maildir.c:704
Mailbox wasn&#39;t recognised.
Definition: mailbox.h:46
struct MxOps MxPopOps
POP Mailbox - Implements MxOps.
Definition: pop.c:1284
struct MxOps MxMboxOps
Mbox Mailbox - Implements MxOps.
Definition: mbox.c:1848
#define mutt_array_size(x)
Definition: memory.h:33
struct MxOps MxCompOps
Compressed Mailbox - Implements MxOps.
Definition: compress.c:936
struct MxOps MxImapOps
IMAP Mailbox - Implements MxOps.
Definition: imap.c:2554
struct MxOps MxNntpOps
NNTP Mailbox - Implements MxOps.
Definition: nntp.c:2883
struct MxOps MxMmdfOps
MMDF Mailbox - Implements MxOps.
Definition: mbox.c:1876
MailboxType
Supported mailbox formats.
Definition: mailbox.h:42
Log at debug level 1.
Definition: logging.h:40
#define mutt_debug(LEVEL,...)
Definition: logging.h:81
char * path
path to temp file
Definition: mx.h:84
The Mailbox API.
Definition: mx.h:103
struct MxOps MxNotmuchOps
Notmuch Mailbox - Implements MxOps.
+ Here is the caller graph for this function:

◆ mx_path_canon()

int mx_path_canon ( char *  buf,
size_t  buflen,
const char *  folder,
enum MailboxType magic 
)

Canonicalise a mailbox path - Wrapper for MxOps::path_canon()

Definition at line 1347 of file mx.c.

1348 {
1349  if (!buf)
1350  return -1;
1351 
1352  for (size_t i = 0; i < 3; i++)
1353  {
1354  /* Look for !! ! - < > or ^ followed by / or NUL */
1355  if ((buf[0] == '!') && (buf[1] == '!'))
1356  {
1357  if (((buf[2] == '/') || (buf[2] == '\0')))
1358  {
1359  mutt_str_inline_replace(buf, buflen, 2, LastFolder);
1360  }
1361  }
1362  else if ((buf[0] == '+') || (buf[0] == '='))
1363  {
1364  size_t folder_len = mutt_str_strlen(folder);
1365  if ((folder_len > 0) && (folder[folder_len - 1] != '/'))
1366  {
1367  buf[0] = '/';
1368  mutt_str_inline_replace(buf, buflen, 0, folder);
1369  }
1370  else
1371  {
1372  mutt_str_inline_replace(buf, buflen, 1, folder);
1373  }
1374  }
1375  else if ((buf[1] == '/') || (buf[1] == '\0'))
1376  {
1377  if (buf[0] == '!')
1378  {
1379  mutt_str_inline_replace(buf, buflen, 1, C_Spoolfile);
1380  }
1381  else if (buf[0] == '-')
1382  {
1383  mutt_str_inline_replace(buf, buflen, 1, LastFolder);
1384  }
1385  else if (buf[0] == '<')
1386  {
1387  mutt_str_inline_replace(buf, buflen, 1, C_Record);
1388  }
1389  else if (buf[0] == '>')
1390  {
1391  mutt_str_inline_replace(buf, buflen, 1, C_Mbox);
1392  }
1393  else if (buf[0] == '^')
1394  {
1395  mutt_str_inline_replace(buf, buflen, 1, CurrentFolder);
1396  }
1397  else if (buf[0] == '~')
1398  {
1399  mutt_str_inline_replace(buf, buflen, 1, HomeDir);
1400  }
1401  }
1402  else if (buf[0] == '@')
1403  {
1404  /* elm compatibility, @ expands alias to user name */
1405  struct AddressList *al = mutt_alias_lookup(buf + 1);
1406  if (TAILQ_EMPTY(al))
1407  break;
1408 
1409  struct Email *e = email_new();
1410  e->env = mutt_env_new();
1411  mutt_addrlist_copy(&e->env->from, al, false);
1412  mutt_addrlist_copy(&e->env->to, al, false);
1413  mutt_default_save(buf, buflen, e);
1414  email_free(&e);
1415  break;
1416  }
1417  else
1418  {
1419  break;
1420  }
1421  }
1422 
1423  // if (!folder) //XXX - use inherited version, or pass NULL to backend?
1424  // return -1;
1425 
1426  enum MailboxType magic2 = mx_path_probe(buf, NULL);
1427  if (magic)
1428  *magic = magic2;
1429  const struct MxOps *ops = mx_get_ops(magic2);
1430  if (!ops || !ops->path_canon)
1431  return -1;
1432 
1433  if (ops->path_canon(buf, buflen) < 0)
1434  {
1435  mutt_path_canon(buf, buflen, HomeDir);
1436  }
1437 
1438  return 0;
1439 }
struct AddressList * mutt_alias_lookup(const char *s)
Find an Alias.
Definition: alias.c:285
The envelope/body of an email.
Definition: email.h:37
void mutt_addrlist_copy(struct AddressList *dst, const struct AddressList *src, bool prune)
Copy a list of addresses into another list.
Definition: address.c:728
WHERE char * LastFolder
Previously selected mailbox.
Definition: globals.h:55
size_t mutt_str_strlen(const char *a)
Calculate the length of a string, safely.
Definition: string.c:666
WHERE char * C_Record
Config: Folder to save &#39;sent&#39; messages.
Definition: globals.h:131
void mutt_default_save(char *path, size_t pathlen, struct Email *e)
Find the default save path for an email.
Definition: hook.c:656
int(* path_canon)(char *buf, size_t buflen)
Canonicalise a Mailbox path.
Definition: mx.h:254
struct AddressList from
Email&#39;s &#39;From&#39; list.
Definition: envelope.h:57
WHERE char * C_Mbox
Config: Folder that receives read emails (see Move)
Definition: globals.h:117
struct Envelope * env
Envelope information.
Definition: email.h:89
WHERE char * HomeDir
User&#39;s home directory.
Definition: globals.h:49
WHERE char * CurrentFolder
Currently selected mailbox.
Definition: globals.h:54
struct Envelope * mutt_env_new(void)
Create a new Envelope.
Definition: envelope.c:42
bool mutt_path_canon(char *buf, size_t buflen, const char *homedir)
Create the canonical version of a path.
Definition: path.c:221
MailboxType
Supported mailbox formats.
Definition: mailbox.h:42
WHERE char * C_Spoolfile
Config: Inbox.
Definition: globals.h:144
const struct MxOps * mx_get_ops(enum MailboxType magic)
Get mailbox operations.
Definition: mx.c:140
struct AddressList to
Email&#39;s &#39;To&#39; list.
Definition: envelope.h:58
struct Email * email_new(void)
Create a new Email.
Definition: email.c:68
bool mutt_str_inline_replace(char *buf, size_t buflen, size_t xlen, const char *rstr)
Replace the beginning of a string.
Definition: string.c:1070
#define TAILQ_EMPTY(head)
Definition: queue.h:714
void email_free(struct Email **ptr)
Free an Email.
Definition: email.c:41
enum MailboxType mx_path_probe(const char *path, struct stat *st)
Find a mailbox that understands a path.
Definition: mx.c:1288
The Mailbox API.
Definition: mx.h:103
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_path_canon2()

int mx_path_canon2 ( struct Mailbox m,
const char *  folder 
)

Canonicalise the path to realpath.

Parameters
mMailbox
folderPath to canonicalise
Return values
0Success
-1Failure

Definition at line 1448 of file mx.c.

1449 {
1450  if (!m)
1451  return -1;
1452 
1453  char buf[PATH_MAX];
1454 
1455  if (m->realpath)
1456  mutt_str_strfcpy(buf, m->realpath, sizeof(buf));
1457  else
1458  mutt_str_strfcpy(buf, mailbox_path(m), sizeof(buf));
1459 
1460  int rc = mx_path_canon(buf, sizeof(buf), folder, &m->magic);
1461 
1462  mutt_str_replace(&m->realpath, buf);
1463 
1464  if (rc >= 0)
1465  {
1466  m->mx_ops = mx_get_ops(m->magic);
1468  }
1469 
1470  return rc;
1471 }
static const char * mailbox_path(const struct Mailbox *m)
Get the Mailbox&#39;s path string.
Definition: mailbox.h:191
int mx_path_canon(char *buf, size_t buflen, const char *folder, enum MailboxType *magic)
Canonicalise a mailbox path - Wrapper for MxOps::path_canon()
Definition: mx.c:1347
char * realpath
Used for duplicate detection, context comparison, and the sidebar.
Definition: mailbox.h:83
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
#define PATH_MAX
Definition: mutt.h:50
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:750
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
void mutt_str_replace(char **p, const char *s)
Replace one string with another.
Definition: string.c:453
size_t mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:312
const struct MxOps * mx_get_ops(enum MailboxType magic)
Get mailbox operations.
Definition: mx.c:140
struct Buffer pathbuf
Definition: mailbox.h:82
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_path_pretty()

int mx_path_pretty ( char *  buf,
size_t  buflen,
const char *  folder 
)

Abbreviate a mailbox path - Wrapper for MxOps::path_pretty()

Definition at line 1476 of file mx.c.

1477 {
1478  enum MailboxType magic = mx_path_probe(buf, NULL);
1479  const struct MxOps *ops = mx_get_ops(magic);
1480  if (!ops)
1481  return -1;
1482 
1483  if (!ops->path_canon)
1484  return -1;
1485 
1486  if (ops->path_canon(buf, buflen) < 0)
1487  return -1;
1488 
1489  if (!ops->path_pretty)
1490  return -1;
1491 
1492  if (ops->path_pretty(buf, buflen, folder) < 0)
1493  return -1;
1494 
1495  return 0;
1496 }
int(* path_canon)(char *buf, size_t buflen)
Canonicalise a Mailbox path.
Definition: mx.h:254
enum MailboxType magic
Mailbox type, e.g. MUTT_IMAP.
Definition: mx.h:105
MailboxType
Supported mailbox formats.
Definition: mailbox.h:42
const struct MxOps * mx_get_ops(enum MailboxType magic)
Get mailbox operations.
Definition: mx.c:140
int(* path_pretty)(char *buf, size_t buflen, const char *folder)
Abbreviate a Mailbox path.
Definition: mx.h:263
enum MailboxType mx_path_probe(const char *path, struct stat *st)
Find a mailbox that understands a path.
Definition: mx.c:1288
The Mailbox API.
Definition: mx.h:103
+ Here is the call graph for this function:

◆ mx_path_parent()

int mx_path_parent ( char *  buf,
size_t  buflen 
)

Find the parent of a mailbox path - Wrapper for MxOps::path_parent()

Definition at line 1501 of file mx.c.

1502 {
1503  if (!buf)
1504  return -1;
1505 
1506  return 0;
1507 }

◆ mx_msg_padding_size()

int mx_msg_padding_size ( struct Mailbox m)

Bytes of padding between messages - Wrapper for MxOps::msg_padding_size()

Parameters
mMailbox
Return values
numNumber of bytes of padding

mmdf and mbox add separators, which leads a small discrepancy when computing vsize for a limited view.

Definition at line 1517 of file mx.c.

1518 {
1519  if (!m || !m->mx_ops || !m->mx_ops->msg_padding_size)
1520  return 0;
1521 
1522  return m->mx_ops->msg_padding_size(m);
1523 }
int(* msg_padding_size)(struct Mailbox *m)
Bytes of padding between messages.
Definition: mx.h:211
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
+ Here is the caller graph for this function:

◆ mx_ac_find()

struct Account* mx_ac_find ( struct Mailbox m)

Find the Account owning a Mailbox.

Parameters
mMailbox
Return values
ptrAccount
NULLNone found

Definition at line 1531 of file mx.c.

1532 {
1533  if (!m || !m->mx_ops)
1534  return NULL;
1535 
1536  struct Account *np = NULL;
1537  TAILQ_FOREACH(np, &NeoMutt->accounts, entries)
1538  {
1539  if (np->magic != m->magic)
1540  continue;
1541 
1542  if (m->mx_ops->ac_find(np, m->realpath))
1543  return np;
1544  }
1545 
1546  return NULL;
1547 }
#define TAILQ_FOREACH(var, head, field)
Definition: queue.h:718
struct AccountList accounts
List of all Accounts.
Definition: neomutt.h:39
char * realpath
Used for duplicate detection, context comparison, and the sidebar.
Definition: mailbox.h:83
A group of associated Mailboxes.
Definition: account.h:36
Container for Accounts, Notifications.
Definition: neomutt.h:35
enum MailboxType magic
Mailbox type.
Definition: mailbox.h:104
enum MailboxType magic
Type of Mailboxes this Account contains.
Definition: account.h:38
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
struct Account *(* ac_find)(struct Account *a, const char *path)
Find an Account that matches a Mailbox path.
Definition: mx.h:115
+ Here is the caller graph for this function:

◆ mx_mbox_find()

struct Mailbox* mx_mbox_find ( struct Account a,
const char *  path 
)

Find a Mailbox on an Account.

Parameters
aAccount to search
pathPath to find
Return values
ptrMailbox

Definition at line 1555 of file mx.c.

1556 {
1557  if (!a || !path)
1558  return NULL;
1559 
1560  struct MailboxNode *np = NULL;
1561  STAILQ_FOREACH(np, &a->mailboxes, entries)
1562  {
1563  if (mutt_str_strcmp(np->mailbox->realpath, path) == 0)
1564  return np->mailbox;
1565  }
1566 
1567  return NULL;
1568 }
char * realpath
Used for duplicate detection, context comparison, and the sidebar.
Definition: mailbox.h:83
struct MailboxList mailboxes
List of Mailboxes.
Definition: account.h:41
#define STAILQ_FOREACH(var, head, field)
Definition: queue.h:349
List of Mailboxes.
Definition: mailbox.h:144
int mutt_str_strcmp(const char *a, const char *b)
Compare two strings, safely.
Definition: string.c:615
struct Mailbox * mailbox
Mailbox in the list.
Definition: mailbox.h:146
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_mbox_find2()

struct Mailbox* mx_mbox_find2 ( const char *  path)

Find a Mailbox on an Account.

Parameters
pathPath to find
Return values
ptrMailbox
NULLNo match

Definition at line 1576 of file mx.c.

1577 {
1578  if (!path)
1579  return NULL;
1580 
1581  char buf[PATH_MAX];
1582  mutt_str_strfcpy(buf, path, sizeof(buf));
1583  mx_path_canon(buf, sizeof(buf), C_Folder, NULL);
1584 
1585  struct Account *np = NULL;
1586  TAILQ_FOREACH(np, &NeoMutt->accounts, entries)
1587  {
1588  struct Mailbox *m = mx_mbox_find(np, buf);
1589  if (m)
1590  return m;
1591  }
1592 
1593  return NULL;
1594 }
#define TAILQ_FOREACH(var, head, field)
Definition: queue.h:718
struct AccountList accounts
List of all Accounts.
Definition: neomutt.h:39
int mx_path_canon(char *buf, size_t buflen, const char *folder, enum MailboxType *magic)
Canonicalise a mailbox path - Wrapper for MxOps::path_canon()
Definition: mx.c:1347
A group of associated Mailboxes.
Definition: account.h:36
struct Mailbox * mx_mbox_find(struct Account *a, const char *path)
Find a Mailbox on an Account.
Definition: mx.c:1555
Container for Accounts, Notifications.
Definition: neomutt.h:35
WHERE char * C_Folder
Config: Base folder for a set of mailboxes.
Definition: globals.h:119
A mailbox.
Definition: mailbox.h:80
#define PATH_MAX
Definition: mutt.h:50
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:750
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_path_resolve()

struct Mailbox* mx_path_resolve ( const char *  path)

Get a Mailbox for a path.

Parameters
pathMailbox path
Return values
ptrMailbox

If there isn't a Mailbox for the path, one will be created.

Definition at line 1603 of file mx.c.

1604 {
1605  if (!path)
1606  return NULL;
1607 
1608  struct Mailbox *m = mx_mbox_find2(path);
1609  if (m)
1610  return m;
1611 
1612  m = mailbox_new();
1613  m->flags = MB_HIDDEN;
1614  mutt_buffer_strcpy(&m->pathbuf, path);
1616 
1617  return m;
1618 }
int mx_path_canon2(struct Mailbox *m, const char *folder)
Canonicalise the path to realpath.
Definition: mx.c:1448
struct Mailbox * mx_mbox_find2(const char *path)
Find a Mailbox on an Account.
Definition: mx.c:1576
int flags
e.g. MB_NORMAL
Definition: mailbox.h:133
#define MB_HIDDEN
Definition: mailbox.h:37
WHERE char * C_Folder
Config: Base folder for a set of mailboxes.
Definition: globals.h:119
A mailbox.
Definition: mailbox.h:80
size_t mutt_buffer_strcpy(struct Buffer *buf, const char *s)
Copy a string into a Buffer.
Definition: buffer.c:312
struct Mailbox * mailbox_new(void)
Create a new Mailbox.
Definition: mailbox.c:42
struct Buffer pathbuf
Definition: mailbox.h:82
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_ac_add()

int mx_ac_add ( struct Account a,
struct Mailbox m 
)

Add a Mailbox to an Account - Wrapper for MxOps::ac_add()

Definition at line 1623 of file mx.c.

1624 {
1625  if (!a || !m || !m->mx_ops || !m->mx_ops->ac_add)
1626  return -1;
1627 
1628  if (m->mx_ops->ac_add(a, m) < 0)
1629  return -1;
1630 
1631  account_mailbox_add(a, m);
1632  return 0;
1633 }
int(* ac_add)(struct Account *a, struct Mailbox *m)
Add a Mailbox to an Account.
Definition: mx.h:123
bool account_mailbox_add(struct Account *a, struct Mailbox *m)
Add a Mailbox to an Account.
Definition: account.c:67
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mx_ac_remove()

int mx_ac_remove ( struct Mailbox m)

Remove a Mailbox from an Account and delete Account if empty.

Parameters
mMailbox to remove

Definition at line 1639 of file mx.c.

1640 {
1641  if (!m || !m->account)
1642  return -1;
1643 
1644  struct Account *a = m->account;
1646  mailbox_free(&m);
1647  if (STAILQ_EMPTY(&a->mailboxes))
1648  {
1650  }
1651  return 0;
1652 }
struct MailboxList mailboxes
List of Mailboxes.
Definition: account.h:41
A group of associated Mailboxes.
Definition: account.h:36
Container for Accounts, Notifications.
Definition: neomutt.h:35
void mailbox_free(struct Mailbox **ptr)
Free a Mailbox.
Definition: mailbox.c:60
struct Account * account
Account that owns this Mailbox.
Definition: mailbox.h:130
bool account_mailbox_remove(struct Account *a, struct Mailbox *m)
Remove a Mailbox from an Account.
Definition: account.c:95
#define STAILQ_EMPTY(head)
Definition: queue.h:345
bool neomutt_account_remove(struct NeoMutt *n, struct Account *a)
Remove an Account from the global list.
Definition: neomutt.c:105
+ Here is the call graph for this function:

◆ mx_mbox_check_stats()

int mx_mbox_check_stats ( struct Mailbox m,
int  flags 
)

Check the statistics for a mailbox - Wrapper for MxOps::mbox_check_stats()

Definition at line 1657 of file mx.c.

1658 {
1659  if (!m)
1660  return -1;
1661 
1662  return m->mx_ops->mbox_check_stats(m, flags);
1663 }
int(* mbox_check_stats)(struct Mailbox *m, int flags)
Check the Mailbox statistics.
Definition: mx.h:156
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
+ Here is the caller graph for this function:

◆ mx_save_hcache()

int mx_save_hcache ( struct Mailbox m,
struct Email e 
)

Save message to the header cache - Wrapper for MxOps::msg_save_hcache()

Parameters
mMailbox
eEmail
Return values
0Success
-1Failure

Write a single header out to the header cache.

Definition at line 1674 of file mx.c.

1675 {
1676  if (!m->mx_ops || !m->mx_ops->msg_save_hcache)
1677  return 0;
1678 
1679  return m->mx_ops->msg_save_hcache(m, e);
1680 }
int(* msg_save_hcache)(struct Mailbox *m, struct Email *e)
Save message to the header cache.
Definition: mx.h:219
const struct MxOps * mx_ops
MXAPI callback functions.
Definition: mailbox.h:110
+ Here is the caller graph for this function:

Variable Documentation

◆ C_CatchupNewsgroup

unsigned char C_CatchupNewsgroup

Config: (nntp) Mark all articles as read when leaving a newsgroup.

Definition at line 81 of file mx.c.

◆ C_KeepFlagged

bool C_KeepFlagged

Config: Don't move flagged messages from C_Spoolfile to C_Mbox.

Definition at line 82 of file mx.c.

◆ C_MboxType

unsigned char C_MboxType

Config: Default type for creating new mailboxes.

Definition at line 83 of file mx.c.

◆ C_Move

unsigned char C_Move

Config: Move emails from C_Spoolfile to C_Mbox when read.

Definition at line 84 of file mx.c.

◆ C_Trash

char* C_Trash

Config: Folder to put deleted emails.

Definition at line 85 of file mx.c.

◆ MagicMap

struct Mapping MagicMap[]
static
Initial value:
= {
{ "mbox", MUTT_MBOX, },
{ "MMDF", MUTT_MMDF, },
{ "MH", MUTT_MH, },
{ "Maildir", MUTT_MAILDIR, },
{ NULL, 0, },
}
&#39;Maildir&#39; Mailbox type
Definition: mailbox.h:50
&#39;mmdf&#39; Mailbox type
Definition: mailbox.h:48
&#39;MH&#39; Mailbox type
Definition: mailbox.h:49
&#39;mbox&#39; Mailbox type
Definition: mailbox.h:47

Definition at line 88 of file mx.c.

◆ MagicDef

struct EnumDef MagicDef
Initial value:
= {
"mbox_type",
4,
(struct Mapping *) &MagicMap,
}
Mapping between user-readable string and a constant.
Definition: mapping.h:29
static struct Mapping MagicMap[]
Definition: mx.c:88

Definition at line 97 of file mx.c.

◆ mx_ops

const struct MxOps* mx_ops[]
static
Initial value:
= {
NULL,
}
struct MxOps MxMhOps
MH Mailbox - Implements MxOps.
Definition: mh.c:814
struct MxOps MxMaildirOps
Maildir Mailbox - Implements MxOps.
Definition: maildir.c:704
struct MxOps MxPopOps
POP Mailbox - Implements MxOps.
Definition: pop.c:1284
struct MxOps MxMboxOps
Mbox Mailbox - Implements MxOps.
Definition: mbox.c:1848
struct MxOps MxCompOps
Compressed Mailbox - Implements MxOps.
Definition: compress.c:936
struct MxOps MxImapOps
IMAP Mailbox - Implements MxOps.
Definition: imap.c:2554
struct MxOps MxNntpOps
NNTP Mailbox - Implements MxOps.
Definition: nntp.c:2883
struct MxOps MxMmdfOps
MMDF Mailbox - Implements MxOps.
Definition: mbox.c:1876
struct MxOps MxNotmuchOps
Notmuch Mailbox - Implements MxOps.

All the Mailbox backends.

Definition at line 106 of file mx.c.