sl_malloc.c revision 1.1.1.1.6.2 1 1.1.1.1.6.2 wrstuden /* sl_malloc.c - malloc routines using a per-thread slab */
2 1.1.1.1.6.2 wrstuden /* $OpenLDAP: pkg/ldap/servers/slapd/sl_malloc.c,v 1.39.2.6 2008/02/11 23:34:15 quanah Exp $ */
3 1.1.1.1.6.2 wrstuden /* This work is part of OpenLDAP Software <http://www.openldap.org/>.
4 1.1.1.1.6.2 wrstuden *
5 1.1.1.1.6.2 wrstuden * Copyright 2003-2008 The OpenLDAP Foundation.
6 1.1.1.1.6.2 wrstuden * All rights reserved.
7 1.1.1.1.6.2 wrstuden *
8 1.1.1.1.6.2 wrstuden * Redistribution and use in source and binary forms, with or without
9 1.1.1.1.6.2 wrstuden * modification, are permitted only as authorized by the OpenLDAP
10 1.1.1.1.6.2 wrstuden * Public License.
11 1.1.1.1.6.2 wrstuden *
12 1.1.1.1.6.2 wrstuden * A copy of this license is available in the file LICENSE in the
13 1.1.1.1.6.2 wrstuden * top-level directory of the distribution or, alternatively, at
14 1.1.1.1.6.2 wrstuden * <http://www.OpenLDAP.org/license.html>.
15 1.1.1.1.6.2 wrstuden */
16 1.1.1.1.6.2 wrstuden
17 1.1.1.1.6.2 wrstuden #include "portable.h"
18 1.1.1.1.6.2 wrstuden
19 1.1.1.1.6.2 wrstuden #include <stdio.h>
20 1.1.1.1.6.2 wrstuden #include <ac/string.h>
21 1.1.1.1.6.2 wrstuden
22 1.1.1.1.6.2 wrstuden #include "slap.h"
23 1.1.1.1.6.2 wrstuden
24 1.1.1.1.6.2 wrstuden static struct slab_object * slap_replenish_sopool(struct slab_heap* sh);
25 1.1.1.1.6.2 wrstuden #ifdef SLAPD_UNUSED
26 1.1.1.1.6.2 wrstuden static void print_slheap(int level, void *ctx);
27 1.1.1.1.6.2 wrstuden #endif
28 1.1.1.1.6.2 wrstuden
29 1.1.1.1.6.2 wrstuden void
30 1.1.1.1.6.2 wrstuden slap_sl_mem_destroy(
31 1.1.1.1.6.2 wrstuden void *key,
32 1.1.1.1.6.2 wrstuden void *data
33 1.1.1.1.6.2 wrstuden )
34 1.1.1.1.6.2 wrstuden {
35 1.1.1.1.6.2 wrstuden struct slab_heap *sh = data;
36 1.1.1.1.6.2 wrstuden int pad = 2*sizeof(int)-1, pad_shift;
37 1.1.1.1.6.2 wrstuden int order_start = -1, i;
38 1.1.1.1.6.2 wrstuden struct slab_object *so;
39 1.1.1.1.6.2 wrstuden
40 1.1.1.1.6.2 wrstuden if (sh->sh_stack) {
41 1.1.1.1.6.2 wrstuden ber_memfree_x(sh->sh_base, NULL);
42 1.1.1.1.6.2 wrstuden ber_memfree_x(sh, NULL);
43 1.1.1.1.6.2 wrstuden } else {
44 1.1.1.1.6.2 wrstuden pad_shift = pad - 1;
45 1.1.1.1.6.2 wrstuden do {
46 1.1.1.1.6.2 wrstuden order_start++;
47 1.1.1.1.6.2 wrstuden } while (pad_shift >>= 1);
48 1.1.1.1.6.2 wrstuden
49 1.1.1.1.6.2 wrstuden for (i = 0; i <= sh->sh_maxorder - order_start; i++) {
50 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_free[i]);
51 1.1.1.1.6.2 wrstuden while (so) {
52 1.1.1.1.6.2 wrstuden struct slab_object *so_tmp = so;
53 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
54 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_sopool, so_tmp, so_link);
55 1.1.1.1.6.2 wrstuden }
56 1.1.1.1.6.2 wrstuden ch_free(sh->sh_map[i]);
57 1.1.1.1.6.2 wrstuden }
58 1.1.1.1.6.2 wrstuden ch_free(sh->sh_free);
59 1.1.1.1.6.2 wrstuden ch_free(sh->sh_map);
60 1.1.1.1.6.2 wrstuden
61 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
62 1.1.1.1.6.2 wrstuden while (so) {
63 1.1.1.1.6.2 wrstuden struct slab_object *so_tmp = so;
64 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
65 1.1.1.1.6.2 wrstuden if (!so_tmp->so_blockhead) {
66 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so_tmp, so_link);
67 1.1.1.1.6.2 wrstuden }
68 1.1.1.1.6.2 wrstuden }
69 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
70 1.1.1.1.6.2 wrstuden while (so) {
71 1.1.1.1.6.2 wrstuden struct slab_object *so_tmp = so;
72 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
73 1.1.1.1.6.2 wrstuden ch_free(so_tmp);
74 1.1.1.1.6.2 wrstuden }
75 1.1.1.1.6.2 wrstuden ber_memfree_x(sh->sh_base, NULL);
76 1.1.1.1.6.2 wrstuden ber_memfree_x(sh, NULL);
77 1.1.1.1.6.2 wrstuden }
78 1.1.1.1.6.2 wrstuden }
79 1.1.1.1.6.2 wrstuden
80 1.1.1.1.6.2 wrstuden BerMemoryFunctions slap_sl_mfuncs =
81 1.1.1.1.6.2 wrstuden { slap_sl_malloc, slap_sl_calloc, slap_sl_realloc, slap_sl_free };
82 1.1.1.1.6.2 wrstuden
83 1.1.1.1.6.2 wrstuden void
84 1.1.1.1.6.2 wrstuden slap_sl_mem_init()
85 1.1.1.1.6.2 wrstuden {
86 1.1.1.1.6.2 wrstuden ber_set_option( NULL, LBER_OPT_MEMORY_FNS, &slap_sl_mfuncs );
87 1.1.1.1.6.2 wrstuden }
88 1.1.1.1.6.2 wrstuden
89 1.1.1.1.6.2 wrstuden #ifdef NO_THREADS
90 1.1.1.1.6.2 wrstuden static struct slab_heap *slheap;
91 1.1.1.1.6.2 wrstuden #endif
92 1.1.1.1.6.2 wrstuden
93 1.1.1.1.6.2 wrstuden void *
94 1.1.1.1.6.2 wrstuden slap_sl_mem_create(
95 1.1.1.1.6.2 wrstuden ber_len_t size,
96 1.1.1.1.6.2 wrstuden int stack,
97 1.1.1.1.6.2 wrstuden void *ctx,
98 1.1.1.1.6.2 wrstuden int new
99 1.1.1.1.6.2 wrstuden )
100 1.1.1.1.6.2 wrstuden {
101 1.1.1.1.6.2 wrstuden struct slab_heap *sh;
102 1.1.1.1.6.2 wrstuden ber_len_t size_shift;
103 1.1.1.1.6.2 wrstuden int pad = 2*sizeof(int)-1, pad_shift;
104 1.1.1.1.6.2 wrstuden int order = -1, order_start = -1, order_end = -1;
105 1.1.1.1.6.2 wrstuden int i;
106 1.1.1.1.6.2 wrstuden struct slab_object *so;
107 1.1.1.1.6.2 wrstuden
108 1.1.1.1.6.2 wrstuden #ifdef NO_THREADS
109 1.1.1.1.6.2 wrstuden sh = slheap;
110 1.1.1.1.6.2 wrstuden #else
111 1.1.1.1.6.2 wrstuden void *sh_tmp = NULL;
112 1.1.1.1.6.2 wrstuden ldap_pvt_thread_pool_getkey(
113 1.1.1.1.6.2 wrstuden ctx, (void *)slap_sl_mem_init, &sh_tmp, NULL );
114 1.1.1.1.6.2 wrstuden sh = sh_tmp;
115 1.1.1.1.6.2 wrstuden #endif
116 1.1.1.1.6.2 wrstuden
117 1.1.1.1.6.2 wrstuden if ( !new )
118 1.1.1.1.6.2 wrstuden return sh;
119 1.1.1.1.6.2 wrstuden
120 1.1.1.1.6.2 wrstuden /* round up to doubleword boundary */
121 1.1.1.1.6.2 wrstuden size += pad;
122 1.1.1.1.6.2 wrstuden size &= ~pad;
123 1.1.1.1.6.2 wrstuden
124 1.1.1.1.6.2 wrstuden if (stack) {
125 1.1.1.1.6.2 wrstuden if (!sh) {
126 1.1.1.1.6.2 wrstuden sh = ch_malloc(sizeof(struct slab_heap));
127 1.1.1.1.6.2 wrstuden sh->sh_base = ch_malloc(size);
128 1.1.1.1.6.2 wrstuden #ifdef NO_THREADS
129 1.1.1.1.6.2 wrstuden slheap = sh;
130 1.1.1.1.6.2 wrstuden #else
131 1.1.1.1.6.2 wrstuden ldap_pvt_thread_pool_setkey(ctx, (void *)slap_sl_mem_init,
132 1.1.1.1.6.2 wrstuden (void *)sh, slap_sl_mem_destroy, NULL, NULL);
133 1.1.1.1.6.2 wrstuden #endif
134 1.1.1.1.6.2 wrstuden } else if ( size > (char *)sh->sh_end - (char *)sh->sh_base ) {
135 1.1.1.1.6.2 wrstuden void *newptr;
136 1.1.1.1.6.2 wrstuden
137 1.1.1.1.6.2 wrstuden newptr = ch_realloc( sh->sh_base, size );
138 1.1.1.1.6.2 wrstuden if ( newptr == NULL ) return NULL;
139 1.1.1.1.6.2 wrstuden sh->sh_base = newptr;
140 1.1.1.1.6.2 wrstuden }
141 1.1.1.1.6.2 wrstuden sh->sh_last = sh->sh_base;
142 1.1.1.1.6.2 wrstuden sh->sh_end = (char *) sh->sh_base + size;
143 1.1.1.1.6.2 wrstuden sh->sh_stack = stack;
144 1.1.1.1.6.2 wrstuden return sh;
145 1.1.1.1.6.2 wrstuden } else {
146 1.1.1.1.6.2 wrstuden size_shift = size - 1;
147 1.1.1.1.6.2 wrstuden do {
148 1.1.1.1.6.2 wrstuden order_end++;
149 1.1.1.1.6.2 wrstuden } while (size_shift >>= 1);
150 1.1.1.1.6.2 wrstuden
151 1.1.1.1.6.2 wrstuden pad_shift = pad - 1;
152 1.1.1.1.6.2 wrstuden do {
153 1.1.1.1.6.2 wrstuden order_start++;
154 1.1.1.1.6.2 wrstuden } while (pad_shift >>= 1);
155 1.1.1.1.6.2 wrstuden
156 1.1.1.1.6.2 wrstuden order = order_end - order_start + 1;
157 1.1.1.1.6.2 wrstuden
158 1.1.1.1.6.2 wrstuden if (!sh) {
159 1.1.1.1.6.2 wrstuden sh = (struct slab_heap *) ch_malloc(sizeof(struct slab_heap));
160 1.1.1.1.6.2 wrstuden sh->sh_base = ch_malloc(size);
161 1.1.1.1.6.2 wrstuden #ifdef NO_THREADS
162 1.1.1.1.6.2 wrstuden slheap = sh;
163 1.1.1.1.6.2 wrstuden #else
164 1.1.1.1.6.2 wrstuden ldap_pvt_thread_pool_setkey(ctx, (void *)slap_sl_mem_init,
165 1.1.1.1.6.2 wrstuden (void *)sh, slap_sl_mem_destroy, NULL, NULL);
166 1.1.1.1.6.2 wrstuden #endif
167 1.1.1.1.6.2 wrstuden } else {
168 1.1.1.1.6.2 wrstuden for (i = 0; i <= sh->sh_maxorder - order_start; i++) {
169 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_free[i]);
170 1.1.1.1.6.2 wrstuden while (so) {
171 1.1.1.1.6.2 wrstuden struct slab_object *so_tmp = so;
172 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
173 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_sopool, so_tmp, so_link);
174 1.1.1.1.6.2 wrstuden }
175 1.1.1.1.6.2 wrstuden ch_free(sh->sh_map[i]);
176 1.1.1.1.6.2 wrstuden }
177 1.1.1.1.6.2 wrstuden ch_free(sh->sh_free);
178 1.1.1.1.6.2 wrstuden ch_free(sh->sh_map);
179 1.1.1.1.6.2 wrstuden
180 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
181 1.1.1.1.6.2 wrstuden while (so) {
182 1.1.1.1.6.2 wrstuden struct slab_object *so_tmp = so;
183 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
184 1.1.1.1.6.2 wrstuden if (!so_tmp->so_blockhead) {
185 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so_tmp, so_link);
186 1.1.1.1.6.2 wrstuden }
187 1.1.1.1.6.2 wrstuden }
188 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
189 1.1.1.1.6.2 wrstuden while (so) {
190 1.1.1.1.6.2 wrstuden struct slab_object *so_tmp = so;
191 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
192 1.1.1.1.6.2 wrstuden ch_free(so_tmp);
193 1.1.1.1.6.2 wrstuden }
194 1.1.1.1.6.2 wrstuden
195 1.1.1.1.6.2 wrstuden if (size > (char *)sh->sh_end - (char *)sh->sh_base) {
196 1.1.1.1.6.2 wrstuden void *newptr;
197 1.1.1.1.6.2 wrstuden
198 1.1.1.1.6.2 wrstuden newptr = realloc( sh->sh_base, size );
199 1.1.1.1.6.2 wrstuden if ( newptr == NULL ) return NULL;
200 1.1.1.1.6.2 wrstuden sh->sh_base = newptr;
201 1.1.1.1.6.2 wrstuden }
202 1.1.1.1.6.2 wrstuden }
203 1.1.1.1.6.2 wrstuden sh->sh_end = (char *)sh->sh_base + size;
204 1.1.1.1.6.2 wrstuden sh->sh_maxorder = order_end;
205 1.1.1.1.6.2 wrstuden
206 1.1.1.1.6.2 wrstuden sh->sh_free = (struct sh_freelist *)
207 1.1.1.1.6.2 wrstuden ch_malloc(order * sizeof(struct sh_freelist));
208 1.1.1.1.6.2 wrstuden for (i = 0; i < order; i++) {
209 1.1.1.1.6.2 wrstuden LDAP_LIST_INIT(&sh->sh_free[i]);
210 1.1.1.1.6.2 wrstuden }
211 1.1.1.1.6.2 wrstuden
212 1.1.1.1.6.2 wrstuden LDAP_LIST_INIT(&sh->sh_sopool);
213 1.1.1.1.6.2 wrstuden
214 1.1.1.1.6.2 wrstuden if (LDAP_LIST_EMPTY(&sh->sh_sopool)) {
215 1.1.1.1.6.2 wrstuden slap_replenish_sopool(sh);
216 1.1.1.1.6.2 wrstuden }
217 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
218 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so, so_link);
219 1.1.1.1.6.2 wrstuden so->so_ptr = sh->sh_base;
220 1.1.1.1.6.2 wrstuden
221 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_free[order-1], so, so_link);
222 1.1.1.1.6.2 wrstuden
223 1.1.1.1.6.2 wrstuden sh->sh_map = (unsigned char **)
224 1.1.1.1.6.2 wrstuden ch_malloc(order * sizeof(unsigned char *));
225 1.1.1.1.6.2 wrstuden for (i = 0; i < order; i++) {
226 1.1.1.1.6.2 wrstuden int shiftamt = order_start + 1 + i;
227 1.1.1.1.6.2 wrstuden int nummaps = size >> shiftamt;
228 1.1.1.1.6.2 wrstuden assert(nummaps);
229 1.1.1.1.6.2 wrstuden nummaps >>= 3;
230 1.1.1.1.6.2 wrstuden if (!nummaps) nummaps = 1;
231 1.1.1.1.6.2 wrstuden sh->sh_map[i] = (unsigned char *) ch_malloc(nummaps);
232 1.1.1.1.6.2 wrstuden memset(sh->sh_map[i], 0, nummaps);
233 1.1.1.1.6.2 wrstuden }
234 1.1.1.1.6.2 wrstuden sh->sh_stack = stack;
235 1.1.1.1.6.2 wrstuden return sh;
236 1.1.1.1.6.2 wrstuden }
237 1.1.1.1.6.2 wrstuden }
238 1.1.1.1.6.2 wrstuden
239 1.1.1.1.6.2 wrstuden void
240 1.1.1.1.6.2 wrstuden slap_sl_mem_detach(
241 1.1.1.1.6.2 wrstuden void *ctx,
242 1.1.1.1.6.2 wrstuden void *memctx
243 1.1.1.1.6.2 wrstuden )
244 1.1.1.1.6.2 wrstuden {
245 1.1.1.1.6.2 wrstuden #ifdef NO_THREADS
246 1.1.1.1.6.2 wrstuden slheap = NULL;
247 1.1.1.1.6.2 wrstuden #else
248 1.1.1.1.6.2 wrstuden /* separate from context */
249 1.1.1.1.6.2 wrstuden ldap_pvt_thread_pool_setkey( ctx, (void *)slap_sl_mem_init,
250 1.1.1.1.6.2 wrstuden NULL, 0, NULL, NULL );
251 1.1.1.1.6.2 wrstuden #endif
252 1.1.1.1.6.2 wrstuden }
253 1.1.1.1.6.2 wrstuden
254 1.1.1.1.6.2 wrstuden void *
255 1.1.1.1.6.2 wrstuden slap_sl_malloc(
256 1.1.1.1.6.2 wrstuden ber_len_t size,
257 1.1.1.1.6.2 wrstuden void *ctx
258 1.1.1.1.6.2 wrstuden )
259 1.1.1.1.6.2 wrstuden {
260 1.1.1.1.6.2 wrstuden struct slab_heap *sh = ctx;
261 1.1.1.1.6.2 wrstuden ber_len_t size_shift;
262 1.1.1.1.6.2 wrstuden int pad = 2*sizeof(int)-1, pad_shift;
263 1.1.1.1.6.2 wrstuden int order = -1, order_start = -1;
264 1.1.1.1.6.2 wrstuden struct slab_object *so_new, *so_left, *so_right;
265 1.1.1.1.6.2 wrstuden ber_len_t *ptr, *newptr;
266 1.1.1.1.6.2 wrstuden unsigned long diff;
267 1.1.1.1.6.2 wrstuden int i, j;
268 1.1.1.1.6.2 wrstuden
269 1.1.1.1.6.2 wrstuden #ifdef SLAP_NO_SL_MALLOC
270 1.1.1.1.6.2 wrstuden return ber_memalloc_x( size, NULL );
271 1.1.1.1.6.2 wrstuden #endif
272 1.1.1.1.6.2 wrstuden
273 1.1.1.1.6.2 wrstuden /* ber_set_option calls us like this */
274 1.1.1.1.6.2 wrstuden if (!ctx) return ber_memalloc_x(size, NULL);
275 1.1.1.1.6.2 wrstuden
276 1.1.1.1.6.2 wrstuden /* round up to doubleword boundary */
277 1.1.1.1.6.2 wrstuden size += sizeof(ber_len_t) + pad;
278 1.1.1.1.6.2 wrstuden size &= ~pad;
279 1.1.1.1.6.2 wrstuden
280 1.1.1.1.6.2 wrstuden if (sh->sh_stack) {
281 1.1.1.1.6.2 wrstuden if ((char *)sh->sh_last + size >= (char *)sh->sh_end) {
282 1.1.1.1.6.2 wrstuden Debug(LDAP_DEBUG_TRACE,
283 1.1.1.1.6.2 wrstuden "slap_sl_malloc of %lu bytes failed, using ch_malloc\n",
284 1.1.1.1.6.2 wrstuden (long)size, 0, 0);
285 1.1.1.1.6.2 wrstuden return ch_malloc(size);
286 1.1.1.1.6.2 wrstuden }
287 1.1.1.1.6.2 wrstuden newptr = sh->sh_last;
288 1.1.1.1.6.2 wrstuden *newptr++ = size - sizeof(ber_len_t);
289 1.1.1.1.6.2 wrstuden sh->sh_last = (char *) sh->sh_last + size;
290 1.1.1.1.6.2 wrstuden return( (void *)newptr );
291 1.1.1.1.6.2 wrstuden } else {
292 1.1.1.1.6.2 wrstuden size_shift = size - 1;
293 1.1.1.1.6.2 wrstuden do {
294 1.1.1.1.6.2 wrstuden order++;
295 1.1.1.1.6.2 wrstuden } while (size_shift >>= 1);
296 1.1.1.1.6.2 wrstuden
297 1.1.1.1.6.2 wrstuden pad_shift = pad - 1;
298 1.1.1.1.6.2 wrstuden do {
299 1.1.1.1.6.2 wrstuden order_start++;
300 1.1.1.1.6.2 wrstuden } while (pad_shift >>= 1);
301 1.1.1.1.6.2 wrstuden
302 1.1.1.1.6.2 wrstuden for (i = order; i <= sh->sh_maxorder &&
303 1.1.1.1.6.2 wrstuden LDAP_LIST_EMPTY(&sh->sh_free[i-order_start]); i++);
304 1.1.1.1.6.2 wrstuden
305 1.1.1.1.6.2 wrstuden if (i == order) {
306 1.1.1.1.6.2 wrstuden so_new = LDAP_LIST_FIRST(&sh->sh_free[i-order_start]);
307 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so_new, so_link);
308 1.1.1.1.6.2 wrstuden ptr = so_new->so_ptr;
309 1.1.1.1.6.2 wrstuden diff = (unsigned long)((char*)ptr -
310 1.1.1.1.6.2 wrstuden (char*)sh->sh_base) >> (order + 1);
311 1.1.1.1.6.2 wrstuden sh->sh_map[order-order_start][diff>>3] |= (1 << (diff & 0x7));
312 1.1.1.1.6.2 wrstuden *ptr++ = size - sizeof(ber_len_t);
313 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_sopool, so_new, so_link);
314 1.1.1.1.6.2 wrstuden return((void*)ptr);
315 1.1.1.1.6.2 wrstuden } else if (i <= sh->sh_maxorder) {
316 1.1.1.1.6.2 wrstuden for (j = i; j > order; j--) {
317 1.1.1.1.6.2 wrstuden so_left = LDAP_LIST_FIRST(&sh->sh_free[j-order_start]);
318 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so_left, so_link);
319 1.1.1.1.6.2 wrstuden if (LDAP_LIST_EMPTY(&sh->sh_sopool)) {
320 1.1.1.1.6.2 wrstuden slap_replenish_sopool(sh);
321 1.1.1.1.6.2 wrstuden }
322 1.1.1.1.6.2 wrstuden so_right = LDAP_LIST_FIRST(&sh->sh_sopool);
323 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so_right, so_link);
324 1.1.1.1.6.2 wrstuden so_right->so_ptr = (void *)((char *)so_left->so_ptr + (1 << j));
325 1.1.1.1.6.2 wrstuden if (j == order + 1) {
326 1.1.1.1.6.2 wrstuden ptr = so_left->so_ptr;
327 1.1.1.1.6.2 wrstuden diff = (unsigned long)((char*)ptr -
328 1.1.1.1.6.2 wrstuden (char*)sh->sh_base) >> (order+1);
329 1.1.1.1.6.2 wrstuden sh->sh_map[order-order_start][diff>>3] |=
330 1.1.1.1.6.2 wrstuden (1 << (diff & 0x7));
331 1.1.1.1.6.2 wrstuden *ptr++ = size - sizeof(ber_len_t);
332 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(
333 1.1.1.1.6.2 wrstuden &sh->sh_free[j-1-order_start], so_right, so_link);
334 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_sopool, so_left, so_link);
335 1.1.1.1.6.2 wrstuden return((void*)ptr);
336 1.1.1.1.6.2 wrstuden } else {
337 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(
338 1.1.1.1.6.2 wrstuden &sh->sh_free[j-1-order_start], so_right, so_link);
339 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(
340 1.1.1.1.6.2 wrstuden &sh->sh_free[j-1-order_start], so_left, so_link);
341 1.1.1.1.6.2 wrstuden }
342 1.1.1.1.6.2 wrstuden }
343 1.1.1.1.6.2 wrstuden } else {
344 1.1.1.1.6.2 wrstuden Debug( LDAP_DEBUG_TRACE,
345 1.1.1.1.6.2 wrstuden "slap_sl_malloc of %lu bytes failed, using ch_malloc\n",
346 1.1.1.1.6.2 wrstuden (long)size, 0, 0);
347 1.1.1.1.6.2 wrstuden return (void*)ch_malloc(size);
348 1.1.1.1.6.2 wrstuden }
349 1.1.1.1.6.2 wrstuden }
350 1.1.1.1.6.2 wrstuden
351 1.1.1.1.6.2 wrstuden /* FIXME: missing return; guessing... */
352 1.1.1.1.6.2 wrstuden return NULL;
353 1.1.1.1.6.2 wrstuden }
354 1.1.1.1.6.2 wrstuden
355 1.1.1.1.6.2 wrstuden void *
356 1.1.1.1.6.2 wrstuden slap_sl_calloc( ber_len_t n, ber_len_t size, void *ctx )
357 1.1.1.1.6.2 wrstuden {
358 1.1.1.1.6.2 wrstuden void *newptr;
359 1.1.1.1.6.2 wrstuden
360 1.1.1.1.6.2 wrstuden newptr = slap_sl_malloc( n*size, ctx );
361 1.1.1.1.6.2 wrstuden if ( newptr ) {
362 1.1.1.1.6.2 wrstuden memset( newptr, 0, n*size );
363 1.1.1.1.6.2 wrstuden }
364 1.1.1.1.6.2 wrstuden return newptr;
365 1.1.1.1.6.2 wrstuden }
366 1.1.1.1.6.2 wrstuden
367 1.1.1.1.6.2 wrstuden void *
368 1.1.1.1.6.2 wrstuden slap_sl_realloc(void *ptr, ber_len_t size, void *ctx)
369 1.1.1.1.6.2 wrstuden {
370 1.1.1.1.6.2 wrstuden struct slab_heap *sh = ctx;
371 1.1.1.1.6.2 wrstuden int pad = 2*sizeof(int) -1;
372 1.1.1.1.6.2 wrstuden ber_len_t *p = (ber_len_t *)ptr, *newptr;
373 1.1.1.1.6.2 wrstuden
374 1.1.1.1.6.2 wrstuden if (ptr == NULL)
375 1.1.1.1.6.2 wrstuden return slap_sl_malloc(size, ctx);
376 1.1.1.1.6.2 wrstuden
377 1.1.1.1.6.2 wrstuden #ifdef SLAP_NO_SL_MALLOC
378 1.1.1.1.6.2 wrstuden return ber_memrealloc_x( ptr, size, NULL );
379 1.1.1.1.6.2 wrstuden #endif
380 1.1.1.1.6.2 wrstuden
381 1.1.1.1.6.2 wrstuden /* Not our memory? */
382 1.1.1.1.6.2 wrstuden if (!sh || ptr < sh->sh_base || ptr >= sh->sh_end) {
383 1.1.1.1.6.2 wrstuden /* duplicate of realloc behavior, oh well */
384 1.1.1.1.6.2 wrstuden newptr = ber_memrealloc_x(ptr, size, NULL);
385 1.1.1.1.6.2 wrstuden if (newptr) {
386 1.1.1.1.6.2 wrstuden return newptr;
387 1.1.1.1.6.2 wrstuden }
388 1.1.1.1.6.2 wrstuden Debug(LDAP_DEBUG_ANY, "ch_realloc of %lu bytes failed\n",
389 1.1.1.1.6.2 wrstuden (long) size, 0, 0);
390 1.1.1.1.6.2 wrstuden assert(0);
391 1.1.1.1.6.2 wrstuden exit( EXIT_FAILURE );
392 1.1.1.1.6.2 wrstuden }
393 1.1.1.1.6.2 wrstuden
394 1.1.1.1.6.2 wrstuden if (size == 0) {
395 1.1.1.1.6.2 wrstuden slap_sl_free(ptr, ctx);
396 1.1.1.1.6.2 wrstuden return NULL;
397 1.1.1.1.6.2 wrstuden }
398 1.1.1.1.6.2 wrstuden
399 1.1.1.1.6.2 wrstuden if (sh->sh_stack) {
400 1.1.1.1.6.2 wrstuden /* round up to doubleword boundary */
401 1.1.1.1.6.2 wrstuden size += pad + sizeof( ber_len_t );
402 1.1.1.1.6.2 wrstuden size &= ~pad;
403 1.1.1.1.6.2 wrstuden
404 1.1.1.1.6.2 wrstuden /* Never shrink blocks */
405 1.1.1.1.6.2 wrstuden if (size <= p[-1]) {
406 1.1.1.1.6.2 wrstuden newptr = p;
407 1.1.1.1.6.2 wrstuden
408 1.1.1.1.6.2 wrstuden /* If reallocing the last block, we can grow it */
409 1.1.1.1.6.2 wrstuden } else if ((char *)ptr + p[-1] == sh->sh_last &&
410 1.1.1.1.6.2 wrstuden (char *)ptr + size < (char *)sh->sh_end ) {
411 1.1.1.1.6.2 wrstuden newptr = p;
412 1.1.1.1.6.2 wrstuden sh->sh_last = (char *)sh->sh_last + size - p[-1];
413 1.1.1.1.6.2 wrstuden p[-1] = size;
414 1.1.1.1.6.2 wrstuden
415 1.1.1.1.6.2 wrstuden /* Nowhere to grow, need to alloc and copy */
416 1.1.1.1.6.2 wrstuden } else {
417 1.1.1.1.6.2 wrstuden newptr = slap_sl_malloc(size, ctx);
418 1.1.1.1.6.2 wrstuden AC_MEMCPY(newptr, ptr, p[-1]);
419 1.1.1.1.6.2 wrstuden }
420 1.1.1.1.6.2 wrstuden return newptr;
421 1.1.1.1.6.2 wrstuden } else {
422 1.1.1.1.6.2 wrstuden void *newptr2;
423 1.1.1.1.6.2 wrstuden
424 1.1.1.1.6.2 wrstuden newptr2 = slap_sl_malloc(size, ctx);
425 1.1.1.1.6.2 wrstuden if (size < p[-1]) {
426 1.1.1.1.6.2 wrstuden AC_MEMCPY(newptr2, ptr, size);
427 1.1.1.1.6.2 wrstuden } else {
428 1.1.1.1.6.2 wrstuden AC_MEMCPY(newptr2, ptr, p[-1]);
429 1.1.1.1.6.2 wrstuden }
430 1.1.1.1.6.2 wrstuden slap_sl_free(ptr, ctx);
431 1.1.1.1.6.2 wrstuden return newptr2;
432 1.1.1.1.6.2 wrstuden }
433 1.1.1.1.6.2 wrstuden }
434 1.1.1.1.6.2 wrstuden
435 1.1.1.1.6.2 wrstuden void
436 1.1.1.1.6.2 wrstuden slap_sl_free(void *ptr, void *ctx)
437 1.1.1.1.6.2 wrstuden {
438 1.1.1.1.6.2 wrstuden struct slab_heap *sh = ctx;
439 1.1.1.1.6.2 wrstuden int size, size_shift, order_size;
440 1.1.1.1.6.2 wrstuden int pad = 2*sizeof(int)-1, pad_shift;
441 1.1.1.1.6.2 wrstuden ber_len_t *p = (ber_len_t *)ptr, *tmpp;
442 1.1.1.1.6.2 wrstuden int order_start = -1, order = -1;
443 1.1.1.1.6.2 wrstuden struct slab_object *so;
444 1.1.1.1.6.2 wrstuden unsigned long diff;
445 1.1.1.1.6.2 wrstuden int i, inserted = 0;
446 1.1.1.1.6.2 wrstuden
447 1.1.1.1.6.2 wrstuden if (!ptr)
448 1.1.1.1.6.2 wrstuden return;
449 1.1.1.1.6.2 wrstuden
450 1.1.1.1.6.2 wrstuden #ifdef SLAP_NO_SL_MALLOC
451 1.1.1.1.6.2 wrstuden ber_memfree_x( ptr, NULL );
452 1.1.1.1.6.2 wrstuden return;
453 1.1.1.1.6.2 wrstuden #endif
454 1.1.1.1.6.2 wrstuden
455 1.1.1.1.6.2 wrstuden if (!sh || ptr < sh->sh_base || ptr >= sh->sh_end) {
456 1.1.1.1.6.2 wrstuden ber_memfree_x(ptr, NULL);
457 1.1.1.1.6.2 wrstuden } else if (sh->sh_stack && (char *)ptr + p[-1] == sh->sh_last) {
458 1.1.1.1.6.2 wrstuden p--;
459 1.1.1.1.6.2 wrstuden sh->sh_last = p;
460 1.1.1.1.6.2 wrstuden } else if (!sh->sh_stack) {
461 1.1.1.1.6.2 wrstuden size = *(--p);
462 1.1.1.1.6.2 wrstuden size_shift = size + sizeof(ber_len_t) - 1;
463 1.1.1.1.6.2 wrstuden do {
464 1.1.1.1.6.2 wrstuden order++;
465 1.1.1.1.6.2 wrstuden } while (size_shift >>= 1);
466 1.1.1.1.6.2 wrstuden
467 1.1.1.1.6.2 wrstuden pad_shift = pad - 1;
468 1.1.1.1.6.2 wrstuden do {
469 1.1.1.1.6.2 wrstuden order_start++;
470 1.1.1.1.6.2 wrstuden } while (pad_shift >>= 1);
471 1.1.1.1.6.2 wrstuden
472 1.1.1.1.6.2 wrstuden for (i = order, tmpp = p; i <= sh->sh_maxorder; i++) {
473 1.1.1.1.6.2 wrstuden order_size = 1 << (i+1);
474 1.1.1.1.6.2 wrstuden diff = (unsigned long)((char*)tmpp - (char*)sh->sh_base) >> (i+1);
475 1.1.1.1.6.2 wrstuden sh->sh_map[i-order_start][diff>>3] &= (~(1 << (diff & 0x7)));
476 1.1.1.1.6.2 wrstuden if (diff == ((diff>>1)<<1)) {
477 1.1.1.1.6.2 wrstuden if (!(sh->sh_map[i-order_start][(diff+1)>>3] &
478 1.1.1.1.6.2 wrstuden (1<<((diff+1)&0x7)))) {
479 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_free[i-order_start]);
480 1.1.1.1.6.2 wrstuden while (so) {
481 1.1.1.1.6.2 wrstuden if ((char*)so->so_ptr == (char*)tmpp) {
482 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE( so, so_link );
483 1.1.1.1.6.2 wrstuden } else if ((char*)so->so_ptr ==
484 1.1.1.1.6.2 wrstuden (char*)tmpp + order_size) {
485 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so, so_link);
486 1.1.1.1.6.2 wrstuden break;
487 1.1.1.1.6.2 wrstuden }
488 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
489 1.1.1.1.6.2 wrstuden }
490 1.1.1.1.6.2 wrstuden if (so) {
491 1.1.1.1.6.2 wrstuden if (i < sh->sh_maxorder) {
492 1.1.1.1.6.2 wrstuden inserted = 1;
493 1.1.1.1.6.2 wrstuden so->so_ptr = tmpp;
494 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_free[i-order_start+1],
495 1.1.1.1.6.2 wrstuden so, so_link);
496 1.1.1.1.6.2 wrstuden }
497 1.1.1.1.6.2 wrstuden continue;
498 1.1.1.1.6.2 wrstuden } else {
499 1.1.1.1.6.2 wrstuden if (LDAP_LIST_EMPTY(&sh->sh_sopool)) {
500 1.1.1.1.6.2 wrstuden slap_replenish_sopool(sh);
501 1.1.1.1.6.2 wrstuden }
502 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
503 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so, so_link);
504 1.1.1.1.6.2 wrstuden so->so_ptr = tmpp;
505 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_free[i-order_start],
506 1.1.1.1.6.2 wrstuden so, so_link);
507 1.1.1.1.6.2 wrstuden break;
508 1.1.1.1.6.2 wrstuden
509 1.1.1.1.6.2 wrstuden Debug(LDAP_DEBUG_TRACE, "slap_sl_free: "
510 1.1.1.1.6.2 wrstuden "free object not found while bit is clear.\n",
511 1.1.1.1.6.2 wrstuden 0, 0, 0);
512 1.1.1.1.6.2 wrstuden assert(so != NULL);
513 1.1.1.1.6.2 wrstuden
514 1.1.1.1.6.2 wrstuden }
515 1.1.1.1.6.2 wrstuden } else {
516 1.1.1.1.6.2 wrstuden if (!inserted) {
517 1.1.1.1.6.2 wrstuden if (LDAP_LIST_EMPTY(&sh->sh_sopool)) {
518 1.1.1.1.6.2 wrstuden slap_replenish_sopool(sh);
519 1.1.1.1.6.2 wrstuden }
520 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
521 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so, so_link);
522 1.1.1.1.6.2 wrstuden so->so_ptr = tmpp;
523 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_free[i-order_start],
524 1.1.1.1.6.2 wrstuden so, so_link);
525 1.1.1.1.6.2 wrstuden }
526 1.1.1.1.6.2 wrstuden break;
527 1.1.1.1.6.2 wrstuden }
528 1.1.1.1.6.2 wrstuden } else {
529 1.1.1.1.6.2 wrstuden if (!(sh->sh_map[i-order_start][(diff-1)>>3] &
530 1.1.1.1.6.2 wrstuden (1<<((diff-1)&0x7)))) {
531 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_free[i-order_start]);
532 1.1.1.1.6.2 wrstuden while (so) {
533 1.1.1.1.6.2 wrstuden if ((char*)so->so_ptr == (char*)tmpp) {
534 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so, so_link);
535 1.1.1.1.6.2 wrstuden } else if ((char*)tmpp == (char *)so->so_ptr + order_size) {
536 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so, so_link);
537 1.1.1.1.6.2 wrstuden tmpp = so->so_ptr;
538 1.1.1.1.6.2 wrstuden break;
539 1.1.1.1.6.2 wrstuden }
540 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
541 1.1.1.1.6.2 wrstuden }
542 1.1.1.1.6.2 wrstuden if (so) {
543 1.1.1.1.6.2 wrstuden if (i < sh->sh_maxorder) {
544 1.1.1.1.6.2 wrstuden inserted = 1;
545 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_free[i-order_start+1], so, so_link);
546 1.1.1.1.6.2 wrstuden continue;
547 1.1.1.1.6.2 wrstuden }
548 1.1.1.1.6.2 wrstuden } else {
549 1.1.1.1.6.2 wrstuden if (LDAP_LIST_EMPTY(&sh->sh_sopool)) {
550 1.1.1.1.6.2 wrstuden slap_replenish_sopool(sh);
551 1.1.1.1.6.2 wrstuden }
552 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
553 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so, so_link);
554 1.1.1.1.6.2 wrstuden so->so_ptr = tmpp;
555 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_free[i-order_start],
556 1.1.1.1.6.2 wrstuden so, so_link);
557 1.1.1.1.6.2 wrstuden break;
558 1.1.1.1.6.2 wrstuden
559 1.1.1.1.6.2 wrstuden Debug(LDAP_DEBUG_TRACE, "slap_sl_free: "
560 1.1.1.1.6.2 wrstuden "free object not found while bit is clear.\n",
561 1.1.1.1.6.2 wrstuden 0, 0, 0 );
562 1.1.1.1.6.2 wrstuden assert(so != NULL);
563 1.1.1.1.6.2 wrstuden
564 1.1.1.1.6.2 wrstuden }
565 1.1.1.1.6.2 wrstuden } else {
566 1.1.1.1.6.2 wrstuden if ( !inserted ) {
567 1.1.1.1.6.2 wrstuden if (LDAP_LIST_EMPTY(&sh->sh_sopool)) {
568 1.1.1.1.6.2 wrstuden slap_replenish_sopool(sh);
569 1.1.1.1.6.2 wrstuden }
570 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_sopool);
571 1.1.1.1.6.2 wrstuden LDAP_LIST_REMOVE(so, so_link);
572 1.1.1.1.6.2 wrstuden so->so_ptr = tmpp;
573 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_free[i-order_start],
574 1.1.1.1.6.2 wrstuden so, so_link);
575 1.1.1.1.6.2 wrstuden }
576 1.1.1.1.6.2 wrstuden break;
577 1.1.1.1.6.2 wrstuden }
578 1.1.1.1.6.2 wrstuden }
579 1.1.1.1.6.2 wrstuden }
580 1.1.1.1.6.2 wrstuden }
581 1.1.1.1.6.2 wrstuden }
582 1.1.1.1.6.2 wrstuden
583 1.1.1.1.6.2 wrstuden void *
584 1.1.1.1.6.2 wrstuden slap_sl_context( void *ptr )
585 1.1.1.1.6.2 wrstuden {
586 1.1.1.1.6.2 wrstuden struct slab_heap *sh;
587 1.1.1.1.6.2 wrstuden void *ctx, *sh_tmp;
588 1.1.1.1.6.2 wrstuden
589 1.1.1.1.6.2 wrstuden if ( slapMode & SLAP_TOOL_MODE ) return NULL;
590 1.1.1.1.6.2 wrstuden
591 1.1.1.1.6.2 wrstuden #ifdef NO_THREADS
592 1.1.1.1.6.2 wrstuden sh = slheap;
593 1.1.1.1.6.2 wrstuden #else
594 1.1.1.1.6.2 wrstuden ctx = ldap_pvt_thread_pool_context();
595 1.1.1.1.6.2 wrstuden
596 1.1.1.1.6.2 wrstuden sh_tmp = NULL;
597 1.1.1.1.6.2 wrstuden ldap_pvt_thread_pool_getkey(
598 1.1.1.1.6.2 wrstuden ctx, (void *)slap_sl_mem_init, &sh_tmp, NULL);
599 1.1.1.1.6.2 wrstuden sh = sh_tmp;
600 1.1.1.1.6.2 wrstuden #endif
601 1.1.1.1.6.2 wrstuden
602 1.1.1.1.6.2 wrstuden if (sh && ptr >= sh->sh_base && ptr <= sh->sh_end) {
603 1.1.1.1.6.2 wrstuden return sh;
604 1.1.1.1.6.2 wrstuden }
605 1.1.1.1.6.2 wrstuden return NULL;
606 1.1.1.1.6.2 wrstuden }
607 1.1.1.1.6.2 wrstuden
608 1.1.1.1.6.2 wrstuden static struct slab_object *
609 1.1.1.1.6.2 wrstuden slap_replenish_sopool(
610 1.1.1.1.6.2 wrstuden struct slab_heap* sh
611 1.1.1.1.6.2 wrstuden )
612 1.1.1.1.6.2 wrstuden {
613 1.1.1.1.6.2 wrstuden struct slab_object *so_block;
614 1.1.1.1.6.2 wrstuden int i;
615 1.1.1.1.6.2 wrstuden
616 1.1.1.1.6.2 wrstuden so_block = (struct slab_object *)ch_malloc(
617 1.1.1.1.6.2 wrstuden SLAP_SLAB_SOBLOCK * sizeof(struct slab_object));
618 1.1.1.1.6.2 wrstuden
619 1.1.1.1.6.2 wrstuden if ( so_block == NULL ) {
620 1.1.1.1.6.2 wrstuden return NULL;
621 1.1.1.1.6.2 wrstuden }
622 1.1.1.1.6.2 wrstuden
623 1.1.1.1.6.2 wrstuden so_block[0].so_blockhead = 1;
624 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_sopool, &so_block[0], so_link);
625 1.1.1.1.6.2 wrstuden for (i = 1; i < SLAP_SLAB_SOBLOCK; i++) {
626 1.1.1.1.6.2 wrstuden so_block[i].so_blockhead = 0;
627 1.1.1.1.6.2 wrstuden LDAP_LIST_INSERT_HEAD(&sh->sh_sopool, &so_block[i], so_link );
628 1.1.1.1.6.2 wrstuden }
629 1.1.1.1.6.2 wrstuden
630 1.1.1.1.6.2 wrstuden return so_block;
631 1.1.1.1.6.2 wrstuden }
632 1.1.1.1.6.2 wrstuden
633 1.1.1.1.6.2 wrstuden #ifdef SLAPD_UNUSED
634 1.1.1.1.6.2 wrstuden static void
635 1.1.1.1.6.2 wrstuden print_slheap(int level, void *ctx)
636 1.1.1.1.6.2 wrstuden {
637 1.1.1.1.6.2 wrstuden struct slab_heap *sh = ctx;
638 1.1.1.1.6.2 wrstuden int order_start = -1;
639 1.1.1.1.6.2 wrstuden int pad = 2*sizeof(int)-1, pad_shift;
640 1.1.1.1.6.2 wrstuden struct slab_object *so;
641 1.1.1.1.6.2 wrstuden int i, j, once = 0;
642 1.1.1.1.6.2 wrstuden
643 1.1.1.1.6.2 wrstuden if (!ctx) {
644 1.1.1.1.6.2 wrstuden Debug(level, "NULL memctx\n", 0, 0, 0);
645 1.1.1.1.6.2 wrstuden return;
646 1.1.1.1.6.2 wrstuden }
647 1.1.1.1.6.2 wrstuden
648 1.1.1.1.6.2 wrstuden pad_shift = pad - 1;
649 1.1.1.1.6.2 wrstuden do {
650 1.1.1.1.6.2 wrstuden order_start++;
651 1.1.1.1.6.2 wrstuden } while (pad_shift >>= 1);
652 1.1.1.1.6.2 wrstuden
653 1.1.1.1.6.2 wrstuden Debug(level, "sh->sh_maxorder=%d\n", sh->sh_maxorder, 0, 0);
654 1.1.1.1.6.2 wrstuden
655 1.1.1.1.6.2 wrstuden for (i = order_start; i <= sh->sh_maxorder; i++) {
656 1.1.1.1.6.2 wrstuden once = 0;
657 1.1.1.1.6.2 wrstuden Debug(level, "order=%d\n", i, 0, 0);
658 1.1.1.1.6.2 wrstuden for (j = 0; j < (1<<(sh->sh_maxorder-i))/8; j++) {
659 1.1.1.1.6.2 wrstuden Debug(level, "%02x ", sh->sh_map[i-order_start][j], 0, 0);
660 1.1.1.1.6.2 wrstuden once = 1;
661 1.1.1.1.6.2 wrstuden }
662 1.1.1.1.6.2 wrstuden if (!once) {
663 1.1.1.1.6.2 wrstuden Debug(level, "%02x ", sh->sh_map[i-order_start][0], 0, 0);
664 1.1.1.1.6.2 wrstuden }
665 1.1.1.1.6.2 wrstuden Debug(level, "\n", 0, 0, 0);
666 1.1.1.1.6.2 wrstuden Debug(level, "free list:\n", 0, 0, 0);
667 1.1.1.1.6.2 wrstuden so = LDAP_LIST_FIRST(&sh->sh_free[i-order_start]);
668 1.1.1.1.6.2 wrstuden while (so) {
669 1.1.1.1.6.2 wrstuden Debug(level, "%lx\n", (unsigned long) so->so_ptr, 0, 0);
670 1.1.1.1.6.2 wrstuden so = LDAP_LIST_NEXT(so, so_link);
671 1.1.1.1.6.2 wrstuden }
672 1.1.1.1.6.2 wrstuden }
673 1.1.1.1.6.2 wrstuden }
674 1.1.1.1.6.2 wrstuden #endif
675