鱼C论坛

 找回密码
 立即注册
查看: 1641|回复: 5

C语言

[复制链接]
发表于 2015-5-30 13:07:40 | 显示全部楼层 |阅读模式
50鱼币
本帖最后由 dt3tc 于 2015-6-1 10:31 编辑

谢谢
bash-4.3$ make
gcc 1.c -Wall -g -o 1
bash-4.3$ ./1
a
pbuffer=
*** Error in `./1': free(): invalid pointer: 0x08b6f00a ***
======= Backtrace: =========
/lib/libc.so.6(+0x6b716)[0xb7590716]
/lib/libc.so.6(+0x7414a)[0xb759914a]
/lib/libc.so.6(cfree+0x50)[0xb759c930]
./1[0x8048523]
/lib/libc.so.6(__libc_start_main+0xf7)[0xb753d6c7]
./1[0x80483d1]
======= Memory map: ========
08048000-08049000 r-xp 00000000 08:03 805443458  /home/mxf/Dev/myself/C/1/1
08049000-0804a000 r--p 00000000 08:03 805443458  /home/mxf/Dev/myself/C/1/1
0804a000-0804b000 rw-p 00001000 08:03 805443458  /home/mxf/Dev/myself/C/1/1
08b6f000-08b90000 rw-p 00000000 00:00 0          [heap]
b7524000-b7525000 rw-p 00000000 00:00 0
b7525000-b76ec000 r-xp 00000000 fd:00 265595     /usr/lib/libc-2.21.so
b76ec000-b76ee000 r--p 001c7000 fd:00 265595     /usr/lib/libc-2.21.so
b76ee000-b76ef000 rw-p 001c9000 fd:00 265595     /usr/lib/libc-2.21.so
b76ef000-b76f2000 rw-p 00000000 00:00 0
b76f6000-b7712000 r-xp 00000000 fd:00 268576     /usr/lib/libgcc_s-5.1.1-20150422.so.1
b7712000-b7713000 r--p 0001b000 fd:00 268576     /usr/lib/libgcc_s-5.1.1-20150422.so.1
b7713000-b7714000 rw-p 0001c000 fd:00 268576     /usr/lib/libgcc_s-5.1.1-20150422.so.1
b7714000-b7718000 rw-p 00000000 00:00 0
b7718000-b771a000 r--p 00000000 00:00 0          [vvar]
b771a000-b771b000 r-xp 00000000 00:00 0          [vdso]
b771b000-b773d000 r-xp 00000000 fd:00 272604     /usr/lib/ld-2.21.so
b773d000-b773e000 r--p 00021000 fd:00 272604     /usr/lib/ld-2.21.so
b773e000-b773f000 rw-p 00022000 fd:00 272604     /usr/lib/ld-2.21.so
bfb79000-bfb9a000 rw-p 00000000 00:00 0          [stack]
已放弃 (核心已转储)
bash-4.3$ cat 1.c
#include <stdio.h>
#include <stdlib.h>
int main()
{
    char *pbuffer;
    pbuffer=(char *)calloc(20,sizeof(char));
    if(pbuffer!=NULL)
    {
        while((*pbuffer++=getchar())!='\n')
        {
            printf("pbuffer=%c\n",*pbuffer);
        }
    }
    free(pbuffer);
    return 0;
}
bash-4.3$


最佳答案

查看完整内容

搜索 复制 楼主注意! 1. 你输入的是a和回车, 而回车默认的字符就是\n(再严格来说应该是\r\n) 所以在第一次循环的时候, 缓冲区里的字符已经是'a'和'\n'换句话说 第二次的循环直接就跳出了 2. 其实跳出就跳出循环吧, 无非就是20个缓冲区里就一个字符, 释放空间也没啥 但是! 楼主 有一种东西叫做局部释放, 对的! pbuffer本来是你申请内存的首地址 但是每次循环你竟然让这个首地址自增. 可以看到此时的pbuffer 是 ...
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2015-5-30 13:07:41 | 显示全部楼层
1.png
搜索
复制

楼主注意!
1. 你输入的是a和回车, 而回车默认的字符就是\n(再严格来说应该是\r\n)
所以在第一次循环的时候, 缓冲区里的字符已经是'a'和'\n'换句话说
第二次的循环直接就跳出了


2.png

2. 其实跳出就跳出循环吧, 无非就是20个缓冲区里就一个字符, 释放空间也没啥
但是! 楼主 有一种东西叫做局部释放, 对的! pbuffer本来是你申请内存的首地址
但是每次循环你竟然让这个首地址自增.
可以看到此时的pbuffer 是空, 即已经自动指向了下一个位置.
而前一个位置(pbuffer - 1)就是那个回车字符'\n'
再前一个位置(pbuffer - 2)的字符串就是'a\n'
所以楼主, 你对内存进行了"局部释放", 即free的并不是当初申请的这块堆内存的首地址, 而是其中的局部地址这和野指针是一样的危害, 内存自然叮咚的一声报错了
ps: 建议申请了地址后, 首地址buff就不要动了
要么利用下表操作符即buff[1], buff[2]这种
要么再顶一个迭代器如char* iter = buff; 然后利用iter去迭代赋值
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2015-5-30 19:28:03 | 显示全部楼层
看看,学习学习
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2015-5-30 20:04:23 | 显示全部楼层
:call:
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

发表于 2015-6-1 13:27:11 | 显示全部楼层
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

 楼主| 发表于 2015-6-2 11:31:32 | 显示全部楼层

我还是建议你发个真大腿更好
想知道小甲鱼最近在做啥?请访问 -> ilovefishc.com
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Archiver|鱼C工作室 ( 粤ICP备18085999号-1 | 粤公网安备 44051102000585号)

GMT+8, 2024-11-26 01:41

Powered by Discuz! X3.4

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表