【问题标题】:Secure handling of string variables安全处理字符串变量
【发布时间】:2013-01-21 10:37:32
【问题描述】:

您好,我是 C 的新手,简而言之,作为课堂作业的一部分,我做了以下工作:

foo (char *var) {
  printf(var);
}

我被告知这是不好的做法且不安全,但我的导师并没有得到太多详细的信息。我假设如果 var 的字符串值可以由用户控制,它可以用来执行缓冲区溢出吗?我将如何正确强化此代码?我必须限制 str 长度吗?

干杯,谢谢!

【问题讨论】:

  • 是的,限制字符串长度以避免可能的无效内存访问。还有一个空指针检查...
  • printf 的第一个参数是格式字符串。让调用者指定它是灾难的根源。考虑一下如果用户传入"%s"会发生什么
  • 看看dwheeler.com/secure-programs(关于安全编程的详细HOWTO)

标签: c string security variables printf


【解决方案1】:

你应该使用:

printf("%s", var);

相反。按照你的方式,我可以输入%s 作为我的输入,printf 会在查找要打印的字符串时读取一段随机的内存。这可能会导致任何数量的意外行为。

【讨论】:

  • 更好的是puts(或者fputs,如果你想避免额外的换行符)
  • 然后它可能导致崩溃或信息泄露或损坏数据,各种各样的事情。
  • @SanderDeDycker puts() 附加 \n,以防万一。
【解决方案2】:

这是不安全,因为它可能导致Format String Attack

【讨论】:

    【解决方案3】:

    嗯,printf 的第一个参数是一个格式字符串。所以你的函数的调用者可以通过:

    foo("%d")
    

    然后printf 会寻找一个不存在的整数,并导致未定义的行为。一种可能的解决方法是让您的函数调用:

    printf("%s", var);
    

    这将使printfvar 解释为常规字符串(而不是格式)。

    【讨论】:

      【解决方案4】:

      Printf 具有以下签名:

      int printf(
         const char *format [,
         argument]... 
      );
      

      如果用户输入格式字符,例如%s,就会发生各种不好的事情。

      如果您只想输出字符串,请使用 puts。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2023-03-31
        • 1970-01-01
        • 1970-01-01
        • 2023-01-13
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-09-05
        相关资源
        最近更新 更多