blob: fc886d15956595d2bcf194295444f40d91b8a17e [file] [log] [blame]
Harald Welte1a36f332018-06-04 17:36:33 +02001/* Simple Osmocom System Monitor (osysmon): Name-Value tree */
2
3/* (C) 2018 by Harald Welte <laforge@gnumonks.org>
4 * All Rights Reserved.
5 *
6 * SPDX-License-Identifier: GPL-2.0+
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
Harald Welte1a36f332018-06-04 17:36:33 +020017 */
18
19#include <talloc.h>
Harald Welte3a964a42018-06-04 19:40:26 +020020#include <string.h>
Harald Welte1a36f332018-06-04 17:36:33 +020021#include <osmocom/core/utils.h>
22
23#include "value_node.h"
24
Maxf41973e2019-01-25 18:40:11 +010025struct value_node *value_node_add(struct value_node *parent,
Harald Welte1a36f332018-06-04 17:36:33 +020026 const char *name, const char *value)
27{
28 struct value_node *vn = talloc_zero(parent, struct value_node);
Harald Welte3a964a42018-06-04 19:40:26 +020029
30 if (parent && value_node_find(parent, name)) {
31 /* duplicate name not permitted! */
32 return NULL;
33 }
34
35 vn = talloc_zero(parent, struct value_node);
Harald Welte1a36f332018-06-04 17:36:33 +020036 OSMO_ASSERT(vn);
Harald Welte3a964a42018-06-04 19:40:26 +020037
Harald Welte1a36f332018-06-04 17:36:33 +020038 /* we assume the name is static/const and owned by caller */
39 vn->name = name;
40 if (value)
41 vn->value = talloc_strdup(vn, value);
42 INIT_LLIST_HEAD(&vn->children);
43 if (parent)
44 llist_add_tail(&vn->list, &parent->children);
45 else
46 INIT_LLIST_HEAD(&vn->list);
47 return vn;
48}
49
Harald Welte3a964a42018-06-04 19:40:26 +020050struct value_node *value_node_find(struct value_node *parent, const char *name)
51{
52 struct value_node *vn;
53 llist_for_each_entry(vn, &parent->children, list) {
54 if (!strcmp(name, vn->name))
55 return vn;
56 }
57 return NULL;
58}
59
60struct value_node *value_node_find_or_add(struct value_node *parent, const char *name)
61{
62 struct value_node *vn;
63 vn = value_node_find(parent, name);
64 if (!vn)
Maxf41973e2019-01-25 18:40:11 +010065 vn = value_node_add(parent, name, NULL);
Harald Welte3a964a42018-06-04 19:40:26 +020066 return vn;
67}
68
Harald Welteb6718f72018-06-04 20:08:21 +020069struct value_node *value_node_find_by_idx(struct value_node *parent, int idx)
70{
71 struct value_node *vn;
72 llist_for_each_entry(vn, &parent->children, list) {
73 if (idx == vn->idx)
74 return vn;
75 }
76 return NULL;
77}
78
79
Harald Welte1a36f332018-06-04 17:36:33 +020080void value_node_del(struct value_node *node)
81{
82 /* remove ourselves from the parent */
83 llist_del(&node->list);
84
85#if 0 /* not actually needed, talloc should do this */
86 struct value_node *ch, *ch2;
87 llist_for_each_entry_safe(ch, ch2, &node->children, list)
88 value_node_del(ch);
89 /* "value" is a talloc child, and "name" is not owned by us */
90#endif
91 /* let talloc do its magic to delete all child nodes */
92 talloc_free(node);
93}