I'm doing some research about the userland memory allocations.
#include <stdio.h>
#include <stdlib.h>
int main(int argc, char *argv[]) {
void *a = malloc(1);
return 0;
}
With the above demo code, I debug the memory allocation and layout with gdb
.
The following result shows that the heap
section goes from 0x555555559000
to 0x55555557a000
.
But the only memory allocated in the program is starting from 0x5555555592a0
. And we can see there is one allocated chunk of size 0x291
starting from the beginning of heap section.
My confusion is what it is? All it contains are 0:
Note: I know what is the top
chunk and other allocation behavior of malloc
in glibc.
I just stumbled upon this post and although a little late I thought it might help others if I still answer the question.
Most likely that initial heap chunk of size 0x290 is the tcache_perthread_struct
of the main thread of the program you're analyzing.
// source: https://elixir.bootlin.com/glibc/glibc-2.31/source/malloc/malloc.c#L2906
typedef struct tcache_perthread_struct
{
uint16_t counts[TCACHE_MAX_BINS];
tcache_entry *entries[TCACHE_MAX_BINS];
} tcache_perthread_struct;
with TCACHE_MAX_BINS=64
.
On x86_64 this results in a struct of size 64*2 + 64*8 = 640 = 0x280
. Together with the chunk header (size 0x10
on x86_64) this equals the 0x290
bytes for the first chunk.
In your screenshot it looks like the chunk has a size of 0x291
bytes but this is not correct (at least not in the likely case that you're using glibc which uses ptmalloc
). Because chunks on the heap are aligned to MALLOC_ALIGNMENT
bytes the last bits of the size
header are never actually needed and have been repurposed as A
, M
and P
flags.
You can find the details about the malloc_chunk
struct here (The A
, M
, P
flags are described in the comment after the struct definition).