ср, 26 авг. 2026 г. в 08:36, Richard Biener <[email protected]>:
>
> On Tue, Aug 25, 2026 at 2:31 PM Oleg Tolmatcev <[email protected]> 
> wrote:
> >
> > вт, 25 авг. 2026 г. в 12:45, Richard Biener <[email protected]>:
> > >
> > > On Mon, Aug 24, 2026 at 10:12 PM Oleg Tolmatcev
> > > <[email protected]> wrote:
> > > >
> > > > Targets that cannot realign the stack cap their stack alignment and rely
> > > > on the middle end to align over-aligned stack objects inside their 
> > > > slots.
> > > > Win64 SEH caps MAX_STACK_ALIGNMENT at 128 bits; aarch64 does not define
> > > > MAX_STACK_ALIGNMENT at all and is capped at STACK_BOUNDARY, also 128.
> > > >
> > > > In several places the middle end does not do that alignment.  A 256-bit
> > > > vector requires 32-byte alignment, its slot gets the capped 16 bytes, 
> > > > and
> > > > MEM_ALIGN is set to 32 anyway.  x86 selects vmovaps from MEM_ALIGN and
> > > > faults on the under-aligned slot (PR54412, MSYS2/MINGW-packages#1209).
> > > > There is an even bigger problem.  Even with MEM_ALIGN and the slot's
> > > > alignment consistent, an escaped pointer loses the information about the
> > > > alignment cap: GCC assumes the object's natural alignment and uses an
> > > > aligned access on an under-aligned object, which faults on x86.
> > > >
> > > > aarch64 does not crash only because its loads and stores do not fault on
> > > > a misaligned address; the object is under-aligned there just the same.
> > > >
> > > > Add assign_stack_local_aligned, which preserves the requested alignment 
> > > > by
> > > > overallocating a slot and aligning an address inside it, and use it
> > > > wherever an object gets a stack slot of its own.  This is what
> > > > assign_parm_setup_block already did for BLKmode parameters and what
> > > > expand_stack_vars does for locals.  Such a slot has no fixed frame 
> > > > offset,
> > > > so it cannot be reused as a temp slot.
> > > >
> > > > Finally, defer_stack_allocation and expand_one_stack_var_1 computed a
> > > > local's stack alignment in two different ways, so a variable the former
> > > > considered small enough to allocate immediately could trip the
> > > > large-alignment assert in the latter (PR target/120192).  Use
> > > > align_local_variable in both.
> > > >
> > > > Regtested on x86_64-pc-linux-gnu and, under QEMU, on
> > > > aarch64-unknown-linux-gnu, with no new failures.
> > > >
> > > > gcc/ChangeLog:
> > > >
> > > >         PR target/54412
> > > >         PR target/120192
> > > >         * cfgexpand.cc (defer_stack_allocation): Use 
> > > > align_local_variable
> > > >         to compute the alignment, matching expand_one_stack_var_1.
> > > >         * function.cc (assign_stack_local_aligned): New function, split
> > > >         out of assign_parm_setup_block.
> > > >         (assign_stack_temp_for_type): Compute the required alignment 
> > > > from
> > > >         the type and the mode.  Allocate an over-aligned temporary with
> > > >         assign_stack_local_aligned and give it no temp_slot entry.  Take
> > > >         the resulting alignment from the allocated slot.
> > > >         (assign_parm_setup_block): Use assign_stack_local_aligned.
> > > >         (assign_parm_setup_reg): Likewise.
> > > >         (assign_parm_setup_stack): Likewise.
> > > >
> > > > Signed-off-by: Oleg Tolmatcev <[email protected]>
> > > > ---
> > > >  gcc/cfgexpand.cc |  8 +++--
> > > >  gcc/function.cc  | 87 +++++++++++++++++++++++++++++++++++-------------
> > > >  2 files changed, 68 insertions(+), 27 deletions(-)
> > > >
> > > > diff --git a/gcc/cfgexpand.cc b/gcc/cfgexpand.cc
> > > > index 128cfc7768..8720b77ced 100644
> > > > --- a/gcc/cfgexpand.cc
> > > > +++ b/gcc/cfgexpand.cc
> > > > @@ -1995,9 +1995,11 @@ defer_stack_allocation (tree var, bool toplevel)
> > > >    if (flag_stack_protect || asan_sanitize_stack_p ())
> > > >      return true;
> > > >
> > > > -  unsigned int align = TREE_CODE (var) == SSA_NAME
> > > > -    ? TYPE_ALIGN (TREE_TYPE (var))
> > > > -    : DECL_ALIGN (var);
> > > > +  /* Keep this in sync with expand_one_stack_var_1.  For some targets,
> > > > +     LOCAL_DECL_ALIGNMENT can raise a local variable's effective stack
> > > > +     alignment above DECL_ALIGN, and immediate allocation would then
> > > > +     trip the high-alignment assert in expand_one_stack_var_1.  */
> > > > +  unsigned int align = align_local_variable (var, false) * 
> > > > BITS_PER_UNIT;
> > >
> > > If you do only this change, which cases improve and why is this not 
> > > sufficient
> > > as fix?  I'm mostly looking for a possibility to split up the change and 
> > > clearly
> > > associate test coverage with fix parts here.
> > >
> > > Thanks,
> > > Richard.
> >
> > With only this change, pr54412-pr120192.c passes; all the other new
> > tests still fail. It
> > fixes only the PR120192 ICE by making defer_stack_allocation use the same
> > alignment calculation as expand_one_stack_var_1. It does not fix the
> > under-aligned
> > slots created through assign_stack_local.
> > I could split this change and its test into a separate PR120192 patch.
>
> Please do that.  This is a quite fragile area, so it's best to divide changes 
> up
> as much as possible.
>
> Richard.

Done. I split the changes for PR 120192 into a separate patch and sent
it to the mailing list.

Do you want me to send an updated version of this patch?

Oleg

Reply via email to