3

Let's say I compile the following with GCC 5.4 with -O2 or -O3 level of optimization.

typedef struct {
  int data[90];
} huge_t;

int foo( const huge_t bar );

// ...

huge_t x = { 0 };
foo(x);

Here, I would venture to say is not necessary to create a second copy of x on the stack because foo is not (supposed to be) modifying its argument. (When) will GCC come to the same conclusion?

In other words, is it ok for me to work with const arguments of type huge_t for convenience, or should I be using pointers? I could imagine both versions being "good style" in one sense or the other and would very much appreciate an informed opinion.

Jesko Hüttenhain
  • 1,278
  • 10
  • 28
  • In general I would doubt that you can be guaranteed that the compiler makes such optimization. However, write the code in the way you find "nice, easy and simple". Then check whether it meets your performance requirements. If it does, just be happy about it. If it doesn't, do a profiling to find where the performance killer is. – Support Ukraine Jun 07 '17 at 15:49
  • If compiler will come to this conclusion and pass reference instead what will happen if foo() is a long running function and there are other threads accessing and possibly modifying your huge_t instance? – mvidelgauz Jun 07 '17 at 15:50
  • @mvidelgauz then is should have been declared `volatile`. Joking ofc. I don't believe the compiler is allowed to make this optimisation but others may know better than me. – Philip Couling Jun 07 '17 at 15:52
  • @PhilipCouling what i wanted to say is that afaik the fundamental C philosophy says that compiler doesn't make any decisions instead of you. If you want to pass reference/ponter - do it, you have language constructs for it. The optimization is only possible if final result is guaranteed to stay the same under all circumstances. Besides threading we can think of other undesired side effects of such optimization – mvidelgauz Jun 07 '17 at 15:58
  • @mvidelgauz Agreed. A better example than threading would be a function which accepts the same struct by value AND by reference. There's no way the compiler could guarantee what the side effects of the pass by reference will be, thus pass by value MUST be kept as pass by value. – Philip Couling Jun 07 '17 at 16:02
  • @mvidelgauz - Your comment is mostly correct but this part: `the fundamental C philosophy says that compiler doesn't make any decisions instead of you` is wrong. The compiler is allowed to every thing it wants to do as long as "the result" (aka side effects) stays the same. – Support Ukraine Jun 07 '17 at 16:07
  • `foo` is permitted to cast away `const` and modify its argument as long as the actual argument is not declared `const`. – n. m. could be an AI Jun 07 '17 at 16:13
  • @4386427 Under "making decisions" I meant changing observed results of program execution, but it's going to be terminology discussion, not for this place. Thanks for your comment :) – mvidelgauz Jun 07 '17 at 16:18
  • @mvidelgauz - Then we agree. Seems I misunderstood what you wanted to say. :) – Support Ukraine Jun 07 '17 at 16:21

1 Answers1

5

If you look here: Why isn't pass struct by reference a common optimization?

Its very unlikely that any C compiler will make this optimisation. It's generally not a safe thing to do.

Never assume your optimiser will do things the way you want. Optimisers have to conform to certain rules so that they never break your code. Sometimes you know something is safe when the optimiser cant. If, for performance, you need your code to behave a certain way then write it that way.

Philip Couling
  • 13,581
  • 5
  • 53
  • 85
  • 1
    In general: also if the specific compiler you are using does the optimization you are looking for, please don't assume that all the compiler does. @Philip said correclty: "if you need your code to behave a certain way then write it that way." – Stefano Buora Jun 07 '17 at 16:05
  • Thanks, great reference, for some reason I did not see that post. Also, remain calm everyone, I was naming gcc just to have a concrete example and I was *honestly* just curious. I will vow solemnly to [not help the compiler](https://youtu.be/AKtHxKJRwp4) ;-). – Jesko Hüttenhain Jun 07 '17 at 16:45