From: Manfred Spraul <manfred@colorfullife.com>

The slab allocator keeps track of the free objects in a slab with a linked
list of integers (typedef'ed to kmem_bufctl_t).  Right now unsigned int is
used for kmem_bufctl_t, i.e.  4 bytes per-object overhead.

The attached patch allows an arch override for this type: Theoretically,
unsigned short is sufficient for kmem_bufctl_t and this would reduce the
per-object overhead to 2 bytes.  But some archs cannot operate on 16-bit
values efficiently, thus it's not possible to switch everyone to ushort.

The patch switches i386, the port maintainers should switch their arch if
there are no problems with 16-bit quantities.  All accesses to kmem_bufctl_t
are under a per-cache spinlock and not in the hottest path.


---

 25-akpm/include/asm-i386/types.h |    3 +++
 25-akpm/include/linux/types.h    |    3 +++
 25-akpm/mm/slab.c                |    7 +++----
 3 files changed, 9 insertions(+), 4 deletions(-)

diff -puN include/asm-i386/types.h~allow-arch-override-for-kmem_bufctl_t include/asm-i386/types.h
--- 25/include/asm-i386/types.h~allow-arch-override-for-kmem_bufctl_t	2004-05-15 23:44:33.190700672 -0700
+++ 25-akpm/include/asm-i386/types.h	2004-05-15 23:44:33.208697936 -0700
@@ -63,6 +63,9 @@ typedef u64 sector_t;
 #define HAVE_SECTOR_T
 #endif
 
+#define HAVE_KMEM_BUFCTL_T 1
+typedef unsigned short kmem_bufctl_t;
+
 #endif /* __ASSEMBLY__ */
 
 #endif /* __KERNEL__ */
diff -puN include/linux/types.h~allow-arch-override-for-kmem_bufctl_t include/linux/types.h
--- 25/include/linux/types.h~allow-arch-override-for-kmem_bufctl_t	2004-05-15 23:44:33.192700368 -0700
+++ 25-akpm/include/linux/types.h	2004-05-15 23:44:33.207698088 -0700
@@ -140,6 +140,9 @@ typedef unsigned long sector_t;
 #define pgoff_t unsigned long
 #endif
 
+#ifndef HAVE_KMEM_BUFCTL_T
+typedef unsigned int kmem_bufctl_t;
+#endif
 #endif /* __KERNEL_STRICT_NAMES */
 
 /*
diff -puN mm/slab.c~allow-arch-override-for-kmem_bufctl_t mm/slab.c
--- 25/mm/slab.c~allow-arch-override-for-kmem_bufctl_t	2004-05-15 23:44:33.193700216 -0700
+++ 25-akpm/mm/slab.c	2004-05-15 23:44:33.207698088 -0700
@@ -161,10 +161,9 @@
  * is less than 512 (PAGE_SIZE<<3), but greater than 256.
  */
 
-#define BUFCTL_END	0xffffFFFF
-#define BUFCTL_FREE	0xffffFFFE
-#define	SLAB_LIMIT	0xffffFFFD
-typedef unsigned int kmem_bufctl_t;
+#define BUFCTL_END	(((kmem_bufctl_t)(~0U))-0)
+#define BUFCTL_FREE	(((kmem_bufctl_t)(~0U))-1)
+#define	SLAB_LIMIT	(((kmem_bufctl_t)(~0U))-2)
 
 /* Max number of objs-per-slab for caches which use off-slab slabs.
  * Needed to avoid a possible looping condition in cache_grow().

_