add reminders in code
[protos/libecoli.git] / libecoli / ecoli_parse.h
1 /* SPDX-License-Identifier: BSD-3-Clause
2  * Copyright 2016, Olivier MATZ <zer0@droids-corp.org>
3  */
4
5 /**
6  * Node parse API.
7  *
8  * The parse operation is to check if an input (a string or vector of
9  * strings) matches the node tree. On success, the result is stored in a
10  * tree that describes which part of the input matches which node.
11  */
12
13 #ifndef ECOLI_PARSE_
14 #define ECOLI_PARSE_
15
16 #include <sys/queue.h>
17 #include <sys/types.h>
18 #include <limits.h>
19 #include <stdio.h>
20 #include <stdbool.h>
21
22 struct ec_node;
23 struct ec_parse;
24
25 /**
26  * Create an empty parse tree.
27  *
28  * @return
29  *   The empty parse tree.
30  */
31 struct ec_parse *ec_parse(const struct ec_node *node);
32
33 /**
34  *
35  *
36  *
37  */
38 void ec_parse_free(struct ec_parse *parse);
39
40 /**
41  *
42  *
43  *
44  */
45 void ec_parse_free_children(struct ec_parse *parse);
46
47 /**
48  *
49  *
50  *
51  */
52 struct ec_parse *ec_parse_dup(const struct ec_parse *parse);
53
54 /**
55  *
56  *
57  *
58  */
59 // _get_ XXX
60 const struct ec_strvec *ec_parse_strvec(const struct ec_parse *parse);
61
62 /* a NULL return value is an error, with errno set
63   ENOTSUP: no ->parse() operation
64 */
65 /**
66  *
67  *
68  *
69  */
70 struct ec_parse *ec_node_parse(const struct ec_node *node, const char *str);
71
72 /**
73  *
74  *
75  *
76  */
77 struct ec_parse *ec_node_parse_strvec(const struct ec_node *node,
78                                 const struct ec_strvec *strvec);
79
80 /**
81  *
82  *
83  *
84  */
85 #define EC_PARSE_NOMATCH INT_MAX
86
87 /* internal: used by nodes
88  *
89  * state is the current parse tree, which is built piece by piece while
90  *   parsing the node tree: ec_node_parse_child() creates a new child in
91  *   this state parse tree, and calls the parse() method for the child
92  *   node, with state pointing to this new child. If it does not match,
93  *   the child is removed in the state, else it is kept, with its
94  *   possible descendants.
95  *
96  * return:
97  * the number of matched strings in strvec on success
98  * EC_PARSE_NOMATCH (positive) if it does not match
99  * -1 on error, and errno is set
100  */
101 int ec_node_parse_child(const struct ec_node *node,
102                         struct ec_parse *state,
103                         const struct ec_strvec *strvec);
104
105 /**
106  *
107  *
108  *
109  */
110 void ec_parse_link_child(struct ec_parse *parse,
111                         struct ec_parse *child);
112 /**
113  *
114  *
115  *
116  */
117 void ec_parse_unlink_child(struct ec_parse *parse,
118                         struct ec_parse *child);
119
120 /* keep the const */
121 #define ec_parse_get_root(parse) ({                             \
122         const struct ec_parse *p_ = parse; /* check type */     \
123         struct ec_parse *parse_ = (struct ec_parse *)parse;     \
124         typeof(parse) res_;                                     \
125         (void)p_;                                               \
126         res_ = __ec_parse_get_root(parse_);                     \
127         res_;                                                   \
128 })
129
130 /**
131  *
132  *
133  *
134  */
135 struct ec_parse *__ec_parse_get_root(struct ec_parse *parse);
136
137 /**
138  *
139  *
140  *
141  */
142 struct ec_parse *ec_parse_get_parent(const struct ec_parse *parse);
143
144 /**
145  * Get the first child of a tree.
146  *
147  */
148 struct ec_parse *ec_parse_get_first_child(const struct ec_parse *parse);
149
150 /**
151  *
152  *
153  *
154  */
155 struct ec_parse *ec_parse_get_last_child(const struct ec_parse *parse);
156
157 /**
158  *
159  *
160  *
161  */
162 struct ec_parse *ec_parse_get_next(const struct ec_parse *parse);
163
164 /**
165  *
166  *
167  *
168  */
169 #define EC_PARSE_FOREACH_CHILD(child, parse)                    \
170         for (child = ec_parse_get_first_child(parse);           \
171                 child != NULL;                                  \
172                 child = ec_parse_get_next(child))               \
173
174 /**
175  *
176  *
177  *
178  */
179 bool ec_parse_has_child(const struct ec_parse *parse);
180
181 /**
182  *
183  *
184  *
185  */
186 const struct ec_node *ec_parse_get_node(const struct ec_parse *parse);
187
188 /**
189  *
190  *
191  *
192  */
193 void ec_parse_del_last_child(struct ec_parse *parse);
194
195 /**
196  *
197  *
198  *
199  */
200 struct ec_keyval *ec_parse_get_attrs(struct ec_parse *parse);
201
202 /**
203  *
204  *
205  *
206  */
207 void ec_parse_dump(FILE *out, const struct ec_parse *parse);
208
209 /**
210  *
211  *
212  *
213  */
214 struct ec_parse *ec_parse_find_first(struct ec_parse *parse,
215         const char *id);
216
217 /**
218  * Iterate among parse tree
219  *
220  * Use it with:
221  * for (iter = state; iter != NULL; iter = ec_parse_iter_next(iter))
222  */
223 struct ec_parse *ec_parse_iter_next(struct ec_parse *parse);
224
225 /**
226  *
227  *
228  *
229  */
230 size_t ec_parse_len(const struct ec_parse *parse);
231
232 /**
233  *
234  *
235  *
236  */
237 size_t ec_parse_matches(const struct ec_parse *parse);
238
239 #endif