malloc()函数是否有最大返回值?

5

malloc()返回的虚拟内存指针的size_t值是否有上限?

我想知道是否可以安全地将64位指针的最高有效位设置为1,以指示这不是指针而是一个字面整数。


int64_tuint64_t有什么问题吗? - pmg
这取决于操作系统的内存映射策略,由于该策略是实现细节,因此它可能会在下一个版本的操作系统中发生变化而没有任何警告。我不会依赖这样的技巧。 - axiac
你的问题中有一些不太清楚(至少对我来说)。假设你调用了 malloc 并且它返回了一个新分配的内存块的地址。如何通过更改该值的最高有效位使其 “指示字面字符串”?我想你的意思是 - “是否有任何值从未被 malloc 返回,我可以安全地使用以将它们与 malloc 返回的值区分开来?” 话虽如此,如果您提供相关的代码片段(即返回指针的函数),这里的某个人可能会建议一种干净安全的方法来实现您的目标。 - barak manos
你可以安全地这样做,但不要在C语言中实现:你需要完全忘记C语言的抽象语义,并了解指针规则适用于你的硬件平台(如果你愿意,可以用C语言编写代码,但这只是一个细节)。可以在x64上完成 - Alex Celeste
3个回答

8
malloc返回的是一个void指针而不是整数。将指针强制转换为整数并不能给你(虚拟内存)地址,而是一些必须遵守C语言标准语义的值(空指针为0,加减与指针算术相关),但仅限于此。你对指针转换为整数的值不能做任何假设。事实上,C实现完全有权在上位比特中标记非空指针转换为整数的某些内部信息。

4
正如@datenwolf的答案所述,你不能假设malloc会提供给你内存地址的方式。最高位可能包含重要的位,如果你试图将它们用于存储元数据,则可能覆盖它们。我曾在一个32位系统上工作过,返回的地址具有设置在地址MSB中的位(不是来自malloc,而是其他特定于系统的内存分配函数)。
然而,malloc保证返回适合您系统对齐的地址。例如,在32位系统上,您将获得4字节对其的指针,在64位系统上,您将获得8字节对其的指针。这意味着您保证较低的2或3个位将为零。您可以通过使用memalign来增加保证位数。这基本上与在最高有效位中存储元数据具有相同的效果。要获取/设置文字,只需将其向上/向下移位到其余位即可。
然而,我不建议使用任一种方法。为自己省些烦恼,分配更多的内存以存储标志。除非你有数十亿个,否则真的不值得。

不错,那会起作用。事实上,我有数十亿个并且已经解决了问题,但我很好奇想更多地了解malloc() - ezorita

0
关于 size_t,它可以保存由 limits.h 定义的值。
#ifndef SIZE_MAX
#ifdef _WIN64 
#define SIZE_MAX _UI64_MAX
#else
#define SIZE_MAX UINT_MAX

_UI64_MAX和UINT_MAX的定义如下。

#define UINT_MAX      0xffffffff    /* maximum unsigned int value */
#define _UI64_MAX     0xffffffffffffffffui64 

至于malloc(),在32位Windows上,它可以返回0到2GB用户模式地址空间内的任何(地址)值,在64位Windows上,它可以返回0到8TB用户模式地址空间内的任何(地址)值。

同样,在32位系统上,从WinNT 4开始,引入了一个启动选项/3G。使用此选项,malloc()可以返回0到3GB用户模式地址空间内的任何(地址)值。

有关更多详细信息,请参阅Mark Russinovich的文章here


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接