summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorVsevolod Stakhov <vsevolod@highsecure.ru>2017-01-10 12:35:55 +0000
committerVsevolod Stakhov <vsevolod@highsecure.ru>2017-01-10 12:35:55 +0000
commitcb846eabcdd306de3ff54c77ad0184f08850dead (patch)
treef4c4705c11f558631528857636d74807fc853223
parent5e4f7ac4c8ec5cf319b3e0aa81cd8dfcf7d23f94 (diff)
downloadrspamd-cb846eabcdd306de3ff54c77ad0184f08850dead.tar.gz
rspamd-cb846eabcdd306de3ff54c77ad0184f08850dead.zip
[Feature] Add ucl_object_iterate_full function
-rw-r--r--contrib/libucl/ucl.h19
-rw-r--r--contrib/libucl/ucl_util.c15
2 files changed, 30 insertions, 4 deletions
diff --git a/contrib/libucl/ucl.h b/contrib/libucl/ucl.h
index 024f5dd8f..ec93bd7e1 100644
--- a/contrib/libucl/ucl.h
+++ b/contrib/libucl/ucl.h
@@ -831,10 +831,29 @@ UCL_EXTERN ucl_object_iter_t ucl_object_iterate_reset (ucl_object_iter_t it,
* Get the next object from the `obj`. This fucntion iterates over arrays, objects
* and implicit arrays
* @param iter safe iterator
+ * @param expand_values expand explicit arrays and objects
* @return the next object in sequence
*/
UCL_EXTERN const ucl_object_t* ucl_object_iterate_safe (ucl_object_iter_t iter,
bool expand_values);
+/**
+ * Iteration type enumerator
+ */
+enum ucl_iterate_type {
+ UCL_ITERATE_EXPLICIT = 1 << 0, /**< Iterate just explicit arrays and objects */
+ UCL_ITERATE_IMPLICIT = 1 << 1, /**< Iterate just implicit arrays */
+ UCL_ITERATE_BOTH = (1 << 0) | (1 << 1), /**< Iterate both explicit and implicit arrays*/
+};
+
+/**
+ * Get the next object from the `obj`. This fucntion iterates over arrays, objects
+ * and implicit arrays if needed
+ * @param iter safe iterator
+ * @param
+ * @return the next object in sequence
+ */
+UCL_EXTERN const ucl_object_t* ucl_object_iterate_full (ucl_object_iter_t iter,
+ enum ucl_iterate_type type);
/**
* Free memory associated with the safe iterator
diff --git a/contrib/libucl/ucl_util.c b/contrib/libucl/ucl_util.c
index 1adb8c3b6..6691c8546 100644
--- a/contrib/libucl/ucl_util.c
+++ b/contrib/libucl/ucl_util.c
@@ -2479,6 +2479,13 @@ ucl_object_iterate_reset (ucl_object_iter_t it, const ucl_object_t *obj)
const ucl_object_t*
ucl_object_iterate_safe (ucl_object_iter_t it, bool expand_values)
{
+ return ucl_object_iterate_full (it, expand_values ? UCL_ITERATE_BOTH :
+ UCL_ITERATE_IMPLICIT);
+}
+
+const ucl_object_t*
+ucl_object_iterate_full (ucl_object_iter_t it, enum ucl_iterate_type type)
+{
struct ucl_object_safe_iter *rit = UCL_SAFE_ITER (it);
const ucl_object_t *ret = NULL;
@@ -2491,21 +2498,21 @@ ucl_object_iterate_safe (ucl_object_iter_t it, bool expand_values)
if (rit->impl_it->type == UCL_OBJECT || rit->impl_it->type == UCL_ARRAY) {
ret = ucl_object_iterate (rit->impl_it, &rit->expl_it, true);
- if (ret == NULL) {
+ if (ret == NULL && (type & UCL_ITERATE_IMPLICIT)) {
/* Need to switch to another implicit object in chain */
rit->impl_it = rit->impl_it->next;
rit->expl_it = NULL;
- return ucl_object_iterate_safe (it, expand_values);
+ return ucl_object_iterate_safe (it, type);
}
}
else {
/* Just iterate over the implicit array */
ret = rit->impl_it;
rit->impl_it = rit->impl_it->next;
- if (expand_values) {
+ if (type & UCL_ITERATE_EXPLICIT) {
/* We flatten objects if need to expand values */
if (ret->type == UCL_OBJECT || ret->type == UCL_ARRAY) {
- return ucl_object_iterate_safe (it, expand_values);
+ return ucl_object_iterate_safe (it, type);
}
}
}