以下代码在我的计算机上生成此输出(Mac OS X Yosemite 64位架构):
#include <stdio.h>
#include <stdlib.h>
int main(int argc, char const *argv[])
{
int *p = malloc(sizeof(int));
*p = 5;
int *q = p;
q = *(p + 1);
printf("p is %p\n", p);
printf("q is %p\n", q);
return 0;
}
输出:
p is 0x7f8f49404c90
q is 0xffffffffb0000000
第二个指针是一个非常大的数字,所以我想知道这是否是一个缓冲区溢出是正确的。
答案 0 :(得分:2)
int *p = malloc(sizeof(int));
正在分配的内存只能容纳一个整数。
你已经在做什么了
*p = 5;
现在你正在递增指针
(p+1)
这是您尚未分配的内存位置。现在你试图读取存储在(p + 1)中的数据,这将导致你提到的未定义的行为,这是一个缓冲区溢出。
*q = *(p+1)
然后尝试将此值分配给*q
,这可能会导致崩溃。
答案 1 :(得分:0)
根据讨论,您的代码应为*q = *(p + 1);
启用编译器中的所有警告。然后,在q = *(p + 1)
之类的情况下,您的合规人员会警告您关于assignment makes pointer from integer without a cast
此处q
[p + 1
]指向未分配给您的程序的内存位置。 malloc()
已将myemory分配给p
一个整数。换句话说,在程序的malloc()
- 内存区域之后,不会禁止您访问内存位置。因此,访问[p + 1
]会导致未定义的行为。
如果您编译程序并通过内存调试器运行它,您可以更深入地了解这一点,比如valgrind
。它将向您显示内存区域访问冲突。
编辑:
检查下面的代码[第8行]
1 #include <stdio.h>
2 #include <stdlib.h>
3 int main(int argc, char const *argv[])
4 {
5 int *p = malloc(sizeof(int));
6 *p = 5;
7 int *q = p;
8 *q = *(p + 1);
9 printf("p is %p\n", p);
10 printf("q is %p\n", q);
11 return 0;
12 }
和运行thr'valgrind
==12786== Invalid read of size 4
==12786== at 0x80483E9: main (test71.c:8)
==12786== Address 0x402602c is 0 bytes after a block of size 4 alloc'd
==12786== at 0x4005903: malloc (vg_replace_malloc.c:195)
==12786== by 0x80483D0: main (test71.c:5)
==12786==