www.delorie.com/archives/browse.cgi   search  
Mail Archives: djgpp/1997/03/17/05:41:05

From: "A.Appleyard" <A DOT APPLEYARD AT fs2 DOT mt DOT umist DOT ac DOT uk>
Organization: Materials Science Centre
To: DJGPP AT DELORIE DOT COM
Date: Mon, 17 Mar 1997 10:16:16 GMT
Subject: malloc
Message-ID: <8FB96F09E8@fs2.mt.umist.ac.uk>

Re my messages about malloc(), here is a version of malloc() free() realloc()
which I made by altering djgpp\src\libc\ansi\stdlib\malloc.c; I have tested it
quickly and it seems to work. See the comments `/*******' herinunder.
  ..................................................................
#include <string.h>
#include <unistd.h>
#define getpagesize() 4096
typedef unsigned char byte;
static char*nextf[31]; /* pointers to chains of free blocks */
static int pagesize=0; /* page size */
#define OW 4 /* size of block-chaining overheads */
/* The first 4 bytes of a block contain:- */
/* while the block is free, a pointer to the next block in that bucket */
/* while the block is allocated, -17, then bucket number, then 2 spare bytes */
/*-----*//* allocate more memory to the indicated bucket. */
static void morecore(int bucket) {int size,amt,nblocks; char*op;
if((size=8<<bucket)<=0) return; /* how many bytes per block */
if(size<pagesize) nblocks=(amt=pagesize)/size; /* pageful of blocks that size */
else {amt=size; nblocks=1;} /* one block, of (size/pagesize) pages */
  /****** If size>=pagesize, the standard form gets (size/pagesize + 1) */
  /****** pages here. What is the extra unused page for? */
op=(char*)sbrk(amt); /* get size*nblocks bytes */
if((int)op==-1) return; /* if no more room */
nextf[bucket]=op; /* chain in the new blocks */
while(--nblocks>0) {*(char**)op=op+size; op+=size;}
*(char**)op=0;}
/*-----*/
void*malloc(long N) {char*op; long bucket,n,amt; if(!N) return 0;
if(pagesize==0) {
/* First time malloc is called, move sbrk up to OW less than a page boundary */
    for(n=0;n<31;n++) nextf[n]=0; pagesize=n=getpagesize(); op=(char*)sbrk(0);
    n=n-OW-((int)op&(n-1)); if(n<0) n+=pagesize;
    if(n) if(sbrk(n)==(char*)-1) return 0;}
{register long i=N+OW-1; i|=i>>16; i|=i>>8; i|=i>>4; i|=i>>2; i|=i>>1; amt=i+1;}
/* amt = i+OW rounded up to next power of 2 */
bucket=ffs(amt)-3; /* 1<<ffs(i) == the lowest order 1-bit in i */
/****** finding which bucket now runs quicker */
if(!(op=nextf[bucket])) {morecore(bucket); if(!(op=nextf[bucket])) return 0;}
/* remove from linked list */
nextf[bucket]=*(char**)op; op[0]=-17; op[1]=bucket; return op+OW;}
/*-----*/
void free(void*cp) {int bucket; char*op; if(!cp) return; op=(char*)cp-OW;
if(op[0]!=-17) return; /* this block was not got by malloc() */
bucket=op[1]; *(char**)op=nextf[bucket]; nextf[bucket]=op;}
/*-----*/
void*realloc(void*Old,long N) {long oldsize,n; char*op; void*New;
if(!Old) return malloc(N); op=(char*)Old-OW; if(op[0]!=-17) return 0;
oldsize=8<<op[1]; if(N+OW<=oldsize) if(N+OW>oldsize/2) return Old;
free(Old); if(!(New=malloc(N))) return 0; /* keep old block if same size */
n=N<oldsize-OW?N:oldsize-OW; if(Old!=New) memcpy(New,Old,n); return New;}
/*-----*/

- Raw text -


  webmaster     delorie software   privacy  
  Copyright © 2019   by DJ Delorie     Updated Jul 2019