root/branches/dmdfe/array.c

Revision 360, 3.5 kB (checked in by Gregor, 2 years ago)

Initial import.

Line 
1 // Copyright (c) 1999-2006 by Digital Mars
2 // All Rights Reserved
3 // written by Walter Bright
4 // www.digitalmars.com
5 // License for redistribution is by either the Artistic License
6 // in artistic.txt, or the GNU General Public License in gnu.txt.
7 // See the included readme.txt for details.
8
9 #include <stdio.h>
10 #include <stdlib.h>
11 #include <stdarg.h>
12 #include <string.h>
13 #include <assert.h>
14
15 #if _MSC_VER || ( __WIN32 && __GNUC__ )
16 #include <malloc.h>
17 #endif
18
19 #if IN_GCC
20 #include "gdc_alloca.h"
21 #endif
22
23 #if _WIN32
24 #include <windows.h>
25 #endif
26
27 #ifndef _WIN32
28 #include <sys/types.h>
29 #include <sys/stat.h>
30 #include <fcntl.h>
31 #include <errno.h>
32 #include <unistd.h>
33 #include <utime.h>
34 #endif
35
36 #include "port.h"
37 #include "root.h"
38 #include "dchar.h"
39 #include "mem.h"
40
41
42 /********************************* Array ****************************/
43
44 Array::Array()
45 {
46     data = NULL;
47     dim = 0;
48     allocdim = 0;
49 }
50
51 Array::~Array()
52 {
53     mem.free(data);
54 }
55
56 void Array::mark()
57 {   unsigned u;
58
59     mem.mark(data);
60     for (u = 0; u < dim; u++)
61     mem.mark(data[u]);  // BUG: what if arrays of Object's?
62 }
63
64 void Array::reserve(unsigned nentries)
65 {
66     //printf("Array::reserve: size = %d, offset = %d, nbytes = %d\n", size, offset, nbytes);
67     if (allocdim - dim < nentries)
68     {
69     allocdim = dim + nentries;
70     data = (void **)mem.realloc(data, allocdim * sizeof(*data));
71     }
72 }
73
74 void Array::setDim(unsigned newdim)
75 {
76     if (dim < newdim)
77     {
78     reserve(newdim - dim);
79     }
80     dim = newdim;
81 }
82
83 void Array::fixDim()
84 {
85     if (dim != allocdim)
86     {   data = (void **)mem.realloc(data, dim * sizeof(*data));
87     allocdim = dim;
88     }
89 }
90
91 void Array::push(void *ptr)
92 {
93     reserve(1);
94     data[dim++] = ptr;
95 }
96
97 void *Array::pop()
98 {
99     return data[--dim];
100 }
101
102 void Array::shift(void *ptr)
103 {
104     reserve(1);
105     memmove(data + 1, data, dim * sizeof(*data));
106     data[0] = ptr;
107     dim++;
108 }
109
110 void Array::insert(unsigned index, void *ptr)
111 {
112     reserve(1);
113     memmove(data + index + 1, data + index, (dim - index) * sizeof(*data));
114     data[index] = ptr;
115     dim++;
116 }
117
118
119 void Array::insert(unsigned index, Array *a)
120 {
121     if (a)
122     {   unsigned d;
123
124     d = a->dim;
125     reserve(d);
126     if (dim != index)
127         memmove(data + index + d, data + index, (dim - index) * sizeof(*data));
128     memcpy(data + index, a->data, d * sizeof(*data));
129     dim += d;
130     }
131 }
132
133
134 /***********************************
135  * Append array a to this array.
136  */
137
138 void Array::append(Array *a)
139 {
140     insert(dim, a);
141 }
142
143 void Array::remove(unsigned i)
144 {
145     memmove(data + i, data + i + 1, (dim - i) * sizeof(data[0]));
146     dim--;
147 }
148
149 char *Array::toChars()
150 {
151     unsigned len;
152     unsigned u;
153     char **buf;
154     char *str;
155     char *p;
156
157     buf = (char **)alloca(dim * sizeof(char *));
158     len = 2;
159     for (u = 0; u < dim; u++)
160     {
161     buf[u] = ((Object *)data[u])->toChars();
162     len += strlen(buf[u]) + 1;
163     }
164     str = (char *)mem.malloc(len);
165
166     str[0] = '[';
167     p = str + 1;
168     for (u = 0; u < dim; u++)
169     {
170     if (u)
171         *p++ = ',';
172     len = strlen(buf[u]);
173     memcpy(p,buf[u],len);
174     p += len;
175     }
176     *p++ = ']';
177     *p = 0;
178     return str;
179 }
180
181 void Array::zero()
182 {
183     memset(data,0,dim * sizeof(data[0]));
184 }
185
186 void *Array::tos()
187 {
188     return dim ? data[dim - 1] : NULL;
189 }
190
191 int
192 #if _WIN32
193   __cdecl
194 #endif
195     Array_sort_compare(const void *x, const void *y)
196 {
197     Object *ox = *(Object **)x;
198     Object *oy = *(Object **)y;
199
200     return ox->compare(oy);
201 }
202
203 void Array::sort()
204 {
205     if (dim)
206     {
207     qsort(data, dim, sizeof(Object *), Array_sort_compare);
208     }
209 }
210
211 Array *Array::copy()
212 {
213     Array *a = new Array();
214
215     a->setDim(dim);
216     memcpy(a->data, data, dim * sizeof(void *));
217     return a;
218 }
Note: See TracBrowser for help on using the browser.