~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/dynamic_array.cc

  • Committer: Mark Atwood
  • Date: 2011-08-11 03:05:03 UTC
  • mfrom: (2385.1.12 refactor4)
  • Revision ID: me@mark.atwood.name-20110811030503-rp9xjihc5x3y0x4q
mergeĀ lp:~olafvdspek/drizzle/refactor4

Show diffs side-by-side

added added

removed removed

Lines of Context:
15
15
 
16
16
/* Handling of arrays that can grow dynamicly. */
17
17
 
18
 
#include "config.h"
19
 
#include "drizzled/internal/my_sys.h"
20
 
#include "drizzled/internal/m_string.h"
21
 
 
 
18
#include <config.h>
22
19
#include <algorithm>
 
20
#include <drizzled/dynamic_array.h>
 
21
#include <drizzled/internal/my_sys.h>
23
22
 
24
23
using namespace std;
25
24
 
26
 
namespace drizzled
27
 
{
28
 
 
29
 
static bool allocate_dynamic(DYNAMIC_ARRAY *array, uint32_t max_elements);
 
25
namespace drizzled {
30
26
 
31
27
/*
32
28
  Initiate dynamic array
50
46
    false       Ok
51
47
*/
52
48
 
53
 
bool init_dynamic_array2(DYNAMIC_ARRAY *array, uint32_t element_size,
 
49
void init_dynamic_array2(DYNAMIC_ARRAY *array, uint32_t element_size,
54
50
                            void *init_buffer, uint32_t init_alloc,
55
51
                            uint32_t alloc_increment)
56
52
{
66
62
    init_alloc=alloc_increment;
67
63
    init_buffer= 0;
68
64
  }
69
 
  array->elements=0;
 
65
  array->set_size(0);
70
66
  array->max_element=init_alloc;
71
67
  array->alloc_increment=alloc_increment;
72
68
  array->size_of_element=element_size;
73
69
  if ((array->buffer= (unsigned char*) init_buffer))
74
 
    return(false);
75
 
  if (!(array->buffer=(unsigned char*) malloc(element_size*init_alloc)))
76
 
  {
77
 
    array->max_element=0;
78
 
    return(true);
79
 
  }
80
 
  return(false);
 
70
    return;
 
71
  array->buffer= (unsigned char*) malloc(element_size*init_alloc);
81
72
}
82
73
 
83
74
/*
93
84
    false       Ok
94
85
*/
95
86
 
96
 
bool insert_dynamic(DYNAMIC_ARRAY *array, unsigned char* element)
 
87
static void insert_dynamic(DYNAMIC_ARRAY *array, void* element)
97
88
{
98
89
  unsigned char* buffer;
99
 
  if (array->elements == array->max_element)
100
 
  {                                             /* Call only when nessesary */
101
 
    if (!(buffer=alloc_dynamic(array)))
102
 
      return true;
103
 
  }
 
90
  if (array->size() == array->max_element)
 
91
    buffer= alloc_dynamic(array);
104
92
  else
105
93
  {
106
 
    buffer=array->buffer+(array->elements * array->size_of_element);
107
 
    array->elements++;
 
94
    buffer= array->buffer+(array->size() * array->size_of_element);
 
95
    array->set_size(array->size() + 1);
108
96
  }
109
 
  memcpy(buffer,element,(size_t) array->size_of_element);
110
 
  return false;
 
97
  memcpy(buffer,element, array->size_of_element);
 
98
}
 
99
 
 
100
void DYNAMIC_ARRAY::push_back(void* v)
 
101
{
 
102
  insert_dynamic(this, v);
111
103
}
112
104
 
113
105
 
130
122
 
131
123
unsigned char *alloc_dynamic(DYNAMIC_ARRAY *array)
132
124
{
133
 
  if (array->elements == array->max_element)
 
125
  if (array->size() == array->max_element)
134
126
  {
135
127
    char *new_ptr;
136
128
    if (array->buffer == (unsigned char *)(array + 1))
139
131
        In this senerio, the buffer is statically preallocated,
140
132
        so we have to create an all-new malloc since we overflowed
141
133
      */
142
 
      if (!(new_ptr= (char *) malloc((array->max_element+
143
 
                                     array->alloc_increment) *
144
 
                                     array->size_of_element)))
145
 
        return 0;
146
 
      memcpy(new_ptr, array->buffer,
147
 
             array->elements * array->size_of_element);
 
134
      new_ptr= (char*) malloc((array->max_element + array->alloc_increment) * array->size_of_element);
 
135
      memcpy(new_ptr, array->buffer, array->size() * array->size_of_element);
148
136
    }
149
 
    else if (!(new_ptr= (char*) realloc(array->buffer,
150
 
                                        (array->max_element+
151
 
                                         array->alloc_increment)*
152
 
                                        array->size_of_element)))
153
 
      return 0;
 
137
    else 
 
138
      new_ptr= (char*) realloc(array->buffer, (array->max_element + array->alloc_increment) * array->size_of_element);
154
139
    array->buffer= (unsigned char*) new_ptr;
155
140
    array->max_element+=array->alloc_increment;
156
141
  }
157
 
  return array->buffer+(array->elements++ * array->size_of_element);
158
 
}
159
 
 
160
 
 
161
 
/*
162
 
  Pop last element from array.
163
 
 
164
 
  SYNOPSIS
165
 
    pop_dynamic()
166
 
      array
167
 
 
168
 
  RETURN VALUE
169
 
    pointer     Ok
170
 
    0           Array is empty
171
 
*/
172
 
 
173
 
unsigned char *pop_dynamic(DYNAMIC_ARRAY *array)
174
 
{
175
 
  if (array->elements)
176
 
    return array->buffer+(--array->elements * array->size_of_element);
177
 
  return 0;
178
 
}
179
 
 
180
 
/*
181
 
  Replace element in array with given element and index
182
 
 
183
 
  SYNOPSIS
184
 
    set_dynamic()
185
 
      array
186
 
      element   Element to be inserted
187
 
      idx       Index where element is to be inserted
188
 
 
189
 
  DESCRIPTION
190
 
    set_dynamic() replaces element in array.
191
 
    If idx > max_element insert new element. Allocate memory if needed.
192
 
 
193
 
  RETURN VALUE
194
 
    true        Idx was out of range and allocation of new memory failed
195
 
    false       Ok
196
 
*/
197
 
 
198
 
bool set_dynamic(DYNAMIC_ARRAY *array, unsigned char* element, uint32_t idx)
199
 
{
200
 
  if (idx >= array->elements)
201
 
  {
202
 
    if (idx >= array->max_element && allocate_dynamic(array, idx))
203
 
      return true;
204
 
    memset(array->buffer+array->elements*array->size_of_element, 0,
205
 
           (idx - array->elements)*array->size_of_element);
206
 
    array->elements=idx+1;
207
 
  }
208
 
  memcpy(array->buffer+(idx * array->size_of_element),element,
209
 
         (size_t) array->size_of_element);
210
 
  return false;
211
 
}
212
 
 
213
 
 
214
 
/*
215
 
  Ensure that dynamic array has enough elements
216
 
 
217
 
  SYNOPSIS
218
 
    allocate_dynamic()
219
 
    array
220
 
    max_elements        Numbers of elements that is needed
221
 
 
222
 
  NOTES
223
 
   Any new allocated element are NOT initialized
224
 
 
225
 
  RETURN VALUE
226
 
    false       Ok
227
 
    true        Allocation of new memory failed
228
 
*/
229
 
 
230
 
static bool allocate_dynamic(DYNAMIC_ARRAY *array, uint32_t max_elements)
231
 
{
232
 
  if (max_elements >= array->max_element)
233
 
  {
234
 
    uint32_t size;
235
 
    unsigned char *new_ptr;
236
 
    size= (max_elements + array->alloc_increment)/array->alloc_increment;
237
 
    size*= array->alloc_increment;
238
 
    if (array->buffer == (unsigned char *)(array + 1))
239
 
    {
240
 
       /*
241
 
         In this senerio, the buffer is statically preallocated,
242
 
         so we have to create an all-new malloc since we overflowed
243
 
       */
244
 
       if (!(new_ptr= (unsigned char *) malloc(size *
245
 
                                               array->size_of_element)))
246
 
         return 0;
247
 
       memcpy(new_ptr, array->buffer,
248
 
              array->elements * array->size_of_element);
249
 
     }
250
 
     else
251
 
 
252
 
 
253
 
    if (!(new_ptr=(unsigned char*) realloc(array->buffer,
254
 
                                        size* array->size_of_element)))
255
 
      return true;
256
 
    array->buffer= new_ptr;
257
 
    array->max_element= size;
258
 
  }
259
 
  return false;
260
 
}
261
 
 
262
 
 
263
 
/*
264
 
  Get an element from array by given index
265
 
 
266
 
  SYNOPSIS
267
 
    get_dynamic()
268
 
      array
269
 
      unsigned char*    Element to be returned. If idx > elements contain zeroes.
270
 
      idx       Index of element wanted.
271
 
*/
272
 
 
273
 
void get_dynamic(DYNAMIC_ARRAY *array, unsigned char* element, uint32_t idx)
274
 
{
275
 
  if (idx >= array->elements)
276
 
  {
277
 
    memset(element, 0, array->size_of_element);
278
 
    return;
279
 
  }
280
 
  memcpy(element,array->buffer+idx*array->size_of_element,
281
 
         (size_t) array->size_of_element);
282
 
}
283
 
 
 
142
  array->set_size(array->size() + 1);
 
143
  return array->buffer + ((array->size() - 1) * array->size_of_element);
 
144
}
284
145
 
285
146
/*
286
147
  Empty array by freeing all memory
296
157
    Just mark as empty if we are using a static buffer
297
158
  */
298
159
  if (array->buffer == (unsigned char *)(array + 1))
299
 
    array->elements= 0;
 
160
    array->set_size(0);
300
161
  else
301
162
  if (array->buffer)
302
163
  {
303
164
    free(array->buffer);
304
165
    array->buffer=0;
305
 
    array->elements=array->max_element=0;
 
166
    array->set_size(array->max_element=0);
306
167
  }
307
168
}
308
169