Muy a menudo, malloc
y free
están utilizando servicios de asignación de memoria virtual de nivel inferior y asignando varias páginas (o incluso megabytes) a la vez, utilizando llamadas al sistema como mmap y munmap (y quizás sbrk). A menudo malloc
prefiere reutilizar anteriormente free
espacio de memoria d cuando sea pertinente. La mayoría malloc
Las implementaciones usan varias y diferentes estrategias para asignaciones "grandes" y "pequeñas", etc...
Tenga en cuenta que el espacio de direcciones virtuales se puede limitar, p. con setrlimit(2). Use en Linux pmap(1) y proc(5) para obtener más información sobre el espacio de direcciones virtuales de algún proceso (por ejemplo, /proc/self/maps
para el tuyo propio o /proc/1234/maps
- también el pmap 1234
comando - para el proceso de pid 1234).
Puede mirar el código fuente de su GNU libc, mirar el código fuente de otras bibliotecas estándar C (como musl-libc), leer sobre malloc
implementaciones, elija otras o implemente las suyas propias, o use strace para averiguarlo experimentalmente.
Lea la página de manual de syscalls (es decir, syscalls(2)) y el archivo <asm/unistd.h>
para obtener una lista de llamadas al sistema.
un malloc
muy rápido
Creo firmemente que el estándar C es muy vago sobre malloc
y free
. Estoy bastante seguro de que las siguientes funciones respetan la letra (pero no el espíritu) del estándar:
/* politically incorrect, but very probably standard conforming */
void *malloc (size_t sz) { if (sz>0) errno = ENOMEM; return NULL; }
void free(void*ptr) { }
Por supuesto, codificarás calloc
y realloc
en consecuencia.
La libc de GNU te da ganchos para tu propio malloc
funciones (e incluso probablemente podría usar el Recolector de basura de Boehm de forma transparente a través de ellas). Estos ganchos podrían quedar obsoletos y no son estándar.
Si usa GNU libc, consulte también mallinfo(3) y malloc_stat(3) y funciones relacionadas.
malloc
y free
son funciones de biblioteca estándar de C que deben implementarse en cada implementación de C.
El estándar C solo define la forma en que se comportan estas funciones y el comportamiento que se espera de ellas. Cómo se van a implementar a la izquierda de cada implementación.
En resumen, son detalles de implementación de la implementación que utiliza.
(Una "implementación" consiste en el compilador, el enlazador, la biblioteca en tiempo de ejecución y probablemente algunas otras cosas).