代码之家  ›  专栏  ›  技术社区  ›  Sudantha

C++的“StrucPy”给出警告(C499)

  •  16
  • Sudantha  · 技术社区  · 16 年前

    我收到这个警告,但所有功能都正常工作。

    'strcpy': This function or variable may be unsafe. 
    Consider using strcpy_s instead. To disable deprecation, 
    use _CRT_SECURE_NO_WARNINGS. See online help for details.
    
    9 回复  |  直到 13 年前
        1
  •  21
  •   Cratylus    16 年前

    此函数(strcpy)被认为是不安全的,因为没有边界检查,并且可能导致缓冲区溢出。(实际上strcpy因溢出攻击而臭名昭著,所有程序员都会避免它,或者至少应该避免它)。建议使用一个考虑到目标缓冲区大小的安全函数,以避免溢出。你也可以使用strncpy(但要小心!)。代码没有问题,即函数将按您所说的方式运行,但请尝试将大于目标缓冲区的缓冲区作为输入。函数将使目标缓冲区溢出。也检查一下这个 link text

        2
  •  11
  •   Montdidier rioc0719    16 年前

    虽然strcpy是一个常见的字符串函数,但它一直是软件中许多错误和安全漏洞的根源(因为缓冲区溢出很容易)。

    你有几个选择。

    1. 如果您不想关心它,请定义“CRT_SECURE_NO_WARNINGS”,这样可能会在您的软件中留下安全问题。
    2. 用安全的字符串函数替换字符串函数,这样会降低软件的可移植性
    3. 包装安全字符串函数并在任何地方使用包装器,在Windows平台上提供增强的安全性,并回到其他平台上的传统版本。包装器函数可以通过宏或编译的函数。

    我通常做3。

        3
  •  10
  •   Konrad Rudolph    16 年前

    既然你在编程C++,正确的解决方案是禁止C风格。 char* std::string (或其他适当的字符串类型)。

    做 使用诸如 strcpy 或 strcpy_s 或 strncpy string 上课。或者如果您真的需要复制缓冲区,请使用 std::copy

        4
  •  8
  •   sharptooth    16 年前

    自VC++ 8 strcpy() 还有一大堆其他的功能 are considered to be unsafe 因为它们没有边界检查,如果使用不当可能导致缓冲区溢出。

    你有两个选择:

    • 如果你不确定-做VC++的话,使用“安全”函数。它们将触发一个错误处理程序,如果出现错误,它将终止您的程序。
    • 如果您知道自己在做什么-您知道不会发生溢出,所有的边缘情况都由您的代码定义处理 _CRT_SECURE_NO_WARNINGS 在包含CRT头之前,这将使警告消失。
        5
  •  4
  •   user180326 user180326    16 年前

    您可以启用 secure template overloads . 他们将(如果可能)通过使用模板重载捕获缓冲区来推断缓冲区的长度。在VisualC++中,为什么默认情况下无法启用这一点,这对我来说是个谜。

        6
  •  4
  •   Gabe Timothy Khouri    16 年前

    \0 很容易导致严重的问题(缓冲区溢出)。strcpy仍然存在并起作用的原因是它是标准库遗留的一部分,但是您应该真正考虑使用str*\u或strn*函数(它不完全依赖于查找终止 ).

    更多细节: http://www.safercode.com/blog/2008/11/04/unsafe-functions-in-c-and-their-safer-replacements-strings-part-i.html

        7
  •  2
  •   Sateesh Pagolu    11 年前
    #pragma warning(disable: 4996)
    

        8
  •  1
  •   Cezar    13 年前

    如果您已经查看了使用C++纯技术的优点和缺点,而不是担心,因为您知道您的字符串将被零终止,那么您也可以禁用MSVC中的警告,这类事情:

    #ifdef _MSC_VER
      // 4231: nonstandard extension used : 'extern' before template explicit instantiation
      // 4250: dominance
      // 4251: member needs to have dll-interface
      // 4275: base needs to have dll-interface
      // 4660: explicitly instantiating a class that's already implicitly instantiated
      // 4661: no suitable definition provided for explicit template instantiation request
      // 4786: identifer was truncated in debug information
      // 4355: 'this' : used in base member initializer list
      // 4910: '__declspec(dllexport)' and 'extern' are incompatible on an explicit instantiation
    #   pragma warning(disable: 4231 4250 4251 4275 4660 4661 4786 4355 4910)
    #endif
    
        9
  •  -1
  •   raidsan    13 年前

    使用 Secure Template Overloads 或 define wrapper functions
    要么修改源代码以使用安全替换,要么忽略它。

    如果代码是自己编写的,最好将这样的strcpy改为strcpy_s等。 如果模块是从受信任的源导入的,则可以选择忽略警告。

    忽略方法1:项目全局作用域:添加安全警告

    #pragma warning(push)
    #pragma warning(disable: 4996)
    #include <sapi.h>  //legacy module
    #include <sphelper.h> //legacy module
    #pragma warning(pop)