On 10/05/2023 16:14, Eli Zaretskii via Gcc wrote:
Date: Wed, 10 May 2023 14:41:27 +0200
Cc: jwakely....@gmail.com, fwei...@redhat.com, gcc@gcc.gnu.org,
  ar...@aarsen.me
From: Gabriel Ravier <gabrav...@gmail.com>

Because GCC is capable of compiling it.
That is not a good argument.  GCC is capable of compiling any code in all
the reported accepts-invalid bugs on which it doesn't ICE.  That doesn't
mean those bugs shouldn't be fixed.
Fixing those bugs, if they are bugs, is not the job of the compiler.
It's the job of the programmer, who is the one that knows what the
code was supposed to do.  If there's a significant risk that the code
is a mistake or might behave in problematic ways, a warning to that
effect is more than enough.

Are you seriously saying that no accepts-invalid bug should ever be
fixed under any circumstances on the basis that some programmers might
rely on code exploiting that bug ??

Sorry, I'm afraid I don't understand the question.  What are
"accepts-invalid bugs"?


They are cases where the C standards (plus documented gcc extensions) have syntax or constraint requirements, but code which breaks these requirements is accepted by the compiler. For example, if the compiler accepted "long long long int" as a type, that would be an "accepts-invalid" bug. They are important for two reasons. One is that they mean the compiler fails to help the developer catch the mistake in their code. The other is that the code might have an inconsistent interpretation, and that might change in the future. In the hypothetical example of a three-long int, a current compiler might treat it as a "long long", while a future standard might add support for it as a new type with minimum 128-bit size.

In any case, I was not not talking about bug-compatibility, I was
talking about being able to compile code which GCC was able to compile
in past versions.  Being able to compile that code is not a bug, it's
a feature.


No, being able to compile /incorrect/ code by default is a bug. It is not helpful.

(The compiler cannot, of course, spot /all/ mistakes - the gcc developers are a smart group, but I think asking them to solve the Halting Problem is a bit much!)

I've seen this kind of argument many times - "The compiler used to accept my code and give the results I wanted, and now newer compiler versions make a mess of it". The cause is almost invariably undefined behaviour, but it can occasionally be through changes to the standards such as removal of old behaviour or other differences in the interpretation of code (there were a number of incompatibilities between K&R and C90, and between C90 and C99).

The compiler is under /no/ obligation to compile undefined behaviour in the same way as it might have done for a particular piece of code. It is under /no/ obligation to continue to accept incorrect or invalid code, just because it used to accept it. It /is/ - IMHO - under an obligation to do what it can to help spot problems in code and help developers get good quality correct code in the end. If it fails to do that, people will, and should, move to using different tools.

New compiler versions are not required to do two's complement wrapping of signed integer overflow, even though old broken code might have been written under the assumption that it did and even though older, less powerful versions of the compiler might have compiled that code into something the developer wanted. In the same way, new compiler versions are not required to support syntax that has been dead for decades - at least not by default. (Unlike most other compilers, gcc developers go far out of their way to support such outdated and incorrect code - all they ask is that people use non-default flags to get such non-standard syntax and semantics.)

If the gcc developers really were required to continue to compile /all/ programs that compiled before, with the same results, then the whole gcc project can be stopped. The only way to ensure perfect backwards compatibility would be to stop development, and no longer release any new versions of the compiler. That is the logical consequence of "it used to compile (with defaults or a given set of flags), so it should continue to compile (with these same flags)" - assuming "compile" here means "giving the same resulting behaviour in the executable" rather than just "giving an executable that may or may not work".

Clearly, you don't mean gcc development should stop. That means a line must be drawn, and some code that compiled with older gcc will not compile with newer gcc. The only question is where the line should be.




Reply via email to