关于gets()函数的弊端

当我们要对数组进行输入一串字符时,我们可能会用scanf()输入,但是很多时候会图方便用gets()函数,但是这个函数是有弊端的,我们就来看这个弊端在哪。

/* Demonstration of buffer overflow */
#include <stdio.h>
#include <stdlib.h>
/* Implementation of library function gets() */
char *gets(char *dest)
{
  int c = getchar();
  char *p = dest;
  while (c != EOF && c != '\n') {
    *p++ = c;
    c = getchar();
  }
  *p = '\0';
  return dest;
}
/* Read input line and write it back */
void echo()
{
    char buf[4];  /* Way too small! */
    gets(buf);
    puts(buf);
}
void call_echo() 
{
    echo();
}
int main()
{
    printf("Type a string:");
    call_echo();
    return 0;
}

在Linux上运行结果:

hxl@hxl-virtual-machine:~/桌面/task/code$ ./b
Type a string:123
123
hxl@hxl-virtual-machine:~/桌面/task/code$ ./b
Type a string:1234
1234
hxl@hxl-virtual-machine:~/桌面/task/code$ ./b 
Type a string:12345
12345
*** stack smashing detected ***: <unknown> terminated
已放弃 (核心已转储)

上述代码是用来显示gets()函数出错的。首先看看gets()函数是怎么写出来的。变量c通过getchar()函数接收从控制台输入的字符,将数组的首地址给指针p,一个循环判断如果c不为换行符\n,不为文件结束符EOF,则进行循环,将c给指针p所指的地址存储空间,指针p后移。这就是gets()函数的大体,这就有个问题了,为什么没有检测指针p是否还在数组地址内,也就是没有检测数组是否越界,主函数通过调用 call_echo(), call_echo()再调用 echo(),这个函数定义一个数组,以及调用gets()和puts()函数。函数调用时会将返回地址入栈,但是一旦数组越界,就会破坏这个返回地址,这样一来,返回的路就找不到了,就出现了上面的“已放弃 (核心已转储)”,但是puts()函数照常执行,破坏的是call_echo()返回到 echo()函数的地址,返回去的代码就不会执行了。
总结:
gets()函数不会越界检测,可能破坏栈中有用的地址,比如返回地址,这样就会导致调用函数后不能返回到调用的地方。所以尽量避免使用gets()函数。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值