| rev |
line source |
|
Me@11
|
1 /*
|
|
Me@11
|
2 * Copyright 2010 OpenSourceCodeStewardshipFoundation
|
|
Me@11
|
3 *
|
|
Me@11
|
4 * Licensed under BSD
|
|
Me@11
|
5 */
|
|
Me@11
|
6
|
|
Me@11
|
7
|
|
Me@11
|
8
|
|
Me@11
|
9 #include <stdio.h>
|
|
Me@11
|
10 #include <malloc.h>
|
|
Me@11
|
11
|
|
Me@11
|
12 #include "DynArray.h"
|
|
Me@11
|
13
|
|
Me@11
|
14
|
|
Me@11
|
15
|
|
Me@11
|
16 DynArrayInfo *
|
|
Me@11
|
17 makeDynArrayInfoFrom( void ***addrOfPtrToArray, int32 sizeOfArray )
|
|
Me@11
|
18 { DynArrayInfo *info;
|
|
Me@11
|
19
|
|
Me@11
|
20 info = malloc( sizeof(DynArrayInfo) );
|
|
Me@11
|
21
|
|
Me@11
|
22 info->addrOfPtrToArray = addrOfPtrToArray;
|
|
Me@11
|
23 info->sizeOfArray = sizeOfArray;
|
|
Me@11
|
24 info->numInArray = 0;
|
|
Me@11
|
25 }
|
|
Me@11
|
26
|
|
Me@11
|
27 DynArrayInfo *
|
|
Me@11
|
28 makeDynArrayOfSize( void ***addrOfPtrToArray, int32 sizeOfArray )
|
|
Me@11
|
29 { DynArrayInfo *info;
|
|
Me@11
|
30
|
|
Me@11
|
31 info = malloc( sizeof(DynArrayInfo) );
|
|
Me@11
|
32
|
|
Me@11
|
33 info->addrOfPtrToArray = addrOfPtrToArray;
|
|
Me@11
|
34
|
|
Me@11
|
35 *(addrOfPtrToArray) = malloc( sizeOfArray * sizeof(void *) );
|
|
Me@11
|
36 info->sizeOfArray = sizeOfArray;
|
|
Me@11
|
37 info->numInArray = 0;
|
|
Me@11
|
38 }
|
|
Me@11
|
39
|
|
Me@11
|
40
|
|
Me@11
|
41 /*A dynamic array is same as any other array, but add a DynArrayInfo next
|
|
Me@11
|
42 * to it. Accesses and updates of array indexes are done normally, it's
|
|
Me@11
|
43 * only when add a new element into array that use the extra info.
|
|
Me@11
|
44 * An add can cause the pointer to the normal array to change.. so must
|
|
Me@11
|
45 * be protected to single VP at a time.
|
|
Me@11
|
46 *
|
|
Me@11
|
47 *Only need to use this Fn when need a new index, higher than any previous
|
|
Me@11
|
48 */
|
|
Me@11
|
49 int32
|
|
Me@11
|
50 addToDynArray( void *value, DynArrayInfo *info )
|
|
Me@11
|
51 { int32 numInArray, sizeOfArray;
|
|
Me@11
|
52 void **array;
|
|
Me@11
|
53
|
|
Me@11
|
54 numInArray = info->numInArray;
|
|
Me@11
|
55 sizeOfArray = info->sizeOfArray;
|
|
Me@11
|
56
|
|
Me@11
|
57 if( numInArray >= sizeOfArray )
|
|
Me@11
|
58 {
|
|
Me@11
|
59 increaseSizeOfDynArrayTo( info, sizeOfArray * 2 );
|
|
Me@11
|
60 }
|
|
Me@11
|
61
|
|
Me@11
|
62 array = *(info->addrOfPtrToArray);
|
|
Me@11
|
63 array[ numInArray ] = value;
|
|
Me@11
|
64 info->numInArray++;
|
|
Me@11
|
65
|
|
Me@11
|
66 return numInArray; //pre-incr value is the index put value into
|
|
Me@11
|
67 }
|
|
Me@11
|
68
|
|
Me@11
|
69
|
|
Me@11
|
70 /*Use this when know how many things going to add in -- then can do this
|
|
Me@11
|
71 * once and use as normal array afterwards. If later add another chunk,
|
|
Me@11
|
72 * do this again. Note, this makes new size be just big enough to hold
|
|
Me@11
|
73 * highest index, so will do a linear number of copies if use only this.
|
|
Me@11
|
74 *To cut down on number of copies, can use the increaseSizeTo Fn to
|
|
Me@11
|
75 * exponentially increase size..
|
|
Me@11
|
76 */
|
|
Me@11
|
77 void
|
|
Me@11
|
78 makeHighestDynArrayIndexBe( DynArrayInfo *info, int32 highestIndex )
|
|
Me@11
|
79 {
|
|
Me@11
|
80 if( info->sizeOfArray <= highestIndex )
|
|
Me@11
|
81 {
|
|
Me@11
|
82 increaseSizeOfDynArrayTo( info, highestIndex + 1 );
|
|
Me@11
|
83 }
|
|
Me@11
|
84 info->numInArray = highestIndex + 1;
|
|
Me@11
|
85 }
|
|
Me@11
|
86
|
|
Me@11
|
87
|
|
Me@11
|
88 /*Only use this if certain new size is bigger than current size
|
|
Me@11
|
89 */
|
|
Me@11
|
90 void
|
|
Me@11
|
91 increaseSizeOfDynArrayTo( DynArrayInfo *info, int32 newSize )
|
|
Me@11
|
92 { int32 oldSizeOfArray, i;
|
|
Me@11
|
93 void **newArray, **oldArray;
|
|
Me@11
|
94
|
|
Me@11
|
95 oldSizeOfArray = info->sizeOfArray;
|
|
Me@11
|
96 if( newSize <= oldSizeOfArray ) return;
|
|
Me@11
|
97
|
|
Me@11
|
98 oldArray = *(info->addrOfPtrToArray);
|
|
Me@11
|
99 newArray = malloc( newSize * sizeof(void *) );
|
|
Me@11
|
100
|
|
Me@11
|
101 for( i = 0; i < oldSizeOfArray; i++ )
|
|
Me@11
|
102 {
|
|
Me@11
|
103 newArray[i] = oldArray[i];
|
|
Me@11
|
104 }
|
|
Me@11
|
105 *(info->addrOfPtrToArray) = newArray; //change location of array-ptr
|
|
Me@11
|
106 info->sizeOfArray = newSize;
|
|
Me@11
|
107
|
|
Me@11
|
108 free( oldArray );
|
|
Me@11
|
109 }
|
|
Me@11
|
110
|
|
Me@11
|
111
|
|
Me@11
|
112 /* Frees the array, plus the info
|
|
Me@11
|
113 */
|
|
Me@11
|
114 void
|
|
Me@11
|
115 freeDynArrayDeep( DynArrayInfo *info, FreeFnPtr freeFnPtr )
|
|
Me@11
|
116 {
|
|
Me@11
|
117 forAllInDynArrayDo( info, freeFnPtr );
|
|
Me@11
|
118 free( *(info->addrOfPtrToArray) );
|
|
Me@11
|
119 free( info );
|
|
Me@11
|
120 }
|
|
Me@11
|
121
|
|
Me@11
|
122 /* Only frees the info
|
|
Me@11
|
123 */
|
|
Me@11
|
124 void
|
|
Me@11
|
125 freeDynArrayFlat( DynArrayInfo *info )
|
|
Me@11
|
126 {
|
|
Me@11
|
127 free( info );
|
|
Me@11
|
128 }
|
|
Me@11
|
129
|
|
Me@11
|
130
|
|
Me@11
|
131 /*The function has a fixed prototype: takes a void * returns void
|
|
Me@11
|
132 * So, the function has to internally cast void * to whatever data struc..
|
|
Me@11
|
133 */
|
|
Me@11
|
134 void
|
|
Me@11
|
135 forAllInDynArrayDo( DynArrayInfo *info, DynArrayFnPtr fnPtr )
|
|
Me@11
|
136 { int32 idx;
|
|
Me@11
|
137 void **array;
|
|
Me@11
|
138
|
|
Me@11
|
139 array = *(info->addrOfPtrToArray);
|
|
Me@11
|
140 for( idx = 0; idx < info->numInArray; idx++ )
|
|
Me@11
|
141 {
|
|
Me@11
|
142 (*fnPtr)(array[idx]);
|
|
Me@11
|
143 }
|
|
Me@11
|
144 }
|
|
Me@11
|
145
|