1 /* 2 * ilist.h 3 * 4 * Generic lists in C 5 * 6 * Author: MontaVista Software, Inc. 7 * Corey Minyard <minyard@mvista.com> 8 * source@mvista.com 9 * 10 * Copyright 2002,2003,2004,2005 MontaVista Software Inc. 11 * 12 * This software is available to you under a choice of one of two 13 * licenses. You may choose to be licensed under the terms of the GNU 14 * Lesser General Public License (GPL) Version 2 or the modified BSD 15 * license below. The following disclamer applies to both licenses: 16 * 17 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED 18 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 19 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 22 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 23 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 24 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR 25 * TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE 26 * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 * 28 * GNU Lesser General Public Licence 29 * 30 * This program is free software; you can redistribute it and/or 31 * modify it under the terms of the GNU Lesser General Public License 32 * as published by the Free Software Foundation; either version 2 of 33 * the License, or (at your option) any later version. 34 * 35 * You should have received a copy of the GNU Lesser General Public 36 * License along with this program; if not, write to the Free 37 * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 38 * 39 * Modified BSD Licence 40 * 41 * Redistribution and use in source and binary forms, with or without 42 * modification, are permitted provided that the following conditions 43 * are met: 44 * 45 * 1. Redistributions of source code must retain the above copyright 46 * notice, this list of conditions and the following disclaimer. 47 * 2. Redistributions in binary form must reproduce the above 48 * copyright notice, this list of conditions and the following 49 * disclaimer in the documentation and/or other materials provided 50 * with the distribution. 51 * 3. The name of the author may not be used to endorse or promote 52 * products derived from this software without specific prior 53 * written permission. 54 */ 55 56 #ifndef OPENIPMI_ILIST_H 57 #define OPENIPMI_ILIST_H 58 59 typedef struct ilist_s ilist_t; 60 typedef struct ilist_iter_s ilist_iter_t; 61 62 /* This is only so the user can supply their own data chunks for the 63 list entries. This is ugly, but it allows the user to pre-allocate 64 (or allocate as part of the entry) the data for the list chunks, 65 and avoid having to worry about error returns from the list 66 operations. */ 67 typedef struct ilist_item_s ilist_item_t; 68 69 /* Returns NULL on failure. */ 70 ilist_t *alloc_ilist(void); 71 ilist_iter_t *alloc_ilist_iter(ilist_t *list); 72 void free_ilist(ilist_t *list); 73 void free_ilist_iter(ilist_iter_t *iter); 74 75 /* Returns true if the list is empty, false if not. */ 76 int ilist_empty(ilist_t *list); 77 78 /* Return false on failure, true on success. entry may be NULL, 79 meaning you want the ilist code to supply the entry. If you supply 80 an entry, the "malloced" flag will be set to zero for you. */ 81 int ilist_add_head(ilist_t *list, void *item, ilist_item_t *entry); 82 int ilist_add_tail(ilist_t *list, void *item, ilist_item_t *entry); 83 int ilist_add_before(ilist_iter_t *iter, void *item, ilist_item_t *entry); 84 int ilist_add_after(ilist_iter_t *iter, void *item, ilist_item_t *entry); 85 86 /* Return false on failure, true on success. This will return a 87 failure (false) if you try to position past the end of the array or 88 try to set first or last on an empty array. In that case it will 89 leave the iterator unchanged. */ 90 int ilist_first(ilist_iter_t *iter); 91 int ilist_last(ilist_iter_t *iter); 92 int ilist_next(ilist_iter_t *iter); 93 int ilist_prev(ilist_iter_t *iter); 94 95 /* Remove the first or last item from the list. It will be deleted 96 from the list and returned. If the list is empty, NULL will be 97 returned. */ 98 void *ilist_remove_first(ilist_t *list); 99 void *ilist_remove_last(ilist_t *list); 100 101 /* Remove a given item from the list, if it is there. Return 1 if it 102 was found and 0 if it was not found. */ 103 int ilist_remove_item_from_list(ilist_t *list, void *item); 104 105 /* Returns failue (false) if unpositioned. */ 106 int ilist_delete(ilist_iter_t *iter); /* Position on next element after del */ 107 108 /* Set unpositioned. Next will go to the first item, prev to the last 109 item. */ 110 void ilist_unpositioned(ilist_iter_t *iter); 111 112 /* Returns NULL if unpositioned or list empty. */ 113 void *ilist_get(ilist_iter_t *iter); 114 115 /* This should return true if the item matches, false if not. */ 116 typedef int (*ilist_search_cb)(void *item, void *cb_data); 117 118 /* Search forward (starting at the next item) for something. Returns 119 NULL if not found, the item if found. iter will be positioned on 120 the item, too. To search from the beginning, set the iterator to 121 the "unpositioined" position. */ 122 void *ilist_search_iter(ilist_iter_t *iter, ilist_search_cb cmp, void *cb_data); 123 124 /* Search from the beginning, but without an iterator. This will return 125 the first item found. */ 126 void *ilist_search(ilist_t *list, ilist_search_cb cmp, void *cb_data); 127 128 /* Called with an iterator positioned on the item. */ 129 typedef void (*ilist_iter_cb)(ilist_iter_t *iter, void *item, void *cb_data); 130 131 /* Call the given handler for each item in the list. You may delete 132 the current item the iterator references while this is happening, 133 but no other items. */ 134 void ilist_iter(ilist_t *list, ilist_iter_cb handler, void *cb_data); 135 136 /* Call the given handler for each item in the list, but run the list 137 backwards. You may delete the current item the iterator references 138 while this is happening, but no other items. */ 139 void ilist_iter_rev(ilist_t *list, ilist_iter_cb handler, void *cb_data); 140 141 /* Initialize a statically declared iterator. */ 142 void ilist_init_iter(ilist_iter_t *iter, ilist_t *list); 143 144 /* Return -1 if item1 < item2, 0 if item1 == item2, and 1 if item1 > item2 */ 145 typedef int (*ilist_sort_cb)(void *item1, void *item2); 146 147 void ilist_sort(ilist_t *list, ilist_sort_cb cmp); 148 149 /* A two-item list. This is useful for managing list of handlers 150 where you have a callback handler and a data item. You create it 151 with the given two data items, and when you call 152 ilist_iter_twoitem, it will call the handler you pass in with the 153 two data items you have given. */ 154 155 typedef void (*ilist_twoitem_cb)(void *data, void *cb_data1, void *cb_data2); 156 157 /* Add an entry to the list. Returns 0 upon failure, 1 if successful. 158 Duplicates are allowed. */ 159 int ilist_add_twoitem(ilist_t *list, void *cb_data1, void *cb_data2); 160 161 /* Remove an entry, returns 1 if present, 0 if not. */ 162 int ilist_remove_twoitem(ilist_t *list, void *cb_data1, void *cb_data2); 163 164 /* Returns 1 if the entry exists in the list, 0 if not. */ 165 int ilist_twoitem_exists(ilist_t *list, void *cb_data1, void *cb_data2); 166 167 /* Call all the callbacks in the list */ 168 void ilist_iter_twoitem(ilist_t *ilist, ilist_twoitem_cb handler, void *data); 169 170 void ilist_twoitem_destroy(ilist_t *list); 171 172 /* Internal data structures, DO NOT USE THESE. */ 173 174 struct ilist_item_s 175 { 176 int malloced; 177 ilist_item_t *next, *prev; 178 void *item; 179 }; 180 181 struct ilist_s 182 { 183 ilist_item_t *head; 184 }; 185 186 struct ilist_iter_s 187 { 188 ilist_t *list; 189 ilist_item_t *curr; 190 }; 191 192 /* You must define these. */ 193 void *ilist_mem_alloc(size_t size); 194 void ilist_mem_free(void *data); 195 196 #endif /* OPENIPMI_ILIST_H */ 197