2012-09-24 24 views
7

¿KMALLOC asigna solo memoria de tamaño de página o puede asignar menos? ¿Cuáles son los tamaños que puede asignar el kmalloc? ¿Dónde puedo encontrar una descripción del mismo, ya que en todas partes que miré realmente no dice cuánta memoria asigna? Lo que quiero saber es cuáles son los tamaños reales que asigna KMALLOC. ¿Se asigna un tamaño de potencia de 2? ¿Acaba de encontrar objetos gratuitos de la memoria caché que está listo?Asignación de tamaño de KMALLOC

+2

El código fuente de 'kmalloc()' puede darte toda esta información. En cuanto a la cantidad real de memoria asignada, consulte [ksize() función] (http://lxr.free-electrons.com/ident?i=ksize). A veces, 'kmalloc()' de hecho busca un objeto libre en un caché apropiado, a veces recurre a la asignación de páginas enteras. Sí, 'kmalloc' puede asignar bloques con el tamaño real de menos de una página. La implementación está cambiando con el tiempo, por lo que podría ser más útil analizar el código fuente de 'kmalloc()' que buscar cualquier otra documentación. – Eugene

Respuesta

10

Mi comprensión es la siguiente: el kernel se ocupa de la memoria física del sistema, que está disponible solo en trozos del tamaño de una página; por lo tanto, cuando llame al kmalloc(), obtendrá solo ciertas matrices predefinidas de bytes de tamaño fijo.

La memoria real que obtiene depende de la arquitectura del sistema, pero la asignación más pequeña que puede manejar kmalloc es de 32 o 64 bytes. Regresará de una llamada al kmalloc()al menos tanta memoria como usted solicitó (generalmente más). Normalmente, usted no recibirá más de 128 KB (de nuevo, dependiente de la arquitectura)

Para obtener el tamaño de página (en bytes) de su sistema, puede ejecutar el comando:

getconf PAGESIZE 

o

getconf PAGE_SIZE 

Esta información sobre el tamaño de página máximo está en /usr/src/linux/include/linux/slab.h

Y sí, los tamaños de página en general son potencias de 2, pero de nuevo, no se va a conseguir exactamente lo que pides, pero un poco más.

Puede utilizar un poco de código como este:

void * stuff; 
stuff = kmalloc(1,GFP_KERNEL); 
printk("I got: %zu bytes of memory\n", ksize(stuff)); 
kfree(stuff); 

Para mostrar la cantidad real de memoria asignada:

[90144.702588] I got: 32 bytes of memory 
2

Se puede ver algunos tamaños comunes utilizados por kmalloc() int su sistema con:

cat /proc/slabinfo | grep kmalloc 

Más importante que la consideración de si kmalloc puede asignar menos de una página es la cuestión de si puede asignar más de una página: si llama al kmalloc() en contexto atómico (con el indicador GFP_ATOMIC), no puede ni intentará encontrar páginas contiguas en la memoria , por lo tanto, si su memoria está muy fragmentada y el orden de su asignación es alto (allocation size → pagesize*2^(allocation order)), la asignación puede fallar. Entonces, en el contexto atómico, es probable que las grandes asignaciones fallen.

Hay un ejemplo de una asignación de pedido fallida 7 (512 Kb) en this other SO question about maximum AF_UNIX datagram size.

2

Todo depende del asignador utilizado en su kernel. Slab, Slub o Slob. Ver siguientes variables de configuración del kernel:

CONFIG_SLAB 
CONFIG_SLUB 
CONFIG_SLOB 

Todos los asignadores anteriores utilizan MAX_ORDER y PAGE_SHIFT para decidir el límite máximo de kmalloc()

El tamaño kmalloc más grande soportado por los asignadores de losa se 32 megabyte (2^25) o el orden de página máximo asignable si es inferior a 32 MB.

#define KMALLOC_SHIFT_HIGH  ((MAX_ORDER + PAGE_SHIFT - 1) <= 25 ? \         (MAX_ORDER + PAGE_SHIFT - 1) : 25) 
#define KMALLOC_SHIFT_MAX  KMALLOC_SHIFT_HIGH 

SLUB asigna directamente las solicitudes de ajuste en a una página de orden-1 (PAGE_SIZE * 2). Las solicitudes más grandes se pasan al asignador de páginas.

#define KMALLOC_SHIFT_HIGH  (PAGE_SHIFT + 1) 
#define KMALLOC_SHIFT_MAX  (MAX_ORDER + PAGE_SHIFT) 

SLOB pasa todas las solicitudes de más de una página al asignador de páginas. No es necesaria ninguna matriz kmalloc, ya que se pueden asignar objetos de diferentes tamaños desde la misma página.

#define KMALLOC_SHIFT_HIGH  PAGE_SHIFT 
#define KMALLOC_SHIFT_MAX  30 

Tamaño máximo asignable por kmalloc() es

#define KMALLOC_MAX_SIZE  (1UL << KMALLOC_SHIFT_MAX) 

tamaño allocatable mínimo de kmalloc() es

#define KMALLOC_MIN_SIZE (1 << KMALLOC_SHIFT_LOW) 

predeterminado KMALLOC_SHIFT_LOW para losa es 5, y por gata y Slob se es 3.

Cuestiones relacionadas