代码如下:
int i;
char *result = (char*)malloc(3*sizeof(char));
memset(result, 0, 3*sizeof(char));
for (i = 0; i < 3; i++) {
result[i] = 'a';
}
result[index] = '#';
为什么不报错?
1
Monad 2015-06-15 15:08:16 +08:00
不报错从标准上来说应该是undefined behaviour
从实际上来说 是因为ptmalloc2(或者其它memory allocator)会Round Up你malloc的大小,所以你写入的区域实际上是属已经向OS申请的内存区域,而不是OS禁止写入的区域(那样会segmentation fault) |
2
nicai000 2015-06-15 15:09:19 +08:00
算越界, 不检查不警告, 就这么设计的
|
3
tabris17 2015-06-15 15:12:11 +08:00
C的数组是不安全的类型,所谓不安全的类型就是语言本身不会越界检查
|
4
xylophone21 2015-06-15 15:12:23 +08:00
因为这样可以写出
char *result = (char*)0x12345678; 这样的代码 |
5
leavic 2015-06-15 15:14:56 +08:00
底层语言变态的地方就是可以让你访问任意地址,而且很轻松
|
6
xionghengheng 2015-06-15 15:20:28 +08:00
看看malloc的源码你就懂了,谁说堆内存malloc一次就是按照申请多少就给你多少,他可能会给你比你申请内存多一点,这都是内存的动态管理
|
7
ChanneW 2015-06-15 15:28:13 +08:00
再加多少都不算越界
|
8
wy315700 2015-06-15 15:30:30 +08:00
还可以访问 result[-1]
|
9
abscon 2015-06-15 15:46:43 +08:00
说一句跑题的话:index 这个变量在哪里定义的?楼主你这段代码编译通过了吗?
|
12
yangff 2015-06-15 17:37:40 +08:00
你可以操作任何一个属于你的地址.
|
13
sleeperqp 2015-06-15 17:47:47 +08:00
不能说是任意地址 只能说是该程序的线性地址
|
14
loveuqian 2015-06-15 17:49:41 +08:00 via iPhone
因为越界不报错啊
|
15
zhicheng 2015-06-15 17:55:04 +08:00
谁丫的知道你 index 是啥值。
|
16
icedx 2015-06-15 18:46:57 +08:00 via Android
C 语言哪有越界一说
想去哪就去哪 |
17
21grams 2015-06-15 18:53:21 +08:00
那你说说由谁来报这个错呢?
|
18
zhangxiao 2015-06-15 19:09:44 +08:00
这就好比一条街上每隔10米一户人家,一共3户(0,1,2)。
写个简单的机器人发,就告诉机器人在n*10的地方丢下包裹就好了。所以你硬要是发给#3,那就丢在了30米的地方,硬要发给#10,就丢在了100米的地方,机器人不管那里有没有住户。 如果让楼主自己去发,你一看就会说,这条街上没有#3啊,就报错了 |
19
thinkIn 2015-06-15 20:00:35 +08:00 via iPhone
虽然越界不会报错,但一定不要做这种事,很可能会覆盖掉malloc与free维护的链表节点头信息,这将会是致命错误。
|
20
zi 2015-06-15 20:57:11 +08:00
C语言的数组名其实是个指针来的,既然是指针,那就可以随便指随便写,至于你随便写之后覆盖掉什么东西。。后果自负。。
|
21
mintist 2015-06-15 22:35:54 +08:00
给你自由,自己把握
|
22
way2exluren 2015-06-15 22:41:50 +08:00 via Android
加句free(result );应该会崩溃
|
23
yaoc 2015-06-16 00:10:42 +08:00 via Android
@way2exluren
应该不会,因为result指向的还是一开始分配给它的内存 |
24
way2exluren 2015-06-16 00:12:52 +08:00 via Android
@yaoc 你去试试。。。。
|
25
way2exluren 2015-06-16 00:14:36 +08:00 via Android
@yaoc 分配好的内存前后都有几个自己是用来管理内存的。覆盖了以后,free再重新整理内存快的时候会出错。。
|
26
yaoc 2015-06-16 00:31:36 +08:00 via Android
@way2exluren 我试了,没有什么问题
|
27
alphonsez 2015-06-16 01:43:22 +08:00
试试看多越界一点,估计就出问题了。这种问题会藏的很深,到时候真崩溃了很难找。一个字节的这种,搞不好还能来个heartbleed.
|
28
Heartwork 2015-06-16 09:01:38 +08:00 via Android
1 因为malloc在分配的内存是16字节补齐的。所以就算你访问了后面的几个字节,也还是在有效内存范围内。
2 即使你访问了多于16字节的非法空间,还是需要根据brk或sbrk查看数据段末端的地址,如果超过这个值,就会有内存访问异常了。 |