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

--- Comment #4 from Wilco <wdijkstr at arm dot com> ---
(In reply to Bernd Edlinger from comment #3)
> (In reply to Wilco from comment #2)
> > (In reply to Bernd Edlinger from comment #1)
> > > some background about this bug can be found here:
> > > 
> > > https://gcc.gnu.org/ml/gcc-patches/2016-10/msg01561.html
> > 
> > The <shift>di3_neon pattern does not constrain the input not to overlap with
> > the output for immediate shifts, and the arm_emit_coreregs_64bit_shift code
> > does not handle partial overlaps. However it is feasible to fix that by
> > swapping the order for the various cases.
> 
> from <shift>di3_neon:
> 
>             if (INTVAL (operands[2]) < 1)
>               {
>                 emit_insn (gen_movdi (operands[0], operands[1]));
>                 DONE;
>               }
> 
> Will the movdi pattern work with partial overlaps?
> It does basically this:
> 
>       emit_move_insn (gen_lowpart (SImode, operands[0]),
>                       gen_lowpart (SImode, operands[1]));
>       emit_move_insn (gen_highpart (SImode, operands[0]),
>                       gen_highpart (SImode, operands[1]));

I think it's OK - that code only triggers if a movdi has a physical register
that is not a valid DI register which is not the case we're dealing with. movdi
has a split that does check for partial overlap around line 5900 in arm.md:

  /* Handle a partial overlap.  */
  if (rtx_equal_p (operands[0], operands[3]))
     ...

However dealing with partial overlaps is complex so maybe the best option would
be to add alternatives to <shift>di3_neon to either allow full overlap "r 0 X X
X" or no overlap "&r r X  X X". The shift code works with full overlap.

Reply via email to