[augeas-devel] augeas: master - Reset old error messages on each entry through the API from the outside
David Lutterkort
lutter at fedoraproject.org
Thu Sep 24 19:08:49 UTC 2009
Gitweb: http://git.fedorahosted.org/git/augeas.git?p=augeas.git;a=commitdiff;h=9ae0e7fb83376ba5facf500012d1987b7bf13e71
Commit: 9ae0e7fb83376ba5facf500012d1987b7bf13e71
Parent: e607e0546b5c99c706eb9988824a9612d6f2108b
Author: David Lutterkort <lutter at redhat.com>
AuthorDate: Fri Sep 18 16:13:26 2009 -0700
Committer: David Lutterkort <lutter at redhat.com>
CommitterDate: Mon Sep 21 15:37:15 2009 -0700
Reset old error messages on each entry through the API from the outside
---
src/augeas.c | 106 ++++++++++++++++++++++++++++++++++++++++++++++++++-----
src/internal.h | 2 +
2 files changed, 98 insertions(+), 10 deletions(-)
diff --git a/src/augeas.c b/src/augeas.c
index 8e87a53..e8e2fc0 100644
--- a/src/augeas.c
+++ b/src/augeas.c
@@ -232,6 +232,8 @@ struct augeas *aug_init(const char *root, const char *loadpath,
struct augeas *result;
struct tree *tree_root = make_tree(NULL, NULL, NULL, NULL);
+ /* There's no point in bothering with api_entry/api_exit here */
+
if (tree_root == NULL)
return NULL;
@@ -338,14 +340,40 @@ static void tree_unlink_children(struct augeas *aug, struct tree *tree) {
tree_unlink(tree->children);
}
+/* Clean up old error messages every time we enter through the public
+ * API. Since we make internal calls through the public API, we keep a
+ * count of how many times a public API call was made, and only reset when
+ * that count is 0. That requires that all public functions enclose their
+ * work within a matching pair of api_entry/api_exit calls.
+ */
+static void api_entry(const struct augeas *aug) {
+ struct error *err = &((struct augeas *) aug)->error;
+
+ ((struct augeas *) aug)->api_entries += 1;
+
+ if (aug->api_entries > 1)
+ return;
+
+ err->code = AUG_NOERROR;
+ err->minor = 0;
+ FREE(err->details);
+ err->minor_details = NULL;
+}
+
+static void api_exit(const struct augeas *aug) {
+ assert(aug->api_entries > 0);
+ ((struct augeas *) aug)->api_entries -= 1;
+}
+
int aug_load(struct augeas *aug) {
struct tree *meta = tree_child_cr(aug->origin, s_augeas);
struct tree *meta_files = tree_child_cr(meta, s_files);
struct tree *files = tree_child_cr(aug->origin, s_files);
struct tree *load = tree_child_cr(meta, s_load);
- if (load == NULL)
- return -1;
+ api_entry(aug);
+
+ ERR_NOMEM(load == NULL, aug);
tree_unlink_children(aug, meta_files);
tree_unlink_children(aug, files);
@@ -355,7 +383,12 @@ int aug_load(struct augeas *aug) {
transform_load(aug, xfm);
}
tree_clean(aug->origin);
+
+ api_exit(aug);
return 0;
+ error:
+ api_exit(aug);
+ return -1;
}
int aug_get(const struct augeas *aug, const char *path, const char **value) {
@@ -363,9 +396,11 @@ int aug_get(const struct augeas *aug, const char *path, const char **value) {
struct tree *match;
int r;
+ api_entry(aug);
+
p = parse_user_pathx((struct augeas *) aug, true, path);
if (p == NULL)
- return -1;
+ goto error;
if (value != NULL)
*value = NULL;
@@ -375,13 +410,19 @@ int aug_get(const struct augeas *aug, const char *path, const char **value) {
*value = match->value;
free_pathx(p);
+ api_exit(aug);
return r;
+ error:
+ api_exit(aug);
+ return -1;
}
int aug_defvar(augeas *aug, const char *name, const char *expr) {
struct pathx *p = NULL;
int result = -1;
+ api_entry(aug);
+
if (expr == NULL) {
result = pathx_symtab_undefine(&(aug->symtab), name);
} else {
@@ -392,6 +433,7 @@ int aug_defvar(augeas *aug, const char *name, const char *expr) {
}
done:
free_pathx(p);
+ api_exit(aug);
return result;
}
@@ -402,8 +444,10 @@ int aug_defnode(augeas *aug, const char *name, const char *expr,
int r, cr;
struct tree *tree;
+ api_entry(aug);
+
if (expr == NULL)
- return -1;
+ goto error;
if (created == NULL)
created = &cr;
@@ -427,7 +471,11 @@ int aug_defnode(augeas *aug, const char *name, const char *expr,
done:
free_pathx(p);
+ api_exit(aug);
return result;
+ error:
+ api_exit(aug);
+ return -1;
}
struct tree *tree_set(struct pathx *p, const char *value) {
@@ -448,13 +496,20 @@ int aug_set(struct augeas *aug, const char *path, const char *value) {
struct pathx *p;
int result;
+ api_entry(aug);
+
p = parse_user_pathx(aug, true, path);
if (p == NULL)
- return -1;
+ goto error;
result = tree_set(p, value) == NULL ? -1 : 0;
free_pathx(p);
+
+ api_exit(aug);
return result;
+ error:
+ api_exit(aug);
+ return -1;
}
int tree_insert(struct pathx *p, const char *label, int before) {
@@ -487,6 +542,8 @@ int aug_insert(struct augeas *aug, const char *path, const char *label,
struct pathx *p = NULL;
int result = -1;
+ api_entry(aug);
+
p = parse_user_pathx(aug, true, path);
if (p == NULL)
goto done;
@@ -494,6 +551,7 @@ int aug_insert(struct augeas *aug, const char *path, const char *label,
result = tree_insert(p, label, before);
done:
free_pathx(p);
+ api_exit(aug);
return result;
}
@@ -599,14 +657,20 @@ int aug_rm(struct augeas *aug, const char *path) {
struct pathx *p = NULL;
int result;
+ api_entry(aug);
+
p = parse_user_pathx(aug, true, path);
if (p == NULL)
- return -1;
+ goto error;
result = tree_rm(p);
free_pathx(p);
+ api_exit(aug);
return result;
+ error:
+ api_exit(aug);
+ return -1;
}
int tree_replace(struct tree *origin, const char *path, struct tree *sub) {
@@ -643,6 +707,8 @@ int aug_mv(struct augeas *aug, const char *src, const char *dst) {
struct tree *ts, *td, *t;
int r, ret;
+ api_entry(aug);
+
ret = -1;
s = parse_user_pathx(aug, true, src);
if (s == NULL)
@@ -687,6 +753,7 @@ int aug_mv(struct augeas *aug, const char *src, const char *dst) {
done:
free_pathx(s);
free_pathx(d);
+ api_exit(aug);
return ret;
}
@@ -695,6 +762,8 @@ int aug_match(const struct augeas *aug, const char *pathin, char ***matches) {
struct tree *tree;
int cnt = 0;
+ api_entry(aug);
+
if (matches != NULL)
*matches = NULL;
@@ -704,7 +773,7 @@ int aug_match(const struct augeas *aug, const char *pathin, char ***matches) {
p = parse_user_pathx((struct augeas *) aug, true, pathin);
if (p == NULL)
- return -1;
+ goto error;
for (tree = pathx_first(p); tree != NULL; tree = pathx_next(p)) {
if (! TREE_HIDDEN(tree))
@@ -729,6 +798,7 @@ int aug_match(const struct augeas *aug, const char *pathin, char ***matches) {
}
done:
free_pathx(p);
+ api_exit(aug);
return cnt;
error:
@@ -740,6 +810,7 @@ int aug_match(const struct augeas *aug, const char *pathin, char ***matches) {
}
}
free_pathx(p);
+ api_exit(aug);
return -1;
}
@@ -857,11 +928,13 @@ int aug_save(struct augeas *aug) {
struct tree *files = tree_child_cr(aug->origin, s_files);
struct tree *load = tree_child_cr(meta, s_load);
+ api_entry(aug);
+
if (update_save_flags(aug) < 0)
- return -1;
+ goto error;
if (files == NULL || meta == NULL || load == NULL)
- return -1;
+ goto error;
aug_rm(aug, AUGEAS_EVENTS_SAVED);
@@ -882,7 +955,12 @@ int aug_save(struct augeas *aug) {
if (!(aug->flags & AUG_SAVE_NOOP)) {
tree_clean(aug->origin);
}
+
+ api_exit(aug);
return ret;
+ error:
+ api_exit(aug);
+ return -1;
}
static int print_one(FILE *out, const char *path, const char *value) {
@@ -976,23 +1054,31 @@ int aug_print(const struct augeas *aug, FILE *out, const char *pathin) {
struct pathx *p;
int result;
+ api_entry(aug);
+
if (pathin == NULL || strlen(pathin) == 0) {
pathin = "/*";
}
p = parse_user_pathx((struct augeas *) aug, true, pathin);
if (p == NULL)
- return -1;
+ goto error;
result = print_tree(out, p, 0);
free_pathx(p);
+ api_exit(aug);
return result;
+ error:
+ api_exit(aug);
+ return -1;
}
void aug_close(struct augeas *aug) {
if (aug == NULL)
return;
+
+ /* There's no point in bothering with api_entry/api_exit here */
free_tree(aug->origin);
unref(aug->modules, module);
free((void *) aug->root);
diff --git a/src/internal.h b/src/internal.h
index 1e0111b..441be84 100644
--- a/src/internal.h
+++ b/src/internal.h
@@ -290,6 +290,8 @@ struct augeas {
glibc argz vector */
struct pathx_symtab *symtab;
struct error error;
+ uint api_entries; /* Number of entries through a public
+ * API, 0 when called from outside */
};
void report_error(struct error *err, aug_errcode_t errcode,
More information about the augeas-devel
mailing list