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

            Bug ID: 116806
           Summary: gcc.dg/cpp/charconst-3.c breakage on 16-bit targets
           Product: gcc
           Version: 14.2.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: testsuite
          Assignee: unassigned at gcc dot gnu.org
          Reporter: mikpelinux at gmail dot com
  Target Milestone: ---

The following is adapted from gcc.dg/cpp/charconst-3.c:

==snip==
void foo (int);
void __attribute__ ((__noreturn__)) _exit (int);

#define A '\234b'
#define B ((int) ((unsigned char) '\234' * scale + (unsigned char) 'b'))

int main (void)
{
    int scale = 256;

    foo (A);
    foo (B);
    if (A != B)
        _exit (1);

    return 0;
}
==snip==

Compiling this for a 16-bit target shows that (1) A and B evaluate to the same
runtime value, but (2) the two are statically considered to be different
causing an unconditional call to _exit.

Taking xstormy16 as an example, this is what gcc-14.2 generates for main:

main:
        mov.w r2,#-25502
        callf foo
        mov.w r2,#-25502
        callf foo
        mov.w r2,#1
        callf _exit

i.e., the values are the same yet somehow different. Other 16-bit targets show
the exact same pattern (tested avr, msp430, pdp11, rl78, and xstormy16).

Compiling for x86-64 shows different behaviour:

main:
.LFB0:
        .cfi_startproc
        pushq   %rax
        .cfi_def_cfa_offset 16
        movl    $40034, %edi
        call    foo
        movl    $40034, %edi
        call    foo
        xorl    %eax, %eax
        popq    %rdx
        .cfi_def_cfa_offset 8
        ret

A and B still evaluate to the same runtime value, but this time gcc realizes
this and does not emit a call to _exit.

Found when debugging this test case on an out-of-tree port to a 16-bit target.

Reply via email to