diff options
Diffstat (limited to 'lib/xmalloc.c')
-rw-r--r-- | lib/xmalloc.c | 241 |
1 files changed, 0 insertions, 241 deletions
diff --git a/lib/xmalloc.c b/lib/xmalloc.c deleted file mode 100644 index 687633c2..00000000 --- a/lib/xmalloc.c +++ /dev/null | |||
@@ -1,241 +0,0 @@ | |||
1 | /* xmalloc.c -- malloc with out of memory checking | ||
2 | |||
3 | Copyright (C) 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, | ||
4 | 1999, 2000, 2002, 2003, 2004, 2005 Free Software Foundation, Inc. | ||
5 | |||
6 | This program is free software; you can redistribute it and/or modify | ||
7 | it under the terms of the GNU General Public License as published by | ||
8 | the Free Software Foundation; either version 2, or (at your option) | ||
9 | any later version. | ||
10 | |||
11 | This program is distributed in the hope that it will be useful, | ||
12 | but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
14 | GNU General Public License for more details. | ||
15 | |||
16 | You should have received a copy of the GNU General Public License | ||
17 | along with this program; if not, write to the Free Software Foundation, | ||
18 | Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ | ||
19 | |||
20 | #ifdef HAVE_CONFIG_H | ||
21 | # include <config.h> | ||
22 | #endif | ||
23 | |||
24 | #include "xalloc.h" | ||
25 | |||
26 | #include <stdlib.h> | ||
27 | #include <string.h> | ||
28 | |||
29 | #ifndef SIZE_MAX | ||
30 | # define SIZE_MAX ((size_t) -1) | ||
31 | #endif | ||
32 | |||
33 | /* 1 if calloc is known to be compatible with GNU calloc. This | ||
34 | matters if we are not also using the calloc module, which defines | ||
35 | HAVE_CALLOC and supports the GNU API even on non-GNU platforms. */ | ||
36 | #if defined HAVE_CALLOC || defined __GLIBC__ | ||
37 | enum { HAVE_GNU_CALLOC = 1 }; | ||
38 | #else | ||
39 | enum { HAVE_GNU_CALLOC = 0 }; | ||
40 | #endif | ||
41 | |||
42 | /* Allocate an array of N objects, each with S bytes of memory, | ||
43 | dynamically, with error checking. S must be nonzero. */ | ||
44 | |||
45 | static inline void * | ||
46 | xnmalloc_inline (size_t n, size_t s) | ||
47 | { | ||
48 | void *p; | ||
49 | if (xalloc_oversized (n, s) || (! (p = malloc (n * s)) && n != 0)) | ||
50 | xalloc_die (); | ||
51 | return p; | ||
52 | } | ||
53 | |||
54 | void * | ||
55 | xnmalloc (size_t n, size_t s) | ||
56 | { | ||
57 | return xnmalloc_inline (n, s); | ||
58 | } | ||
59 | |||
60 | /* Allocate N bytes of memory dynamically, with error checking. */ | ||
61 | |||
62 | void * | ||
63 | xmalloc (size_t n) | ||
64 | { | ||
65 | return xnmalloc_inline (n, 1); | ||
66 | } | ||
67 | |||
68 | /* Change the size of an allocated block of memory P to an array of N | ||
69 | objects each of S bytes, with error checking. S must be nonzero. */ | ||
70 | |||
71 | static inline void * | ||
72 | xnrealloc_inline (void *p, size_t n, size_t s) | ||
73 | { | ||
74 | if (xalloc_oversized (n, s) || (! (p = realloc (p, n * s)) && n != 0)) | ||
75 | xalloc_die (); | ||
76 | return p; | ||
77 | } | ||
78 | |||
79 | void * | ||
80 | xnrealloc (void *p, size_t n, size_t s) | ||
81 | { | ||
82 | return xnrealloc_inline (p, n, s); | ||
83 | } | ||
84 | |||
85 | /* Change the size of an allocated block of memory P to N bytes, | ||
86 | with error checking. */ | ||
87 | |||
88 | void * | ||
89 | xrealloc (void *p, size_t n) | ||
90 | { | ||
91 | return xnrealloc_inline (p, n, 1); | ||
92 | } | ||
93 | |||
94 | |||
95 | /* If P is null, allocate a block of at least *PN such objects; | ||
96 | otherwise, reallocate P so that it contains more than *PN objects | ||
97 | each of S bytes. *PN must be nonzero unless P is null, and S must | ||
98 | be nonzero. Set *PN to the new number of objects, and return the | ||
99 | pointer to the new block. *PN is never set to zero, and the | ||
100 | returned pointer is never null. | ||
101 | |||
102 | Repeated reallocations are guaranteed to make progress, either by | ||
103 | allocating an initial block with a nonzero size, or by allocating a | ||
104 | larger block. | ||
105 | |||
106 | In the following implementation, nonzero sizes are doubled so that | ||
107 | repeated reallocations have O(N log N) overall cost rather than | ||
108 | O(N**2) cost, but the specification for this function does not | ||
109 | guarantee that sizes are doubled. | ||
110 | |||
111 | Here is an example of use: | ||
112 | |||
113 | int *p = NULL; | ||
114 | size_t used = 0; | ||
115 | size_t allocated = 0; | ||
116 | |||
117 | void | ||
118 | append_int (int value) | ||
119 | { | ||
120 | if (used == allocated) | ||
121 | p = x2nrealloc (p, &allocated, sizeof *p); | ||
122 | p[used++] = value; | ||
123 | } | ||
124 | |||
125 | This causes x2nrealloc to allocate a block of some nonzero size the | ||
126 | first time it is called. | ||
127 | |||
128 | To have finer-grained control over the initial size, set *PN to a | ||
129 | nonzero value before calling this function with P == NULL. For | ||
130 | example: | ||
131 | |||
132 | int *p = NULL; | ||
133 | size_t used = 0; | ||
134 | size_t allocated = 0; | ||
135 | size_t allocated1 = 1000; | ||
136 | |||
137 | void | ||
138 | append_int (int value) | ||
139 | { | ||
140 | if (used == allocated) | ||
141 | { | ||
142 | p = x2nrealloc (p, &allocated1, sizeof *p); | ||
143 | allocated = allocated1; | ||
144 | } | ||
145 | p[used++] = value; | ||
146 | } | ||
147 | |||
148 | */ | ||
149 | |||
150 | static inline void * | ||
151 | x2nrealloc_inline (void *p, size_t *pn, size_t s) | ||
152 | { | ||
153 | size_t n = *pn; | ||
154 | |||
155 | if (! p) | ||
156 | { | ||
157 | if (! n) | ||
158 | { | ||
159 | /* The approximate size to use for initial small allocation | ||
160 | requests, when the invoking code specifies an old size of | ||
161 | zero. 64 bytes is the largest "small" request for the | ||
162 | GNU C library malloc. */ | ||
163 | enum { DEFAULT_MXFAST = 64 }; | ||
164 | |||
165 | n = DEFAULT_MXFAST / s; | ||
166 | n += !n; | ||
167 | } | ||
168 | } | ||
169 | else | ||
170 | { | ||
171 | if (SIZE_MAX / 2 / s < n) | ||
172 | xalloc_die (); | ||
173 | n *= 2; | ||
174 | } | ||
175 | |||
176 | *pn = n; | ||
177 | return xrealloc (p, n * s); | ||
178 | } | ||
179 | |||
180 | void * | ||
181 | x2nrealloc (void *p, size_t *pn, size_t s) | ||
182 | { | ||
183 | return x2nrealloc_inline (p, pn, s); | ||
184 | } | ||
185 | |||
186 | /* If P is null, allocate a block of at least *PN bytes; otherwise, | ||
187 | reallocate P so that it contains more than *PN bytes. *PN must be | ||
188 | nonzero unless P is null. Set *PN to the new block's size, and | ||
189 | return the pointer to the new block. *PN is never set to zero, and | ||
190 | the returned pointer is never null. */ | ||
191 | |||
192 | void * | ||
193 | x2realloc (void *p, size_t *pn) | ||
194 | { | ||
195 | return x2nrealloc_inline (p, pn, 1); | ||
196 | } | ||
197 | |||
198 | /* Allocate S bytes of zeroed memory dynamically, with error checking. | ||
199 | There's no need for xnzalloc (N, S), since it would be equivalent | ||
200 | to xcalloc (N, S). */ | ||
201 | |||
202 | void * | ||
203 | xzalloc (size_t s) | ||
204 | { | ||
205 | return memset (xmalloc (s), 0, s); | ||
206 | } | ||
207 | |||
208 | /* Allocate zeroed memory for N elements of S bytes, with error | ||
209 | checking. S must be nonzero. */ | ||
210 | |||
211 | void * | ||
212 | xcalloc (size_t n, size_t s) | ||
213 | { | ||
214 | void *p; | ||
215 | /* Test for overflow, since some calloc implementations don't have | ||
216 | proper overflow checks. But omit overflow and size-zero tests if | ||
217 | HAVE_GNU_CALLOC, since GNU calloc catches overflow and never | ||
218 | returns NULL if successful. */ | ||
219 | if ((! HAVE_GNU_CALLOC && xalloc_oversized (n, s)) | ||
220 | || (! (p = calloc (n, s)) && (HAVE_GNU_CALLOC || n != 0))) | ||
221 | xalloc_die (); | ||
222 | return p; | ||
223 | } | ||
224 | |||
225 | /* Clone an object P of size S, with error checking. There's no need | ||
226 | for xnmemdup (P, N, S), since xmemdup (P, N * S) works without any | ||
227 | need for an arithmetic overflow check. */ | ||
228 | |||
229 | void * | ||
230 | xmemdup (void const *p, size_t s) | ||
231 | { | ||
232 | return memcpy (xmalloc (s), p, s); | ||
233 | } | ||
234 | |||
235 | /* Clone STRING. */ | ||
236 | |||
237 | char * | ||
238 | xstrdup (char const *string) | ||
239 | { | ||
240 | return xmemdup (string, strlen (string) + 1); | ||
241 | } | ||