public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition
@ 2023-06-27 17:03 jan.zizka at nokia dot com
  2023-06-27 17:13 ` [Bug c++/110437] " pinskia at gcc dot gnu.org
                   ` (12 more replies)
  0 siblings, 13 replies; 14+ messages in thread
From: jan.zizka at nokia dot com @ 2023-06-27 17:03 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

            Bug ID: 110437
           Summary: SIGILL when return missing in a C++ function with a
                    condition
           Product: gcc
           Version: 13.1.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c++
          Assignee: unassigned at gcc dot gnu.org
          Reporter: jan.zizka at nokia dot com
  Target Milestone: ---

Created attachment 55404
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=55404&action=edit
Reproducer fails with g++

With gcc 13 following code triggers SIGILL:

#include<iostream>

int func1() {
        int value = 1;
        if (value == 1) {
                std::cout << "ONE" << std::endl;
        } else {
                std::cout << "ZERO" << std::endl;
        }
}

int main() {
        func1();
}

To reproduce:

g++ -o reproduce reproduce.cpp
./reproduce

Resulting with:

ONE
[1]    19714 illegal hardware instruction (core dumped)  ./reproduce

Warning is generated by compiler:

reproduce.cpp: In function ‘int func1()’:
reproduce.cpp:10:1: warning: no return statement in function returning non-void
[-Wreturn-type]
   10 | }
      | ^

With similar C code the SIGILL is not triggered:

#include<stdio.h>

int func1() {
        int value = 1;
        if (value == 1) {
                printf("ONE\n");
        } else {
                printf("ZERO\n");
        }
}

int main() {
        func1();
}

Warning is still generated with -Wall.

Is there some reason this behaves differently in C and C++? And shouldn't
rather compiler throw error instead of warning if this will crash in runtime?
We have caught this on some very old legacy code which just had missing return
statement and with upgrade to gcc 13.1.1 we have started to see SIGILL in
runtime.

Based on disassembled code the compiler emits ud2 instruction triggering
SIGILL.

With gcc 12.2 at least the same code doesn't trigger SIGILL. I didn't check the
disassembly.

I have run this on Fedora 38 and I didn't try to bisect which exact commit
triggers this. If it would be useful I can run bisect.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
@ 2023-06-27 17:13 ` pinskia at gcc dot gnu.org
  2023-06-27 17:19 ` pinskia at gcc dot gnu.org
                   ` (11 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-06-27 17:13 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

Andrew Pinski <pinskia at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|UNCONFIRMED                 |RESOLVED
         Resolution|---                         |INVALID

--- Comment #1 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
>reproduce.cpp:10:1: warning: no return statement in function returning non-void [-Wreturn-type]


Yes it is undefined code (at runtime) if the code falls through from a function
which has a non-void return type for C++. The rules for C is slightly
different, it is only undefined if the return value from the function is tried
to be used.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
  2023-06-27 17:13 ` [Bug c++/110437] " pinskia at gcc dot gnu.org
