警告 C26454:算术溢出:“-”操作在编译时产生负的无符号结果 (io.5)

And*_*kle 6 c++ mfc code-analysis treecontrol visual-studio-2017

代码分析:

ON_NOTIFY(TCN_SELCHANGE, IDC_TAB_HISTORY_TYPE,
  &CAssignHistoryDlg::OnTcnSelchangeTabHistoryType)
Run Code Online (Sandbox Code Playgroud)

警告 C26454:

算术溢出:'-' 操作在编译时 (io.5) 产生负的无符号结果。

的定义TCN_SELCHANGE是:

#define TCN_FIRST (0U-550U)
#define TCN_SELCHANGE           (TCN_FIRST - 1)
Run Code Online (Sandbox Code Playgroud)

我看不出我还能做什么!

Bar*_*ani 6

//windows header file:
#define TCN_FIRST (0U-550U)
#define TCN_SELCHANGE           (TCN_FIRST - 1)

//user file:
...
unsigned int i = TCN_SELCHANGE;
Run Code Online (Sandbox Code Playgroud)

上面的代码在 C++ 中是有效的,它应该在没有任何警告的情况下编译。没有溢出,这只是意味着-550U如果他们将其写为#define TCN_FIRST 0xFFFFFDDA0xFFFFFFFFU-549U

代码分析似乎使用了不同的方法并看到了溢出。

可能的解决方案:

禁用代码中的警告:

#pragma warning( push )
#pragma warning( disable : 26454 )

BEGIN_MESSAGE_MAP(CMyDialog, CDialogEx)
    ON_NOTIFY(TCN_SELCHANGE, IDC_TAB1, OnTcnSelchangeTabHistoryType)
END_MESSAGE_MAP()

#pragma warning( pop )
Run Code Online (Sandbox Code Playgroud)

或者,禁用代码分析规则中的警告
使用代码分析规则集编辑器

在此处输入图片说明


Cas*_*sey 2

您试图从较小的无符号值中减去较大的无符号值,这会导致结果超过零。在您的情况下,我假设TCN_FIRST定义为 0,因此设置TCN_SELCHANGE为 1 将解决问题。

无论如何,您还应该使用constexprorconst代替定义。

根据 MSDN:

C++ Core Check 中的算术溢出检查

C26451 RESULT_OF_ARITHMETIC_OPERATION_CAST_TO_LARGER_SIZE:[operator] 操作绕过去 0 并在编译时生成一个大的无符号数。此警告表明减法运算产生负结果,该结果是在无符号上下文中计算的。这会导致结果回绕超过 0 并产生一个非常大的无符号数,这可能会导致意外溢出。

1 // Example source:
2 unsigned int negativeunsigned() {
3    const unsigned int x = 1u - 2u; // C26454 reported here
4    return x;
5 }

1 // Corrected source:
2 unsigned int negativeunsigned() {
3     const unsigned int x = 4294967295; // OK
4     return x;
5 }
Run Code Online (Sandbox Code Playgroud)

在更正的源中,正值被分配给无符号结果。