realloc保持posix_memalign的内存alignment吗?

alignment的mallocposix_memalign ,没关系,但是alignment的realloc呢? realloc是否保留alignment或如何确保重新分配的内存具有相同的alignment方式? 假设Linux和x86_64。

不,从posix_memalign返回的内存的realloc不能保证被ISO或POSIX保持相同的对齐。 realloc 可以简单地扩展当前块在相同的地址,但它也可以移动到一个不同的地址,其对齐不像原来那么严格。

如果你想要相同的对齐,最好分配另一个块并复制数据。

不幸的是,Single UNIX Specification中也没有posix_memalign_realloc函数。

如果你不想经历每次复制数据的麻烦,你可以尝试realloc (a) ,如果这个对齐不符合预期, 那么只有调用posix_memalign才能得到正确的对齐地址,将数据复制到那里,完成后释放旧地址。

这可能会导致:

  • 零拷贝(如果当前块可以在原地扩展);
  • 一个副本(如果realloc副本,但恰好给你一个正确的对齐块); 要么
  • 两份(如果realloc副本,那么你也必须复制,由于错位)。

也可能会导致复制的数量少于根据底层内存管理实现的情况。 例如,“复制”可能只涉及重新映射内存块,而不是物理移动数据。

所以你可能想保留一些统计数据,看看这个方案是否值得。


(a)请记住,POSIX和Linux手册页都不能指定你是否可以传递这些指针来重新分配,只有你可以将它们传递给free

然而,根据目前的GNU libc源代码,它似乎工作,虽然这不能保证它将来继续工作:-)

我担心的是它会正常分配内存(标准对齐),并返回一个偏移地址(即不是分配的实际地址,而是超出该地址的N个字节),这些地址在编译之前足够​​智能,可以转回到实际地址魔法。

这样做的一种方法是在返回的地址之前立即存储实际的地址,尽管这当然会导致即使对于定期分配的浪费。

在这种情况下, free可能已经变得聪明(因为规范说它必须能够处理由posix_memalign完成的分配),但是realloc可能没有被赋予相同的智能(因为文档对此没有提及)。

然而,基于GNU glibc 2.14.1,它实际上分配了比需要更多的内存,然后摆脱了竞技场的空间,以释放前后空间,所以返回的地址是一个“真实”的地址,可用freerealloc

但是,正如所述,文件不能保证这一点。

realloc的行为与malloc相同,所以由realloc返回的内存与malloc的对齐约束相同。

如果您查看realloc的glibc源代码,则直接调用malloc。 所以内存和malloc一样。