public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
From: "meissner at gcc dot gnu.org" <gcc-bugzilla@gcc.gnu.org>
To: gcc-bugs@gcc.gnu.org
Subject: [Bug target/111778] New: PowerPC constant code change uses an undefined shift
Date: Thu, 12 Oct 2023 03:48:59 +0000	[thread overview]
Message-ID: <bug-111778-4@http.gcc.gnu.org/bugzilla/> (raw)

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

            Bug ID: 111778
           Summary: PowerPC constant code change uses an undefined shift
           Product: gcc
           Version: 14.0
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: target
          Assignee: unassigned at gcc dot gnu.org
          Reporter: meissner at gcc dot gnu.org
  Target Milestone: ---

I was building a cross compiler to PowerPC on my x86_86 workstation with the
latest version of GCC on October 11th.  I could not build the compiler on the
x86_64 system as it died in building libgcc.  I looked into it, and I
discovered the compiler was recursing until it ran out of stack space.  If I
build a native compiler with the same sources on a PowerPC system, it builds
fine.

I traced this down to a change made around October 10th:

commit 8f1a70a4fbcc6441c70da60d4ef6db1e5635e18a (HEAD)
Author: Jiufu Guo <guojiufu@linux.ibm.com>
Date:   Tue Jan 10 20:52:33 2023 +0800

    rs6000: build constant via li/lis;rldicl/rldicr

    If a constant is possible left/right cleaned on a rotated value from
    a negative value of "li/lis".  Then, using "li/lis ; rldicl/rldicr"
    to build the constant.

    gcc/ChangeLog:

            * config/rs6000/rs6000.cc (can_be_built_by_li_lis_and_rldicl): New
            function.
            (can_be_built_by_li_lis_and_rldicr): New function.
            (rs6000_emit_set_long_const): Call
can_be_built_by_li_lis_and_rldicr and
            can_be_built_by_li_lis_and_rldicl.

    gcc/testsuite/ChangeLog:

            * gcc.target/powerpc/const-build.c: Add more tests.


In particular, the code is:

static bool
can_be_built_by_li_lis_and_rldicl (HOST_WIDE_INT c, int *shift,
                                   HOST_WIDE_INT *mask)
{
  /* Leading zeros may be cleaned by rldicl with a mask.  Change leading zeros
     to ones and then recheck it.  */
  int lz = clz_hwi (c);
  HOST_WIDE_INT unmask_c
    = c | (HOST_WIDE_INT_M1U << (HOST_BITS_PER_WIDE_INT - lz));
  int n;

  if (can_be_rotated_to_lowbits (~unmask_c, 15, &n)
      || can_be_rotated_to_negative_lis (unmask_c, &n))
    {
      *mask = HOST_WIDE_INT_M1U >> lz;
      *shift = n == 0 ? 0 : HOST_BITS_PER_WIDE_INT - n;
      return true;
    }

  return false;
}

In particular, if lz is 0 due to the constant having the highest bit set, the
-1 shift to set the mask in unmask_c would do a shift left by 64.

Different machines interpret num << shift differently if shift is at least the
number of bits in num's representation.  It is explicitly undefined behavior in
the C/C++ langauges.

In particular (-1 << 64) on an x86_64 produces -1 and (-1 << 64) on a 64-bit
PowerPC produces 0.

If I add a test for lz being 0 and returning false, the compiler builds fine.

One other note is the ChangeLog date is not correct for Jiufu Guo's changes
that include this change.  The several changes that were submitted list dates
of:

Tue Jan 10 21:40:48 2023 +0800
Tue Jan 10 20:52:33 2023 +0800
Thu Jun 15 21:11:53 2023 +0800
Thu Aug 24 09:08:34 2023 +0800

             reply	other threads:[~2023-10-12  3:49 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-10-12  3:48 meissner at gcc dot gnu.org [this message]
2023-10-12  3:50 ` [Bug target/111778] " meissner at gcc dot gnu.org
2023-10-12  4:34 ` pinskia at gcc dot gnu.org
2023-10-12  6:22 ` guojiufu at gcc dot gnu.org
2023-10-12 20:19 ` cvs-commit at gcc dot gnu.org
2023-10-13  6:46 ` rguenth at gcc dot gnu.org
2023-10-13 15:03 ` [Bug target/111778] [14 Regression] " pinskia at gcc dot gnu.org
2023-10-13 15:04 ` pinskia at gcc dot gnu.org

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=bug-111778-4@http.gcc.gnu.org/bugzilla/ \
    --to=gcc-bugzilla@gcc.gnu.org \
    --cc=gcc-bugs@gcc.gnu.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
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).