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

--- Comment #7 from GCC Commits <cvs-commit at gcc dot gnu.org> ---
The releases/gcc-16 branch has been updated by Kyrylo Tkachov
<[email protected]>:

https://gcc.gnu.org/g:3e5af3a489291ed5adba26132351ae6c59d6d629

commit r16-9425-g3e5af3a489291ed5adba26132351ae6c59d6d629
Author: Kyrylo Tkachov <[email protected]>
Date:   Sun Jul 26 01:48:55 2026 -0700

    out-of-SSA: Use all partition names to find the decl to split [PR126405]

    split_overlapping_partition_decls gives every partition but one of a
    memory-resident VAR_DECL its own artificial decl, so that distinct stack
slots
    do not end up sharing a MEM_EXPR.  It takes the variable of a partition
from
    that partition's representative.  set_rtl attaches the base variable of any
    name in a partition to that partition's location, so the variable a
partition
    is given need not be the one of its representative.

    Here the partition holding the loop-carried versions of an oversized vector
    temporary has an anonymous representative:

      Partition 1  (_2 - 2 14 16 )        _2 has no base variable, while
                                          14 and 16 are g18_lsm.11_14 and _16
      Partition 30 (g18_lsm.11_41 - 41 )

    Partition 1 is skipped because SSA_NAME_VAR of _2 is null, so partition 30
    believes it is the only partition of g18_lsm.11 and keeps the user decl. 
Both
    128 byte slots then get MEM_EXPR g18_lsm.11.  The load/store pair-fusion
pass
    groups accesses by MEM_EXPR base and MEM_OFFSET, so it treated two stores
that
    are 144 bytes apart as adjacent and fused them:

      before  (set (mem:V4SI [sp+240]) (reg v17))   ; g18_lsm.11+96
              (set (mem:V4SI [sp+384]) (reg v27))   ; g18_lsm.11+112

      after   (set (mem:V2x16QI [sp+240])
                   (unspec [(reg v17) (reg v27)] UNSPEC_STP))

    [sp+384] is never written.

    Work out the variable each partition will be given and key the keep/split
    decision on that, reusing the function set_rtl makes the same choice with,
    renamed to expand_leader_merge now.
    That function keeps the variable it is given first unless
    a later one is DECL_IGNORED_P, and expansion hands set_rtl the
representative
    before the other names, so the representative's variable goes in first.
    A partition holding names of two variables would otherwise be keyed on the
    wrong one.

    Bootstrapped and tested on aarch64-none-linux-gnu.

    gcc/ChangeLog:

            PR middle-end/126405
            * cfgexpand.cc (leader_merge): Rename to...
            (expand_leader_merge): ...this.  Make external.
            * cfgexpand.h (expand_leader_merge): Declare.
            * tree-outof-ssa.cc: Include cfgexpand.h.
            (split_overlapping_partition_decls): Determine the variable of a
            partition from all of its names.

    gcc/testsuite/ChangeLog:

            PR middle-end/126405
            * gcc.c-torture/execute/pr126405.c: New test.
            * gcc.c-torture/execute/pr126405-2.c: New test.
            * gcc.dg/pr126405-1.c: New test.
            * gcc.dg/pr126405-2.c: New test.
            * gcc.dg/pr126405-3.c: New test.

    Signed-off-by: Kyrylo Tkachov <[email protected]>
    (cherry picked from commit 6f8fff34e8d854c3f66b2b7c9c64e973a71661cb)

Reply via email to