1 #ifndef NETSNMP_CONTAINER_H
2 #define NETSNMP_CONTAINER_H
5 * WARNING: This is a recently created file, and all of it's contents are
6 * subject to change at any time.
8 * A basic container template. A generic way for code to store and
9 * retrieve data. Allows for interchangable storage algorithms.
11 #ifndef NET_SNMP_CONFIG_H
12 #error "Please include <net-snmp/net-snmp-config.h> before this file"
15 #include <net-snmp/types.h>
16 #include <net-snmp/library/factory.h>
22 /*************************************************************************
24 * function pointer definitions
26 *************************************************************************/
27 struct netsnmp_iterator_s; /** forward declare */
28 struct netsnmp_container_s; /** forward declare */
31 * function returning an int for an operation on a container
33 typedef int (netsnmp_container_rc)(struct netsnmp_container_s *);
36 * function returning an int for an operation on a container
38 typedef struct netsnmp_iterator_s * (netsnmp_container_it)
39 (struct netsnmp_container_s *);
42 * function returning a size_t for an operation on a container
44 typedef size_t (netsnmp_container_size)(struct netsnmp_container_s *);
47 * function returning an int for an operation on an object and
50 typedef int (netsnmp_container_op)(struct netsnmp_container_s *,
54 * function returning an oject for an operation on an object and a
57 typedef void * (netsnmp_container_rtn)(struct netsnmp_container_s *,
61 * function with no return which acts on an object
63 typedef void (netsnmp_container_obj_func)(void *data, void *context);
66 * function with no return which acts on an object
68 typedef void (netsnmp_container_func)(struct netsnmp_container_s *,
69 netsnmp_container_obj_func *,
73 * function returning an array of objects for an operation on an
74 * ojbect and a container
76 typedef netsnmp_void_array * (netsnmp_container_set)
77 (struct netsnmp_container_s *, void *data);
80 * function returning an int for a comparison between two objects
82 typedef int (netsnmp_container_compare)(const void *lhs,
85 /*************************************************************************
89 *************************************************************************/
90 typedef struct netsnmp_container_s {
93 * pointer for container
98 * returns the number of items in a container
100 netsnmp_container_size *get_size;
103 * initialize a container
105 netsnmp_container_rc *init;
108 * release memory used by a container.
110 * Note: if your data structures contained allcoated
111 * memory, you are responsible for releasing that
112 * memory before calling this function!
114 netsnmp_container_rc *cfree;
117 * add an entry to the container
119 netsnmp_container_op *insert;
122 * remove an entry from the container
124 netsnmp_container_op *remove;
127 * Note: do not change the key! If you need to
128 * change a key, remove the entry, change the key,
129 * and the re-add the entry.
133 * find the entry in the container with the same key
136 netsnmp_container_rtn *find;
139 * find the first entry in the container with a key greater than
142 * If the key is NULL, return the first item in the container.
144 netsnmp_container_rtn *find_next;
147 * find all entries iin the container which match the partial key
149 netsnmp_container_set *get_subset;
152 * function to return an iterator for the container
154 struct netsnmp_container_it *get_iterator;
157 * function to call another function for each object in the container
159 netsnmp_container_func *for_each;
162 * function to compare two object stored in the container.
170 netsnmp_container_compare *compare;
173 * same as compare, but RHS will be a partial key
175 netsnmp_container_compare *ncompare;
178 * containers can contain other containers (additional indexes)
180 struct netsnmp_container_s *next, *prev;
185 * initialize a container of container factories. used by
186 * netsnmp_container_find* functions.
188 void netsnmp_container_init_list(void);
191 * register a new container factory
193 int netsnmp_container_register(const char* name, netsnmp_factory *f);
196 * search for and create a container from a list of types or a
199 netsnmp_container * netsnmp_container_find(const char *type_list);
200 netsnmp_container * netsnmp_container_get(const char *type);
203 * search for and create a container from a list of types or a
204 * specific type, using the provided container structure
206 int netsnmp_container_find_noalloc(const char *type_list,
207 netsnmp_container* c);
208 int netsnmp_container_get_noalloc(const char *type, netsnmp_container* c);
213 void netsnmp_container_add_index(netsnmp_container *primary,
214 netsnmp_container *new_index);
218 * commone comparison routines
220 /** first data element is a 'netsnmp_index' */
221 int netsnmp_compare_netsnmp_index(const void *lhs, const void *rhs);
222 int netsnmp_ncompare_netsnmp_index(const void *lhs, const void *rhs);
224 /** first data element is a 'char *' */
225 int netsnmp_compare_cstring(const void * lhs, const void * rhs);
226 int netsnmp_ncompare_cstring(const void * lhs, const void * rhs);
228 /** useful for octet strings */
229 int netsnmp_compare_mem(const char * lhs, size_t lhs_len,
230 const char * rhs, size_t rhs_len);
236 #define CONTAINER_FIRST(x) (x)->find(x,NULL)
237 #define CONTAINER_FIND(x,k) (x)->find(x,k)
238 #define CONTAINER_NEXT(x,k) (x)->find_next(x,k)
239 #define CONTAINER_GET_SUBSET(x,k) (x)->get_subset(x,k)
240 #define CONTAINER_SIZE(x) (x)->get_size(x)
241 #define CONTAINER_ITERATOR(x) (x)->get_iterator(x)
242 #define CONTAINER_COMPARE(x,l,r) (x)->compare(l,r)
243 #define CONTAINER_FOR_EACH(x,f,c) (x)->for_each(x,f,c)
246 * if you are getting multiple definitions of these three
247 * inline functions, you most likely have optimizations turned off for your
248 * compiler (-O flag). Either turn them back on, or make sure that
249 * NETSNMP_INLINE is not defined in net-snmp-config.h.
251 #ifdef NETSNMP_NO_INLINE
252 int CONTAINER_INSERT(netsnmp_container *x, const void *k);
253 int CONTAINER_REMOVE(netsnmp_container *x, const void *k);
254 int CONTAINER_FREE(netsnmp_container *x);
256 /*------------------------------------------------------------------
257 * These functions should EXACTLY match the function version in
258 * container.c. If you change one, change them both.
260 static NETSNMP_INLINE /* gcc docs recommend static w/inline */
261 int CONTAINER_INSERT(netsnmp_container *x, const void *k)
266 if (NULL != x->next) {
267 netsnmp_container *tmp = x->next;
270 rc2 = tmp->insert(tmp,k);
272 snmp_log(LOG_ERR,"error on subcontainer insert (%d)", rc2);
279 /*------------------------------------------------------------------
280 * These functions should EXACTLY match the function version in
281 * container.c. If you change one, change them both.
283 static NETSNMP_INLINE /* gcc docs recommend static w/inline */
284 int CONTAINER_REMOVE(netsnmp_container *x, const void *k)
286 if (NULL != x->next) {
287 netsnmp_container *tmp = x->next;
292 rc = tmp->remove(tmp,k);
294 snmp_log(LOG_ERR,"error on subcontainer remove (%d)", rc);
298 return x->remove(x,k);
301 /*------------------------------------------------------------------
302 * These functions should EXACTLY match the function version in
303 * container.c. If you change one, change them both.
305 static NETSNMP_INLINE /* gcc docs recommend static w/inline */
306 int CONTAINER_FREE(netsnmp_container *x)
309 if (NULL != x->next) {
310 netsnmp_container *tmp = x->next;
315 rc = tmp->cfree(tmp);
317 snmp_log(LOG_ERR,"error on subcontainer cfree (%d)", rc);
325 /*************************************************************************
329 *************************************************************************/
331 * function returning an int for an operation on an iterator
333 typedef int (netsnmp_iterator_rc)(struct netsnmp_iterator_s *);
336 * function returning an int for an operation on an iterator and
337 * an object in the container.
339 typedef int (netsnmp_iterator_rc_op)(struct netsnmp_iterator_s *,
343 * function returning an oject for an operation on an iterator
345 typedef void * (netsnmp_iterator_rtn)(struct netsnmp_iterator_s *);
347 typedef struct netsnmp_iterator_s {
349 netsnmp_container *container;
353 netsnmp_iterator_rc *init;
354 netsnmp_iterator_rc_op *position;
355 netsnmp_iterator_rtn *first;
356 netsnmp_iterator_rtn *next;
357 netsnmp_iterator_rtn *last;
362 #define ITERATOR_FIRST(x) x->first(x)
363 #define ITERATOR_NEXT(x) x->next(x)
364 #define ITERATOR_LAST(x) x->last(x)
367 /*************************************************************************
371 *************************************************************************/
372 typedef struct netsnmp_sorted_container_s {
374 netsnmp_container bc;
377 * methods to manipulate container
380 netsnmp_container_rtn *first;
381 netsnmp_container_rtn *next;
382 netsnmp_container_set *subset;
384 } netsnmp_sorted_container;
388 netsnmp_init_sorted_container(netsnmp_sorted_container *sc,
389 netsnmp_container_rtn *first,
390 netsnmp_container_rtn *next,
391 netsnmp_container_set *subset);
399 #endif /** NETSNMP_CONTAINER_H */