~ubuntu-branches/ubuntu/trusty/net-snmp/trusty

« back to all changes in this revision

Viewing changes to snmplib/container_list_ssll.c

  • Committer: Bazaar Package Importer
  • Author(s): Martin Pitt
  • Date: 2004-09-13 12:06:21 UTC
  • Revision ID: james.westby@ubuntu.com-20040913120621-g952ntonlleihcvm
Tags: upstream-5.1.1
ImportĀ upstreamĀ versionĀ 5.1.1

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/*
 
2
 * container_list_sl.c
 
3
 * $Id: container_list_ssll.c,v 1.3.2.1 2004/02/04 11:25:20 slif Exp $
 
4
 *
 
5
 */
 
6
 
 
7
#include <net-snmp/net-snmp-config.h>
 
8
 
 
9
#include <stdio.h>
 
10
#if HAVE_STDLIB_H
 
11
#include <stdlib.h>
 
12
#endif
 
13
#if HAVE_MALLOC_H
 
14
#include <malloc.h>
 
15
#endif
 
16
#include <sys/types.h>
 
17
#if HAVE_STRING_H
 
18
#include <string.h>
 
19
#else
 
20
#include <strings.h>
 
21
#endif
 
22
 
 
23
#include <net-snmp/net-snmp-includes.h>
 
24
#include <net-snmp/types.h>
 
25
#include <net-snmp/library/snmp_api.h>
 
26
#include <net-snmp/library/container.h>
 
27
#include <net-snmp/library/tools.h>
 
28
#include <net-snmp/library/snmp_assert.h>
 
29
 
 
30
#include <net-snmp/library/container_list_ssll.h>
 
31
 
 
32
typedef struct sl_node {
 
33
   const void     *data;
 
34
   struct sl_node *next;
 
35
} sl_node;
 
36
 
 
37
typedef struct sl_container_s {
 
38
   netsnmp_container          c;
 
39
   
 
40
   size_t                     count;      /* Index of the next free entry */
 
41
   sl_node                   *head;       /* head of list */
 
42
} sl_container;
 
43
 
 
44
 
 
45
static void *
 
46
_get(netsnmp_container *c, const void *key, int exact)
 
47
{
 
48
    sl_container *sl = (sl_container*)c;
 
49
    sl_node  *curr = sl->head;
 
50
    
 
51
    if( (NULL != curr) && (NULL != key)) {
 
52
        while (curr) {
 
53
            if (sl->c.compare(curr->data, key) == 0)
 
54
                break;
 
55
            curr = curr->next;
 
56
        }
 
57
        
 
58
        if((curr) && (!exact)) {
 
59
            curr = curr->next;
 
60
        }
 
61
    }
 
62
 
 
63
    return curr ? (void *)curr->data : NULL;
 
64
}
 
65
 
 
66
/**********************************************************************
 
67
 *
 
68
 *
 
69
 *
 
70
 **********************************************************************/
 
71
static void
 
72
_ssll_free(netsnmp_container *c)
 
73
{
 
74
    if(c) {
 
75
        free(c);
 
76
    }
 
77
}
 
78
 
 
79
static void *
 
80
_ssll_find(netsnmp_container *c, const void *data)
 
81
{
 
82
    if((NULL == c) || (NULL == data))
 
83
        return NULL;
 
84
 
 
85
    return _get(c, data, 1);
 
86
}
 
87
 
 
88
static void *
 
89
_ssll_find_next(netsnmp_container *c, const void *data)
 
90
{
 
91
    if(NULL == c)
 
92
        return NULL;
 
93
 
 
94
    return _get(c, data, 0);
 
95
}
 
96
 
 
97
static int
 
98
_ssll_insert(netsnmp_container *c, const void *data)
 
99
{
 
100
    sl_container *sl = (sl_container*)c;
 
101
    sl_node  *new_node;
 
102
    
 
103
    if(NULL == c)
 
104
        return -1;
 
105
 
 
106
    new_node = SNMP_MALLOC_TYPEDEF(sl_node);
 
107
    if(NULL == new_node)
 
108
        return -1;
 
109
    new_node->data = data;
 
110
    
 
111
    if(NULL == sl->head) {
 
112
        sl->head = new_node;
 
113
    }
 
114
    else {
 
115
        sl_node *curr = sl->head, *last = NULL;
 
116
        for( ; curr; last = curr, curr = curr->next) {
 
117
            if(sl->c.compare(curr->data, data) > 0)
 
118
                break;
 
119
        }
 
120
        if(NULL == last) {
 
121
            new_node->next = sl->head;
 
122
            sl->head = new_node;
 
123
        }
 
124
        else {
 
125
            new_node->next = last->next;
 
126
            last->next = new_node;
 
127
        }
 
128
    }
 
129
    ++sl->count;
 
130
    return 0;
 
131
}
 
