- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
我遇到了一些涉及 Clang -Wconditional-uninitialized
的异常行为。考虑以下示例:
typedef struct { int x[1]; } test_t;
test_t foo(void);
test_t foo() {
test_t t;
for(int i = 0; i < 1; i++) t.x[i] = 0;
return t;
}
int main() { }
编译,例如
clang -o test -Weverything test.c
给出以下警告:
test.c:6:12: warning: variable 't' may be uninitialized when used here [-Wconditional-uninitialized]
return t;
^
test.c:4:5: note: variable 't' is declared here
test_t t;
^
1 warning generated.
然而,切换线路:
for(int i = 0; i < 1; i++) t.x[i] = 0;
与
t.x[0] = 0;
不产生任何警告。请注意,使用 -Wconditional-uninitialized
就足够了,不必传递 -Weverything
。两种情况下的 -O3
优化程序集是相同的,在两种情况下都发出了一个 xorl %eax, %eax
。这是我可以创建的显示此行为的最小示例。
我对 Clang 的一些 -Weverything
输出持保留态度,但这在我看来像是一个错误,我很困惑。是否有某种我正在调用的未定义行为导致了这种情况,或者这是误报?保持 -Wconditional-uninitialized
启用通常是好主意还是坏主意?我在 Linux 上的 Clang 3.8.1 和 macOS 上的 (Apple) 9.1.0 上看到了相同的行为。
最佳答案
正如@R.. 在上面的评论中所建议的那样,我将其报告为 LLVM bug 38856 .显然,根据他们的说法:
-Wconditional-uninitialized is expected to have false positives: it warns in cases where a simple control flow analysis cannot prove that a variable was written to prior to each use. It is not field-sensitive nor data flow sensitive, so it cannot tell the difference between writing to one array element and writing to the whole array, and doesn't know that the loop actually always executes at least once.
-Winitialized, by contrast, only warns when we can prove your program has a bug (or contains dead code).
There are a few improvements we could make to reduce the false positive rate here (some crude field sensitivity might be relatively straightforward to add), but we don't want to recreate the full intelligence of the clang static analyser here, and keeping this warning simple enough that we can run it as part of normal compilations is a goal.
我还在该报告中指出,即使其中一个数组成员明显未初始化,以下示例也没有给出警告:
#include <stdio.h>
typedef struct { int x[2]; } test_t;
test_t foo_3(void);
test_t foo_3() {
test_t t;
t.x[0] = 0;
return t;
}
int main() {
test_t t;
t = foo_3();
printf("%i %i\n", t.x[0], t.x[1]);
}
这让我得到了回复:
As I mentioned in comment#1, the analysis we currently perform cannot tell the difference between writing to one array element and writing to the whole array. In simple cases, this should be relatively straightforward to improve, so I think for that reason this bug is valid (but of low priority, given that this warning is expected to have false positives).
所以 -Wconditional-uninitialized
以给出误报而闻名。显然,静态分析器并不像我预期的那样彻底。我很惊讶在给出分析器似乎工作得更好的更复杂的场景之前我没有遇到过这样的事情,但正如@toohonestforthissite 在上面的评论中也指出的那样,通过像这样的结构按值传递数组不是在 C 中做的标准事情。
-Wno-conditional-uninitialized
或 #pragma clang diagnostic ignored "-Wconditional-uninitialized"
应该为那些想要使用 -Weverything 的人消除警告
在这种情况下。
关于Clang -Wconditional-uninitialized on struct member array 赋值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52194930/
我想问一个让我困惑的问题。我正在尝试扫描字符串并将其转换为实数。使用该数字来计算值(value)。这是我的代码: string input_file_name1 = "shen_test_38_30_
我正在为我的 C 类入门编写一个程序,当我尝试使用 gcc 进行编译时,我不断收到一些警告。 这是我的代码: char **outList; *outList = strdup(cloudDevice
我正在使用 Chromium 嵌入式框架。我将以下内容放在主函数中。 CefRefPtr cef; CefRequest::ReferrerPolicy origin = origin; cef->S
我是C++的新手,正在测试while循环以及C++的绝对速度及其对我的CPU的影响,但出现以下错误: Severity Code Description Project File Line Suppr
string foo; try { foo = "test"; // yeah, i know ... } catch // yeah, i know this one too :) {
当尝试在 Mac OS X 10.6 上使用 FFMPEG gem 时,ruby 会抛出一个 NameError 异常,如下所示: NameError: uninitialized constant
我做了一个程序来计算 View 的总宽度/高度(有时我想要总宽度,有时我想要总高度)。唯一的问题是:如果我正在计算宽度,我想添加一个额外的 10到总数。这是我当前的代码: func calculate
所以我只想从常规地址(字符串)中提取经度/纬度坐标。我查阅了 geokit gem 文档并按照记录的内容进行了操作,但我不断收到此错误:“NameError:未初始化的常量 Geokit::Geoco
为什么 perl -we '$c = $c+3' 上升 Use of uninitialized value $c in addition (+) at -e line 1. perl -we '$c
我有以下代码: class circularList { public: circularList() : data(0), next(this) {} public: int dat
我的情况 我正在 ASP.NET MVC4 应用程序中进行测试。我正在开发的应用程序部分将现代 WebSecurity/SimpleMembershipProvider 与正在逐步淘汰的遗留身份验证系
我是 Ruby on Rails 的新手,我想使用迁移生成 mysql 数据库。 我尝试过这个命令 ruby bin/rake db:drop db:create db:migrate --trace
我需要一些调试帮助,因为我遇到的错误真的很难。 这是一款具有复杂动画的游戏。然而,问题不在于 SpriteKit .我希望动画按照严格的顺序彼此跟随,所以我实现了 Operation 的子类: cla
这是一个示例代码: #include int main() { int n = 5; float v[n]; float sum; int i; for(i
我正在使用 SQL Server 2012 并尝试实现事务复制。我正在使用系统存储过程来创建发布和订阅。我成功地创建了这些东西,但是当我检查复制监视器时,它显示“未初始化的订阅”。 当我检查订阅的同步
我有以下脚本: use 5.12.4; use strict; use warnings; say "Enter a functionality:"; while (<>) { if (/ad
我已经阅读了有关 has_many 的文档和大量教程:通过 Rails 中的关系,但我终生无法掌握它的窍门。 我正在尝试向我的 current_user(devise) 添加一个组,并且我在 Grou
我正在尝试为移动 API 设置路由,它应该有一个版本化的 api-path。我已经可以让移动 Auth 工作了,这是在位于 的单独 Controller AuthController 中实现的。/co
我正在使用 luacheck(在 Atom 编辑器中),但对其他静态分析工具开放。 有没有办法检查我是否使用了未初始化的表字段?我阅读了文档( http://luacheck.readthedocs.
我有一家工厂,例如: FactoryGirl.define do factory :page do title 'Fake Title For Page' end end 并进行测试:
我是一名优秀的程序员,十分优秀!