annotate src/dynarr.c @ 510:5bdbc721d46a

[xemacs-hg @ 2001-05-06 08:33:35 by ben] implement printing the selection when it's selected. force redisplay when set-charset-ccl-program called. if bytecomp or byte-optimize need recompiling, then load the .el version of them first, recompile them, and reload the .elc versions to recompile everything else (so we won't be waiting until the cows come home).
author ben
date Sun, 06 May 2001 08:33:41 +0000
parents abe6d1db359e
children b39c14581166
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
1 /* Simple 'n' stupid dynamic-array module.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
2 Copyright (C) 1993 Sun Microsystems, Inc.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
3
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
4 This file is part of XEmacs.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
5
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
6 XEmacs is free software; you can redistribute it and/or modify it
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
7 under the terms of the GNU General Public License as published by the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
8 Free Software Foundation; either version 2, or (at your option) any
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
9 later version.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
10
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
11 XEmacs is distributed in the hope that it will be useful, but WITHOUT
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
12 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
14 for more details.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
15
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
16 You should have received a copy of the GNU General Public License
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
17 along with XEmacs; see the file COPYING. If not, write to
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
18 the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
19 Boston, MA 02111-1307, USA. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
20
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
21 /* Synched up with: Not in FSF. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
22
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
23 /* Written by Ben Wing, December 1993. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
24
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
25 /*
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
26
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
27 A "dynamic array" is a contiguous array of fixed-size elements where there
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
28 is no upper limit (except available memory) on the number of elements in the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
29 array. Because the elements are maintained contiguously, space is used
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
30 efficiently (no per-element pointers necessary) and random access to a
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
31 particular element is in constant time. At any one point, the block of memory
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
32 that holds the array has an upper limit; if this limit is exceeded, the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
33 memory is realloc()ed into a new array that is twice as big. Assuming that
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
34 the time to grow the array is on the order of the new size of the array
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
35 block, this scheme has a provably constant amortized time (i.e. average
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
36 time over all additions).
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
37
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
38 When you add elements or retrieve elements, pointers are used. Note that
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
39 the element itself (of whatever size it is), and not the pointer to it,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
40 is stored in the array; thus you do not have to allocate any heap memory
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
41 on your own. Also, returned pointers are only guaranteed to be valid
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
42 until the next operation that changes the length of the array.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
43
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
44 This is a container object. Declare a dynamic array of a specific type
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
45 as follows:
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
46
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
47 typedef struct
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
48 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
49 Dynarr_declare (mytype);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
50 } mytype_dynarr;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
51
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
52 Use the following functions/macros:
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
53
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
54 void *Dynarr_new(type)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
55 [MACRO] Create a new dynamic-array object, with each element of the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
56 specified type. The return value is cast to (type##_dynarr).
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
57 This requires following the convention that types are declared in
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
58 such a way that this type concatenation works. In particular, TYPE
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
59 must be a symbol, not an arbitrary C type.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
60
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
61 Dynarr_add(d, el)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
62 [MACRO] Add an element to the end of a dynamic array. EL is a pointer
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
63 to the element; the element itself is stored in the array, however.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
64 No function call is performed unless the array needs to be resized.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
65
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
66 Dynarr_add_many(d, base, len)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
67 [MACRO] Add LEN elements to the end of the dynamic array. The elements
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
68 should be contiguous in memory, starting at BASE.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
69
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
70 Dynarr_insert_many_at_start(d, base, len)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
71 [MACRO] Append LEN elements to the beginning of the dynamic array.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
72 The elements should be contiguous in memory, starting at BASE.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
73
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
74 Dynarr_insert_many(d, base, len, start)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
75 Insert LEN elements to the dynamic array starting at position
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
76 START. The elements should be contiguous in memory, starting at BASE.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
77
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
78 int Dynarr_length(d)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
79 [MACRO] Return the number of elements currently in a dynamic array.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
80
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
81 int Dynarr_largest(d)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
82 [MACRO] Return the maximum value that Dynarr_length(d) would
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
83 ever have returned.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
84
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
85 type Dynarr_at(d, i)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
86 [MACRO] Return the element at the specified index (no bounds checking
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
87 done on the index). The element itself is returned, not a pointer
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
88 to it.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
89
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
90 type *Dynarr_atp(d, i)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
91 [MACRO] Return a pointer to the element at the specified index (no
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
92 bounds checking done on the index). The pointer may not be valid
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
93 after an element is added to or removed from the array.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
94
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
95 Dynarr_reset(d)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
96 [MACRO] Reset the length of a dynamic array to 0.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
97
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
98 Dynarr_free(d)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
99 Destroy a dynamic array and the memory allocated to it.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
100
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
101 Use the following global variable:
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
102
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
103 Dynarr_min_size
440
8de8e3f6228a Import from CVS: tag r21-2-28
cvs
parents: 428
diff changeset
104 Minimum allowable size for a dynamic array when it is resized.
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
105
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
106 */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
107
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
108 #include <config.h>
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
109 #include "lisp.h"
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
110
440
8de8e3f6228a Import from CVS: tag r21-2-28
cvs
parents: 428
diff changeset
111 static int Dynarr_min_size = 8;
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
112
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
113 static void
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
114 Dynarr_realloc (Dynarr *dy, int new_size)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
115 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
116 if (DUMPEDP (dy->base))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
117 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
118 void *new_base = malloc (new_size);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
119 memcpy (new_base, dy->base, dy->max > new_size ? new_size : dy->max);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
120 dy->base = new_base;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
121 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
122 else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
123 dy->base = xrealloc (dy->base, new_size);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
124 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
125
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
126 void *
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
127 Dynarr_newf (int elsize)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
128 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
129 Dynarr *d = xnew_and_zero (Dynarr);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
130 d->elsize = elsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
131
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
132 return d;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
133 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
134
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
135 void
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
136 Dynarr_resize (void *d, int size)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
137 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
138 int newsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
139 double multiplier;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
140 Dynarr *dy = (Dynarr *) d;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
141
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
142 if (dy->max <= 8)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
143 multiplier = 2;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
144 else
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
145 multiplier = 1.5;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
146
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
147 for (newsize = dy->max; newsize < size;)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
148 newsize = max (Dynarr_min_size, (int) (multiplier * newsize));
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
149
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
150 /* Don't do anything if the array is already big enough. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
151 if (newsize > dy->max)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
152 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
153 Dynarr_realloc (dy, newsize*dy->elsize);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
154 dy->max = newsize;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
155 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
156 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
157
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
158 /* Add a number of contiguous elements to the array starting at START. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
159 void
442
abe6d1db359e Import from CVS: tag r21-2-36
cvs
parents: 440
diff changeset
160 Dynarr_insert_many (void *d, const void *el, int len, int start)
428
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
161 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
162 Dynarr *dy = (Dynarr *) d;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
163
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
164 Dynarr_resize (dy, dy->cur+len);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
165 /* Silently adjust start to be valid. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
166 if (start > dy->cur)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
167 start = dy->cur;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
168 else if (start < 0)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
169 start = 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
170
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
171 if (start != dy->cur)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
172 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
173 memmove ((char *) dy->base + (start + len)*dy->elsize,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
174 (char *) dy->base + start*dy->elsize,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
175 (dy->cur - start)*dy->elsize);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
176 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
177 memcpy ((char *) dy->base + start*dy->elsize, el, len*dy->elsize);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
178 dy->cur += len;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
179
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
180 if (dy->cur > dy->largest)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
181 dy->largest = dy->cur;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
182 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
183
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
184 void
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
185 Dynarr_delete_many (void *d, int start, int len)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
186 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
187 Dynarr *dy = (Dynarr *) d;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
188
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
189 assert (start >= 0 && len >= 0 && start + len <= dy->cur);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
190 memmove ((char *) dy->base + start*dy->elsize,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
191 (char *) dy->base + (start + len)*dy->elsize,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
192 (dy->cur - start - len)*dy->elsize);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
193 dy->cur -= len;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
194 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
195
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
196 void
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
197 Dynarr_free (void *d)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
198 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
199 Dynarr *dy = (Dynarr *) d;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
200
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
201 if (dy->base && !DUMPEDP (dy->base))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
202 xfree (dy->base);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
203 if(!DUMPEDP (dy))
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
204 xfree (dy);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
205 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
206
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
207 #ifdef MEMORY_USAGE_STATS
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
208
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
209 /* Return memory usage for Dynarr D. The returned value is the total
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
210 amount of bytes actually being used for the Dynarr, including all
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
211 overhead. The extra amount of space in the Dynarr that is
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
212 allocated beyond what was requested is returned in DYNARR_OVERHEAD
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
213 in STATS. The extra amount of space that malloc() allocates beyond
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
214 what was requested of it is returned in MALLOC_OVERHEAD in STATS.
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
215 See the comment above the definition of this structure. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
216
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
217 size_t
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
218 Dynarr_memory_usage (void *d, struct overhead_stats *stats)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
219 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
220 size_t total = 0;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
221 Dynarr *dy = (Dynarr *) d;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
222
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
223 /* We have to be a bit tricky here because not all of the
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
224 memory that malloc() will claim as "requested" was actually
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
225 requested. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
226
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
227 if (dy->base)
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
228 {
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
229 size_t malloc_used = malloced_storage_size (dy->base,
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
230 dy->elsize * dy->max, 0);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
231 /* #### This may or may not be correct. Some Dynarrs would
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
232 prefer that we use dy->cur instead of dy->largest here. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
233 int was_requested = dy->elsize * dy->largest;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
234 int dynarr_overhead = dy->elsize * (dy->max - dy->largest);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
235
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
236 total += malloc_used;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
237 stats->was_requested += was_requested;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
238 stats->dynarr_overhead += dynarr_overhead;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
239 /* And the remainder must be malloc overhead. */
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
240 stats->malloc_overhead +=
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
241 malloc_used - was_requested - dynarr_overhead;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
242 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
243
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
244 total += malloced_storage_size (d, sizeof (*dy), stats);
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
245
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
246 return total;
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
247 }
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
248
3ecd8885ac67 Import from CVS: tag r21-2-22
cvs
parents:
diff changeset
249 #endif /* MEMORY_USAGE_STATS */