【问题标题】:Why "-flto" silent GCC's warning "stringop-truncation"为什么“-flto”沉默 GCC 的警告“stringop-truncation”
【发布时间】:2021-06-29 02:42:29
【问题描述】:

我了解较新的 GCC 版本针对可能错误的字符串操作“stringop-truncation”引入了警告

这是我可以轻松触发此警告的示例代码:

$ cat strncpy-warning.cxx
#include <cstring>

extern char g_buf[16];

void mycopy ( const char* src_c_str )
{
    strncpy ( g_buf, src_c_str, sizeof ( g_buf ) );
}

使用以下标志编译它会触发此警告:

$ g++ --version
g++ (GCC) 8.3.0
Copyright (C) 2018 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

$ g++ -Wall -std=c++14 -Wextra -Werror -O3 -c strncpy-warning.cxx
strncpy-warning.cxx: In function ‘void mycopy(const char*)’:
strncpy-warning.cxx:7:13: error: ‘char* strncpy(char*, const char*, size_t)’ specified bound 16 equals destination size [-Werror=stringop-truncation]
     strncpy ( g_buf, src_c_str, sizeof ( g_buf ) );
     ~~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
cc1plus: all warnings being treated as errors

这是意料之中的,但是,如果我在标志中添加了 -flto,则此警告消失并生成目标文件:

$ g++ -Wall -std=c++14 -Wextra -Werror -O3 -c strncpy-warning.cxx -flto
$ ls strncpy-warning.o
strncpy-warning.o

显然,-flto 会捕捉到一些编译时警告,所以不确定为什么没有捕捉到 stringop-truncation,例如:

$ cat strncpy-warning.cxx
#include <cstring>

extern char g_buf[16];

void mycopy ( const char* src_c_str, const char* unused )
{
    strncpy ( g_buf, src_c_str, sizeof ( g_buf ) );
}

$ g++ -Wall -std=c++14 -Wextra -Werror -O3 -c strncpy-warning.cxx -flto
strncpy-warning.cxx: In function ‘void mycopy(const char*, const char*)’:
strncpy-warning.cxx:5:50: error: unused parameter ‘unused’ [-Werror=unused-parameter]
 void mycopy ( const char* src_c_str, const char* unused )
                                      ~~~~~~~~~~~~^~~~~~
cc1plus: all warnings being treated as errors                                               

所以问题是:

  1. 这是预期行为吗?
  2. 我知道在为源文件指定-flto 后,GCC 会将特殊内容写入生成的目标文件(*.o),但问题是为什么 GCC 会跳过警告?这是故意的吗?
  3. 即使给出-flto,是否有办法启用此警告?
  4. 或者上面的第 3 点有意义吗?

非常感谢!

【问题讨论】:

  • 使用-flto,生成目标文件并不会真正编译,这会延迟到“链接”时间。并在编译期间发出警告。
  • 谢谢马克。我编辑了另一个带有“flto”的警告的问题,并且该警告按预期报告。
  • 我会用 gcc 提交一个错误。在 LTO 模式下没有理由不会出现警告。
  • 谢谢 rustyx,会的。 (将首先在 GCC bugzilla 中创建一个帐户 :))

标签: c++ c gcc g++ gcc-warning


【解决方案1】:

大致来说,GCC 有两种警告:

  • 简单分析源代码产生的警告
  • 复杂的数据流分析产生的警告

未使用的参数是第一类:在函数中根本不使用参数是微不足道的。

strncpy 的错误用法是,除了琐碎的情况外,第二种:编译器需要了解strncpy 的第一个和第三个参数之间的关系,它需要知道实际的(或至少是符号的)在第三个参数中传递的值,它需要知道第一个参数中可用的实际(或至少是符号)大小。

第一种警告是由前端解析器生成的。因此,它总是会触发。

第二种是由优化代码的同一个组件生成的,因为只有这个组件有必要的信息。在-flto 模式下,此组件不会针对单个源文件运行。

第二种有时也取决于正在执行的特定优化:如果您将第一个命令行中的优化级别更改为-O1,也不会发出警告。

【讨论】:

  • 非常感谢塞巴斯蒂安。所以听起来如果我想看到这个警告,我应该在没有 LTO 的情况下编译我的代码,即使我最后只需要 LTO 二进制文件。 (类似于调试与优化构建之间的情况)
猜你喜欢
  • 1970-01-01
  • 2020-01-22
  • 2022-12-03
  • 1970-01-01
  • 2018-10-16
  • 1970-01-01
  • 2021-12-27
  • 2020-04-03
  • 2016-11-25
相关资源
最近更新 更多