[BACK]Return to subr_vmem.c CVS log [TXT][DIR] Up to [cvs.NetBSD.org] / src / sys / kern

Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.

Diff for /src/sys/kern/subr_vmem.c between version 1.42 and 1.42.10.1

version 1.42, 2008/03/17 08:27:50 version 1.42.10.1, 2008/12/13 01:15:08
Line 40 
Line 40 
 #include <sys/cdefs.h>  #include <sys/cdefs.h>
 __KERNEL_RCSID(0, "$NetBSD$");  __KERNEL_RCSID(0, "$NetBSD$");
   
 #define VMEM_DEBUG  
 #if defined(_KERNEL)  #if defined(_KERNEL)
 #include "opt_ddb.h"  #include "opt_ddb.h"
 #define QCACHE  #define QCACHE
Line 575  vmem_add1(vmem_t *vm, vmem_addr_t addr, 
Line 574  vmem_add1(vmem_t *vm, vmem_addr_t addr, 
   
         KASSERT((flags & (VM_SLEEP|VM_NOSLEEP)) != 0);          KASSERT((flags & (VM_SLEEP|VM_NOSLEEP)) != 0);
         KASSERT((~flags & (VM_SLEEP|VM_NOSLEEP)) != 0);          KASSERT((~flags & (VM_SLEEP|VM_NOSLEEP)) != 0);
           KASSERT(spanbttype == BT_TYPE_SPAN || spanbttype == BT_TYPE_SPAN_STATIC);
   
         btspan = bt_alloc(vm, flags);          btspan = bt_alloc(vm, flags);
         if (btspan == NULL) {          if (btspan == NULL) {
Line 744  vmem_fit(const bt_t *bt, vmem_size_t siz
Line 744  vmem_fit(const bt_t *bt, vmem_size_t siz
         return VMEM_ADDR_NULL;          return VMEM_ADDR_NULL;
 }  }
   
   #if !defined(VMEM_DEBUG)
   #define vmem_check_sanity(vm)   true
   #else
   
   static bool
   vmem_check_spanoverlap(const char *func, const vmem_t *vm,
                           const bt_t *bt, const bt_t *bt2)
   {
           switch (bt->bt_type) {
           case BT_TYPE_BUSY:
           case BT_TYPE_FREE:
                   if (BT_ISSPAN_P(bt2))
                           return true;
                   break;
           case BT_TYPE_SPAN:
           case BT_TYPE_SPAN_STATIC:
                   if (bt2->bt_type == BT_TYPE_BUSY
                      || bt2->bt_type == BT_TYPE_FREE)
                           return true;
                   break;
           }
   
           if (bt->bt_start > bt2->bt_start) {
                   if (bt->bt_start >= BT_END(bt2))
                           return true;
   
                   printf("%s: overlapping VMEM '%s' span 0x%"
                           PRIx64" - 0x%"PRIx64" %s\n",
                           func, vm->vm_name,
                           (uint64_t)bt->bt_start,
                           (uint64_t)BT_END(bt),
                           (bt->bt_type == BT_TYPE_BUSY) ?
                           "allocated" :
                           (bt->bt_type == BT_TYPE_FREE) ?
                           "free" :
                           (bt->bt_type == BT_TYPE_SPAN) ?
                           "span" : "static span");
                   printf("%s: overlapping VMEM '%s' span 0x%"
                           PRIx64" - 0x%"PRIx64" %s\n",
                           func, vm->vm_name,
                           (uint64_t)bt2->bt_start,
                           (uint64_t)BT_END(bt2),
                           (bt2->bt_type == BT_TYPE_BUSY) ?
                           "allocated" :
                           (bt2->bt_type == BT_TYPE_FREE) ?
                           "free" :
                           (bt2->bt_type == BT_TYPE_SPAN) ?
                           "span" : "static span");
                   return false;
           }
           if (BT_END(bt) > bt2->bt_start) {
                   printf("%s: overlapping VMEM '%s' span 0x%"
                           PRIx64" - 0x%"PRIx64" %s\n",
                           func, vm->vm_name,
                           (uint64_t)bt->bt_start,
                           (uint64_t)BT_END(bt),
                           (bt->bt_type == BT_TYPE_BUSY) ?
                           "allocated" :
                           (bt->bt_type == BT_TYPE_FREE) ?
                           "free" :
                           (bt->bt_type == BT_TYPE_SPAN) ?
                           "span" : "static span");
                   printf("%s: overlapping VMEM '%s' span 0x%"
                           PRIx64" - 0x%"PRIx64" %s\n",
                           func, vm->vm_name,
                           (uint64_t)bt2->bt_start,
                           (uint64_t)BT_END(bt2),
                           (bt2->bt_type == BT_TYPE_BUSY) ?
                           "allocated" :
                           (bt2->bt_type == BT_TYPE_FREE) ?
                           "free" :
                           (bt2->bt_type == BT_TYPE_SPAN) ?
                           "span" : "static span");
                   return false;
           }
   
           return true;
   }
   
   static bool
   vmem_check_sanity(vmem_t *vm)
   {
           const bt_t *bt, *bt2;
   
           KASSERT(vm != NULL);
   
           CIRCLEQ_FOREACH(bt, &vm->vm_seglist, bt_seglist) {
                   if (bt->bt_start >= BT_END(bt)) {
                           printf("%s: bogus VMEM '%s' span 0x%"PRIx64
                                   " - 0x%"PRIx64" %s\n",
                                   __func__, vm->vm_name,
                                   (uint64_t)bt->bt_start, (uint64_t)BT_END(bt),
                                   (bt->bt_type == BT_TYPE_BUSY) ?
                                   "allocated" :
                                   (bt->bt_type == BT_TYPE_FREE) ?
                                   "free" :
                                   (bt->bt_type == BT_TYPE_SPAN) ?
                                   "span" : "static span");
                           return false;
                   }
   
                   CIRCLEQ_FOREACH(bt2, &vm->vm_seglist, bt_seglist) {
                           if (bt2->bt_start >= BT_END(bt2)) {
                                   printf("%s: bogus VMEM '%s' span 0x%"PRIx64
                                           " - 0x%"PRIx64" %s\n",
                                           __func__, vm->vm_name,
                                           (uint64_t)bt2->bt_start,
                                           (uint64_t)BT_END(bt2),
                                           (bt2->bt_type == BT_TYPE_BUSY) ?
                                           "allocated" :
                                           (bt2->bt_type == BT_TYPE_FREE) ?
                                           "free" :
                                           (bt2->bt_type == BT_TYPE_SPAN) ?
                                           "span" : "static span");
                                   return false;
                           }
                           if (bt == bt2)
                                   continue;
   
                           if (vmem_check_spanoverlap(__func__, vm, bt, bt2)
                                   == false)
                                   return false;
                   }
           }
   
           return true;
   }
   #endif  /* VMEM_DEBUG */
   
 /* ---- vmem API */  /* ---- vmem API */
   
 /*  /*
Line 922  retry_strat:
Line 1051  retry_strat:
 retry:  retry:
         bt = NULL;          bt = NULL;
         VMEM_LOCK(vm);          VMEM_LOCK(vm);
           KASSERT(vmem_check_sanity(vm));
         if (strat == VM_INSTANTFIT) {          if (strat == VM_INSTANTFIT) {
                 for (list = first; list < end; list++) {                  for (list = first; list < end; list++) {
                         bt = LIST_FIRST(list);                          bt = LIST_FIRST(list);
Line 976  gotit:
Line 1106  gotit:
         KASSERT(bt->bt_type == BT_TYPE_FREE);          KASSERT(bt->bt_type == BT_TYPE_FREE);
         KASSERT(bt->bt_size >= size);          KASSERT(bt->bt_size >= size);
         bt_remfree(vm, bt);          bt_remfree(vm, bt);
           KASSERT(vmem_check_sanity(vm));
         if (bt->bt_start != start) {          if (bt->bt_start != start) {
                 btnew2->bt_type = BT_TYPE_FREE;                  btnew2->bt_type = BT_TYPE_FREE;
                 btnew2->bt_start = bt->bt_start;                  btnew2->bt_start = bt->bt_start;
Line 985  gotit:
Line 1116  gotit:
                 bt_insfree(vm, btnew2);                  bt_insfree(vm, btnew2);
                 bt_insseg(vm, btnew2, CIRCLEQ_PREV(bt, bt_seglist));                  bt_insseg(vm, btnew2, CIRCLEQ_PREV(bt, bt_seglist));
                 btnew2 = NULL;                  btnew2 = NULL;
                   KASSERT(vmem_check_sanity(vm));
         }          }
         KASSERT(bt->bt_start == start);          KASSERT(bt->bt_start == start);
         if (bt->bt_size != size && bt->bt_size - size > vm->vm_quantum_mask) {          if (bt->bt_size != size && bt->bt_size - size > vm->vm_quantum_mask) {
Line 997  gotit:
Line 1129  gotit:
                 bt_insfree(vm, bt);                  bt_insfree(vm, bt);
                 bt_insseg(vm, btnew, CIRCLEQ_PREV(bt, bt_seglist));                  bt_insseg(vm, btnew, CIRCLEQ_PREV(bt, bt_seglist));
                 bt_insbusy(vm, btnew);                  bt_insbusy(vm, btnew);
                   KASSERT(vmem_check_sanity(vm));
                 VMEM_UNLOCK(vm);                  VMEM_UNLOCK(vm);
         } else {          } else {
                 bt->bt_type = BT_TYPE_BUSY;                  bt->bt_type = BT_TYPE_BUSY;
                 bt_insbusy(vm, bt);                  bt_insbusy(vm, bt);
                   KASSERT(vmem_check_sanity(vm));
                 VMEM_UNLOCK(vm);                  VMEM_UNLOCK(vm);
                 bt_free(vm, btnew);                  bt_free(vm, btnew);
                 btnew = bt;                  btnew = bt;
Line 1011  gotit:
Line 1145  gotit:
         KASSERT(btnew->bt_size >= size);          KASSERT(btnew->bt_size >= size);
         btnew->bt_type = BT_TYPE_BUSY;          btnew->bt_type = BT_TYPE_BUSY;
   
           KASSERT(vmem_check_sanity(vm));
         return btnew->bt_start;          return btnew->bt_start;
 }  }
   
Line 1236  vmem_whatis(uintptr_t addr, void (*pr)(c
Line 1371  vmem_whatis(uintptr_t addr, void (*pr)(c
                     (bt->bt_type == BT_TYPE_BUSY) ? "allocated" : "free");                      (bt->bt_type == BT_TYPE_BUSY) ? "allocated" : "free");
         }          }
 }  }
   
   static void
   vmem_showall(void (*pr)(const char *, ...))
   {
           vmem_t *vm;
   
           LIST_FOREACH(vm, &vmem_list, vm_alllist) {
                   (*pr)("VMEM '%s' at %p\n", vm->vm_name, vm);
                   if (vm->vm_source)
                           (*pr)("  VMEM backend '%s' at %p\n",
                                   vm->vm_source->vm_name, vm->vm_source);
           }
   }
   
   static void
   vmem_show(uintptr_t addr, void (*pr)(const char *, ...))
   {
           vmem_t *vm;
           bt_t *bt = NULL;
   
           LIST_FOREACH(vm, &vmem_list, vm_alllist) {
                   if ((uintptr_t)vm == addr)
                           goto found;
           }
   
           LIST_FOREACH(vm, &vmem_list, vm_alllist) {
                   bt = vmem_whatis_lookup(vm, addr);
                   if (bt != NULL)
                           goto found;
           }
   
           return;
   found:
   
           (*pr)("VMEM '%s' spans\n", vm->vm_name);
           CIRCLEQ_FOREACH(bt, &vm->vm_seglist, bt_seglist) {
                   (*pr)(" 0x%"PRIx64" - 0x%"PRIx64" %s\n",
                           bt->bt_start, BT_END(bt),
                           (bt->bt_type == BT_TYPE_BUSY) ?
                           "allocated" :
                           (bt->bt_type == BT_TYPE_FREE) ?
                           "free" :
                           (bt->bt_type == BT_TYPE_SPAN) ?
                           "span" : "static span");
           }
   }
   
   void
   vmem_print(uintptr_t addr, const char *modif, void (*pr)(const char *, ...))
   {
           if (modif[0] == 'a') {
                   vmem_showall(pr);
                   return;
           }
   
           vmem_show(addr, pr);
   }
 #endif /* defined(DDB) */  #endif /* defined(DDB) */
   
 #if defined(VMEM_DEBUG)  #if defined(VMEM_DEBUG)

Legend:
Removed from v.1.42  
changed lines
  Added in v.1.42.10.1

CVSweb <webmaster@jp.NetBSD.org>