Subversion Repositories Kolibri OS

Rev

Go to most recent revision | Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
4358 Serge 1
/**************************************************************************
2
 *
3
 * Copyright 2010 LunarG, Inc.
4
 * All Rights Reserved.
5
 *
6
 * Permission is hereby granted, free of charge, to any person obtaining a
7
 * copy of this software and associated documentation files (the
8
 * "Software"), to deal in the Software without restriction, including
9
 * without limitation the rights to use, copy, modify, merge, publish,
10
 * distribute, sub license, and/or sell copies of the Software, and to
11
 * permit persons to whom the Software is furnished to do so, subject to
12
 * the following conditions:
13
 *
14
 * The above copyright notice and this permission notice (including the
15
 * next paragraph) shall be included in all copies or substantial portions
16
 * of the Software.
17
 *
18
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
21
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
23
 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
24
 * DEALINGS IN THE SOFTWARE.
25
 *
26
 **************************************************************************/
27
 
28
 
29
#include 
30
#include 
31
 
32
#include "egllog.h"
33
#include "eglarray.h"
34
 
35
 
36
/**
37
 * Grow the size of the array.
38
 */
39
static EGLBoolean
40
_eglGrowArray(_EGLArray *array)
41
{
42
   EGLint new_size;
43
   void **elems;
44
 
45
   new_size = array->MaxSize;
46
   while (new_size <= array->Size)
47
      new_size *= 2;
48
 
49
   elems = realloc(array->Elements, new_size * sizeof(array->Elements[0]));
50
   if (!elems) {
51
      _eglLog(_EGL_DEBUG, "failed to grow %s array to %d",
52
            array->Name, new_size);
53
      return EGL_FALSE;
54
   }
55
 
56
   array->Elements = elems;
57
   array->MaxSize = new_size;
58
 
59
   return EGL_TRUE;
60
}
61
 
62
 
63
/**
64
 * Create an array.
65
 */
66
_EGLArray *
67
_eglCreateArray(const char *name, EGLint init_size)
68
{
69
   _EGLArray *array;
70
 
71
   array = calloc(1, sizeof(*array));
72
   if (array) {
73
      array->Name = name;
74
      array->MaxSize = (init_size > 0) ? init_size : 1;
75
      if (!_eglGrowArray(array)) {
76
         free(array);
77
         array = NULL;
78
      }
79
   }
80
 
81
   return array;
82
}
83
 
84
 
85
/**
86
 * Destroy an array, optionally free the data.
87
 */
88
void
89
_eglDestroyArray(_EGLArray *array, void (*free_cb)(void *))
90
{
91
   if (free_cb) {
92
      EGLint i;
93
      for (i = 0; i < array->Size; i++)
94
         free_cb(array->Elements[i]);
95
   }
96
   free(array->Elements);
97
   free(array);
98
}
99
 
100
 
101
/**
102
 * Append a element to an array.
103
 */
104
void
105
_eglAppendArray(_EGLArray *array, void *elem)
106
{
107
   if (array->Size >= array->MaxSize && !_eglGrowArray(array))
108
      return;
109
 
110
   array->Elements[array->Size++] = elem;
111
}
112
 
113
 
114
/**
115
 * Erase an element from an array.
116
 */
117
void
118
_eglEraseArray(_EGLArray *array, EGLint i, void (*free_cb)(void *))
119
{
120
   if (free_cb)
121
      free_cb(array->Elements[i]);
122
   if (i < array->Size - 1) {
123
      memmove(&array->Elements[i], &array->Elements[i + 1],
124
            (array->Size - i - 1) * sizeof(array->Elements[0]));
125
   }
126
   array->Size--;
127
}
128
 
129
 
130
/**
131
 * Find in an array for the given element.
132
 */
133
void *
134
_eglFindArray(_EGLArray *array, void *elem)
135
{
136
   EGLint i;
137
 
138
   if (!array)
139
      return NULL;
140
 
141
   for (i = 0; i < array->Size; i++)
142
      if (array->Elements[i] == elem)
143
         return elem;
144
   return NULL;
145
}
146
 
147
 
148
/**
149
 * Filter an array and return the number of filtered elements.
150
 */
151
EGLint
152
_eglFilterArray(_EGLArray *array, void **data, EGLint size,
153
                _EGLArrayForEach filter, void *filter_data)
154
{
155
   EGLint count = 0, i;
156
 
157
   if (!array)
158
      return 0;
159
 
160
   if (filter) {
161
      for (i = 0; i < array->Size; i++) {
162
         if (filter(array->Elements[i], filter_data)) {
163
            if (data && count < size)
164
               data[count] = array->Elements[i];
165
            count++;
166
         }
167
         if (data && count >= size)
168
            break;
169
      }
170
   }
171
   else {
172
      if (data) {
173
         count = (size < array->Size) ? size : array->Size;
174
         memcpy(data, array->Elements, count * sizeof(array->Elements[0]));
175
      }
176
      else {
177
         count = array->Size;
178
      }
179
   }
180
 
181
   return count;
182
}
183
 
184
 
185
/**
186
 * Flatten an array by converting array elements into another form and store
187
 * them in a buffer.
188
 */
189
EGLint
190
_eglFlattenArray(_EGLArray *array, void *buffer, EGLint elem_size, EGLint size,
191
                 _EGLArrayForEach flatten)
192
{
193
   EGLint i, count;
194
 
195
   if (!array)
196
      return 0;
197
 
198
   count = array->Size;
199
   if (buffer) {
200
      /* do not exceed buffer size */
201
      if (count > size)
202
         count = size;
203
      for (i = 0; i < count; i++)
204
         flatten(array->Elements[i],
205
               (void *) ((char *) buffer + elem_size * i));
206
   }
207
 
208
   return count;
209
}