这容易受到堆栈溢出的影响吗? [英] Is this vulnerable to a stack overflow?

查看:96
本文介绍了这容易受到堆栈溢出的影响吗?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

void gctinp (char *inp, int siz)
{

  puts ("Input value: ");
  fgets (inp, siz, stdin);
  printf ("buffer3 getinp read %s", inp);
}

根据我的阅读,当您想限制输入的大小时,应该使用fgets.因此,此代码不应该容易受到攻击吗?

From what I've read, fgets is supposed to be used when you want to limit the size of input. So this code shouldn't be vulnerable right?

它被这样称呼:

int main (int argc, char *argv[])

{

 char buf[16];

 getinp (buf, sizeof (buf));

 display (buf);

 printf ("buffer3 done\n");

}

感谢您的时间.

推荐答案

如果输入的字符数超出安全存储的字符数,则不会出现缓冲区溢出问题,因为fgets会限制输入.它还添加了一个空终止符(当然,假定缓冲区的大小大于0).

You won't strike buffer overflow problems if you enter more characters than can be safely stored since fgets restricts the input. It also adds a null terminator (assuming buffer size is greater than 0, of course).

但是,您遇到问题,下次您尝试阅读某些内容时会将信息保留在输入缓冲区中-这是用户会非常烦恼的内容,输入类似hello again的内容,然后将其视为两个单独的输入,例如hello again. fgets并没有指示它在行尾之前停止检索输入,因此,据您的代码所知,一切都很好.

However, you will have problems with information being left in the input buffer the next time you try to read something - this is something that users will find very annoying, entering something like hello again and having it treated as two separate inputs like hello ag and ain. And there's no indication given by fgets that it stopped retrieving input before the end of the line so, as far as your code is aware, everything is fine.

您需要注意的主要事情(输入上的缓冲区溢出)至少是具有无限制的%s格式字符串和getsscanf,该字符串没有大小限制参数,两个都没有在您的代码中.

The major things you need to look out for (re buffer overflows on input) are, at a minimum, scanf with an unbounded %s format string and gets, which has no limiting size argument, neither of which are in your code.

如果您正在寻找具有大小限制,提示和缓冲区清除功能的更强大的输入解决方案,请查看此代码,其中提供了所有这些功能:

If you're looking for a more robust input solution with size limiting, prompting and buffer clearing, check out this code, which provides all those features:

#include <stdio.h>
#include <string.h>

#define OK       0
#define NO_INPUT 1
#define TOO_LONG 2
static int getLine (char *prmpt, char *buff, size_t sz) {
    int ch, extra;

    // Get line with buffer overrun protection.
    if (prmpt != NULL) {
        printf ("%s", prmpt);
        fflush (stdout);
    }
    if (fgets (buff, sz, stdin) == NULL)
        return NO_INPUT;

    // If it was too long, there'll be no newline. In that case, we flush
    // to end of line so that excess doesn't affect the next call.
    if (buff[strlen(buff)-1] != '\n') {
        extra = 0;
        while (((ch = getchar()) != '\n') && (ch != EOF))
            extra = 1;
        return (extra == 1) ? TOO_LONG : OK;
    }

    // Otherwise remove newline and give string back to caller.
    buff[strlen(buff)-1] = '\0';
    return OK;
}

 

// Test program for getLine().

int main (void) {
    int rc;
    char buff[10];

    rc = getLine ("Enter string> ", buff, sizeof(buff));
    if (rc == NO_INPUT) {
        // Extra NL since my system doesn't output that on EOF.
        printf ("\nNo input\n");
        return 1;
    }

    if (rc == TOO_LONG) {
        printf ("Input too long [%s]\n", buff);
        rc = getLine ("Hit ENTER to check remains> ", buff, sizeof(buff));
        printf ("Excess [%s]\n", buff);
        return 1;
    }

    printf ("OK [%s]\n", buff);

    return 0;
}

然后进行一些基本测试:

And, doing some basic tests:

pax> ./prog
Enter string> [CTRL-D]
No input

pax> ./prog
Enter string> x
OK [x]

pax> ./prog
Enter string> hello
OK [hello]

pax> ./prog
Enter string> hello from earth
Input too long [hello fro]
Hit ENTER to check remains> [ENTER]
Excess []

pax> ./prog
Enter string> i am pax
OK [i am pax]

这篇关于这容易受到堆栈溢出的影响吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