Fix a bug in krealloc(). Note that krealloc() is very rarely used.
authorMatthew Dillon <dillon@apollo.backplane.com>
Wed, 22 Apr 2009 20:04:23 +0000 (13:04 -0700)
committerMatthew Dillon <dillon@apollo.backplane.com>
Wed, 22 Apr 2009 20:04:23 +0000 (13:04 -0700)
krealloc() was improperly calling zoneindex() when transitioning from
zone-controlled memory to non-zone-controlled (big) memory.

sys/kern/kern_slaballoc.c

index 0e607a7..0374f8e 100644 (file)
@@ -781,15 +781,22 @@ krealloc(void *ptr, unsigned long size, struct malloc_type *type, int flags)
     z = (SLZone *)((uintptr_t)ptr & ~(uintptr_t)ZoneMask);
     KKASSERT(z->z_Magic == ZALLOC_SLAB_MAGIC);
 
-    zoneindex(&size);
-    if (z->z_ChunkSize == size)
-       return(ptr);
-
     /*
      * Allocate memory for the new request size.  Note that zoneindex has
      * already adjusted the request size to the appropriate chunk size, which
      * should optimize our bcopy().  Then copy and return the new pointer.
+     *
+     * Resizing a non-power-of-2 allocation to a power-of-2 size does not
+     * necessary align the result.
+     *
+     * We can only zoneindex (to align size to the chunk size) if the new
+     * size is not too large.
      */
+    if (size < ZoneLimit) {
+       zoneindex(&size);
+       if (z->z_ChunkSize == size)
+           return(ptr);
+    }
     if ((nptr = kmalloc(size, type, flags)) == NULL)
        return(NULL);
     bcopy(ptr, nptr, min(size, z->z_ChunkSize));