GCC:指定的边界取决于源参数的长度

use*_*940 8 c++ gcc

以下代码:

while (node)
{
    if (node->previous== NULL) break;
    struct Node* prevNode = node->previous;
    len = strlen(prevNode->entity);
    //pp is a char* fyi
    pp-=len;
    strncpy(pp, prevNode->entity, len+1);
    *(--pp) = '/';
    node = prevNode;
}
Run Code Online (Sandbox Code Playgroud)

在 GCC 中生成以下警告/错误(我将所有警告视为错误):

../someFile.C:1116:24: error: 'char* strncpy(char*, const char*, size_t)' specified bound depends on the length of the source argument [-Werror=stringop-overflow=]
 1116 |                 strncpy(pp, prevNode->entity, len+1);
      |                 ~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
../someFile.C:1114:29: note: length computed here
 1114 |                 len = strlen(prevNode->entity);
      |                       ~~~~~~^~~~~~~~~~~~~~~~~~~~
Run Code Online (Sandbox Code Playgroud)

为什么 GCC 给我一个警告?依赖缓冲区大小的源参数大小有什么问题?有人可以举例说明这可能导致什么问题吗?代码做了它应该做什么我只是好奇为什么我会收到警告。

Ton*_*nyK 8

关键是传递给的长度绑定strncpy应该取决于目标参数的大小,而不是源参数。否则,它到底是为了什么?编译器正确地识别出在strncpy此处使用没有意义,并为您提供有关该效果的信息性错误消息。

  • 对于将来阅读本文的任何人,您(取决于您的用例)也许可以将 strcpy 切换到 memcpy 以消除编译警告。 (11认同)
  • 如果你事先知道缓冲区的大小,memcpy 会更快。如果您不知道缓冲区的大小,则永远不会发生此错误。因此在这种情况下,我认为 memcpy 是解决此编译器警告的更好方法。 (3认同)