Commit c08b926f c08b926f664b27953483a0dffcbe381ddaa154e5 by Sergey Poznyakoff

Re-implement MH sequences via mailbox properties.

* libmailutils/mailbox/header.c (mu_header_clear): New function.
(mu_header_sget_value_n): Tolerate pval == NULL.
* libmailutils/property/assocprop.c (_assoc_prop_setval): Bugfix.
(_assoc_prop_clear): New method.
(mu_assoc_property_init): Reference the stream.
(mu_assoc_property_init): Initialize _prop_clear.
* libmailutils/property/create.c (_mu_property_init): Now extern.
* libmailutils/property/propset.c (mu_property_set_value): Null value
means unset.
* libmailutils/tests/prop.at: Test property clear and invalidate.
* libmailutils/tests/prop.c: New commands: 0 for property clear and ! for
invalidate.

* libmailutils/property/mhprop.c: New file.
* libmailutils/property/propclr.c: New file.
* libmailutils/property/propinv.c: New file.
* libmailutils/property/Makefile.am (noinst_LTLIBRARIES): Add new files.

* include/mailutils/header.h (mu_header_clear): New proto.
* include/mailutils/property.h (mu_property_clear)
(mu_property_invalidate): New protos.
(mu_mh_prop): New struct.
(mu_mh_property_init): New proto.
* include/mailutils/sys/property.h (_mu_property) <_prop_clear>: New member.
(_mu_property_init): New proto.
* include/mailutils/mh.h: New file.
* include/mailutils/Makefile.am (pkginclude_HEADERS): Add mh.h

* libproto/mh/profile.c: New file.
* libproto/mh/Makefile.am (libmu_mh_la_SOURCES): Add new files.

* libproto/mh/mbox.c (mh_get_property): New static function.
(_mailbox_mh_init): Set _get_property.

* mh/mh_global.c (current_message, sequences): Remove.  Use mbox
properties instead.
(mh_global_sequences_get)
(mh_global_sequences_set)
(mh_global_sequences_iterate)
(mh_global_sequences_drop): Take mbox as first argument. All callers
updated.
* mh/mh_init.c (mh_init2): Remove call to mh_global_sequences_get.
* mh/mh_msgset.c (msgset_cur): Use mh_mailbox_get_cur.
* mh/mh_sequence.c (mh_seq_read, write_sequence)
(delete_sequence, mh_seq_add, mh_seq_delete): Take mbox as first argument.
All callers updated.

* mh/mh.h: Include mailutils/property.h.
(current_message): Remove.
(mh_mailbox_cur_default): New extern.
(mh_global_sequences_get)
(mh_global_sequences_set)
(mh_global_sequences_iterate)
(mh_global_sequences_drop): Take mbox as first argument. All callers
updated.

* mh/mh_format.c (builtin_cur): Rewrite using mh_message_number.

* mh/mboxprop.c: New file.
* mh/Makefile.am (libmh_a_SOURCES): Add new file.

* mh/folder.c: Update calls to sequence management functions.
* mh/mark.c: Likewise.
* mh/pick.c: Likewise.

* mh/inc.c (main): Set mh_mailbox_cur_default to 1.
Invalidate properties if changecur is not set.
* mh/prompter.c (main): Destroy the iterator.
* mh/rmf.c: Rewrite using mu_mailbox_remove.
* mh/scan.c: Always close the mailbox.

