内存分配
void *malloc(unsigned int len) { struct _bucket_dir *bdir; struct bucket_desc *bdesc; void *retval; /* * First we search the bucket_dir to find the right bucket change * for this request. */ for (bdir = bucket_dir; bdir->size; bdir++) if (bdir->size >= len) break; if (!bdir->size) { printk("malloc called with impossibly large argument (%d)\n", len); panic("malloc: bad arg"); } /* * Now we search for a bucket descriptor which has free space */ cli(); /* Avoid race conditions */ for (bdesc = bdir->chain; bdesc; bdesc = bdesc->next) if (bdesc->freeptr) break; /* * If we didn't find a bucket with free space, then we'll * allocate a new one. */ if (!bdesc) { char *cp; int i; if (!free_bucket_desc) init_bucket_desc(); bdesc = free_bucket_desc; free_bucket_desc = bdesc->next; bdesc->refcnt = 0; bdesc->bucket_size = bdir->size; bdesc->page = bdesc->freeptr = (void *) cp = get_free_page(); if (!cp) panic("Out of memory in kernel malloc()"); /* Set up the chain of free objects */ for (i=PAGE_SIZE/bdir->size; i > 1; i--) { *((char **) cp) = cp + bdir->size; cp += bdir->size; } *((char **) cp) = 0; bdesc->next = bdir->chain; /* OK, link it in! */ bdir->chain = bdesc; } retval = (void *) bdesc->freeptr; bdesc->freeptr = *((void **) retval); bdesc->refcnt++; sti(); /* OK, we're safe again */ return(retval); }
/* these are not to be changed without changing head.s etc */ #define LOW_MEM 0x100000 #define PAGING_MEMORY (15*1024*1024) #define PAGING_PAGES (PAGING_MEMORY>>12) #define MAP_NR(addr) (((addr)-LOW_MEM)>>12) #define USED 100 static unsigned char mem_map [ PAGING_PAGES ] = {0,}; unsigned long get_free_page(void) { register unsigned long __res asm("ax"); __asm__("std ; repne ; scasb\n\t" "jne 1f\n\t" "movb $1,1(%%edi)\n\t" "sall $12,%%ecx\n\t" "addl %2,%%ecx\n\t" "movl %%ecx,%%edx\n\t" "movl $1024,%%ecx\n\t" "leal 4092(%%edx),%%edi\n\t" "rep ; stosl\n\t" "movl %%edx,%%eax\n" "1:" :"=a" (__res) :"0" (0),"i" (LOW_MEM),"c" (PAGING_PAGES), "D" (mem_map+PAGING_PAGES-1) :"di","cx","dx"); return __res; }
#define copy_page(from,to) \ __asm__("cld ; rep ; movsl"::"S" (from),"D" (to),"c" (1024):"cx","di","si")