clang-tidy静态分析器检测变量在移动后的使用。
class a_class {
std::unique_ptr<int> p_;
public:
auto p() -> auto& {return p_;}
void f() const {}
};
int main() {
auto aa = a_class{};
[[maybe_unused]] auto bb = std::move(aa);
aa.f();
}
error: Method called on moved-from object 'aa' [clang-analyzer-cplusplus.Move,-warnings-as-errors]
太棒了!
*如何让 * 编译器 、clang或GCC也检测到相同的问题?通过激活一些警告选项或通过一些(非标准?)属性?
我尝试在clang中使用-Wmove
和[[consumed]]
属性,但它们没有帮助。也许我用错了。
代码在这里:https://godbolt.org/z/18hr4vn7x(下面的面板是clang-tidy,右边的中间面板是[empty]编译器输出)
编译器是否有可能对此发出警告,或者编译器检查此模式的成本太高?
2条答案
按热度按时间wko9yo5t1#
我找到了一种方法,在clang中使用属性。。(GCC或更标准的解决方案仍然受欢迎。
1.需要clang 6或更高
1.将类标记为“可消耗”
1.将方法标记为“callable-when-unconsumed”(不确定如何将其设为默认值)
https://godbolt.org/z/45q8vzdnc
配方由https://awesomekling.github.io/Catching-use-after-move-bugs-with-Clang-consumed-annotations/简化而来。我找不到关于如何使用这些功能的 * 详细 * 文档。
之所以简化,是因为:
a)看起来“clang-consumable”移动的对象在moved-from时默认变为“consumed”,因此没有必要编写特殊的函数来无效(不需要
[[clang::set_typestate(consumed)]]
)。B)默认情况下,构造函数似乎使对象处于未使用状态(不需要
[[clang::return_typestate(unconsumed)]]
);tkclm6bt2#
如果编译器在构建时没有设置这样做,那么你就不能让它这样做。use-after-move在C++中是合法的,因此没有编译器必须将其视为错误。
这类事情正是静态分析器的用途。