以下代码:
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;
}
在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);
| ~~~~~~^~~~~~~~~~~~~~~~~~~~
为什么GCC会警告我?依赖源参数的大小作为缓冲区大小有什么问题?有人可以举例说明这可能导致什么问题吗?代码做了应该做的事情,我只是很好奇为什么收到警告。
答案 0 :(得分:1)
重点是传递给strncpy
的绑定长度应取决于目标参数的大小,而不取决于源参数的大小。否则,它甚至还能做什么?编译器正确地识别出此处没有必要使用strncpy
,并为此提供了一条信息丰富的错误消息。
答案 1 :(得分:0)
根据手册页,
"stpncpy() 和 strncpy() 函数最多将 len 个字符从 src 复制到 dst。如果 src 长度小于 len 个字符,则 dst 的剩余部分用 `\0' 字符填充。否则,dst 不是终止。”
这与目标缓冲区中的空间量无关,而与需要复制的字符数有关。如果希望将 len 字符从 src 复制到 dst 并且 src 有超过 len 个字符,那么替换 strcpy 将不会产生相同的结果。此外,如果 dst 缓冲区的大小是按预期大小分配的,那么 strcpy 将产生缓冲区溢出。
在这种情况下,警告具有误导性,应被忽略或静音。