缓冲区memcpy and other functions可以处理的最大大小是多少?这个实现依赖吗?这是否受到作为参数传入的大小(size_t)的限制?
答案 0 :(得分:11)
这完全取决于实现。
这取决于硬件和任何东西,但也取决于编译器的时代。对于拥有相当现代编译器的任何人(意味着任何基于90年代或更晚的标准的东西),size参数是size_t
。这可以合理地是最大的16位无符号,最大的32位无符号或最大的64位无符号,具体取决于编译器编译的内存模型。在这种情况下,您只需要找出实施中size_t
的大小。但是,对于非常旧编译器(即在ANSI-C和perhaps for some early versions of ANSI C之前),所有投注均已关闭。
在标准方面,例如,查看cygwin和Solaris 7,size参数是size_t
。查看我可用的嵌入式系统,size参数为unsigned
(表示16位无符号)。 (这个嵌入式系统的编译器是用80年代编写的。)我找到了一些ANSI C where the size parameter is an int
的Web引用。
您可能希望在size_t
以及this article上看到size_t
错误签名的某些早期GCC版本的错误功能。
总之,对于几乎所有人,size_t
将是正确的使用参考。但是,对于那些使用嵌入式系统或具有非常旧的编译器的遗留系统的少数人,您需要检查您的手册页。
答案 1 :(得分:1)
函数通常使用size_t
来传递大小作为参数。我说通常是因为fgets()
使用int
参数,我认为这是C标准中的一个缺陷。
size_t
被定义为一种类型,它可以包含您可以访问的任何对象的大小(以字节为单位)。通常它是unsigned int
或unsigned long
的typedef
这就是sizeof
运算符返回的值为size_t
类型的原因。
所以2 **(sizeof(size_t)
* CHAR_BIT
)为您提供程序可以处理的最大内存量,但它肯定不是最精确的内存。
(CHAR_BIT
在limits.h
中定义,并生成char
中包含的位数。
答案 2 :(得分:0)
他们采用size_t参数;所以它依赖于平台。
答案 3 :(得分:0)
依赖于实现,但您可以查看需要包含的标题(.h)文件,然后才能使用memcpy。声明会告诉你(寻找size_t或其他)。
然后你问大小是什么,嗯,这是依赖于实现的部分。
答案 4 :(得分:0)
是的,你不能复制大于2 ^(sizeof(size_t)* 8)字节的区域。但这没什么可担心的,因为你也无法分配更多空间,因为malloc
也将大小作为size_t参数。
答案 5 :(得分:0)
还有一个问题与size_t
可以代表您的平台允许进程实际解决的内容有关。
即使在64位平台上使用虚拟内存,本周也不太可能调用大小超过几TB的memcpy()
,即便如此,这也是一台非常热门的机器。 ...很难想象在哪个机器上安装一个完全覆盖的64位地址空间是可能的。
不要介意只有几KB总可写内存的嵌入式系统,无论memcpy()
的定义如何,尝试size_t
比RAM更多的信息是没有意义的。如果你这样做的话,请考虑刚从该调用中获取返回地址的堆栈发生了什么?
或者进程看到的虚拟地址空间小于安装的物理内存的系统。例如,在Win64平台上运行Win32进程就是这种情况。 (我第一次遇到这个问题是在PDP-11上运行的OS TSX-11,物理内存为4MB,每个进程都有64KB的虚拟地址。然后4MB的内存占用了很多内存,IBM PC没有还存在。)