gpt4 book ai didi

c++ - 没有有用且可靠的方法来检测 C/C++ 中的整数溢出?

转载 作者:可可西里 更新时间:2023-11-01 15:09:29 41 4
gpt4 key购买 nike

不,这不是 How to detect integer overflow? 的拷贝.问题是一样的,但问题是不同的。

gcc 编译器可以优化溢出检查(使用 -O2),例如:

int a, b;
b = abs(a); // will overflow if a = 0x80000000
if (b < 0) printf("overflow"); // optimized away

gcc 的人认为这不是一个错误。根据 C 标准,溢出是未定义的行为,它允许编译器做任何事情。显然,任何事情都包括假设永远不会发生溢出。不幸的是,这允许编译器优化溢出检查。

最近的 CERT paper 中描述了检查溢出的安全方法。 .本文建议在添加两个整数之前做这样的事情:
if ( ((si1^si2) | (((si1^(~(si1^si2) & INT_MIN)) + si2)^si2)) >= 0) { 
/* handle error condition */
} else {
sum = si1 + si2;
}

显然,当您想确保结果有效时,您必须在一系列计算中的每个 +、-、*、/和其他操作之前执行类似的操作。例如,如果您想确保数组索引没有越界。这太麻烦了,几乎没有人这样做。至少我从未见过系统地执行此操作的 C/C++ 程序。

现在,这是一个基本问题:
  • 在访问数组之前检查数组索引很有用,但不可靠。
  • 使用 CERT 方法检查一系列计算中的每个操作是可靠的,但没有用。
  • 结论:在 C/C++ 中没有检查溢出的有用且可靠的方法!

  • 我拒绝相信这是编写标准时的意图。

    我知道有一些命令行选项可以解决这个问题,但这并不能改变我们对标准或对它的当前解释存在根本问题的事实。

    现在我的问题是:
    当 gcc 人员允许他们优化溢出检查时,对“未定义行为”的解释是否太过分了,还是 C/C++ 标准被破坏了?

    添加注释:
    抱歉,您可能误解了我的问题。我不是在问如何解决这个问题 - 已经回答了 elsewhere .我在问一个关于 C 标准的更基本的问题。如果没有检查溢出的有用且可靠的方法,那么语言本身就是可疑的。例如,如果我创建了一个带有边界检查的安全数组类,那么我应该是安全的,但是如果边界检查可以被优化掉,我就不安全了。

    如果标准允许这种情况发生,则标准需要修订或标准的解释需要修订。

    添加注释 2:
    这里的人似乎不愿意讨论“未定义行为”这个可疑的概念。 C99 标准列出了 191 种不同类型的未定义行为( link )这一事实表明标准很草率。

    许多程序员欣然接受这样的说法,即“未定义行为”允许做任何事情,包括格式化硬盘。我认为标准将整数溢出与在数组边界外写入相同的危险类别是一个问题。

    为什么这两种“未定义行为”不同?因为:
  • 许多程序依赖于良性整数溢出,但很少有程序依赖于在您不知道数组边界之外写入什么内容。
  • 在数组边界之外写入实际上可以做一些与格式化硬盘一样糟糕的事情(至少在像 DOS 这样不 protected 操作系统中),并且大多数程序员都知道这是危险的。
  • 当您将整数溢出归入危险的“任何事情”类别时,它允许编译器做任何事情,包括对其所做的事情撒谎(在溢出检查被优化掉的情况下)
  • 使用调试器可以发现诸如写入数组边界之外的错误,但是优化掉溢出检查的错误则不能,因为调试时优化通常是关闭的。
  • 在整数溢出的情况下,gcc 编译器显然避免了“任何事情都会发生”的策略。在很多情况下它会避免优化,例如一个循环,除非它可以验证溢出是不可能的。出于某种原因,gcc 人员已经认识到,如果他们在这里遵循“任何事情都可以”的政策,我们会犯很多错误,但是他们对优化溢出检查的问题有不同的态度。

  • 也许这不是讨论此类哲学问题的合适场所。至少,这里的大多数答案都离题了。有没有更好的地方来讨论这个?

    最佳答案

    问问自己:您实际上多久需要一次检查算术?如果你经常需要它,你应该写一个 checked_int重载通用运算符并将检查封装到此类中的类。在开源网站上分享实现的 Prop 。

    更好的是(可以说),使用 big_integer类,以便首先不会发生溢出。

    关于c++ - 没有有用且可靠的方法来检测 C/C++ 中的整数溢出?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6856227/

    41 4 0