1/*
2 * Copyright (c) 2003 Apple Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. Please obtain a copy of the License at
10 * http://www.opensource.apple.com/apsl/ and read it before using this
11 * file.
12 *
13 * The Original Code and all software distributed under the License are
14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
18 * Please see the License for the specific language governing rights and
19 * limitations under the License.
20 *
21 * @APPLE_LICENSE_HEADER_END@
22 */
23
24/*
25 * dynarray.c
26 * - simple array "object" that grows when needed, and has caller-supplied
27 *   functions to free/duplicate elements
28 */
29
30/*
31 * Modification History
32 *
33 * December 6, 1999	Dieter Siegmund (dieter@apple)
34 * - initial revision
35 */
36
37#include <unistd.h>
38#include <stdlib.h>
39#include <stdio.h>
40#include <sys/types.h>
41#include <strings.h>
42
43#include "dynarray.h"
44
45void
46dynarray_init(dynarray_t * list, dynarray_free_func_t * free_func,
47	      dynarray_copy_func_t * copy_func)
48{
49    ptrlist_init(&list->list);
50    list->free_func = free_func;
51    list->copy_func = copy_func;
52    return;
53}
54
55void
56dynarray_free(dynarray_t * list)
57{
58    void *	element;
59
60    while (ptrlist_remove(&list->list, 0, &element)) {
61	if (element && list->free_func) {
62	    (list->free_func)(element);
63	}
64    }
65    ptrlist_free(&list->list);
66    return;
67}
68
69boolean_t
70dynarray_add(dynarray_t * list, void * element)
71{
72    return (ptrlist_add(&list->list, element));
73}
74
75boolean_t
76dynarray_insert(dynarray_t * list, void * element, int i)
77{
78    return (ptrlist_insert(&list->list, element, i));
79}
80
81boolean_t
82dynarray_remove(dynarray_t * list, int i, void * * element_p)
83{
84    return (ptrlist_remove(&list->list, i , element_p));
85}
86
87boolean_t
88dynarray_free_element(dynarray_t * list, int i)
89{
90    void * p;
91
92    if (dynarray_remove(list, i, &p)) {
93	if (p && list->free_func) {
94	    (*list->free_func)(p);
95	}
96	return (TRUE);
97    }
98    return (FALSE);
99}
100
101boolean_t
102dynarray_dup(dynarray_t * dest, dynarray_t * source)
103{
104    int i;
105
106    dest->copy_func = source->copy_func;
107    dest->free_func = source->free_func;
108    ptrlist_init(&dest->list);
109
110    for (i = 0; i < ptrlist_count(&source->list); i++) {
111	void * element = ptrlist_element(&source->list, i);
112
113	if (element && dest->copy_func) {
114	    element = (*dest->copy_func)(element);
115	}
116	ptrlist_add(&dest->list, element);
117    }
118    return (TRUE);
119}
120
121#if 0
122/* concatenates extra onto list */
123boolean_t
124dynarray_concat(dynarray_t * list, dynarray_t * extra)
125{
126    if (extra->count == 0)
127	return (TRUE);
128    if (list->el_size != extra->el_size)
129	return (FALSE);
130
131    if ((extra->count + list->count) > list->size) {
132	list->size = extra->count + list->count;
133	if (list->array == NULL)
134	    list->array = malloc(list->el_size * list->size);
135	else
136	    list->array = realloc(list->array,
137				  list->el_size * list->size);
138    }
139    if (list->array == NULL)
140	return (FALSE);
141    bcopy(extra->array, list->array + list->count,
142	  extra->count * list->el_size);
143    list->count += extra->count;
144    return (TRUE);
145}
146#endif /* 0 */
147
148int
149dynarray_count(dynarray_t * list)
150{
151    return (ptrlist_count(&list->list));
152}
153
154void *
155dynarray_element(dynarray_t * list, int i)
156{
157    return (ptrlist_element(&list->list, i));
158}
159
160int
161dynarray_index(dynarray_t * list, void * element)
162{
163    return (ptrlist_index(&list->list, element));
164}
165
166