@ 2023-06-27 17:19 ` pinskia at gcc dot gnu.org
  2023-06-27 17:28 ` jan.zizka at nokia dot com
                   ` (10 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-06-27 17:19 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #2 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
>With gcc 12.2 at least the same code doesn't trigger SIGILL.

Well in GCC 13+ at -O0 and -Og, GCC behavior changed from being fully undefined
to be trapping for folks to try to catch instead of saying they were seeing odd
behavior.

GCC 8+ changed the behavior to become unreachable:
https://gcc.gnu.org/gcc-8/porting_to.html

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
  2023-06-27 17:13 ` [Bug c++/110437] " pinskia at gcc dot gnu.org
  2023-06-27 17:19 ` pinskia at gcc dot gnu.org
@ 2023-06-27 17:28 ` jan.zizka at nokia dot com
  2023-06-27 17:30 ` pinskia at gcc dot gnu.org
                   ` (9 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: jan.zizka at nokia dot com @ 2023-06-27 17:28 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #3 from Jan Žižka <jan.zizka at nokia dot com> ---
Good thanks for pointer and clarification.

Is there some reason this cannot be caught during compile time already? I mean
the warning should be an error maybe? It would be much easier to fix in legacy
code.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (2 preceding siblings ...)
  2023-06-27 17:28 ` jan.zizka at nokia dot com
@ 2023-06-27 17:30 ` pinskia at gcc dot gnu.org
  2023-06-27 17:31 ` pinskia at gcc dot gnu.org
                   ` (8 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-06-27 17:30 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #4 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
-Werror=return-type

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (3 preceding siblings ...)
  2023-06-27 17:30 ` pinskia at gcc dot gnu.org
@ 2023-06-27 17:31 ` pinskia at gcc dot gnu.org
  2023-06-27 17:46 ` jan.zizka at nokia dot com
                   ` (7 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-06-27 17:31 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #5 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
(In reply to Jan Žižka from comment #3)
> Good thanks for pointer and clarification.
> 
> Is there some reason this cannot be caught during compile time already? I
> mean the warning should be an error maybe? It would be much easier to fix in
> legacy code.

Well it is undefined behavior at runtime (not at compile time) so rejecting it
would not be a valid thing to do.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (4 preceding siblings ...)
  2023-06-27 17:31 ` pinskia at gcc dot gnu.org
@ 2023-06-27 17:46 ` jan.zizka at nokia dot com
  2023-06-27 17:52 ` pinskia at gcc dot gnu.org
                   ` (6 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: jan.zizka at nokia dot com @ 2023-06-27 17:46 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #6 from Jan Žižka <jan.zizka at nokia dot com> ---
Thanks ;-) hope this BZ will at least help others if they hit the same thing to
understand the reasoning.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (5 preceding siblings ...)
  2023-06-27 17:46 ` jan.zizka at nokia dot com
@ 2023-06-27 17:52 ` pinskia at gcc dot gnu.org
  2023-06-27 18:02 ` jan.zizka at nokia dot com
                   ` (5 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: pinskia at gcc dot gnu.org @ 2023-06-27 17:52 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

Andrew Pinski <pinskia at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
         Resolution|INVALID                     |DUPLICATE

--- Comment #7 from Andrew Pinski <pinskia at gcc dot gnu.org> ---
(In reply to Jan Žižka from comment #6)
> Thanks ;-) hope this BZ will at least help others if they hit the same thing
> to understand the reasoning.

Not really ...

*** This bug has been marked as a duplicate of bug 86761 ***

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (6 preceding siblings ...)
  2023-06-27 17:52 ` pinskia at gcc dot gnu.org
@ 2023-06-27 18:02 ` jan.zizka at nokia dot com
  2023-06-27 20:10 ` redi at gcc dot gnu.org
                   ` (4 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: jan.zizka at nokia dot com @ 2023-06-27 18:02 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #8 from Jan Žižka <jan.zizka at nokia dot com> ---
Well then I apologize for stealing your time. I did try to search both BZ and
Internet and didn't hit any hints as what is happening and why exactly with gcc
13 if gcc 12 didn't "catch" these. I need to work on my search skills.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (7 preceding siblings ...)
  2023-06-27 18:02 ` jan.zizka at nokia dot com
@ 2023-06-27 20:10 ` redi at gcc dot gnu.org
  2023-06-27 20:22 ` jan.zizka at nokia dot com
                   ` (3 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: redi at gcc dot gnu.org @ 2023-06-27 20:10 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #9 from Jonathan Wakely <redi at gcc dot gnu.org> ---
The trap was added for PR 104642 because people keep ignoring the -Wreturn-type
warning and then complaining that the code misbehaves.

Of course now people complain that they prefer the unpredictable undefined
behaviour instead of predictable trapping.

You can't please everybody.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (8 preceding siblings ...)
  2023-06-27 20:10 ` redi at gcc dot gnu.org
@ 2023-06-27 20:22 ` jan.zizka at nokia dot com
  2023-06-28  7:55 ` xry111 at gcc dot gnu.org
                   ` (2 subsequent siblings)
  12 siblings, 0 replies; 14+ messages in thread
From: jan.zizka at nokia dot com @ 2023-06-27 20:22 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #10 from Jan Žižka <jan.zizka at nokia dot com> ---
Ah I didn't really complain, this is fine by me and I'm happy we can catch
these. The code 
 and build configuration, which hit this, was not touched for 20 years :-) so
any help is welcome for us at least.

For me it is enough that this is not possible to catch by compilation error. I
agree -Werror should be used, but for such old code base as ours noone is
really going to modify the flags :-) ... so then crashing is better then
invisibility.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (9 preceding siblings ...)
  2023-06-27 20:22 ` jan.zizka at nokia dot com
@ 2023-06-28  7:55 ` xry111 at gcc dot gnu.org
  2023-06-28  8:02 ` jan.zizka at nokia dot com
  2023-06-28  8:32 ` redi at gcc dot gnu.org
  12 siblings, 0 replies; 14+ messages in thread
From: xry111 at gcc dot gnu.org @ 2023-06-28  7:55 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

Xi Ruoyao <xry111 at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |xry111 at gcc dot gnu.org

--- Comment #11 from Xi Ruoyao <xry111 at gcc dot gnu.org> ---
(In reply to Jan Žižka from comment #3)
> Good thanks for pointer and clarification.
> 
> Is there some reason this cannot be caught during compile time already? I
> mean the warning should be an error maybe? It would be much easier to fix in
> legacy code.

Note that -Werror=return-type cannot be the default because...

int f(int a)
{
  if (a == 1)
    return 0xdead;
  else if (a == 42)
    return 0xbeef;
}

is perfectly legal if the caller doesn't pass anything other than 1 or 42 to f.
 So we cannot just reject it at the compile time, we can only issue a warning.

And generally there is no way to determine if an "unsupported" value is passed
to f at compile time because doing so will need to solve the halting problem.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (10 preceding siblings ...)
  2023-06-28  7:55 ` xry111 at gcc dot gnu.org
@ 2023-06-28  8:02 ` jan.zizka at nokia dot com
  2023-06-28  8:32 ` redi at gcc dot gnu.org
  12 siblings, 0 replies; 14+ messages in thread
From: jan.zizka at nokia dot com @ 2023-06-28  8:02 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #12 from Jan Žižka <jan.zizka at nokia dot com> ---
(In reply to Xi Ruoyao from comment #11)
> is perfectly legal if the caller doesn't pass anything other than 1 or 42 to
> f.  So we cannot just reject it at the compile time, we can only issue a
> warning.

True that, still this doesn't make it sound software implementation :-)

Another example pointed out by one colleague of mine:

int f(int a)
{
  if (a == 1)
    exit(0);
  else
    return 0xbeef;
}

> And generally there is no way to determine if an "unsupported" value is
> passed to f at compile time because doing so will need to solve the halting
> problem.

That is true :-) but from software implementation if you reuse such a function
or it is a library I'd personally disallow this as this is bad coding. But this
will be opinionated so better not to dive to such a rabbit hole.

Thanks for comments.

^ permalink raw reply	[flat|nested] 14+ messages in thread

* [Bug c++/110437] SIGILL when return missing in a C++ function with a condition
  2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
                   ` (11 preceding siblings ...)
  2023-06-28  8:02 ` jan.zizka at nokia dot com
@ 2023-06-28  8:32 ` redi at gcc dot gnu.org
  12 siblings, 0 replies; 14+ messages in thread
From: redi at gcc dot gnu.org @ 2023-06-28  8:32 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=110437

--- Comment #13 from Jonathan Wakely <redi at gcc dot gnu.org> ---
(In reply to Jan Žižka from comment #12)
> Another example pointed out by one colleague of mine:
> 
> int f(int a)
> {
>   if (a == 1)
>     exit(0);

exit is marked noreturn so the compiler knows this function never reaches the
end without returning. But a user-defined function like "log_and_exit" might
not be marked noreturn, so the same argument applies there. The code is
correct, but the compiler can't prove it, so it can't give an error by default.


> That is true :-) but from software implementation if you reuse such a
> function or it is a library I'd personally disallow this as this is bad
> coding. But this will be opinionated so better not to dive to such a rabbit
> hole.

Right, the C++ standard isn't based on opinions. If you want to disallow it,
you can use -Werror=return-type. That can't be the default though.

^ permalink raw reply	[flat|nested] 14+ messages in thread

end of thread, other threads:[~2023-06-28  8:32 UTC | newest]

Thread overview: 14+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-06-27 17:03 [Bug c++/110437] New: SIGILL when return missing in a C++ function with a condition jan.zizka at nokia dot com
2023-06-27 17:13 ` [Bug c++/110437] " pinskia at gcc dot gnu.org
2023-06-27 17:19 ` pinskia at gcc dot gnu.org
2023-06-27 17:28 ` jan.zizka at nokia dot com
2023-06-27 17:30 ` pinskia at gcc dot gnu.org
2023-06-27 17:31 ` pinskia at gcc dot gnu.org
2023-06-27 17:46 ` jan.zizka at nokia dot com
2023-06-27 17:52 ` pinskia at gcc dot gnu.org
2023-06-27 18:02 ` jan.zizka at nokia dot com
2023-06-27 20:10 ` redi at gcc dot gnu.org
2023-06-27 20:22 ` jan.zizka at nokia dot com
2023-06-28  7:55 ` xry111 at gcc dot gnu.org
2023-06-28  8:02 ` jan.zizka at nokia dot com
2023-06-28  8:32 ` redi at gcc dot gnu.org

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).