summaryrefslogtreecommitdiff
path: root/libmailutils
diff options
context:
space:
mode:
authorSergey Poznyakoff <gray@gnu.org.ua>2016-12-31 14:25:13 +0200
committerSergey Poznyakoff <gray@gnu.org.ua>2016-12-31 14:25:13 +0200
commit66f7ed9562cce859f20166f9cf0c38a018a83dbe (patch)
treee2b11f6d2d74fd07bd981eae1d774ff58f2d80a7 /libmailutils
parentda63ec15b4c8fb3084075730332a8d20a9af374f (diff)
downloadmailutils-66f7ed9562cce859f20166f9cf0c38a018a83dbe.tar.gz
mailutils-66f7ed9562cce859f20166f9cf0c38a018a83dbe.tar.bz2
Provide a way to discern between erroneous return and user-induced break condition in foreach iterator functions
* libmailutils/diag/errors (MU_ERR_USER0-MU_ERR_USER7): New error constants. Reserved for user's purposes, such as breaking from foreach iterators. * libmaildutils/list/foreach.c (mu_list_foreach): Treat NULL list as a list of 0 elements. * libmailutils/list/foreachdir.c (mu_list_foreach_dir): Likewise. * imap4d/imap4d.h (imap4d_auth_result): Remap constants to MU_ERR_USER[0-2] * libmu_sieve/prog.c (mu_i_sv_lint_command): Use mu_list_locate with the default comparator. * mh/mh_list.c (_comp_name): Rewrite to match the definition of mu_list_comparator_t (mhl_format_run): Set _comp_name as comparator for the env.printed_fields list. (header_is_printed): Use mu_list_locate. * imap4d/authenticate.c: Use MU_ERR_USER0-MU_ERR_USER7 to indicate normal break condition in foreach iterators. * imap4d/imap4d.c: Likewise. * imap4d/namespace.c: Likewise. * libmailutils/auth/auth.c: Likewise. * libmailutils/cfg/driver.c: Likewise. * libmailutils/cfg/parser.y: Likewise. * libmailutils/server/acl.c: Likewise. * libmailutils/server/msrv.c: Likewise. * libmu_sieve/conf.c: Likewise. * libmu_sieve/load.c: Likewise. * libmu_sieve/sieve.l: Likewise. * libmu_sieve/strexp.c: Likewise. * libproto/imap/mbox.c: Likewise. * libproto/imap/search.c: Likewise. * mh/mh_format.c: Likewise. * mh/send.c: Likewise. * mh/sortm.c: Likewise. * mimeview/mimetypes.y: Likewise. * movemail/movemail.c: Likewise.
Diffstat (limited to 'libmailutils')
-rw-r--r--libmailutils/auth/auth.c2
-rw-r--r--libmailutils/cfg/driver.c30
-rw-r--r--libmailutils/cfg/parser.y25
-rw-r--r--libmailutils/diag/errors11
-rw-r--r--libmailutils/list/foreach.c4
-rw-r--r--libmailutils/list/foreachdir.c4
-rw-r--r--libmailutils/server/acl.c14
-rw-r--r--libmailutils/server/msrv.c2
8 files changed, 62 insertions, 30 deletions
diff --git a/libmailutils/auth/auth.c b/libmailutils/auth/auth.c
index 0b5daf584..413092eb6 100644
--- a/libmailutils/auth/auth.c
+++ b/libmailutils/auth/auth.c
@@ -123,7 +123,7 @@ try_auth (void *item, void *data)
if (authenticate (cb->authority) == 0)
{
cb->status = 0;
- return 1;
+ return MU_ERR_USER0;
}
return 0;
}
diff --git a/libmailutils/cfg/driver.c b/libmailutils/cfg/driver.c
index 1c897af32..2d1022f75 100644
--- a/libmailutils/cfg/driver.c
+++ b/libmailutils/cfg/driver.c
@@ -165,7 +165,13 @@ dup_container (struct mu_cfg_cont **pcont)
newcont->v.section.offset = oldcont->v.section.offset;
newcont->v.section.docstring = oldcont->v.section.docstring;
newcont->v.section.children = NULL;
- mu_list_foreach (oldcont->v.section.children, _dup_cont_action, &dd);
+ rc = mu_list_foreach (oldcont->v.section.children, _dup_cont_action, &dd);
+ if (rc)
+ {
+ mu_diag_funcall (MU_DIAG_ERROR, "_dup_cont_action",
+ oldcont->v.section.ident, rc);
+ abort ();
+ }
break;
case mu_cfg_cont_param:
@@ -325,8 +331,7 @@ mu_config_clone_container (struct mu_cfg_cont *cont)
switch (cont->type)
{
case mu_cfg_cont_section:
- mu_list_foreach (cont->v.section.children, _clone_action, NULL);
- break;
+ return mu_list_foreach (cont->v.section.children, _clone_action, NULL);
case mu_cfg_cont_param:
break;
@@ -590,7 +595,6 @@ struct mapping_closure
{
mu_assoc_t assoc;
char *err_term;
- int err;
};
static int
@@ -600,6 +604,7 @@ parse_mapping (void *item, void *data)
char *str = item;
size_t len;
char *key, *val;
+ int rc;
len = strcspn (str, "=");
if (str[len] == 0)
@@ -613,11 +618,9 @@ parse_mapping (void *item, void *data)
val = mu_strdup (str + len + 1);
if (!val)
return ENOMEM;
- clos->err = mu_assoc_install (clos->assoc, key, val);
+ rc = mu_assoc_install (clos->assoc, key, val);
free (key);
- if (clos->err)
- return 1;
- return 0;
+ return rc;
}
int
@@ -655,10 +658,15 @@ mu_cfg_field_map (struct mu_config_value const *val, mu_assoc_t *passoc,
if (rc)
{
- if (err_term)
- *err_term = clos.err_term;
+ if (rc == MU_ERR_PARSE)
+ {
+ if (err_term)
+ *err_term = clos.err_term;
+ else
+ free (clos.err_term);
+ }
else
- free (clos.err_term);
+ mu_error ("%s:%d: %s", __FILE__, __LINE__, mu_strerror (rc));
mu_assoc_destroy (&clos.assoc);
}
else
diff --git a/libmailutils/cfg/parser.y b/libmailutils/cfg/parser.y
index 48f94d968..d66edb1b2 100644
--- a/libmailutils/cfg/parser.y
+++ b/libmailutils/cfg/parser.y
@@ -565,7 +565,7 @@ mu_cfg_tree_postprocess (mu_cfg_tree_t *tree, struct mu_cfg_parse_hints *hints)
{
/* Reset the parent node */
mu_list_foreach (node->nodes, _node_set_parent,
- node->parent);
+ node->parent);
/* Move all nodes from this block to the topmost
level */
mu_iterator_ctl (itr, mu_itrctl_insert_list,
@@ -619,6 +619,7 @@ _mu_cfg_preorder_recursive (void *item, void *cbdata)
{
mu_cfg_node_t *node = item;
struct mu_cfg_iter_closure *clos = cbdata;
+ int rc;
switch (node->type)
{
@@ -629,22 +630,24 @@ _mu_cfg_preorder_recursive (void *item, void *cbdata)
switch (clos->beg (node, clos->data))
{
case MU_CFG_ITER_OK:
- if (mu_cfg_preorder (node->nodes, clos))
- return 1;
+ rc = mu_cfg_preorder (node->nodes, clos);
+ if (rc)
+ return rc;
if (clos->end && clos->end (node, clos->data) == MU_CFG_ITER_STOP)
- return 1;
+ return MU_ERR_USER0;
break;
case MU_CFG_ITER_SKIP:
break;
case MU_CFG_ITER_STOP:
- return 1;
+ return MU_ERR_USER0;
}
break;
case mu_cfg_node_param:
- return clos->beg (node, clos->data) == MU_CFG_ITER_STOP;
+ if (clos->beg (node, clos->data) == MU_CFG_ITER_STOP)
+ return MU_ERR_USER0;
}
return 0;
}
@@ -1035,6 +1038,7 @@ mu_cfg_scan_tree (mu_cfg_tree_t *tree, struct mu_cfg_section *sections,
struct mu_cfg_iter_closure clos;
int save_mode = 0, mode;
struct mu_locus save_locus = { NULL, };
+ int rc;
dat.tree = tree;
dat.list = NULL;
@@ -1055,9 +1059,10 @@ mu_cfg_scan_tree (mu_cfg_tree_t *tree, struct mu_cfg_section *sections,
clos.beg = _scan_tree_helper;
clos.end = _scan_tree_end_helper;
clos.data = &dat;
- mu_cfg_preorder (tree->nodes, &clos);
+ rc = mu_cfg_preorder (tree->nodes, &clos);
pop_section (&dat);
-
+ if (rc && rc != MU_ERR_USER0)
+ dat.error++;
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
MU_IOCTL_LOGSTREAM_SET_MODE, &save_mode);
mu_stream_ioctl (mu_strerr, MU_IOCTL_LOGSTREAM,
@@ -1448,11 +1453,13 @@ mu_cfg_find_node (mu_cfg_tree_t *tree, const char *path, mu_cfg_node_t **pval)
clos.data = &data;
rc = mu_cfg_preorder (tree->nodes, &clos);
destroy_value (data.label);
- if (rc)
+ if (rc == MU_ERR_USER0)
{
*pval = (mu_cfg_node_t *) data.node;
return 0;
}
+ else
+ mu_diag_funcall (MU_DIAG_ERR, "mu_cfg_preorder", NULL, rc);
}
return MU_ERR_NOENT;
}
diff --git a/libmailutils/diag/errors b/libmailutils/diag/errors
index c4fec20e1..9cd561106 100644
--- a/libmailutils/diag/errors
+++ b/libmailutils/diag/errors
@@ -129,3 +129,14 @@ MU_ERR_FORMAT _("Error in format string")
MU_ERR_REMOVE_SOURCE _("Failed to remove source file")
MU_ERR_REMOVE_DEST _("Failed to remove destination file")
MU_ERR_RESTORE_META _("Failed to restore ownership or mode")
+
+# User-defined errors are meant to be returned by foreach iterator
+# callbacks when they need to break iterations.
+MU_ERR_USER0 _("User-defined error 0")
+MU_ERR_USER1 _("User-defined error 1")
+MU_ERR_USER2 _("User-defined error 2")
+MU_ERR_USER3 _("User-defined error 3")
+MU_ERR_USER4 _("User-defined error 4")
+MU_ERR_USER5 _("User-defined error 5")
+MU_ERR_USER6 _("User-defined error 6")
+MU_ERR_USER7 _("User-defined error 7")
diff --git a/libmailutils/list/foreach.c b/libmailutils/list/foreach.c
index 353de05d7..9794dda0d 100644
--- a/libmailutils/list/foreach.c
+++ b/libmailutils/list/foreach.c
@@ -29,7 +29,9 @@ mu_list_foreach (mu_list_t list, mu_list_action_t action, void *cbdata)
mu_iterator_t itr;
int status = 0;
- if (list == NULL || action == NULL)
+ if (list == NULL)
+ return 0;
+ if (action == NULL)
return EINVAL;
status = mu_list_get_iterator (list, &itr);
if (status)
diff --git a/libmailutils/list/foreachdir.c b/libmailutils/list/foreachdir.c
index 4cce203b4..6fa487447 100644
--- a/libmailutils/list/foreachdir.c
+++ b/libmailutils/list/foreachdir.c
@@ -30,7 +30,9 @@ mu_list_foreach_dir (mu_list_t list, int dir,
mu_iterator_t itr;
int status = 0;
- if (list == NULL || action == NULL)
+ if (list == NULL)
+ return 0;
+ if (action == NULL)
return EINVAL;
status = mu_list_get_iterator (list, &itr);
if (status)
diff --git a/libmailutils/server/acl.c b/libmailutils/server/acl.c
index f37e1eba6..1c5906c52 100644
--- a/libmailutils/server/acl.c
+++ b/libmailutils/server/acl.c
@@ -483,12 +483,12 @@ _run_entry (void *item, void *data)
{
case mu_acl_accept:
*rp->result = mu_acl_result_accept;
- status = 1;
+ status = MU_ERR_USER0;
break;
case mu_acl_deny:
*rp->result = mu_acl_result_deny;
- status = 1;
+ status = MU_ERR_USER0;
break;
case mu_acl_log:
@@ -523,12 +523,12 @@ _run_entry (void *item, void *data)
{
case 0:
*rp->result = mu_acl_result_accept;
- status = 1;
+ status = MU_ERR_USER0;
break;
case 1:
*rp->result = mu_acl_result_deny;
- status = 1;
+ status = MU_ERR_USER0;
}
}
}
@@ -573,9 +573,11 @@ mu_acl_check_sockaddr (mu_acl_t acl, const struct sockaddr *sa, int salen,
r.result = pres;
r.env = acl->envv;
*r.result = mu_acl_result_undefined;
- mu_list_foreach (acl->aclist, _run_entry, &r);
+ rc = mu_list_foreach (acl->aclist, _run_entry, &r);
free (r.addrstr);
- return 0;
+ if (rc == MU_ERR_USER0)
+ rc = 0;
+ return rc;
}
int
diff --git a/libmailutils/server/msrv.c b/libmailutils/server/msrv.c
index 1048a5e9c..19c30a1d3 100644
--- a/libmailutils/server/msrv.c
+++ b/libmailutils/server/msrv.c
@@ -216,7 +216,7 @@ m_server_cleanup (void *item, void *data)
mu_diag_output (MU_DIAG_ERR,
"process %lu terminated (cause unknown)",
(unsigned long) datp->pid);
- return 1;
+ return MU_ERR_USER0;
}
return 0;
}

Return to:

Send suggestions and report system problems to the System administrator.