* mh/tests/folder.at: Update.
* mh/tests/inc.at: Update.  Inc now sets cur to 1 if it was not
originally set.  This is what others MHs do.
1 parent 77d2867d
......@@ -67,6 +67,7 @@ pkginclude_HEADERS = \
mailutils.h\
md5.h\
message.h\
mh.h\
mime.h\
monitor.h\
mu_auth.h\
......
......@@ -78,6 +78,7 @@ extern "C" {
extern int mu_header_create (mu_header_t *, const char *, size_t);
extern void mu_header_destroy (mu_header_t *);
extern int mu_header_invalidate (mu_header_t);
extern int mu_header_clear (mu_header_t header);
extern int mu_header_is_modified (mu_header_t);
extern int mu_header_clear_modified (mu_header_t);
......
/* GNU Mailutils -- a suite of utilities for electronic mail
Copyright (C) 1999, 2000, 2001, 2007, 2010 Free Software Foundation,
Inc.
GNU Mailutils is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GNU Mailutils 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 GNU Mailutils. If not, see <http://www.gnu.org/licenses/>. */
#ifndef _MAILUTILS_MH_H
#define _MAILUTILS_MH_H
extern mu_property_t mu_mh_profile;
extern mu_property_t mu_mh_context;
#define MU_MH_SEQUENCES_FILE ".mh_sequences"
#define MU_MH_USER_PROFILE ".mh_profile"
#define MU_MH_GLOBAL_PROFILE "mh-profile"
#define MU_MH_CONTEXT_FILE "context"
typedef int (*mu_mhprop_iterator_t) (const char *field, const char *value,
void *data);
const char *mu_mhprop_get_value (mu_property_t prop, const char *name,
const char *defval);
int mu_mhprop_iterate (mu_property_t prop, mu_mhprop_iterator_t fp,
void *data);
#endif
......@@ -46,6 +46,8 @@ int mu_property_sget_value (mu_property_t prop, const char *key,
const char **buffer);
int mu_property_aget_value (mu_property_t prop, const char *key,
char **buffer);
int mu_property_clear (mu_property_t prop);
int mu_property_invalidate (mu_property_t prop);
/* Helper functions. */
int mu_property_set (mu_property_t, const char *);
......@@ -56,6 +58,14 @@ int mu_property_get_iterator (mu_property_t, mu_iterator_t *itr);
/* Implementation init functions */
int mu_assoc_property_init (mu_property_t);
struct mu_mh_prop
{
char *filename;
int ro;
};
int mu_mh_property_init (mu_property_t);
#ifdef __cplusplus
}
......
......@@ -62,8 +62,11 @@ struct _mu_property
int (*_prop_unset) (struct _mu_property *, const char *);
/* Return iterator for this property object */
int (*_prop_getitr) (struct _mu_property *, mu_iterator_t *);
/* Clear all properties. */
int (*_prop_clear) (struct _mu_property *);
};
int _mu_property_init (mu_property_t prop);
int _mu_property_check (mu_property_t prop);
# ifdef __cplusplus
......
......@@ -611,7 +611,23 @@ mu_header_insert (mu_header_t header,
HEADER_SET_MODIFIED (header);
return 0;
}
int
mu_header_clear (mu_header_t header)
{
int status;
if (header == NULL)
return EINVAL;
status = mu_header_fill (header);
if (status)
return status;
mu_header_invalidate (header);
HEADER_SET_MODIFIED (header);
return 0;
}
int
mu_header_sget_value_n (mu_header_t header,
......@@ -630,8 +646,8 @@ mu_header_sget_value_n (mu_header_t header,
ent = mu_hdrent_find (header, name, n);
if (!ent)
return MU_ERR_NOENT;
*pval = MU_HDRENT_VALUE (header, ent);
if (pval)
*pval = MU_HDRENT_VALUE (header, ent);
return 0;
}
......
......@@ -20,8 +20,11 @@ noinst_LTLIBRARIES = libproperty.la
libproperty_la_SOURCES = \
assocprop.c\
create.c\
mhprop.c\
propclr.c\
propget.c\
propitr.c\
propinv.c\
propset.c
INCLUDES = @MU_LIB_COMMON_INCLUDES@ -I/libmailutils
......
......@@ -66,7 +66,7 @@ _assoc_prop_setval (struct _mu_property *prop, const char *key,
int rc;
rc = mu_assoc_ref_install (assoc, key, (void **)&item);
if (rc == MU_ERR_NOENT)
if (rc == 0)
{
item->value = strdup (val);
if (!item->value)
......@@ -75,7 +75,7 @@ _assoc_prop_setval (struct _mu_property *prop, const char *key,
return ENOMEM;
}
}
else if (overwrite)
else if (rc == MU_ERR_EXISTS && overwrite)
{
char *newval = strdup (val);
if (!newval)
......@@ -84,7 +84,7 @@ _assoc_prop_setval (struct _mu_property *prop, const char *key,
item->value = newval;
}
else
return MU_ERR_EXISTS;
return rc;
return 0;
}
......@@ -96,6 +96,14 @@ _assoc_prop_unset (struct _mu_property *prop, const char *key)
return mu_assoc_remove (assoc, key);
}
static int
_assoc_prop_clear (struct _mu_property *prop)
{
mu_assoc_t assoc = prop->_prop_data;
mu_assoc_clear (assoc);
return 0;
}
static void *
_assoc_prop_dataptr (void *in)
......@@ -186,7 +194,6 @@ _assoc_prop_save (struct _mu_property *prop)
rc = mu_stream_truncate (str, off);
return rc;
}
int
mu_assoc_property_init (struct _mu_property *prop)
......@@ -203,8 +210,6 @@ mu_assoc_property_init (struct _mu_property *prop)
prop->_prop_done = _assoc_prop_done;
if (prop->_prop_init_data)
{
mu_stream_t str = prop->_prop_init_data;
mu_stream_ref (str);
prop->_prop_fill = _assoc_prop_fill;
prop->_prop_save = _assoc_prop_save;
}
......@@ -217,6 +222,7 @@ mu_assoc_property_init (struct _mu_property *prop)
prop->_prop_setval = _assoc_prop_setval;
prop->_prop_unset = _assoc_prop_unset;
prop->_prop_getitr = _assoc_prop_getitr;
prop->_prop_clear = _assoc_prop_clear;
return 0;
}
......
......@@ -122,7 +122,7 @@ mu_property_save (mu_property_t prop)
return rc;
}
static int
int
_mu_property_init (mu_property_t prop)
{
int rc = 0;
......
/* GNU Mailutils -- a suite of utilities for electronic mail
Copyright (C) 2010 Free Software Foundation, Inc.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 3 of the License, or (at your option) any later version.
This library 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
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General
Public License along with this library. If not, see
<http://www.gnu.org/licenses/>. */
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <mailutils/errno.h>
#include <mailutils/error.h>
#include <mailutils/stream.h>
#include <mailutils/iterator.h>
#include <mailutils/header.h>
#include <mailutils/nls.h>
#include <mailutils/filter.h>
#include <mailutils/property.h>
#include <mailutils/sys/property.h>
#include <stdlib.h>
static void
_mh_prop_done (struct _mu_property *prop)
{
struct mu_mh_prop *mhprop = prop->_prop_init_data;
mu_header_t header = prop->_prop_data;
mu_header_destroy (&header);
free (mhprop->filename);
free (mhprop);
}
static int
_mh_prop_getval (struct _mu_property *prop,
const char *key, const char **pval)
{
mu_header_t header = prop->_prop_data;
if (!header)
return MU_ERR_NOENT;
return mu_header_sget_value (header, key, pval);
}
static int
_mh_prop_setval (struct _mu_property *prop, const char *key,
const char *val, int overwrite)
{
struct mu_mh_prop *mhprop = prop->_prop_init_data;
mu_header_t header = prop->_prop_data;
if (!header)
{
int rc;
if ((rc = mu_header_create (&header, NULL, 0)) != 0)
{
mu_error (_("cannot create context %s: %s"),
mhprop->filename, mu_strerror (rc));
return 1;
}
prop->_prop_data = header;
}
return mu_header_set_value (header, key, val, overwrite);
}
static int
_mh_prop_unset (struct _mu_property *prop, const char *key)
{
mu_header_t header = prop->_prop_data;
if (!header)
return 0;
return mu_header_remove (header, key, 1);
}
static int
_mh_prop_getitr (struct _mu_property *prop, mu_iterator_t *pitr)
{
mu_header_t header = prop->_prop_data;
return mu_header_get_iterator (header, pitr);
}
static int
_mh_prop_clear (struct _mu_property *prop)
{
mu_header_t header = prop->_prop_data;
return mu_header_clear (header);
}
static int
_mh_prop_read_stream (mu_header_t *phdr, mu_stream_t stream)
{
int rc;
mu_stream_t flt;
const char *argv[3];
mu_off_t size;
size_t total;
char *blurb;
rc = mu_stream_size (stream, &size);
if (rc)
return rc;
argv[0] = "INLINE-COMMENT";
argv[1] = "#";
argv[2] = NULL;
rc = mu_filter_create_args (&flt, stream, argv[0], 2, argv,
MU_FILTER_DECODE, MU_STREAM_READ);
if (rc)
{
mu_error (_("cannot open filter stream: %s"), mu_strerror (rc));
return rc;
}
blurb = malloc (size + 1);
if (!blurb)
{
mu_stream_destroy (&flt);
return ENOMEM;
}
total = 0;
while (1)
{
size_t n;
rc = mu_stream_read (flt, blurb + total, size - total, &n);
if (rc)
break;
if (n == 0)
break;
total += n;
}
mu_stream_destroy (&flt);
if (rc)
{
free (blurb);
return rc;
}
rc = mu_header_create (phdr, blurb, total);
free (blurb);
return rc;
}
static int
_mh_prop_write_stream (mu_header_t header, struct mu_mh_prop *mhprop,
mu_stream_t stream)
{
int rc;
mu_stream_t instream;
mu_off_t size;
mu_header_get_streamref (header, &instream);
rc = mu_stream_copy (stream, instream, 0, &size);
if (rc)
{
mu_error (_("error writing to context file %s: %s"),
mhprop->filename, mu_strerror (rc));
return rc;
}
else
rc = mu_stream_truncate (stream, size);
mu_stream_destroy (&instream);
return rc;
}
static int
_mh_prop_fill (struct _mu_property *prop)
{
struct mu_mh_prop *mhprop = prop->_prop_init_data;
int rc;
mu_stream_t stream;
mu_header_t header;
rc = mu_file_stream_create (&stream, mhprop->filename, MU_STREAM_READ);
if (rc)
{
if ((rc = mu_header_create (&header, NULL, 0)) != 0)
mu_error (_("cannot create context %s: %s"),
mhprop->filename, mu_strerror (rc));
}
else
{
rc = _mh_prop_read_stream (&header, stream);
mu_stream_unref (stream);
}
if (rc == 0)
prop->_prop_data = header;
return rc;
}
static int
_mh_prop_save (struct _mu_property *prop)
{
struct mu_mh_prop *mhprop = prop->_prop_init_data;
mu_header_t header = prop->_prop_data;
mu_stream_t stream;
int rc;
if (mhprop->ro)
return 0;
rc = mu_file_stream_create (&stream, mhprop->filename,
MU_STREAM_WRITE|MU_STREAM_CREAT);
if (rc)
return rc;
rc = _mh_prop_write_stream (header, mhprop, stream);
mu_stream_unref (stream);
return rc;
}
int
mu_mh_property_init (struct _mu_property *prop)
{
struct mu_mh_prop *mhprop = prop->_prop_init_data;
if (!mhprop)
return EINVAL;
prop->_prop_data = NULL;
prop->_prop_done = _mh_prop_done;
prop->_prop_fill = _mh_prop_fill;
prop->_prop_save = _mh_prop_save;
prop->_prop_getval = _mh_prop_getval;
prop->_prop_setval = _mh_prop_setval;
prop->_prop_unset = _mh_prop_unset;
prop->_prop_getitr = _mh_prop_getitr;
prop->_prop_clear = _mh_prop_clear;
return 0;
}
/* GNU Mailutils -- a suite of utilities for electronic mail
Copyright (C) 2010 Free Software Foundation, Inc.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 3 of the License, or (at your option) any later version.
This library 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
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General
Public License along with this library. If not, see
<http://www.gnu.org/licenses/>. */
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <mailutils/types.h>
#include <mailutils/errno.h>
#include <mailutils/sys/property.h>
int
mu_property_clear (mu_property_t prop)
{
int rc = _mu_property_check (prop);
if (rc)
return rc;
if (!prop->_prop_clear)
return MU_ERR_EMPTY_VFN;
rc = prop->_prop_clear (prop);
if (rc == 0)
prop->_prop_flags |= MU_PROP_MODIFIED;
return rc;
}
/* GNU Mailutils -- a suite of utilities for electronic mail
Copyright (C) 2010 Free Software Foundation, Inc.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 3 of the License, or (at your option) any later version.
This library 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
Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General
Public License along with this library. If not, see
<http://www.gnu.org/licenses/>. */
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <mailutils/types.h>
#include <mailutils/errno.h>
#include <mailutils/sys/property.h>
int
mu_property_invalidate (mu_property_t prop)
{
int rc;
if (!prop)
return EINVAL;
rc = _mu_property_init (prop);
if (rc)
return rc;
if (prop->_prop_flags & MU_PROP_FILL)
{
if (!prop->_prop_clear)
return MU_ERR_EMPTY_VFN;
rc = prop->_prop_clear (prop);
if (rc)
return rc;
prop->_prop_flags &= ~(MU_PROP_FILL | MU_PROP_MODIFIED);
}
return 0;
}
......@@ -28,14 +28,21 @@ int
mu_property_set_value (mu_property_t prop, const char *key,
const char *value, int overwrite)
{
int rc = _mu_property_check (prop);
if (rc)
return rc;
if (!prop->_prop_setval)
return MU_ERR_EMPTY_VFN;
rc = prop->_prop_setval (prop, key, value, overwrite);
if (rc == 0)
prop->_prop_flags |= MU_PROP_MODIFIED;
int rc;
if (!value)
rc = mu_property_unset (prop, key);
else
{
rc = _mu_property_check (prop);
if (rc)
return rc;
if (!prop->_prop_setval)
return MU_ERR_EMPTY_VFN;
rc = prop->_prop_setval (prop, key, value, overwrite);
if (rc == 0)
prop->_prop_flags |= MU_PROP_MODIFIED;
}
return rc;
}
......
......@@ -97,5 +97,28 @@ test=6.b
user=gray
])
TESTPROP([clear],[prop07],[
prop --dump user=gray package=mailutils org=GNU 0 ?org
],
[0: user=gray: Success
1: package=mailutils: Success
2: org=GNU: Success
3: clear: Success
4: org is not set
Property dump:
])
TESTPROP([invalidate],[prop08],[
prop --file=db user=foo
prop --file=db ?user user=bar +user '!' +user
],
[0: user=foo: Success
0: user is set
1: user=bar: Success
2: user=bar
3: invalidate: Success
4: user=foo
])
m4_popdef([TESTPROP])
......
......@@ -29,6 +29,8 @@ help (char *progname)
printf (" ?X query whether X is set\n");
printf (" +X query the value of the property X\n");
printf (" -X unset property X\n");
printf (" 0 clear all properties\n");
printf (" ! invalidate properties\n");
exit (0);
}
......@@ -66,7 +68,6 @@ main (int argc, char **argv)
{
MU_ASSERT (mu_file_stream_create (&str, filename,
MU_STREAM_RDWR|MU_STREAM_CREAT));
mu_stream_unref (str);
if (i == argc)
dumpit = 1;
}
......@@ -119,6 +120,16 @@ main (int argc, char **argv)
else
printf ("%d: %s=%s\n", j, key, val);
}
else if (key[0] == '0' && key[1] == 0)
{
rc = mu_property_clear (prop);
printf ("%d: clear: %s\n", j, mu_strerror (rc));
}
else if (key[0] == '!' && key[1] == 0)
{
rc = mu_property_invalidate (prop);
printf ("%d: invalidate: %s\n", j, mu_strerror (rc));
}
else
{
mu_error ("%d: unrecognized command", i);
......
......@@ -22,6 +22,7 @@ libmu_mh_la_LDFLAGS=-version-info @VI_CURRENT@:@VI_REVISION@:@VI_AGE@
libmu_mh_la_LIBADD = ${MU_LIB_MAILUTILS}
libmu_mh_la_SOURCES = \
folder.c\
mbox.c
mbox.c\
profile.c
......
......@@ -22,8 +22,6 @@
# include <config.h>
#endif
#ifdef ENABLE_MH
#include <sys/types.h>
#include <stdlib.h>
#include <stdio.h>
......@@ -63,6 +61,7 @@
#include <mailutils/observer.h>
#include <mailutils/io.h>
#include <mailutils/cctype.h>
#include <mailutils/mh.h>
#include <mailutils/sys/mailbox.h>
#include <mailutils/sys/registrar.h>
#include <mailutils/sys/amd.h>
......@@ -359,6 +358,30 @@ mh_remove (struct _amd_data *amd)
}
static int
mh_get_property (mu_mailbox_t mailbox, mu_property_t *pprop)
{
struct _amd_data *amd = mailbox->data;
mu_property_t property = NULL;
struct mu_mh_prop *mhprop;
const char *p;
mhprop = calloc (1, sizeof (mhprop[0]));
if (!mhprop)
return ENOMEM;
p = mu_mhprop_get_value (mu_mh_profile, "mh-sequences",
MU_MH_SEQUENCES_FILE);
mhprop->filename = mu_make_file_name (amd->name, p);
mu_property_create_init (&property, mu_mh_property_init, mhprop);
mu_mailbox_set_property (mailbox, property);
/*FIXME mu_property_set_value (property, "TYPE", "MH", 1);*/
*pprop = property;
return 0;
}
int
_mailbox_mh_init (mu_mailbox_t mailbox)
......@@ -383,14 +406,9 @@ _mailbox_mh_init (mu_mailbox_t mailbox)
amd->next_uid = _mh_next_seq;
amd->remove = mh_remove;
/* Set our properties. */
{
mu_property_t property = NULL;
mu_mailbox_get_property (mailbox, &property);
mu_property_set_value (property, "TYPE", "MH", 1);
}
mailbox->_get_property = mh_get_property;
return 0;
}
#endif
......
/* GNU Mailutils -- a suite of utilities for electronic mail
Copyright (C) 2010 Free Software Foundation, Inc.
GNU Mailutils is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GNU Mailutils 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 GNU Mailutils. If not, see <http://www.gnu.org/licenses/>. */
#ifdef HAVE_CONFIG_H
# include <config.h>
#endif
#include <mailutils/property.h>
#include <mailutils/iterator.h>
#include <mailutils/errno.h>
#include <mailutils/mh.h>
mu_property_t mu_mh_profile;
mu_property_t mu_mh_context;
const char *
mu_mhprop_get_value (mu_property_t prop, const char *name, const char *defval)
{
const char *p;
if (!prop || mu_property_sget_value (prop, name, &p))
p = defval;
return p;
}
int
mu_mhprop_iterate (mu_property_t prop, mu_mhprop_iterator_t fp, void *data)
{
mu_iterator_t itr;
int rc;
if (!prop)
return EINVAL;
rc = mu_property_get_iterator (prop, &itr);
if (rc)
return rc;
for (mu_iterator_first (itr); !mu_iterator_is_done (itr);
mu_iterator_next (itr))
{
const char *name, *val;
mu_iterator_current_kv (itr, (const void **)&name, (void**)&val);
rc = fp (name, val, data);
if (rc)
break;
}
mu_iterator_destroy (&itr);
return rc;
}
......@@ -28,6 +28,7 @@ mhpath
pick
pick-gram.c
pick-gram.h
prompter
refile
repl
rmf
......
......@@ -64,6 +64,7 @@ noinst_LIBRARIES = libmh.a
libmh_a_SOURCES= \
compcommon.c\
mboxprop.c\
mh_alias_gram.c\
mh_alias_lex.c\
mh_argp.c\
......
......@@ -740,6 +740,7 @@ roll_back (const char *folder_name, struct pack_tab *pack_tab, size_t i)
struct fixup_data
{
mu_mailbox_t mbox;
const char *folder_dir;
struct pack_tab *pack_tab;
size_t count;
......@@ -797,12 +798,12 @@ _fixup (const char *name, const char *value, struct fixup_data *fd, int flags)
mu_wordsplit_free (&ws);
mh_seq_add (name, &msgset, flags | SEQ_ZERO);
mh_seq_add (fd->mbox, name, &msgset, flags | SEQ_ZERO);
free (msgset.list);
if (verbose)
{
const char *p = mh_seq_read (name, flags);
const char *p = mh_seq_read (fd->mbox, name, flags);
fprintf (stderr, "Sequence %s: %s\n", name, p);
}
......@@ -917,18 +918,23 @@ action_pack ()
fprintf (stderr, _("Finished packing messages.\n"));
/* Fix-up sequences */
fd.folder_dir = folder_dir;
fd.pack_tab = pack_tab;
fd.count = count;
if (verbose)
fprintf (stderr, _("Fixing global sequences\n"));
mh_global_sequences_iterate (fixup_global, &fd);
if (verbose)
fprintf (stderr, _("Fixing private sequences\n"));
mh_global_context_iterate (fixup_private, &fd);
if (!dry_run)
mh_global_save_state ();
{
mbox = mh_open_folder (mh_current_folder (), 0);
fd.mbox = mbox;
fd.folder_dir = folder_dir;
fd.pack_tab = pack_tab;
fd.count = count;
if (verbose)
fprintf (stderr, _("Fixing global sequences\n"));
mh_global_sequences_iterate (mbox, fixup_global, &fd);
if (verbose)
fprintf (stderr, _("Fixing private sequences\n"));
mh_global_context_iterate (fixup_private, &fd);
mu_mailbox_close (mbox);
mu_mailbox_destroy (&mbox);
mh_global_save_state ();
}
return 0;
}
......
......@@ -175,6 +175,8 @@ main (int argc, char **argv)
mh_argp_init ();
mh_argp_parse (&argc, &argv, 0, options, mh_option, args_doc, doc,
opt_handler, NULL, NULL);
/* Inc sets missing cur to 1 */
mh_mailbox_cur_default = 1;
if (!quiet && mh_format_parse (format_str, &format))
{
......@@ -256,9 +258,11 @@ main (int argc, char **argv)
if (n == 1 && changecur)
{
mu_message_t msg = NULL;
mu_mailbox_get_message (output, lastmsg+1, &msg);
mh_message_number (msg, &current_message);
size_t cur;
mu_mailbox_get_message (output, lastmsg + 1, &msg);
mh_message_number (msg, &cur);
mh_mailbox_set_cur (output, cur);
}
if (!quiet)
......@@ -272,8 +276,12 @@ main (int argc, char **argv)
}
}
if (changecur)
mh_global_save_state ();
if (!changecur)
{
mu_property_t prop = mh_mailbox_get_property (output);
mu_property_invalidate (prop);
}
mh_global_save_state ();
mu_mailbox_close (output);
mu_mailbox_destroy (&output);
......
......@@ -116,31 +116,41 @@ opt_handler (int key, char *arg, struct argp_state *state)
}
return 0;
}
struct mark_closure
{
mu_mailbox_t mbox;
mh_msgset_t *msgset;
};
static int
action_add (void *item, void *data)
{
mh_seq_add ((char *)item, (mh_msgset_t *)data, seq_flags);
struct mark_closure *clos = data;
mh_seq_add (clos->mbox, (char *)item, clos->msgset, seq_flags);
return 0;
}
static int
action_delete (void *item, void *data)
{
mh_seq_delete ((char *)item, (mh_msgset_t *)data, seq_flags);
struct mark_closure *clos = data;
mh_seq_delete (clos->mbox, (char *)item, clos->msgset, seq_flags);
return 0;
}
static int
action_list (void *item, void *data)
{
struct mark_closure *clos = data;
char *name = item;
const char *val;
val = mh_seq_read (name, 0);
val = mh_seq_read (clos->mbox, name, 0);
if (val)
printf ("%s: %s\n", name, val);
else if ((val = mh_seq_read (name, SEQ_PRIVATE)))
else if ((val = mh_seq_read (clos->mbox, name, SEQ_PRIVATE)))
printf ("%s (%s): %s\n", name, _("private"), val);
return 0;
}
......@@ -171,9 +181,9 @@ list_public (const char *name, const char *value, void *data)
}
static void
list_all ()
list_all (mu_mailbox_t mbox)
{
mh_global_sequences_iterate (list_public, NULL);
mh_global_sequences_iterate (mbox, list_public, NULL);
mh_global_context_iterate (list_private, NULL);
}
......@@ -184,6 +194,7 @@ main (int argc, char **argv)
mh_msgset_t msgset;
mu_mailbox_t mbox;
mu_url_t url;
struct mark_closure clos;
MU_APP_INIT_NLS ();
mh_argp_init ();
......@@ -201,6 +212,8 @@ main (int argc, char **argv)
mh_msgset_parse (mbox, &msgset, argc, argv, "cur");
mh_msgset_uids (mbox, &msgset);
clos.mbox = mbox;
clos.msgset = &msgset;
switch (action)
{
case ARG_ADD:
......@@ -209,7 +222,7 @@ main (int argc, char **argv)
mu_error (_("--add requires at least one --sequence argument"));
return 1;
}
mu_list_do (seq_list, action_add, (void *) &msgset);
mu_list_do (seq_list, action_add, (void *) &clos);
mh_global_save_state ();
break;
......@@ -219,17 +232,18 @@ main (int argc, char **argv)
mu_error (_("--delete requires at least one --sequence argument"));
return 1;
}
mu_list_do (seq_list, action_delete, (void *) &msgset);
mu_list_do (seq_list, action_delete, (void *) &clos);
mh_global_save_state ();
break;
case ARG_LIST:
if (!seq_list)
list_all ();
list_all (mbox);
else
mu_list_do (seq_list, action_list, NULL);
mu_list_do (seq_list, action_list, &clos);
break;
}
mu_mailbox_close (mbox);
mu_mailbox_destroy (&mbox);
return 0;
}
......
/* GNU Mailutils -- a suite of utilities for electronic mail
Copyright (C) 1999, 2000, 2001, 2005, 2006, 2007, 2009, 2010 Free
Software Foundation, Inc.
GNU Mailutils is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GNU Mailutils 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 GNU Mailutils. If not, see <http://www.gnu.org/licenses/>. */
/* MH message sets. */
#include <mh.h>
/* Default value for missing "cur". Valid values are 0 and 1. */
int mh_mailbox_cur_default = 0;
void
mh_mailbox_get_cur (mu_mailbox_t mbox, size_t *pcur)
{
mu_property_t prop = NULL;
const char *s;
int rc = mu_mailbox_get_property (mbox, &prop);
if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_mailbox_get_property", NULL, rc);
exit (1);
}
rc = mu_property_sget_value (prop, "cur", &s);
if (rc == MU_ERR_NOENT)
*pcur = mh_mailbox_cur_default;
else if (rc == 0)
{
char *p;
*pcur = strtoul (s, &p, 10);
if (*p)
{
mu_error (_("invalid \"cur\" value (%s)"), s);
*pcur = 1;
}
}
else
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_property_sget_value", NULL, rc);
exit (1);
}
}
void
mh_mailbox_set_cur (mu_mailbox_t mbox, size_t cur)
{
mu_property_t prop = NULL;
int rc = mu_mailbox_get_property (mbox, &prop);
if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_mailbox_get_property", NULL, rc);
exit (1);
}
rc = mu_property_set_value (prop, "cur", mu_umaxtostr (0, cur), 1);
if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_property_set_value", NULL, rc);
exit (1);
}
}
......@@ -55,6 +55,7 @@
#include <mailutils/envelope.h>
#include <mailutils/mime.h>
#include <mailutils/io.h>
#include <mailutils/property.h>
#include <mu_umaxtostr.h>
......@@ -233,9 +234,9 @@ typedef int (*mh_context_iterator) (const char *field, const char *value,
#define SEQ_PRIVATE 1
#define SEQ_ZERO 2
extern size_t current_message;
extern char mh_list_format[];
extern int rcpt_mask;
extern int mh_mailbox_cur_default;
void mh_init (void);
void mh_init2 (void);
......@@ -251,13 +252,19 @@ const char *mh_global_context_get (const char *name, const char *defval);
int mh_global_context_set (const char *name, const char *value);
const char *mh_set_current_folder (const char *val);
const char *mh_current_folder (void);
const char *mh_global_sequences_get (const char *name, const char *defval);
int mh_global_sequences_set (const char *name, const char *value);
mu_property_t mh_mailbox_get_property (mu_mailbox_t mbox);
const char *mh_global_sequences_get (mu_mailbox_t mbox,
const char *name, const char *defval);
void mh_global_sequences_set (mu_mailbox_t mbox,
const char *name, const char *value);
void mh_global_sequences_iterate (mu_mailbox_t mbox,
mh_context_iterator fp, void *data);
void mh_global_sequences_drop (mu_mailbox_t mbox);
void mh_global_save_state (void);
int mh_global_profile_iterate (mh_context_iterator fp, void *data);
int mh_global_context_iterate (mh_context_iterator fp, void *data);
int mh_global_sequences_iterate (mh_context_iterator fp, void *data);
void mh_global_sequences_drop (void);
int mh_interactive_mode_p (void);
int mh_getyn (const char *fmt, ...) MU_PRINTFLIKE(1,2);
......@@ -300,7 +307,7 @@ int mh_msgset_parse (mu_mailbox_t mbox, mh_msgset_t *msgset,
int mh_msgset_member (mh_msgset_t *msgset, size_t num);
void mh_msgset_reverse (mh_msgset_t *msgset);
void mh_msgset_negate (mu_mailbox_t mbox, mh_msgset_t *msgset);
int mh_msgset_current (mu_mailbox_t mbox, mh_msgset_t *msgset, int index);
void mh_msgset_current (mu_mailbox_t mbox, mh_msgset_t *msgset, int index);
void mh_msgset_free (mh_msgset_t *msgset);
void mh_msgset_uids (mu_mailbox_t mbox, mh_msgset_t *msgset);
......@@ -358,9 +365,11 @@ int mhl_format_run (mu_list_t fmt, int width, int length, int flags,
mu_message_t msg, mu_stream_t output);
void mhl_format_destroy (mu_list_t *fmt);
void mh_seq_add (const char *name, mh_msgset_t *mset, int flags);
int mh_seq_delete (const char *name, mh_msgset_t *mset, int flags);
const char *mh_seq_read (const char *name, int flags);
void mh_seq_add (mu_mailbox_t mbox, const char *name, mh_msgset_t *mset,
int flags);
int mh_seq_delete (mu_mailbox_t mbox, const char *name, mh_msgset_t *mset,
int flags);
const char *mh_seq_read (mu_mailbox_t mbox, const char *name, int flags);
void mh_comp_draft (const char *formfile, const char *defformfile,
const char *draftfile);
......@@ -371,3 +380,6 @@ void ali_verbatim (int enable);
char *mh_safe_make_file_name (const char *dir, const char *file);
void mh_mailbox_get_cur (mu_mailbox_t mbox, size_t *pcur);
void mh_mailbox_set_cur (mu_mailbox_t mbox, size_t cur);
......
......@@ -913,8 +913,19 @@ static void
builtin_cur (struct mh_machine *mach)
{
size_t msgno = mach->msgno;
size_t cur;
int rc;
mu_mailbox_t mbox;
rc = mu_message_get_mailbox (mach->message, &mbox);
if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_message_get_mailbox", NULL, rc);
exit (1);
}
mh_message_number (mach->message, &msgno);
mach->arg_num = msgno == current_message;
mh_mailbox_get_cur (mbox, &cur); /* FIXME: Cache this */
mach->arg_num = msgno == cur;
}
static void
......
......@@ -49,7 +49,7 @@ struct mh_machine
mu_list_t addrlist; /* The list of email addresses output this far */
int fmtflags; /* Current formatting flags */
mu_message_t message; /* Current message */
size_t msgno; /* Its number */
};
......
......@@ -20,10 +20,8 @@
#include <mh.h>
static const char *current_folder = NULL;
size_t current_message = 0;
mh_context_t *context;
mh_context_t *profile;
mh_context_t *sequences;
int rcpt_mask = RCPT_DEFAULT;
int mh_auto_install = 1;
......@@ -137,54 +135,88 @@ mh_set_current_folder (const char *val)
current_folder = mh_current_folder ();
return current_folder;
}
/* Global sequences */
void
_mh_init_global_sequences ()
mu_property_t
mh_mailbox_get_property (mu_mailbox_t mbox)
{
const char *name;
char *p, *seq_name;
if (sequences)
return;
_mh_init_global_context ();
name = mh_global_profile_get ("mh-sequences", MH_SEQUENCES_FILE);
p = mh_expand_name (NULL, current_folder, 0);
seq_name = mh_safe_make_file_name (p, name);
free (p);
sequences = mh_context_create (seq_name, 1);
if (mh_context_read (sequences) == 0)
current_message = strtoul (mh_context_get_value (sequences, "cur", "0"),
NULL, 10);
mu_property_t prop;
int rc = mu_mailbox_get_property (mbox, &prop);
if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_mailbox_get_property", NULL, rc);
exit (1);
}
return prop;
}
void
mh_global_sequences_drop ()
mh_global_sequences_drop (mu_mailbox_t mbox)
{
mh_context_destroy (&sequences);
mu_property_t prop = mh_mailbox_get_property (mbox);
int rc = mu_property_clear (prop);
if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_property_clear", NULL, rc);
exit (1);
}
}
const char *
mh_global_sequences_get (const char *name, const char *defval)
{
_mh_init_global_sequences ();
return mh_context_get_value (sequences, name, defval);
mh_global_sequences_get (mu_mailbox_t mbox, const char *name,
const char *defval)
{
mu_property_t prop = mh_mailbox_get_property (mbox);
const char *s;
int rc = mu_property_sget_value (prop, name, &s);
if (rc == MU_ERR_NOENT)
s = defval;
else if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_property_sget_value", name, rc);
exit (1);
}
return s;
}
int
mh_global_sequences_set (const char *name, const char *value)
void
mh_global_sequences_set (mu_mailbox_t mbox, const char *name,
const char *value)
{
_mh_init_global_sequences ();
return mh_context_set_value (sequences, name, value);
mu_property_t prop = mh_mailbox_get_property (mbox);
int rc = mu_property_set_value (prop, name, value, 1);
if (rc && !(!value && rc == MU_ERR_NOENT))
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_property_set_value", name, rc);
exit (1);
}
}
int
mh_global_sequences_iterate (mh_context_iterator fp, void *data)
/* FIXME: Rewrite using mu_mhprop_iterate */
void
mh_global_sequences_iterate (mu_mailbox_t mbox,
mh_context_iterator fp, void *data)
{
_mh_init_global_context ();
return mh_context_iterate (sequences, fp, data);
int rc;
mu_iterator_t itr;
mu_property_t prop = mh_mailbox_get_property (mbox);
rc = mu_property_get_iterator (prop, &itr);
if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_property_get_iterator", NULL, rc);
exit (1);
}
for (mu_iterator_first (itr); !mu_iterator_is_done (itr);
mu_iterator_next (itr))
{
const char *name, *val;
mu_iterator_current_kv (itr, (const void **)&name, (void**)&val);
if (fp (name, val, data))
break;
}
mu_iterator_destroy (&itr);
}
/* Global state */
......@@ -192,9 +224,6 @@ mh_global_sequences_iterate (mh_context_iterator fp, void *data)
void
mh_global_save_state ()
{
mh_context_set_value (sequences, "cur", mu_umaxtostr (0, current_message));
mh_context_write (sequences);
mh_context_set_value (context, "Current-Folder", current_folder);
mh_context_write (context);
}
......
......@@ -67,7 +67,6 @@ void
mh_init2 ()
{
mh_current_folder ();
mh_global_sequences_get ("cur", NULL);
}
int
......
......@@ -18,7 +18,6 @@
/* MH message sets. */
#include <mh.h>
#include <mailutils/argcv.h>
/* Expand a message set (msgcnt;msglist) to accomodate `inc' more
elements */
......@@ -72,13 +71,16 @@ msgset_cur (mu_mailbox_t mbox, size_t *pnum)
{
size_t i, count = 0;
static int cached_n = 0;
size_t cur;
mh_mailbox_get_cur (mbox, &cur);
if (cached_n)
{
*pnum = cached_n;
return 0;
}
mu_mailbox_messages_count (mbox, &count);
for (i = 1; i <= count; i++)
{
......@@ -87,7 +89,7 @@ msgset_cur (mu_mailbox_t mbox, size_t *pnum)
mu_mailbox_get_message (mbox, i, &msg);
mh_message_number (msg, &uid);
if (uid == current_message)
if (uid == cur)
{
*pnum = cached_n = i;
return 0;
......@@ -244,7 +246,7 @@ expand_user_seq (mu_mailbox_t mbox, mh_msgset_t *msgset, char *arg)
p = strchr (arg, ':');
if (p)
*p++ = 0;
listp = mh_global_sequences_get (arg, NULL);
listp = mh_global_sequences_get (mbox, arg, NULL);
if (!listp)
{
int len;
......@@ -255,7 +257,7 @@ expand_user_seq (mu_mailbox_t mbox, mh_msgset_t *msgset, char *arg)
if (strncmp (arg, neg, len))
return 1;
negate = 1;
listp = mh_global_sequences_get (arg + len, NULL);
listp = mh_global_sequences_get (mbox, arg + len, NULL);
if (!listp)
return 1;
}
......@@ -569,13 +571,21 @@ mh_msgset_reverse (mh_msgset_t *msgset)
/* Set the current message to that contained at position `index'
in the given message set */
int
void
mh_msgset_current (mu_mailbox_t mbox, mh_msgset_t *msgset, int index)
{
mu_message_t msg = NULL;
if (mu_mailbox_get_message (mbox, msgset->list[index], &msg))
return 1;
return mh_message_number (msg, &current_message);
int rc;
size_t cur;
rc = mu_mailbox_get_message (mbox, msgset->list[index], &msg);
if (rc)
{
mu_diag_funcall (MU_DIAG_ERROR, "mu_mailbox_get_message", NULL, rc);
exit (1);
}
mh_message_number (msg, &cur);
mh_mailbox_set_cur (mbox, cur);
}
/* Free memory allocated for the message set. Note, that the msgset
......
......@@ -28,7 +28,7 @@ private_sequence_name (const char *name)
}
const char *
mh_seq_read (const char *name, int flags)
mh_seq_read (mu_mailbox_t mbox, const char *name, int flags)
{
const char *value;
......@@ -39,12 +39,12 @@ mh_seq_read (const char *name, int flags)
free (p);
}
else
value = mh_global_sequences_get (name, NULL);
value = mh_global_sequences_get (mbox, name, NULL);
return value;
}
static void
write_sequence (const char *name, char *value, int private)
write_sequence (mu_mailbox_t mbox, const char *name, char *value, int private)
{
if (private)
{
......@@ -53,24 +53,24 @@ write_sequence (const char *name, char *value, int private)
free (p);
}
else
mh_global_sequences_set (name, value);
mh_global_sequences_set (mbox, name, value);
}
static void
delete_sequence (const char *name, int private)
delete_sequence (mu_mailbox_t mbox, const char *name, int private)
{
write_sequence (name, NULL, private);
write_sequence (mbox, name, NULL, private);
}
void
mh_seq_add (const char *name, mh_msgset_t *mset, int flags)
mh_seq_add (mu_mailbox_t mbox, const char *name, mh_msgset_t *mset, int flags)
{
const char *value = mh_seq_read (name, flags);
const char *value = mh_seq_read (mbox, name, flags);
char *new_value, *p;
const char *buf;
size_t i, len;
delete_sequence (name, !(flags & SEQ_PRIVATE));
delete_sequence (mbox, name, !(flags & SEQ_PRIVATE));
if (flags & SEQ_ZERO)
value = NULL;
......@@ -99,9 +99,11 @@ mh_seq_add (const char *name, mh_msgset_t *mset, int flags)
*p++ = ' ';
}
*p = 0;
write_sequence (name, new_value, flags & SEQ_PRIVATE);
write_sequence (mbox, name, new_value, flags & SEQ_PRIVATE);
/* FIXME
if (mu_c_strcasecmp (name, "cur") == 0)
current_message = strtoul (new_value, NULL, 0);
*/
free (new_value);
}
......@@ -119,9 +121,10 @@ cmp_msgnum (const void *a, const void *b)
}
int
mh_seq_delete (const char *name, mh_msgset_t *mset, int flags)
mh_seq_delete (mu_mailbox_t mbox, const char *name,
mh_msgset_t *mset, int flags)
{
const char *value = mh_seq_read (name, flags);
const char *value = mh_seq_read (mbox, name, flags);
char *new_val;
char *p;
size_t i, count;
......@@ -167,7 +170,7 @@ mh_seq_delete (const char *name, mh_msgset_t *mset, int flags)
}
}
*p = 0;
write_sequence (name, count > 0 ? new_val : NULL, flags & SEQ_PRIVATE);
write_sequence (mbox, name, count > 0 ? new_val : NULL, flags & SEQ_PRIVATE);
mu_wordsplit_free (&ws);
free (new_val);
......
......@@ -298,10 +298,18 @@ pick_message (mu_mailbox_t mbox, mu_message_t msg, size_t num, void *data)
}
}
struct pick_closure
{
mu_mailbox_t mbox;
mh_msgset_t *msgset;
};
static int
action_add (void *item, void *data)
{
mh_seq_add ((char *)item, (mh_msgset_t *)data, seq_flags);
struct pick_closure *clos = data;
mh_seq_add (clos->mbox, (char *)item, clos->msgset, seq_flags);
return 0;
}
......@@ -395,13 +403,18 @@ main (int argc, char **argv)
if (seq_list)
{
struct pick_closure clos;
mh_msgset_t msgset;
msgset.count = msgno_count;
msgset.list = obstack_finish (&msgno_stk);
mu_list_do (seq_list, action_add, (void*) &msgset);
clos.mbox = mbox;
clos.msgset = &msgset;
mu_list_do (seq_list, action_add, &clos);
}
mh_global_save_state ();
mu_mailbox_close (mbox);
mu_mailbox_destroy (&mbox);
return status;
}
......
......@@ -255,6 +255,7 @@ main (int argc, char **argv)
mu_opool_destroy (&opool);
}
}
mu_iterator_destroy (&itr);
mu_stream_printf (strout, "--------\n");
mu_stream_write (tmp, "\n", 1, NULL);
......
......@@ -53,7 +53,7 @@ struct mh_option mh_option[] = {
int explicit_folder; /* Was the folder explicitly given */
int interactive; /* Ask for confirmation before deleting */
int recurse; /* Recursively process all the sub-directories */
int recursive; /* Recursively process all the sub-directories */
static char *cur_folder_path; /* Full pathname of the current folder */
static char *folder_name; /* Name of the (topmost) folder to be
......@@ -78,11 +78,11 @@ opt_handler (int key, char *arg, struct argp_state *state)
break;
case ARG_RECURSIVE:
recurse = is_true (arg);
recursive = is_true (arg);
break;
case ARG_NORECURSIVE:
recurse = 0;
recursive = 0;
break;
default:
......@@ -107,6 +107,31 @@ current_folder_path ()
static int
rmf (const char *name)
{
mu_mailbox_t mbox = NULL;
int rc;
rc = mu_mailbox_create_default (&mbox, name);
if (rc)
{
mu_error (_("cannot create mailbox %s: %s"),
name, strerror (rc));
return 1;
}
rc = mu_mailbox_remove (mbox);
mu_mailbox_destroy (&mbox);
if (rc)
{
mu_error (_("cannot remove %s: %s"), name, mu_strerror (rc));
return 1;
}
return 0;
}
/* Recursive rmf */
static int
recrmf (const char *name)
{
DIR *dir;
struct dirent *entry;
int failures = 0;
......@@ -137,50 +162,24 @@ rmf (const char *name)
mu_diag_funcall (MU_DIAG_ERROR, "stat", p, errno);
}
else if (S_ISDIR (st.st_mode))
{
if (recurse)
failures += rmf (p);
else
{
printf ("%s: file `%s' not deleted, continuing...\n",
mu_program_name, p);
failures++;
}
}
else
{
if (unlink (p))
{
mu_diag_funcall (MU_DIAG_ERROR, "unlink", p, errno);
failures++;
}
}
failures += recrmf (p);
free (p);
}
closedir (dir);
if (failures == 0)
failures += rmdir (name);
failures += rmf (name);
else
printf ("%s: folder `%s' not removed\n",
mu_program_name, name);
if (failures == 0)
{
if (cur_folder_path && strcmp (name, cur_folder_path) == 0)
{
mh_set_current_folder ("inbox");
mh_global_sequences_drop ();
mh_global_save_state ();
printf ("[+inbox now current]\n");
}
}
return failures;
}
int
main (int argc, char **argv)
{
int status;
char *name;
/* Native Language Support */
......@@ -199,6 +198,23 @@ main (int argc, char **argv)
}
else
name = mh_expand_name (NULL, folder_name, 0);
rmf (name);
return 0;
if (recursive)
status = recrmf (name);
else
{
if (interactive && !mh_getyn (_("Remove folder %s"), name))
exit (0);
status = rmf (name);
}
if (status == 0)
{
if (cur_folder_path && strcmp (name, cur_folder_path) == 0)
{
mh_set_current_folder ("inbox");
mh_global_save_state ();
printf ("[+inbox now current]\n");
}
return 0;
}
return 1;
}
......
......@@ -219,7 +219,8 @@ main (int argc, char **argv)
clear_screen ();
mh_global_save_state ();
mu_mailbox_close (mbox);
mu_mailbox_destroy (&mbox);
return status;
}
......
......@@ -96,7 +96,6 @@ Mail/inbox/2
Mail/inbox/3
Mail/inbox/4
Mail/inbox/5
Mail/inbox/.mh_sequences
])
MH_CHECK([folder --pack=N],[folder06 folder--pack=N],[
......@@ -115,7 +114,6 @@ Mail/inbox/2
Mail/inbox/3
Mail/inbox/4
Mail/inbox/5
Mail/inbox/.mh_sequences
])
MH_CHECK([folder -push/-pop],[folder07 folder-push folder-pop folder-push-pop],
......
......@@ -22,7 +22,7 @@ inc -notruncate -file ./mbox1 | sed 's/ *$//'
cmp $abs_top_srcdir/testsuite/spool/mbox1 mbox1
],
[0],
[ 1 12/28 Foo Bar <foobar@n Jabberwocky<<`Twas brillig, and the slithy toves
[ 1+ 12/28 Foo Bar <foobar@n Jabberwocky<<`Twas brillig, and the slithy toves
2 12/28 Bar <bar@dontmail Re: Jabberwocky<<It seems very pretty, but it's
3 07/13 Sergey Poznyakoff Simple MIME<<------- =_aaaaaaaaaa0 Content-Type:
4 07/13 Sergey Poznyakoff Nested MIME<<------- =_aaaaaaaaaa0 Content-Type:
......@@ -36,7 +36,7 @@ echo "Next"
inc -truncate -file ./mbox1 | sed 's/ *$//'
],
[0],
[ 1 12/28 Foo Bar <foobar@n Jabberwocky<<`Twas brillig, and the slithy toves
[ 1+ 12/28 Foo Bar <foobar@n Jabberwocky<<`Twas brillig, and the slithy toves
2 12/28 Bar <bar@dontmail Re: Jabberwocky<<It seems very pretty, but it's
3 07/13 Sergey Poznyakoff Simple MIME<<------- =_aaaaaaaaaa0 Content-Type:
4 07/13 Sergey Poznyakoff Nested MIME<<------- =_aaaaaaaaaa0 Content-Type:
......@@ -50,12 +50,42 @@ mkdir Mail/new
inc +new -file ./mbox1 | sed 's/ *$//'
],
[0],
[ 1 12/28 Foo Bar <foobar@n Jabberwocky<<`Twas brillig, and the slithy toves
[ 1+ 12/28 Foo Bar <foobar@n Jabberwocky<<`Twas brillig, and the slithy toves
2 12/28 Bar <bar@dontmail Re: Jabberwocky<<It seems very pretty, but it's
3 07/13 Sergey Poznyakoff Simple MIME<<------- =_aaaaaaaaaa0 Content-Type:
4 07/13 Sergey Poznyakoff Nested MIME<<------- =_aaaaaaaaaa0 Content-Type:
5 07/13 Sergey Poznyakoff Empty MIME Parts<<------- =_aaaaaaaaaa0 Content-
])
MH_CHECK([inc -changecur],[inc03 inc-changecur],[
MUT_MBCOPY($abs_top_srcdir/testsuite/mh/mbox1,[Mail/inbox])
MUT_MBCOPY([$abs_top_srcdir/testsuite/spool/mbox1])
inc -changecur -file ./mbox1 | sed 's/ *$//'
],
[0],
[ 6+ 12/28 Foo Bar <foobar@n Jabberwocky<<`Twas brillig, and the slithy toves
7 12/28 Bar <bar@dontmail Re: Jabberwocky<<It seems very pretty, but it's
8 07/13 Sergey Poznyakoff Simple MIME<<------- =_aaaaaaaaaa0 Content-Type:
9 07/13 Sergey Poznyakoff Nested MIME<<------- =_aaaaaaaaaa0 Content-Type:
10 07/13 Sergey Poznyakoff Empty MIME Parts<<------- =_aaaaaaaaaa0 Content-
])
MH_CHECK([inc -nochangecur],[inc04 inc-nochangecur],[
MUT_MBCOPY($abs_top_srcdir/testsuite/mh/mbox1,[Mail/inbox])
echo "cur: 1" > Mail/inbox/.mh_sequences
MUT_MBCOPY([$abs_top_srcdir/testsuite/spool/mbox1])
inc -nochangecur -file ./mbox1 | sed 's/ *$//'
grep ^cur: Mail/inbox/.mh_sequences
],
[0],
[ 6 12/28 Foo Bar <foobar@n Jabberwocky<<`Twas brillig, and the slithy toves
7 12/28 Bar <bar@dontmail Re: Jabberwocky<<It seems very pretty, but it's
8 07/13 Sergey Poznyakoff Simple MIME<<------- =_aaaaaaaaaa0 Content-Type:
9 07/13 Sergey Poznyakoff Nested MIME<<------- =_aaaaaaaaaa0 Content-Type:
10 07/13 Sergey Poznyakoff Empty MIME Parts<<------- =_aaaaaaaaaa0 Content-
cur: 1
])
m4_popdef[MH_KEYWORDS])
# End of inc.at
......