美文网首页
glibc内存分配函数malloc的内存

glibc内存分配函数malloc的内存

作者: CodingCode | 来源:发表于2023-10-26 05:08 被阅读0次

原型:
void * malloc(size_t size)

返回地址的前面size_t空间存储的是此次分配内存的chunk大小。

chunk大小的规则是:
align(size + sizeof(size_t), 2 * sizeof(size_t))
就是待分配用户空间大小+一个metadata的头大小,然后按照两倍size_t对齐分配。所以:

  1. 对于32bit系统, sizeof(size_t) == 4,所以两倍地址是8字节对齐。
  2. 对应64bit系统,sizeof(size_t) == 8,所以两倍地址是16字节对齐。

然后chunk大小的后3bit是标志位,既然chunk大小是固定的必须满足对齐格式,所以这末几位也没有用处才,正好用在其他标记位:

(...size...|A|M|P)

  • P: PREV_INUSE : 0x1
  • M: IS_MMAPPED: 0x2
  • A: NON_MAIN_ARENA: 0x4

用代码测试一下:

void * mymalloc(size_t sz) {
    size_t cksz = 0;
    void * p= malloc(sz);

    //struct malloc_chunk * mc= ((struct malloc_chunk *)((char*)(p) - 2 * sizeof(size_t)));
    //cksz = (mc)->size;

    cksz = *(size_t *)((unsigned char *)p - sizeof(size_t));

    cksz = cksz & ~0x7; // the size's last 3bits are PREV_INUSE|IS_MMAPPED|NON_MAIN_ARENA flag
    printf("p=%p, mallocsz=%04d, chunksz=%04d(%02d)\n", p, sz, cksz, cksz-sz);

    return p;
}

运行几个例子:

p=0x1881010, mallocsz=0071, chunksz=0080(09)
p=0x1881060, mallocsz=0072, chunksz=0080(08)
p=0x18810b0, mallocsz=0073, chunksz=0096(23)
p=0x1881110, mallocsz=0074, chunksz=0096(22)
p=0x1881170, mallocsz=0075, chunksz=0096(21)
p=0x18811d0, mallocsz=0076, chunksz=0096(20)
p=0x1881230, mallocsz=0077, chunksz=0096(19)
p=0x1881290, mallocsz=0078, chunksz=0096(18)
p=0x18812f0, mallocsz=0079, chunksz=0096(17)
p=0x1881350, mallocsz=0080, chunksz=0096(16)
p=0x18813b0, mallocsz=0081, chunksz=0096(15)
p=0x1881410, mallocsz=0082, chunksz=0096(14)
p=0x1881470, mallocsz=0083, chunksz=0096(13)
p=0x18814d0, mallocsz=0084, chunksz=0096(12)
p=0x1881530, mallocsz=0085, chunksz=0096(11)
  1. 分配71字节,加上头8字迹,然后align(79, 16)=80
  2. 分配72字节,加上头8字迹,然后align(80, 16)=80
  3. 分配73字节,加上头8字迹,然后align(81, 16)=96
    ...

前面是64bit系统的,chunksz按照对齐是16字节对齐的,而对于32bit系统而言:gcc -m32 ...,运行结果是:

p=0x9f20008, mallocsz=0071, chunksz=0080(09)
p=0x9f20058, mallocsz=0072, chunksz=0080(08)
p=0x9f200a8, mallocsz=0073, chunksz=0080(07)
p=0x9f200f8, mallocsz=0074, chunksz=0080(06)
p=0x9f20148, mallocsz=0075, chunksz=0080(05)
p=0x9f20198, mallocsz=0076, chunksz=0080(04)
p=0x9f201e8, mallocsz=0077, chunksz=0088(11)
p=0x9f20240, mallocsz=0078, chunksz=0088(10)
p=0x9f20298, mallocsz=0079, chunksz=0088(09)
p=0x9f202f0, mallocsz=0080, chunksz=0088(08)
p=0x9f20348, mallocsz=0081, chunksz=0088(07)
p=0x9f203a0, mallocsz=0082, chunksz=0088(06)
p=0x9f203f8, mallocsz=0083, chunksz=0088(05)
p=0x9f20450, mallocsz=0084, chunksz=0088(04)
p=0x9f204a8, mallocsz=0085, chunksz=0096(11)
  1. 分配71字节,加上头4字迹,然后align(75, 8)=80
  2. 分配72字节,加上头4字迹,然后align(76, 8)=80
  3. 分配73字节,加上头4字迹,然后align(77, 8)=80
    ...

相关文章

  • Linux 内存布局

    关于内存分配,一般的 C 语言开发者使用的更多的是 glibc 库提供的 malloc 和 calloc 等函数,...

  • 08/09

    总结 动态存储分配 1、用到的函数: a、malloc 函数 : 1 分配内存快,内存快不初始化 2 函数...

  • 2018-05-13 (旧文整理) 内存碎片综述

    2016/01/25 内存分配的过程 用户态的程序调用 malloc 函数申请内存. malloc 是一个库函数...

  • 内存分配函数

    malloc函数---分配内存块,但是不对内存块进行初始化。(memory allocation)calloc函数...

  • C语言-用指针实现内存动态分配

    动态存储分配函数 在C语言中,动态分配内存是通过动态存储分配函数 malloc() 来实现的,其功能是: 在内存的...

  • (十一)golang 内存分析

    前言 编写过C语言程序的肯定知道通过malloc()方法动态申请内存,其中内存分配器使用的是glibc提供的ptm...

  • golang 内存分配原理

    1. 前言 编写过C语言程序的肯定知道通过malloc()方法动态申请内存,其中内存分配器使用的是glibc提供的...

  • 一些tips分享

    1.动态分配内存地址malloc函数 该函数分配了NumBytes个字节,并返回了指向这块内存的指针。如果分配失...

  • C/C++动态内存分配与释放

    1. malloc()函数 1.1 malloc的全称是memory allocation,中文叫动态内存分配。 ...

  • C++ new 和 delete 运算符

    在 C 语言中,动态分配内存用 malloc () 函数,释放内存用 free () 函数。如下所示: 在 C++...

网友评论

      本文标题:glibc内存分配函数malloc的内存

      本文链接:https://www.haomeiwen.com/subject/rejyidtx.html