This is the mail archive of the binutils@sourceware.org mailing list for the binutils 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: [patch - gas] MIPS: fix problem with mips16 delay branch optimization.


David Ung <davidu@mips.com> writes:
> This patch fixes a problem for Mips16 delay branch optimization when
> swapping instructions, but the instructions belongs to different
> fragments.  This shows up in the GCC C regressions for mips16.

> *************** append_insn (struct mips_cl_insn *ip, ex
> *** 2698,2706 ****
>   	      struct mips_cl_insn delay = history[0];
>   	      if (mips_opts.mips16)
>   		{
> ! 		  know (delay.frag == ip->frag);
>   		  move_insn (ip, delay.frag, delay.where);
> ! 		  move_insn (&delay, ip->frag, ip->where + insn_length (ip));
>   		}
>   	      else if (relaxed_branch)
>   		{
> --- 2698,2719 ----
>   	      struct mips_cl_insn delay = history[0];
>   	      if (mips_opts.mips16)
>   		{
> ! 		  if (delay.frag == ip->frag)
> ! 		    {
>   		      move_insn (ip, delay.frag, delay.where);
> ! 		      move_insn (&delay, ip->frag, delay.where 
> ! 				 + insn_length (ip));
> ! 		    }
> ! 		  else if (insn_length (ip) == insn_length (&delay))
> ! 		    {
> ! 		      move_insn (&delay, ip->frag, ip->where);
> ! 		      move_insn (ip, history[0].frag, history[0].where);
> ! 		    }
> ! 		  else
> ! 		    {
> ! 		      add_fixed_insn (NOP_INSN);
> ! 		      delay = *NOP_INSN;
> ! 		    }
>   		}
>   	      else if (relaxed_branch)
>   		{

Can you explain the patch in more detail?  Do you have a reduced testcase?

In theory, the code adding the instruction is supposed to guarantee
that the frag has enough room to accomodate the branch:

      /* Make sure there is enough room to swap this instruction with
         a following jump instruction.  */
      frag_grow (6);
      add_fixed_insn (ip);

Presumably this code isn't triggering, or something else has decided
to close the frag between the previous instruction and the branch,
even though there was enough room.  If the latter, then how does
this happen?

Richard


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