132
 
 
133
static int
 
134
_ssll_remove(netsnmp_container *c, const void *data)
 
135
{
 
136
    sl_container *sl = (sl_container*)c;
 
137
    sl_node  *curr = sl->head;
 
138
    
 
139
    if((NULL == c) || (NULL == curr))
 
140
        return -1;
 
141
 
 
142
    if(sl->c.compare(sl->head->data, data) == 0) {
 
143
        curr = sl->head;
 
144
        sl->head = sl->head->next;
 
145
    }
 
146
    else {
 
147
        sl_node *last = sl->head;
 
148
        for(curr = sl->head->next ; curr; last = curr, curr = curr->next)
 
149
            if(sl->c.compare(curr->data, data) == 0) {
 
150
                last->next = curr->next;
 
151
                break;
 
152
            }
 
153
    }
 
154
 
 
155
    if(NULL == curr)
 
156
        return -2;
 
157
    
 
158
    /*
 
159
     * free our node structure, but not the data
 
160
     */
 
161
    free(curr);
 
162
    --sl->count;
 
163
    
 
164
    return 0;
 
165
}
 
166
 
 
167
static size_t
 
168
_ssll_size(netsnmp_container *c)
 
169
{
 
170
    sl_container *sl = (sl_container*)c;
 
171
    
 
172
    if(NULL == c)
 
173
        return 0;
 
174
 
 
175
    return sl->count;
 
176
}
 
177
 
 
178
static void
 
179
_ssll_for_each(netsnmp_container *c, netsnmp_container_obj_func *f,
 
180
             void *context)
 
181
{
 
182
    sl_container *sl = (sl_container*)c;
 
183
    sl_node  *curr;
 
184
    
 
185
    if(NULL == c)
 
186
        return;
 
187
    
 
188
    for(curr = sl->head; curr; curr = curr->next)
 
189
        (*f) ((void *)curr->data, context);
 
190
}
 
191
 
 
192
/**********************************************************************
 
193
 *
 
194
 *
 
195
 *
 
196
 **********************************************************************/
 
197
netsnmp_container *
 
198
netsnmp_container_get_ssll(void)
 
199
{
 
200
    /*
 
201
     * allocate memory
 
202
     */
 
203
    sl_container *sl = SNMP_MALLOC_TYPEDEF(sl_container);
 
204
    if (NULL==sl) {
 
205
        snmp_log(LOG_ERR, "couldn't allocate memory\n");
 
206
        return NULL;
 
207
    }
 
208
 
 
209
    sl->c.cfree = (netsnmp_container_rc*)_ssll_free;
 
210
        
 
211
    sl->c.get_size = _ssll_size;
 
212
    sl->c.init = NULL;
 
213
    sl->c.insert = _ssll_insert;
 
214
    sl->c.remove = _ssll_remove;
 
215
    sl->c.find = _ssll_find;
 
216
    sl->c.find_next = _ssll_find_next;
 
217
    sl->c.get_subset = NULL;
 
218
    sl->c.get_iterator = NULL;
 
219
    sl->c.for_each = _ssll_for_each;
 
220
 
 
221
       
 
222
    return (netsnmp_container*)sl;
 
223
}
 
224
 
 
225
netsnmp_factory *
 
226
netsnmp_container_get_ssll_factory(void)
 
227
{
 
228
    static netsnmp_factory f = {"sorted_singly_linked_list",
 
229
                                (netsnmp_factory_produce_f*)
 
230
                                netsnmp_container_get_ssll };
 
231
    
 
232
    return &f;
 
233
}
 
234
 
 
235
void
 
236
netsnmp_container_ssll_init(void)
 
237
{
 
238
    netsnmp_container_register("sorted_singly_linked_list",
 
239
                               netsnmp_container_get_ssll_factory());
 
240
}