c - calloc(10,4) 和 calloc(1,40) 有什么区别?

标签 c calloc

<分区>

calloc(10,4) 和 calloc(1,40) 有什么区别?

我看到了这种行为:

Thing** things = (Thing**)calloc(1, 10 * sizeof(Thing*));
// things[0] != 0

Thing** things = (Thing**)calloc(10, sizeof(Thing*));
// things[0] == 0

我想知道为什么。编辑:失去理智的原因是,现在两者似乎都为零......为了至少让这个问题变得有趣,为什么 calloc 不像 malloc 那样只接受一个参数?

最佳答案

实际上是一样的。但是这为您提供了一项重要功能。

假设您正在从网络接收一些数据,并且协议(protocol)有一个字段指定一个数组将包含多少个元素,这些元素将被发送给您。你做这样的事情:

uint32_t n = read_number_of_array_elements_from_network(conn);
struct element *el = malloc(n * sizeof(*el));
if (el == NULL)
    return -1;
read_array_elements_from_network(conn, el, n);

这看起来无害,不是吗?好吧,没那么快。连接的另一端是邪恶的,实际上向您发送了一个非常大的数字作为元素的数量,以便乘法环绕。假设 sizeof(*el) 是 4,n 读作 2^30+1。乘法 2^30+1 * 4 换行,结果变为 4,这就是您在告诉函数读取 2^30+1 元素时分配的内容。 read_array_elements_from_network 函数将快速溢出您分配的数组。

calloc 的任何体面的实现都会检查该乘法是否溢出,并会防止这种攻击(这种错误很常见)。

关于c - calloc(10,4) 和 calloc(1,40) 有什么区别?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19021266/

相关文章:

在 C 中使用 malloc 创建字符串数组

调用一个二维数组

c - 结构体数组的动态内存分配。计划结束 [C]

c - C 中的数据结构,指针为 : I want to store an array of information in each position

linux - 使 calloc 机会化

c++ - 如何在更大的存储上重新分配内容,但其余内容为零?

CLion - 我的输出在哪里?

c - 嘈杂的 ADC dsPIC

c - 当我在构建中添加 lib 链接时出现段错误

c - 查找指针指向的字符串的大小