summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPeter Rajnoha <prajnoha@redhat.com>2015-10-20 16:01:10 +0200
committerPeter Rajnoha <prajnoha@redhat.com>2015-10-30 15:47:56 +0100
commit0d5b1294f0350e10698232eb764c28b3ca54df1a (patch)
tree52cfba3228333f1708c79891941a3d7f0d4151d5
parent097d14e64e845bdb1c0b8106e33f38f775e54fe5 (diff)
downloadlvm2-0d5b1294f0350e10698232eb764c28b3ca54df1a.tar.gz
str_list: add str_list_to_str and str_to_str_list functions
The str_list_to_str and str_to_str_list are helper functions to convert string list to a single string and vice versa.
-rw-r--r--lib/datastruct/str_list.c87
-rw-r--r--lib/datastruct/str_list.h2
2 files changed, 89 insertions, 0 deletions
diff --git a/lib/datastruct/str_list.c b/lib/datastruct/str_list.c
index 25ffddd2c..a600f607e 100644
--- a/lib/datastruct/str_list.c
+++ b/lib/datastruct/str_list.c
@@ -16,6 +16,8 @@
#include "lib.h"
#include "str_list.h"
+#include <ctype.h>
+
struct dm_list *str_list_create(struct dm_pool *mem)
{
struct dm_list *sl;
@@ -160,3 +162,88 @@ int str_list_lists_equal(const struct dm_list *sll, const struct dm_list *sll2)
return 1;
}
+
+char *str_list_to_str(struct dm_pool *mem, const struct dm_list *list,
+ const char *delim)
+{
+ size_t delim_len = strlen(delim);
+ unsigned list_size = dm_list_size(list);
+ struct dm_str_list *sl;
+ char *str, *p;
+ size_t len = 0;
+ unsigned i = 0;
+
+ dm_list_iterate_items(sl, list)
+ len += strlen(sl->str);
+ if (list_size > 1)
+ len += ((list_size - 1) * delim_len);
+
+ str = mem ? dm_pool_alloc(mem, len+1) : dm_malloc(len+1);
+ if (!str) {
+ log_error("str_list_to_str: string allocation failed.");
+ return NULL;
+ }
+ str[len] = '\0';
+ p = str;
+
+ dm_list_iterate_items(sl, list) {
+ len = strlen(sl->str);
+ memcpy(p, sl->str, len);
+ p += len;
+
+ if (++i != list_size) {
+ memcpy(p, delim, delim_len);
+ p += delim_len;
+ }
+ }
+
+ return str;
+}
+
+struct dm_list *str_to_str_list(struct dm_pool *mem, const char *str,
+ const char *delim, int ignore_multiple_delim)
+{
+ size_t delim_len = strlen(delim);
+ struct dm_list *list;
+ const char *p1, *p2, *next;
+ char *str_item;
+ size_t len;
+
+ if (!(list = str_list_create(mem))) {
+ log_error("str_to_str_list: string list allocation failed.");
+ return NULL;
+ }
+
+ p1 = p2 = str;
+ while (*p1) {
+ if (!(p2 = strstr(p1, delim)))
+ next = p2 = str + strlen(str);
+ else
+ next = p2 + delim_len;
+
+ len = p2 - p1;
+ str_item = mem ? dm_pool_alloc(mem, len+1) : dm_malloc(len+1);
+ if (!str_item) {
+ log_error("str_to_str_list: string list item allocation failed.");
+ goto bad;
+ }
+ memcpy(str_item, p1, len);
+ str_item[len] = '\0';
+
+ if (!str_list_add_no_dup_check(mem, list, str_item))
+ goto_bad;
+
+ if (ignore_multiple_delim) {
+ while (!strncmp(next, delim, delim_len))
+ next += delim_len;
+ }
+
+ p1 = next;
+ }
+
+ return list;
+bad:
+ if (mem)
+ dm_pool_free(mem, list);
+ return NULL;
+}
diff --git a/lib/datastruct/str_list.h b/lib/datastruct/str_list.h
index 3121a28ce..268a3cf75 100644
--- a/lib/datastruct/str_list.h
+++ b/lib/datastruct/str_list.h
@@ -30,5 +30,7 @@ int str_list_match_list(const struct dm_list *sll, const struct dm_list *sll2, c
int str_list_lists_equal(const struct dm_list *sll, const struct dm_list *sll2);
int str_list_dup(struct dm_pool *mem, struct dm_list *sllnew,
const struct dm_list *sllold);
+char *str_list_to_str(struct dm_pool *mem, const struct dm_list *list, const char *delim);
+struct dm_list *str_to_str_list(struct dm_pool *mem, const char *str, const char *delim, int ignore_multiple_delim);
#endif