This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [4.8 & 4.9] Backport of r211885


On Wed, Oct 08, 2014 at 11:00:24PM +0800, Felix Yang wrote:
> The enclosed patch for 4.8 & 4.9 branch is a backport of r211885 from trunk.
> 
> The only change is to use:
> 
> for (def_rec = DF_INSN_INFO_DEFS (insn_info); *def_rec; def_rec++)
> 
> other than the new FOR_EACH_INSN_INFO_DEF interface.
> 
> Bootstrapped on x86_64-SUSE-Linux for both branches. OK to apply?

ChangeLog entry is missing, plus description why do you want to backport it.
If it fixes a bug on the branches, it would be better to have a bugzilla
PR for that, and definitely a testcase.

> --- gcc/loop-invariant.c    (revision 216001)
> +++ gcc/loop-invariant.c    (working copy)
> @@ -839,6 +839,41 @@ check_dependencies (rtx insn, bitmap depends_on)
>    return true;
>  }
> 
> +/* Pre-check candidate DEST to skip the one which can not make a valid insn
> +   during move_invariant_reg.  SIMPLE is to skip HARD_REGISTER.  */
> +
> +static bool
> +pre_check_invariant_p (bool simple, rtx dest)
> +{
> +  if (simple && REG_P (dest) && DF_REG_DEF_COUNT (REGNO (dest)) > 1)
> +    {
> +      df_ref use;
> +      rtx ref;
> +      unsigned int i = REGNO (dest);
> +      struct df_insn_info *insn_info;
> +      df_ref *def_rec;
> +
> +      for (use = DF_REG_USE_CHAIN (i); use; use = DF_REF_NEXT_REG (use))
> +    {
> +      ref = DF_REF_INSN (use);
> +      insn_info = DF_INSN_INFO_GET (ref);
> +
> +      for (def_rec = DF_INSN_INFO_DEFS (insn_info); *def_rec; def_rec++)
> +        if (DF_REF_REGNO (*def_rec) == i)
> +          {
> +        /* Multi definitions at this stage, most likely are due to
> +           instruction constraints, which requires both read and write
> +           on the same register.  Since move_invariant_reg is not
> +           powerful enough to handle such cases, just ignore the INV
> +           and leave the chance to others.  */
> +        return false;
> +          }
> +    }
> +    }
> +
> +  return true;
> +}
> +
>  /* Finds invariant in INSN.  ALWAYS_REACHED is true if the insn is always
>     executed.  ALWAYS_EXECUTED is true if the insn is always executed,
>     unless the program ends due to a function call.  */
> @@ -869,6 +904,7 @@ find_invariant_insn (rtx insn, bool always_reached
>      simple = false;
> 
>    if (!may_assign_reg_p (SET_DEST (set))
> +      || !pre_check_invariant_p (simple, dest)
>        || !check_maybe_invariant (SET_SRC (set)))
>      return;
> 
> 
> Cheers,
> Felix

	Jakub


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]