返回信息流```
char * p = (char*) malloc(27);
for(int i = 0;i<26;++i){
*(p+i) = 'a'+i;
}
*(p+26) = '\0';
for(int i = 0;*(p+i) != '\0';++i){
cout<<*p;
}
free (p);
for(int i = 0;*(p+i) != '\0';++i){
cout<<*p;
}
为什么最后一个for循环不能正常输出26个字母? 求指导
这是一条镜像帖。来源:北邮人论坛 / cpp / #94258同步于 2016/12/15
该镜像源已超过 30 天没有更新,可能在源站已被删除。
CPP机器人发帖
free到底做了什么?
byr10086
2016/12/15镜像同步11 回复
订阅后,新回复会通过你的通知中心匿名送达。
9 条回复
【 在 nuanyangyang 的大作中提到: 】
: free以后,把分配的内存释放了。内存释放之后再访问,是”未定义行为“。不能正常输出是正常的。
话虽这么说,但是在刚把内存free掉以后,里面的内容应该没有改变才是啊? 但为什么多次运行程序后,输出都不是我所预期的。。。
free掉的内存,里面是什么,就不是一件可以预估的事情。它可以是原来的东西,也可以是一堆乱码,还可能是一堆0。取决于编译器。不要用任何逻辑去判断未定义行为,因为这种地方,编译器想怎么做就怎么做。
【 在 byr10086 (nieng) 的大作中提到: 】
: 话虽这么说,但是在刚把内存free掉以后,里面的内容应该没有改变才是啊? 但为什么多次运行程序后,输出都不是我所预期的。。。
【 在 byr10086 的大作中提到: 】
:
: 话虽这么说,但是在刚把内存free掉以后,里面的内容应该没有改变才是啊? 但为什么多次运行程序后,输出都不是我所预期的。。。
不能这么想。C语言把free之后读取定为“未定义行为”,就是为了让内存分配器自由行事。你不能认为“刚free”所以“里面内容没有变”。刚好相反,某些内存分配器会在free之后把里面的内容全部用某种poison value覆盖,这样程序会读到某些很搞笑的值,程序猿一看就知道发生free后访问的错误了。有时候,标准库用memory map来实现内存分配,free之后可能就把一个page的内存unmap了,这会导致CPU的mmu删除这块地址区域到物理内存的映射,然后再访问程序就崩溃了。
总之free之后访问是“未定义行为”,从什么都不发生到机器冒烟都有可能发生。
【 在 NachtZ 的大作中提到: 】
: free掉的内存,里面是什么,就不是一件可以预估的事情。它可以是原来的东西,也可以是一堆乱码,还可能是一堆0。取决于编译器。不要用任何逻辑去判断未定义行为,因为这种地方,编译器想怎么做就怎么做。
记住了,谢谢你!
【 在 nuanyangyang 的大作中提到: 】
:
: 不能这么想。C语言把free之后读取定为“未定义行为”,就是为了让内存分配器自由行事。你不能认为“刚free”所以“里面内容没有变”。刚好相反,某些内存分配器会在free之后把里面的内容全部用某种poison value覆盖,这样程序会读到某些很搞笑的值,程序猿一看就知道发生free后访问的错误了。有时候,标准库用memory map来实现内存分配,free之后可能就把一个page的内存unmap了,这会导致CPU的mmu删除这块地址区域到物理内存的映射,然后再访问程序就崩溃了。
: 总之free之后访问是“未定义行为”,从什么都不发生到机器冒烟都有可能发生。
明白了,谢暖神
只有这样才会有UAF漏洞嘛,我们才有饭吃[ema1][ema1]
【 在 NachtZ 的大作中提到: 】
: free掉的内存,里面是什么,就不是一件可以预估的事情。它可以是原来的东西,也可以是一堆乱码,还可能是一堆0。取决于编译器。不要用任何逻辑去判断未定义行为,因为这种地方,编译器想怎么做就怎么做。