xref: /netbsd-src/lib/libc/stdlib/malloc.c (revision 03dcb730d46d34d85c9f496c1f5a3a6a43f2b7b3)
1 /*	$NetBSD: malloc.c,v 1.59 2017/01/13 04:18:54 christos Exp $	*/
2 
3 /*
4  * ----------------------------------------------------------------------------
5  * "THE BEER-WARE LICENSE" (Revision 42):
6  * <phk@FreeBSD.ORG> wrote this file.  As long as you retain this notice you
7  * can do whatever you want with this stuff. If we meet some day, and you think
8  * this stuff is worth it, you can buy me a beer in return.   Poul-Henning Kamp
9  * ----------------------------------------------------------------------------
10  *
11  * From FreeBSD: malloc.c,v 1.91 2006/01/12 07:28:20 jasone
12  *
13  */
14 
15 /*
16  * Defining MALLOC_EXTRA_SANITY will enable extra checks which are related
17  * to internal conditions and consistency in malloc.c. This has a
18  * noticeable runtime performance hit, and generally will not do you
19  * any good unless you fiddle with the internals of malloc or want
20  * to catch random pointer corruption as early as possible.
21  */
22 #ifndef MALLOC_EXTRA_SANITY
23 #undef MALLOC_EXTRA_SANITY
24 #endif
25 
26 /*
27  * What to use for Junk.  This is the byte value we use to fill with
28  * when the 'J' option is enabled.
29  */
30 #define SOME_JUNK	0xd0		/* as in "Duh" :-) */
31 
32 /*
33  * The basic parameters you can tweak.
34  *
35  * malloc_minsize	minimum size of an allocation in bytes.
36  *			If this is too small it's too much work
37  *			to manage them.  This is also the smallest
38  *			unit of alignment used for the storage
39  *			returned by malloc/realloc.
40  *
41  */
42 
43 #include "namespace.h"
44 #if defined(__FreeBSD__)
45 #   if defined(__i386__)
46 #       define malloc_minsize		16U
47 #   endif
48 #   if defined(__ia64__)
49 #	define malloc_pageshift		13U
50 #	define malloc_minsize		16U
51 #   endif
52 #   if defined(__alpha__)
53 #       define malloc_pageshift		13U
54 #       define malloc_minsize		16U
55 #   endif
56 #   if defined(__sparc64__)
57 #       define malloc_pageshift		13U
58 #       define malloc_minsize		16U
59 #   endif
60 #   if defined(__amd64__)
61 #       define malloc_pageshift		12U
62 #       define malloc_minsize		16U
63 #   endif
64 #   if defined(__arm__)
65 #       define malloc_pageshift         12U
66 #       define malloc_minsize           16U
67 #   endif
68 #   define HAS_UTRACE
69 #   define UTRACE_LABEL
70 
71 #include <sys/cdefs.h>
72 void utrace(struct ut *, int);
73 
74     /*
75      * Make malloc/free/realloc thread-safe in libc for use with
76      * kernel threads.
77      */
78 #   include "libc_private.h"
79 #   include "spinlock.h"
80     static spinlock_t thread_lock	= _SPINLOCK_INITIALIZER;
81 #   define _MALLOC_LOCK()		if (__isthreaded) _SPINLOCK(&thread_lock);
82 #   define _MALLOC_UNLOCK()		if (__isthreaded) _SPINUNLOCK(&thread_lock);
83 #endif /* __FreeBSD__ */
84 
85 #include <sys/types.h>
86 #if defined(__NetBSD__)
87 # define malloc_minsize               16U
88 # ifdef _LIBC
89 #  define HAS_UTRACE
90 #  define UTRACE_LABEL "malloc",
91 int utrace(const char *, void *, size_t);
92 # endif
93 # include <sys/cdefs.h>
94 # include "extern.h"
95 # if defined(LIBC_SCCS) && !defined(lint)
96 __RCSID("$NetBSD: malloc.c,v 1.59 2017/01/13 04:18:54 christos Exp $");
97 # endif /* LIBC_SCCS and not lint */
98 # include <reentrant.h>
99 # ifdef _REENTRANT
100 extern int __isthreaded;
101 static mutex_t thread_lock = MUTEX_INITIALIZER;
102 #  define _MALLOC_LOCK()	if (__isthreaded) mutex_lock(&thread_lock);
103 #  define _MALLOC_UNLOCK()	if (__isthreaded) mutex_unlock(&thread_lock);
104 # else
105 #  define _MALLOC_LOCK()
106 #  define _MALLOC_UNLOCK()
107 # endif
108 #endif /* __NetBSD__ */
109 
110 #if defined(__sparc__) && defined(sun)
111 #   define malloc_minsize		16U
112 #   define MAP_ANON			(0)
113     static int fdzero;
114 #   define MMAP_FD	fdzero
115 #   define INIT_MMAP() \
116 	{ if ((fdzero = open(_PATH_DEVZERO, O_RDWR | O_CLOEXEC, 0000)) == -1) \
117 	    wrterror("open of /dev/zero"); }
118 #endif /* __sparc__ */
119 
120 /* Insert your combination here... */
121 #if defined(__FOOCPU__) && defined(__BAROS__)
122 #   define malloc_minsize		16U
123 #endif /* __FOOCPU__ && __BAROS__ */
124 
125 #ifndef ZEROSIZEPTR
126 #define ZEROSIZEPTR	((void *)(uintptr_t)(1UL << (malloc_pageshift - 1)))
127 #endif
128 
129 /*
130  * No user serviceable parts behind this point.
131  */
132 #include <sys/types.h>
133 #include <sys/mman.h>
134 #include <errno.h>
135 #include <fcntl.h>
136 #include <paths.h>
137 #include <stddef.h>
138 #include <stdio.h>
139 #include <stdlib.h>
140 #include <string.h>
141 #include <unistd.h>
142 
143 /*
144  * This structure describes a page worth of chunks.
145  */
146 
147 struct pginfo {
148     struct pginfo	*next;	/* next on the free list */
149     void		*page;	/* Pointer to the page */
150     u_short		size;	/* size of this page's chunks */
151     u_short		shift;	/* How far to shift for this size chunks */
152     u_short		free;	/* How many free chunks */
153     u_short		total;	/* How many chunk */
154     u_int		bits[1]; /* Which chunks are free */
155 };
156 
157 /*
158  * This structure describes a number of free pages.
159  */
160 
161 struct pgfree {
162     struct pgfree	*next;	/* next run of free pages */
163     struct pgfree	*prev;	/* prev run of free pages */
164     void		*page;	/* pointer to free pages */
165     void		*end;	/* pointer to end of free pages */
166     size_t		size;	/* number of bytes free */
167 };
168 
169 /*
170  * How many bits per u_int in the bitmap.
171  * Change only if not 8 bits/byte
172  */
173 #define	MALLOC_BITS	((int)(8*sizeof(u_int)))
174 
175 /*
176  * Magic values to put in the page_directory
177  */
178 #define MALLOC_NOT_MINE	((struct pginfo*) 0)
179 #define MALLOC_FREE 	((struct pginfo*) 1)
180 #define MALLOC_FIRST	((struct pginfo*) 2)
181 #define MALLOC_FOLLOW	((struct pginfo*) 3)
182 #define MALLOC_MAGIC	((struct pginfo*) 4)
183 
184 /*
185  * Page size related parameters, computed at run-time.
186  */
187 static size_t malloc_pagesize;
188 static size_t malloc_pageshift;
189 static size_t malloc_pagemask;
190 
191 #ifndef malloc_minsize
192 #define malloc_minsize			16U
193 #endif
194 
195 #ifndef malloc_maxsize
196 #define malloc_maxsize			((malloc_pagesize)>>1)
197 #endif
198 
199 #define pageround(foo) (((foo) + (malloc_pagemask))&(~(malloc_pagemask)))
200 #define ptr2idx(foo) \
201     (((size_t)(uintptr_t)(foo) >> malloc_pageshift)-malloc_origo)
202 
203 #ifndef _MALLOC_LOCK
204 #define _MALLOC_LOCK()
205 #endif
206 
207 #ifndef _MALLOC_UNLOCK
208 #define _MALLOC_UNLOCK()
209 #endif
210 
211 #ifndef MMAP_FD
212 #define MMAP_FD (-1)
213 #endif
214 
215 #ifndef INIT_MMAP
216 #define INIT_MMAP()
217 #endif
218 
219 #ifndef MADV_FREE
220 #define MADV_FREE MADV_DONTNEED
221 #endif
222 
223 /* Number of free pages we cache */
224 static size_t malloc_cache = 16;
225 
226 /* The offset from pagenumber to index into the page directory */
227 static size_t malloc_origo;
228 
229 /* The last index in the page directory we care about */
230 static size_t last_idx;
231 
232 /* Pointer to page directory. Allocated "as if with" malloc */
233 static struct	pginfo **page_dir;
234 
235 /* How many slots in the page directory */
236 static size_t	malloc_ninfo;
237 
238 /* Free pages line up here */
239 static struct pgfree free_list;
240 
241 /* Abort(), user doesn't handle problems.  */
242 static int malloc_abort;
243 
244 /* Are we trying to die ?  */
245 static int suicide;
246 
247 /* always realloc ?  */
248 static int malloc_realloc;
249 
250 /* pass the kernel a hint on free pages ?  */
251 #if defined(MADV_FREE)
252 static int malloc_hint = 0;
253 #endif
254 
255 /* xmalloc behaviour ?  */
256 static int malloc_xmalloc;
257 
258 /* sysv behaviour for malloc(0) ?  */
259 static int malloc_sysv;
260 
261 /* zero fill ?  */
262 static int malloc_zero;
263 
264 /* junk fill ?  */
265 static int malloc_junk;
266 
267 #ifdef HAS_UTRACE
268 
269 /* utrace ?  */
270 static int malloc_utrace;
271 
272 struct ut { void *p; size_t s; void *r; };
273 
274 #define UTRACE(a, b, c) \
275 	if (malloc_utrace) {			\
276 		struct ut u;			\
277 		u.p=a; u.s = b; u.r=c;		\
278 		utrace(UTRACE_LABEL (void *) &u, sizeof u);	\
279 	}
280 #else /* !HAS_UTRACE */
281 #define UTRACE(a,b,c)
282 #endif /* HAS_UTRACE */
283 
284 /* my last break. */
285 static void *malloc_brk;
286 
287 /* one location cache for free-list holders */
288 static struct pgfree *px;
289 
290 /* compile-time options */
291 const char *_malloc_options;
292 
293 /* Name of the current public function */
294 static const char *malloc_func;
295 
296 /* Macro for mmap */
297 #define MMAP(size) \
298 	mmap(NULL, (size), PROT_READ|PROT_WRITE, MAP_ANON|MAP_PRIVATE, \
299 	    MMAP_FD, (off_t)0);
300 
301 /*
302  * Necessary function declarations
303  */
304 static int extend_pgdir(size_t idx);
305 static void *imalloc(size_t size);
306 static void ifree(void *ptr);
307 static void *irealloc(void *ptr, size_t size);
308 
309 static void
310 wrtmessage(const char *p1, const char *p2, const char *p3, const char *p4)
311 {
312 
313     write(STDERR_FILENO, p1, strlen(p1));
314     write(STDERR_FILENO, p2, strlen(p2));
315     write(STDERR_FILENO, p3, strlen(p3));
316     write(STDERR_FILENO, p4, strlen(p4));
317 }
318 
319 void (*_malloc_message)(const char *p1, const char *p2, const char *p3,
320 	    const char *p4) = wrtmessage;
321 static void
322 wrterror(const char *p)
323 {
324 
325     suicide = 1;
326     _malloc_message(getprogname(), malloc_func, " error: ", p);
327     abort();
328 }
329 
330 static void
331 wrtwarning(const char *p)
332 {
333 
334     /*
335      * Sensitive processes, somewhat arbitrarily defined here as setuid,
336      * setgid, root and wheel cannot afford to have malloc mistakes.
337      */
338     if (malloc_abort || issetugid() || getuid() == 0 || getgid() == 0)
339 	wrterror(p);
340 }
341 
342 /*
343  * Allocate a number of pages from the OS
344  */
345 static void *
346 map_pages(size_t pages)
347 {
348     caddr_t result, rresult, tail;
349     intptr_t bytes = pages << malloc_pageshift;
350 
351     if (bytes < 0 || (size_t)bytes < pages) {
352 	errno = ENOMEM;
353 	return NULL;
354     }
355 
356     if ((result = sbrk(bytes)) == (void *)-1)
357 	return NULL;
358 
359     /*
360      * Round to a page, in case sbrk(2) did not do this for us
361      */
362     rresult = (caddr_t)pageround((size_t)(uintptr_t)result);
363     if (result < rresult) {
364 	/* make sure we have enough space to fit bytes */
365 	if (sbrk((intptr_t)(rresult - result)) == (void *) -1) {
366 	    /* we failed, put everything back */
367 	    if (brk(result)) {
368 		wrterror("brk(2) failed [internal error]\n");
369 	    }
370 	}
371     }
372     tail = rresult + (size_t)bytes;
373 
374     last_idx = ptr2idx(tail) - 1;
375     malloc_brk = tail;
376 
377     if ((last_idx+1) >= malloc_ninfo && !extend_pgdir(last_idx)) {
378 	malloc_brk = result;
379 	last_idx = ptr2idx(malloc_brk) - 1;
380 	/* Put back break point since we failed. */
381 	if (brk(malloc_brk))
382 	    wrterror("brk(2) failed [internal error]\n");
383 	return 0;
384     }
385 
386     return rresult;
387 }
388 
389 /*
390  * Extend page directory
391  */
392 static int
393 extend_pgdir(size_t idx)
394 {
395     struct  pginfo **new, **old;
396     size_t newlen, oldlen;
397 
398     /* check for overflow */
399     if ((((~(1UL << ((sizeof(size_t) * NBBY) - 1)) / sizeof(*page_dir)) + 1)
400 	+ (malloc_pagesize / sizeof *page_dir)) < idx) {
401 	errno = ENOMEM;
402 	return 0;
403     }
404 
405     /* Make it this many pages */
406     newlen = pageround(idx * sizeof *page_dir) + malloc_pagesize;
407 
408     /* remember the old mapping size */
409     oldlen = malloc_ninfo * sizeof *page_dir;
410 
411     /*
412      * NOTE: we allocate new pages and copy the directory rather than tempt
413      * fate by trying to "grow" the region.. There is nothing to prevent
414      * us from accidentally re-mapping space that's been allocated by our caller
415      * via dlopen() or other mmap().
416      *
417      * The copy problem is not too bad, as there is 4K of page index per
418      * 4MB of malloc arena.
419      *
420      * We can totally avoid the copy if we open a file descriptor to associate
421      * the anon mappings with.  Then, when we remap the pages at the new
422      * address, the old pages will be "magically" remapped..  But this means
423      * keeping open a "secret" file descriptor.....
424      */
425 
426     /* Get new pages */
427     new = MMAP(newlen);
428     if (new == MAP_FAILED)
429 	return 0;
430 
431     /* Copy the old stuff */
432     memcpy(new, page_dir, oldlen);
433 
434     /* register the new size */
435     malloc_ninfo = newlen / sizeof *page_dir;
436 
437     /* swap the pointers */
438     old = page_dir;
439     page_dir = new;
440 
441     /* Now free the old stuff */
442     munmap(old, oldlen);
443     return 1;
444 }
445 
446 /*
447  * Initialize the world
448  */
449 static void
450 malloc_init(void)
451 {
452     const char *p;
453     char b[64];
454     size_t i;
455     ssize_t j;
456     int serrno = errno;
457 
458     /*
459      * Compute page-size related variables.
460      */
461     malloc_pagesize = getpagesize();
462     malloc_pagemask = malloc_pagesize - 1;
463     for (malloc_pageshift = 0;
464 	 (1UL << malloc_pageshift) != malloc_pagesize;
465 	 malloc_pageshift++)
466 	/* nothing */ ;
467 
468     INIT_MMAP();
469 
470 #ifdef MALLOC_EXTRA_SANITY
471     malloc_junk = 1;
472 #endif /* MALLOC_EXTRA_SANITY */
473 
474     for (i = 0; i < 3; i++) {
475 	if (i == 0) {
476 	    j = readlink("/etc/malloc.conf", b, sizeof b - 1);
477 	    if (j == -1)
478 		continue;
479 	    b[j] = '\0';
480 	    p = b;
481 #ifdef _LIBC
482 	} else if (i == 1 && issetugid() == 0) {
483 	    p = getenv("MALLOC_OPTIONS");
484 #endif
485 	} else if (i == 1) {
486 	    continue;
487 	} else {
488 	    p = _malloc_options;
489 	}
490 	for (; p != NULL && *p != '\0'; p++) {
491 	    switch (*p) {
492 		case '>': malloc_cache   <<= 1; break;
493 		case '<': malloc_cache   >>= 1; break;
494 		case 'a': malloc_abort   = 0; break;
495 		case 'A': malloc_abort   = 1; break;
496 		case 'h': malloc_hint    = 0; break;
497 		case 'H': malloc_hint    = 1; break;
498 		case 'r': malloc_realloc = 0; break;
499 		case 'R': malloc_realloc = 1; break;
500 		case 'j': malloc_junk    = 0; break;
501 		case 'J': malloc_junk    = 1; break;
502 #ifdef HAS_UTRACE
503 		case 'u': malloc_utrace  = 0; break;
504 		case 'U': malloc_utrace  = 1; break;
505 #endif
506 		case 'v': malloc_sysv    = 0; break;
507 		case 'V': malloc_sysv    = 1; break;
508 		case 'x': malloc_xmalloc = 0; break;
509 		case 'X': malloc_xmalloc = 1; break;
510 		case 'z': malloc_zero    = 0; break;
511 		case 'Z': malloc_zero    = 1; break;
512 		default:
513 		    _malloc_message(getprogname(), malloc_func,
514 			 " warning: ", "unknown char in MALLOC_OPTIONS\n");
515 		    break;
516 	    }
517 	}
518     }
519 
520     UTRACE(0, 0, 0);
521 
522     /*
523      * We want junk in the entire allocation, and zero only in the part
524      * the user asked for.
525      */
526     if (malloc_zero)
527 	malloc_junk = 1;
528 
529     /* Allocate one page for the page directory */
530     page_dir = MMAP(malloc_pagesize);
531 
532     if (page_dir == MAP_FAILED)
533 	wrterror("mmap(2) failed, check limits.\n");
534 
535     /*
536      * We need a maximum of malloc_pageshift buckets, steal these from the
537      * front of the page_directory;
538      */
539     malloc_origo = pageround((size_t)(uintptr_t)sbrk((intptr_t)0))
540 	>> malloc_pageshift;
541     malloc_origo -= malloc_pageshift;
542 
543     malloc_ninfo = malloc_pagesize / sizeof *page_dir;
544 
545     /* Recalculate the cache size in bytes, and make sure it's nonzero */
546 
547     if (!malloc_cache)
548 	malloc_cache++;
549 
550     malloc_cache <<= malloc_pageshift;
551 
552     /*
553      * This is a nice hack from Kaleb Keithly (kaleb@x.org).
554      * We can sbrk(2) further back when we keep this on a low address.
555      */
556     px = imalloc(sizeof *px);
557 
558     errno = serrno;
559 }
560 
561 /*
562  * Allocate a number of complete pages
563  */
564 static void *
565 malloc_pages(size_t size)
566 {
567     void *p, *delay_free = NULL;
568     size_t i;
569     struct pgfree *pf;
570     size_t idx;
571 
572     idx = pageround(size);
573     if (idx < size) {
574 	errno = ENOMEM;
575 	return NULL;
576     } else
577 	size = idx;
578 
579     p = NULL;
580 
581     /* Look for free pages before asking for more */
582     for(pf = free_list.next; pf; pf = pf->next) {
583 
584 #ifdef MALLOC_EXTRA_SANITY
585 	if (pf->size & malloc_pagemask)
586 	    wrterror("(ES): junk length entry on free_list.\n");
587 	if (!pf->size)
588 	    wrterror("(ES): zero length entry on free_list.\n");
589 	if (pf->page == pf->end)
590 	    wrterror("(ES): zero entry on free_list.\n");
591 	if (pf->page > pf->end)
592 	    wrterror("(ES): sick entry on free_list.\n");
593 	if ((void*)pf->page >= (void*)sbrk(0))
594 	    wrterror("(ES): entry on free_list past brk.\n");
595 	if (page_dir[ptr2idx(pf->page)] != MALLOC_FREE)
596 	    wrterror("(ES): non-free first page on free-list.\n");
597 	if (page_dir[ptr2idx(pf->end)-1] != MALLOC_FREE)
598 	    wrterror("(ES): non-free last page on free-list.\n");
599 #endif /* MALLOC_EXTRA_SANITY */
600 
601 	if (pf->size < size)
602 	    continue;
603 
604 	if (pf->size == size) {
605 	    p = pf->page;
606 	    if (pf->next != NULL)
607 		    pf->next->prev = pf->prev;
608 	    pf->prev->next = pf->next;
609 	    delay_free = pf;
610 	    break;
611 	}
612 
613 	p = pf->page;
614 	pf->page = (char *)pf->page + size;
615 	pf->size -= size;
616 	break;
617     }
618 
619 #ifdef MALLOC_EXTRA_SANITY
620     if (p != NULL && page_dir[ptr2idx(p)] != MALLOC_FREE)
621 	wrterror("(ES): allocated non-free page on free-list.\n");
622 #endif /* MALLOC_EXTRA_SANITY */
623 
624     size >>= malloc_pageshift;
625 
626     /* Map new pages */
627     if (p == NULL)
628 	p = map_pages(size);
629 
630     if (p != NULL) {
631 
632 	idx = ptr2idx(p);
633 	page_dir[idx] = MALLOC_FIRST;
634 	for (i=1;i<size;i++)
635 	    page_dir[idx+i] = MALLOC_FOLLOW;
636 
637 	if (malloc_junk)
638 	    memset(p, SOME_JUNK, size << malloc_pageshift);
639     }
640 
641     if (delay_free) {
642 	if (px == NULL)
643 	    px = delay_free;
644 	else
645 	    ifree(delay_free);
646     }
647 
648     return p;
649 }
650 
651 /*
652  * Allocate a page of fragments
653  */
654 
655 static inline int
656 malloc_make_chunks(int bits)
657 {
658     struct  pginfo *bp;
659     void *pp;
660     int i, k;
661     long l;
662 
663     /* Allocate a new bucket */
664     pp = malloc_pages(malloc_pagesize);
665     if (pp == NULL)
666 	return 0;
667 
668     /* Find length of admin structure */
669     l = (long)offsetof(struct pginfo, bits[0]);
670     l += (long)sizeof bp->bits[0] *
671 	(((malloc_pagesize >> bits)+MALLOC_BITS-1) / MALLOC_BITS);
672 
673     /* Don't waste more than two chunks on this */
674     if ((1<<(bits)) <= l+l) {
675 	bp = (struct  pginfo *)pp;
676     } else {
677 	bp = imalloc((size_t)l);
678 	if (bp == NULL) {
679 	    ifree(pp);
680 	    return 0;
681 	}
682     }
683 
684     bp->size = (1<<bits);
685     bp->shift = bits;
686     bp->total = bp->free = (u_short)(malloc_pagesize >> bits);
687     bp->page = pp;
688 
689     /* set all valid bits in the bitmap */
690     k = bp->total;
691     i = 0;
692 
693     /* Do a bunch at a time */
694     for(;k-i >= MALLOC_BITS; i += MALLOC_BITS)
695 	bp->bits[i / MALLOC_BITS] = ~0U;
696 
697     for(; i < k; i++)
698         bp->bits[i/MALLOC_BITS] |= 1<<(i%MALLOC_BITS);
699 
700     if (bp == bp->page) {
701 	/* Mark the ones we stole for ourselves */
702 	for(i = 0; l > 0; i++) {
703 	    bp->bits[i / MALLOC_BITS] &= ~(1 << (i % MALLOC_BITS));
704 	    bp->free--;
705 	    bp->total--;
706 	    l -= (long)(1 << bits);
707 	}
708     }
709 
710     /* MALLOC_LOCK */
711 
712     page_dir[ptr2idx(pp)] = bp;
713 
714     bp->next = page_dir[bits];
715     page_dir[bits] = bp;
716 
717     /* MALLOC_UNLOCK */
718 
719     return 1;
720 }
721 
722 /*
723  * Allocate a fragment
724  */
725 static void *
726 malloc_bytes(size_t size)
727 {
728     size_t i;
729     int j;
730     u_int u;
731     struct  pginfo *bp;
732     size_t k;
733     u_int *lp;
734 
735     /* Don't bother with anything less than this */
736     if (size < malloc_minsize)
737 	size = malloc_minsize;
738 
739 
740     /* Find the right bucket */
741     j = 1;
742     i = size-1;
743     while (i >>= 1)
744 	j++;
745 
746     /* If it's empty, make a page more of that size chunks */
747     if (page_dir[j] == NULL && !malloc_make_chunks(j))
748 	return NULL;
749 
750     bp = page_dir[j];
751 
752     /* Find first word of bitmap which isn't empty */
753     for (lp = bp->bits; !*lp; lp++)
754 	;
755 
756     /* Find that bit, and tweak it */
757     u = 1;
758     k = 0;
759     while (!(*lp & u)) {
760 	u += u;
761 	k++;
762     }
763     *lp ^= u;
764 
765     /* If there are no more free, remove from free-list */
766     if (!--bp->free) {
767 	page_dir[j] = bp->next;
768 	bp->next = NULL;
769     }
770 
771     /* Adjust to the real offset of that chunk */
772     k += (lp-bp->bits)*MALLOC_BITS;
773     k <<= bp->shift;
774 
775     if (malloc_junk)
776 	memset((u_char*)bp->page + k, SOME_JUNK, (size_t)bp->size);
777 
778     return (u_char *)bp->page + k;
779 }
780 
781 /*
782  * Allocate a piece of memory
783  */
784 static void *
785 imalloc(size_t size)
786 {
787     void *result;
788 
789     if (suicide)
790 	abort();
791 
792     if ((size + malloc_pagesize) < size)	/* Check for overflow */
793 	result = NULL;
794     else if ((size + malloc_pagesize) >= (uintptr_t)page_dir)
795 	result = NULL;
796     else if (size <= malloc_maxsize)
797 	result = malloc_bytes(size);
798     else
799 	result = malloc_pages(size);
800 
801     if (malloc_abort && result == NULL)
802 	wrterror("allocation failed.\n");
803 
804     if (malloc_zero && result != NULL)
805 	memset(result, 0, size);
806 
807     return result;
808 }
809 
810 /*
811  * Change the size of an allocation.
812  */
813 static void *
814 irealloc(void *ptr, size_t size)
815 {
816     void *p;
817     size_t osize, idx;
818     struct pginfo **mp;
819     size_t i;
820 
821     if (suicide)
822 	abort();
823 
824     idx = ptr2idx(ptr);
825 
826     if (idx < malloc_pageshift) {
827 	wrtwarning("junk pointer, too low to make sense.\n");
828 	return 0;
829     }
830 
831     if (idx > last_idx) {
832 	wrtwarning("junk pointer, too high to make sense.\n");
833 	return 0;
834     }
835 
836     mp = &page_dir[idx];
837 
838     if (*mp == MALLOC_FIRST) {			/* Page allocation */
839 
840 	/* Check the pointer */
841 	if ((size_t)(uintptr_t)ptr & malloc_pagemask) {
842 	    wrtwarning("modified (page-) pointer.\n");
843 	    return NULL;
844 	}
845 
846 	/* Find the size in bytes */
847 	for (osize = malloc_pagesize; *++mp == MALLOC_FOLLOW;)
848 	    osize += malloc_pagesize;
849 
850         if (!malloc_realloc && 			/* unless we have to, */
851 	  size <= osize && 			/* .. or are too small, */
852 	  size > (osize - malloc_pagesize)) {	/* .. or can free a page, */
853 	    if (malloc_junk)
854 		memset((u_char *)ptr + size, SOME_JUNK, osize-size);
855 	    return ptr;				/* don't do anything. */
856 	}
857 
858     } else if (*mp >= MALLOC_MAGIC) {		/* Chunk allocation */
859 
860 	/* Check the pointer for sane values */
861 	if (((size_t)(uintptr_t)ptr & ((*mp)->size-1))) {
862 	    wrtwarning("modified (chunk-) pointer.\n");
863 	    return NULL;
864 	}
865 
866 	/* Find the chunk index in the page */
867 	i = ((size_t)(uintptr_t)ptr & malloc_pagemask) >> (*mp)->shift;
868 
869 	/* Verify that it isn't a free chunk already */
870         if ((*mp)->bits[i/MALLOC_BITS] & (1UL << (i % MALLOC_BITS))) {
871 	    wrtwarning("chunk is already free.\n");
872 	    return NULL;
873 	}
874 
875 	osize = (*mp)->size;
876 
877 	if (!malloc_realloc &&		/* Unless we have to, */
878 	  size <= osize && 		/* ..or are too small, */
879 	  (size > osize / 2 ||	 	/* ..or could use a smaller size, */
880 	  osize == malloc_minsize)) {	/* ..(if there is one) */
881 	    if (malloc_junk)
882 		memset((u_char *)ptr + size, SOME_JUNK, osize-size);
883 	    return ptr;			/* ..Don't do anything */
884 	}
885 
886     } else {
887 	wrtwarning("pointer to wrong page.\n");
888 	return NULL;
889     }
890 
891     p = imalloc(size);
892 
893     if (p != NULL) {
894 	/* copy the lesser of the two sizes, and free the old one */
895 	if (!size || !osize)
896 	    ;
897 	else if (osize < size)
898 	    memcpy(p, ptr, osize);
899 	else
900 	    memcpy(p, ptr, size);
901 	ifree(ptr);
902     }
903     return p;
904 }
905 
906 /*
907  * Free a sequence of pages
908  */
909 
910 static inline void
911 free_pages(void *ptr, size_t idx, struct pginfo *info)
912 {
913     size_t i;
914     struct pgfree *pf, *pt=NULL;
915     size_t l;
916     void *tail;
917 
918     if (info == MALLOC_FREE) {
919 	wrtwarning("page is already free.\n");
920 	return;
921     }
922 
923     if (info != MALLOC_FIRST) {
924 	wrtwarning("pointer to wrong page.\n");
925 	return;
926     }
927 
928     if ((size_t)(uintptr_t)ptr & malloc_pagemask) {
929 	wrtwarning("modified (page-) pointer.\n");
930 	return;
931     }
932 
933     /* Count how many pages and mark them free at the same time */
934     page_dir[idx] = MALLOC_FREE;
935     for (i = 1; page_dir[idx+i] == MALLOC_FOLLOW; i++)
936 	page_dir[idx + i] = MALLOC_FREE;
937 
938     l = i << malloc_pageshift;
939 
940     if (malloc_junk)
941 	memset(ptr, SOME_JUNK, l);
942 
943     if (malloc_hint)
944 	madvise(ptr, l, MADV_FREE);
945 
946     tail = (char *)ptr+l;
947 
948     /* add to free-list */
949     if (px == NULL)
950 	px = imalloc(sizeof *px);	/* This cannot fail... */
951     px->page = ptr;
952     px->end =  tail;
953     px->size = l;
954     if (free_list.next == NULL) {
955 
956 	/* Nothing on free list, put this at head */
957 	px->next = free_list.next;
958 	px->prev = &free_list;
959 	free_list.next = px;
960 	pf = px;
961 	px = NULL;
962 
963     } else {
964 
965 	/* Find the right spot, leave pf pointing to the modified entry. */
966 	tail = (char *)ptr+l;
967 
968 	for(pf = free_list.next; pf->end < ptr && pf->next != NULL;
969 	    pf = pf->next)
970 	    ; /* Race ahead here */
971 
972 	if (pf->page > tail) {
973 	    /* Insert before entry */
974 	    px->next = pf;
975 	    px->prev = pf->prev;
976 	    pf->prev = px;
977 	    px->prev->next = px;
978 	    pf = px;
979 	    px = NULL;
980 	} else if (pf->end == ptr ) {
981 	    /* Append to the previous entry */
982 	    pf->end = (char *)pf->end + l;
983 	    pf->size += l;
984 	    if (pf->next != NULL && pf->end == pf->next->page ) {
985 		/* And collapse the next too. */
986 		pt = pf->next;
987 		pf->end = pt->end;
988 		pf->size += pt->size;
989 		pf->next = pt->next;
990 		if (pf->next != NULL)
991 		    pf->next->prev = pf;
992 	    }
993 	} else if (pf->page == tail) {
994 	    /* Prepend to entry */
995 	    pf->size += l;
996 	    pf->page = ptr;
997 	} else if (pf->next == NULL) {
998 	    /* Append at tail of chain */
999 	    px->next = NULL;
1000 	    px->prev = pf;
1001 	    pf->next = px;
1002 	    pf = px;
1003 	    px = NULL;
1004 	} else {
1005 	    wrterror("freelist is destroyed.\n");
1006 	}
1007     }
1008 
1009     /* Return something to OS ? */
1010     if (pf->next == NULL &&			/* If we're the last one, */
1011       pf->size > malloc_cache &&		/* ..and the cache is full, */
1012       pf->end == malloc_brk &&			/* ..and none behind us, */
1013       malloc_brk == sbrk((intptr_t)0)) {	/* ..and it's OK to do... */
1014 
1015 	/*
1016 	 * Keep the cache intact.  Notice that the '>' above guarantees that
1017 	 * the pf will always have at least one page afterwards.
1018 	 */
1019 	pf->end = (char *)pf->page + malloc_cache;
1020 	pf->size = malloc_cache;
1021 
1022 	brk(pf->end);
1023 	malloc_brk = pf->end;
1024 
1025 	idx = ptr2idx(pf->end);
1026 
1027 	for(i=idx;i <= last_idx;)
1028 	    page_dir[i++] = MALLOC_NOT_MINE;
1029 
1030 	last_idx = idx - 1;
1031 
1032 	/* XXX: We could realloc/shrink the pagedir here I guess. */
1033     }
1034     if (pt != NULL)
1035 	ifree(pt);
1036 }
1037 
1038 /*
1039  * Free a chunk, and possibly the page it's on, if the page becomes empty.
1040  */
1041 
1042 static inline void
1043 free_bytes(void *ptr, size_t idx, struct pginfo *info)
1044 {
1045     size_t i;
1046     struct pginfo **mp;
1047     void *vp;
1048 
1049     /* Find the chunk number on the page */
1050     i = ((size_t)(uintptr_t)ptr & malloc_pagemask) >> info->shift;
1051 
1052     if (((size_t)(uintptr_t)ptr & (info->size-1))) {
1053 	wrtwarning("modified (chunk-) pointer.\n");
1054 	return;
1055     }
1056 
1057     if (info->bits[i/MALLOC_BITS] & (1UL << (i % MALLOC_BITS))) {
1058 	wrtwarning("chunk is already free.\n");
1059 	return;
1060     }
1061 
1062     if (malloc_junk)
1063 	memset(ptr, SOME_JUNK, (size_t)info->size);
1064 
1065     info->bits[i/MALLOC_BITS] |= (u_int)(1UL << (i % MALLOC_BITS));
1066     info->free++;
1067 
1068     mp = page_dir + info->shift;
1069 
1070     if (info->free == 1) {
1071 
1072 	/* Page became non-full */
1073 
1074 	mp = page_dir + info->shift;
1075 	/* Insert in address order */
1076 	while (*mp && (*mp)->next && (*mp)->next->page < info->page)
1077 	    mp = &(*mp)->next;
1078 	info->next = *mp;
1079 	*mp = info;
1080 	return;
1081     }
1082 
1083     if (info->free != info->total)
1084 	return;
1085 
1086     /* Find & remove this page in the queue */
1087     while (*mp != info) {
1088 	mp = &((*mp)->next);
1089 #ifdef MALLOC_EXTRA_SANITY
1090 	if (!*mp)
1091 		wrterror("(ES): Not on queue.\n");
1092 #endif /* MALLOC_EXTRA_SANITY */
1093     }
1094     *mp = info->next;
1095 
1096     /* Free the page & the info structure if need be */
1097     page_dir[idx] = MALLOC_FIRST;
1098     vp = info->page;		/* Order is important ! */
1099     if(vp != (void*)info)
1100 	ifree(info);
1101     ifree(vp);
1102 }
1103 
1104 static void
1105 ifree(void *ptr)
1106 {
1107     struct pginfo *info;
1108     size_t idx;
1109 
1110     /* This is legal */
1111     if (ptr == NULL)
1112 	return;
1113 
1114     /* If we're already sinking, don't make matters any worse. */
1115     if (suicide)
1116 	return;
1117 
1118     idx = ptr2idx(ptr);
1119 
1120     if (idx < malloc_pageshift) {
1121 	wrtwarning("junk pointer, too low to make sense.\n");
1122 	return;
1123     }
1124 
1125     if (idx > last_idx) {
1126 	wrtwarning("junk pointer, too high to make sense.\n");
1127 	return;
1128     }
1129 
1130     info = page_dir[idx];
1131 
1132     if (info < MALLOC_MAGIC)
1133         free_pages(ptr, idx, info);
1134     else
1135 	free_bytes(ptr, idx, info);
1136     return;
1137 }
1138 
1139 static int malloc_active; /* Recursion flag for public interface. */
1140 static unsigned malloc_started; /* Set when initialization has been done */
1141 
1142 static void *
1143 pubrealloc(void *ptr, size_t size, const char *func)
1144 {
1145     void *r;
1146     int err = 0;
1147 
1148     /*
1149      * If a thread is inside our code with a functional lock held, and then
1150      * catches a signal which calls us again, we would get a deadlock if the
1151      * lock is not of a recursive type.
1152      */
1153     _MALLOC_LOCK();
1154     malloc_func = func;
1155     if (malloc_active > 0) {
1156 	if (malloc_active == 1) {
1157 	    wrtwarning("recursive call\n");
1158 	    malloc_active = 2;
1159 	}
1160         _MALLOC_UNLOCK();
1161 	errno = EINVAL;
1162 	return (NULL);
1163     }
1164     malloc_active = 1;
1165 
1166     if (!malloc_started) {
1167         if (ptr != NULL) {
1168 	    wrtwarning("malloc() has never been called\n");
1169 	    malloc_active = 0;
1170             _MALLOC_UNLOCK();
1171 	    errno = EINVAL;
1172 	    return (NULL);
1173 	}
1174 	malloc_init();
1175 	malloc_started = 1;
1176     }
1177 
1178     if (ptr == ZEROSIZEPTR)
1179 	ptr = NULL;
1180     if (malloc_sysv && !size) {
1181 	if (ptr != NULL)
1182 	    ifree(ptr);
1183 	r = NULL;
1184     } else if (!size) {
1185 	if (ptr != NULL)
1186 	    ifree(ptr);
1187 	r = ZEROSIZEPTR;
1188     } else if (ptr == NULL) {
1189 	r = imalloc(size);
1190 	err = (r == NULL);
1191     } else {
1192         r = irealloc(ptr, size);
1193 	err = (r == NULL);
1194     }
1195     UTRACE(ptr, size, r);
1196     malloc_active = 0;
1197     _MALLOC_UNLOCK();
1198     if (malloc_xmalloc && err)
1199 	wrterror("out of memory\n");
1200     if (err)
1201 	errno = ENOMEM;
1202     return (r);
1203 }
1204 
1205 /*
1206  * These are the public exported interface routines.
1207  */
1208 
1209 void *
1210 malloc(size_t size)
1211 {
1212 
1213     return pubrealloc(NULL, size, " in malloc():");
1214 }
1215 
1216 int
1217 posix_memalign(void **memptr, size_t alignment, size_t size)
1218 {
1219     int err;
1220     void *result;
1221 
1222     if (!malloc_started) {
1223 	    malloc_init();
1224 	    malloc_started = 1;
1225     }
1226     /* Make sure that alignment is a large enough power of 2. */
1227     if (((alignment - 1) & alignment) != 0 || alignment < sizeof(void *) ||
1228 	alignment > malloc_pagesize)
1229 	    return EINVAL;
1230 
1231     /*
1232      * (size | alignment) is enough to assure the requested alignment, since
1233      * the allocator always allocates power-of-two blocks.
1234      */
1235     err = errno; /* Protect errno against changes in pubrealloc(). */
1236     result = pubrealloc(NULL, (size | alignment), " in posix_memalign()");
1237     errno = err;
1238 
1239     if (result == NULL)
1240 	return ENOMEM;
1241 
1242     *memptr = result;
1243     return 0;
1244 }
1245 
1246 void *
1247 calloc(size_t num, size_t size)
1248 {
1249     void *ret;
1250 
1251     if (size != 0 && (num * size) / size != num) {
1252 	/* size_t overflow. */
1253 	errno = ENOMEM;
1254 	return (NULL);
1255     }
1256 
1257     ret = pubrealloc(NULL, num * size, " in calloc():");
1258 
1259     if (ret != NULL)
1260 	memset(ret, 0, num * size);
1261 
1262     return ret;
1263 }
1264 
1265 void
1266 free(void *ptr)
1267 {
1268 
1269     pubrealloc(ptr, 0, " in free():");
1270 }
1271 
1272 void *
1273 realloc(void *ptr, size_t size)
1274 {
1275 
1276     return pubrealloc(ptr, size, " in realloc():");
1277 }
1278 
1279 /*
1280  * Begin library-private functions, used by threading libraries for protection
1281  * of malloc during fork().  These functions are only called if the program is
1282  * running in threaded mode, so there is no need to check whether the program
1283  * is threaded here.
1284  */
1285 
1286 void
1287 _malloc_prefork(void)
1288 {
1289 
1290 	_MALLOC_LOCK();
1291 }
1292 
1293 void
1294 _malloc_postfork(void)
1295 {
1296 
1297 	_MALLOC_UNLOCK();
1298 }
1299