Note that there are some explanatory texts on larger screens.

plurals
  1. POAre comma separated statements considered full statements? (and other diagnostic issues)
    primarykey
    data
    text
    <p>I guess the answer is "no", but from a compiler point of view, I don't understand why.</p> <p>I made a very simple code which freaks out compiler diagnostics quite badly (both clang and gcc), but I would like to have confirmation that the code is not ill formatted before I report mis-diagnostics. I should point out that these are <strong>not compiler bugs</strong>, the output is correct in all cases, but I have doubts about the warnings.</p> <p>Consider the following code:</p> <pre><code>#include &lt;iostream&gt; int main(){ int b,a; b = 3; b == 3 ? a = 1 : b = 2; b == 2 ? a = 2 : b = 1; a = a; std::cerr &lt;&lt; a &lt;&lt; std::endl; } </code></pre> <p>The assignment of <code>a</code> is a tautology, meaning that <code>a</code> will be initialized after the two ternary statements, regardless of <code>b</code>. GCC is perfectly happy with this code. Clang is slighly more clever and spot something silly (<code>warning: explicitly assigning a variable of type 'int' to itself [-Wself-assign]</code>), but no big deal.</p> <p>Now the same thing (semantically at least), but shorter syntax:</p> <pre><code>#include &lt;iostream&gt; int main(){ int b,a = (b=3, b == 3 ? a = 1 : b = 2, b == 2 ? a = 2 : b = 1, a); std::cerr &lt;&lt; a &lt;&lt; std::endl; } </code></pre> <p>Now the compilers give me completely different warnings. Clang doesn't report anything strange anymore (which is probably correct because of the parenthesis precedence). gcc is a bit more scary and says:</p> <pre><code>test.cpp: In function ‘int main()’: test.cpp:7:15: warning: operation on ‘a’ may be undefined [-Wsequence-point] </code></pre> <p>But is that true? That sequence-point warning gives me a hint that coma separated statements are not handled in the same way in practice, but I don't know if they should or not.</p> <p>And it gets weirder, changing the code to:</p> <pre><code>#include &lt;iostream&gt; int main(){ int b,a = (b=3, b == 3 ? a = 1 : b = 2, b == 2 ? a = 2 : b = 1, a+0); // &lt;- i just changed this line std::cerr &lt;&lt; a &lt;&lt; std::endl; } </code></pre> <p>and then suddenly clang realized that there might be something fishy with <code>a</code>:</p> <pre><code>test.cpp:7:14: warning: variable 'a' is uninitialized when used within its own initialization [-Wuninitialized] a+0); ^ </code></pre> <p>But there was no problem with <code>a</code> before... For some reasons clang cannot spot the tautology in this case. Again, it might simply be because those are not full statements anymore. </p> <p><strong>The problems are:</strong></p> <ul> <li>is this code valid and well defined (in all versions)?</li> <li>how is the list of comma separated statements handled? Should it be different from the first version of the code with explicit statements?</li> <li>is GCC right to report undefined behavior and sequence point issues? (in this case clang is missing some important diagnostics) I am aware that it says <strong>may</strong>, but still...</li> <li>is clang right to report that <code>a</code> might be uninitialized in the last case? (then it should have the same diagnostic for the previous case)</li> </ul> <p><strong>Edit and comments:</strong></p> <ul> <li>I am getting several (rightful) comments that this code is anything but simple. This is true, but the point is that the compilers mis-diagnose when they encounter comma-separated statements in initializers. This is a bad thing. I made my code more complete to avoid the <em>"have you tried this syntax..."</em> comments. A much more realistic and human readable version of the problem could be written, which would exhibit wrong diagnostics, but I think this version shows more information and is more complete.</li> <li>in a compiler-torture test suite, this would be considered very understandable and readable, they do much much worse :) We need code like that to test and assess compilers. This would not look pretty in production code, but that is not the point here.</li> </ul>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload