1

I'm watching a CppCon video, which shows this code:

void foo(const int&);

bool bar(int x)
{
    const int y = x + 1;
    foo(y);
    return y > x;
}

First of all the speaker says that since the foo() function takes 'y' by const reference, and 'y' is actually a const int, then changing the value in foo() is undefined behaviour at runtime. And seems to be saying that since this is illegal the compiler, should actually assume that 'y' doesn't change in the call to foo(), and that the bar() function should just return true without doing the comparison.

The compiler is allowed, as far as I know, to just return true, because it really is illegal for foo() to change 'y'.

Then says "but it doesn't", as if to imply that it's a shortcoming of the compiler which missed out on an optimisation. Is he right about this?

Also, about the assumption that 'y' will always be bigger than 'x' and so the function should just return true instead of comparing them, isn't there a value that can be passed into the function, namely the max value that type can hold, where "y = x + 1" will cause an overflow meaning that y > x is no longer true? This I believe is the case for both signed and unsigned.

So in this example there's signed integers, 'y' is equal to 'x' plus 1, so if 'y' doesn't change, it's now always bigger than 'x'. The compiler's allowed to make that assumption for signed, not unsigned.

He also says:

If you change it to pass by value, then it works.

As if to say that the comparison instruction is gone and the function just returns true, but how can the compiler make this assumption given the integer overflow point?

Here is the relevant point in the video.

Zebrafish
  • 11,682
  • 3
  • 43
  • 119
  • Signed overflow is undefined behavior and compiler will and do optimize around the assumption of no undefined behavior. See this [gcc aggressive loop optimization around signed overflow](https://stackoverflow.com/q/24296571/1708801) or this one [same optimization but based on OOB access](https://stackoverflow.com/q/32506643/1708801) – Shafik Yaghmour Dec 21 '18 at 14:06

1 Answers1

3

Signed int overflow is undefined, so a compiler is allowed to ignore the possibility that x + 1 might reduce x.

Compilers are getting better and better at devising optimisation strategies; you can expect your function to be optimised to call foo then to return true; in future.

Bathsheba
  • 231,907
  • 34
  • 361
  • 483
  • 1
    Optimizing compilers are not that new (my father wrote [one](https://en.wikipedia.org/wiki/CAB500) in 1959). But optimization is an undecidable problem, and some optimizations are not worth to be implemented. – Basile Starynkevitch Dec 21 '18 at 08:16
  • @BasileStarynkevitch: Wow, you must be proud! The days of real computer science! – Bathsheba Dec 21 '18 at 08:19
  • That was just to say that your sentence "optimization theory is a fairly new science" (for compilers, it has a different meaning for [operations reasearch](https://en.wikipedia.org/wiki/Operations_research)) is false. A 60+ years old theory cannot be qualified as fairly new! – Basile Starynkevitch Dec 21 '18 at 08:21
  • I see. I don't know how many implementations treat an integer overflow by returning the lowest value, but in the case this did happen then the function would fail. Is this optimisation done regardless because of the fact that since the overflow is UB then the compiler isn't required to generate code that's correct anyway? – Zebrafish Dec 21 '18 at 08:25
  • @Zebrafish Its being undefined makes the entire program undefined if it overflows, so there is no "correct". (Undefined behaviour can have effects both in the past and at a distance.) See [this LLVM blog](http://blog.llvm.org/2011/05/what-every-c-programmer-should-know.html) for details. – molbdnilo Dec 21 '18 at 10:21
  • 1
    Unless the compiler knows more about `foo()` it is not possible to reduce the function to `return true`. The function must contain a call to `foo()` in case it performs any side-effects. – Johan Dec 21 '18 at 19:39
  • @Johan: indeed - funny I didn’t spot that. Thanks! – Bathsheba Dec 21 '18 at 19:42