This is the mail archive of the binutils@sources.redhat.com 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: MIPS patch to correct the size of %neg() fixups


Richard Sandiford wrote:
[snip]
> It sounds like you're saying that:
> 
>         R_MIPS_GPREL16
>         R_MIPS_SUB
>         R_MIPS_HI16
> 
> should be treated as having a 64-bit relocation field, but that's
> exactly what I'm trying to avoid. ;)
> 
> The ABI says:
> 
>     The implication [...] is that a relocation type consists of two
>     components.  The first component is the operation to be
>     performed [...].  The second component is a specification of
>     field to be relocated, which is relevant only for the first
>     operation in the sequence (where it may specify an addend for
>     the Elf64_Rel relocation) and the last operation in a sequence
>     (where it specifies the field rewritten by the relocation).

Ah, thanks, I had missed this.

Another thing: At least the FIXME about RSS_* values should be retained,
so I prefer a patch like the one below.


Thiemo


diff -urpNX /bigdisk/src/gcc-exclude source-orig/gas/config/tc-mips.c source/gas/config/tc-mips.c
--- source-orig/gas/config/tc-mips.c	Tue Jun 10 17:05:26 2003
+++ source/gas/config/tc-mips.c	Wed Jun 11 12:49:42 2003
@@ -2154,15 +2173,22 @@ append_insn (place, ip, address_expr, re
 	}
       else
 	{
-	  reloc_howto_type *howto;
-
 	need_reloc:
 	  /* Don't generate a reloc if we are writing into a variant frag.  */
 	  if (place == NULL)
 	    {
-	      howto = bfd_reloc_type_lookup (stdoutput, reloc_type[0]);
+	      reloc_howto_type *howto;
+	      int i;
+
+	      /* In a compound relocation, it is the final (outermost)
+		 operator that determines the relocated field.  */
+	      for (i = 1; i < 3; i++)
+	      if (reloc_type[i] == BFD_RELOC_UNUSED)
+		break;
+
+	      howto = bfd_reloc_type_lookup (stdoutput, reloc_type[i - 1]);
 	      fixp[0] = fix_new_exp (frag_now, f - frag_now->fr_literal,
-				     bfd_get_reloc_size(howto),
+				     bfd_get_reloc_size (howto),
 				     address_expr,
 				     reloc_type[0] == BFD_RELOC_16_PCREL_S2,
 				     reloc_type[0]);
@@ -2216,31 +2242,9 @@ append_insn (place, ip, address_expr, re
 		  address_expr->X_add_number = 0;
 
 		  howto = bfd_reloc_type_lookup (stdoutput, reloc_type[1]);
-		  fixp[1] = fix_new_exp (frag_now, f - frag_now->fr_literal,
-					 bfd_get_reloc_size(howto),
-					 address_expr, FALSE, reloc_type[1]);
-
-		  /* These relocations can have an addend that won't fit in
-		     4 octets for 64bit assembly.  */
-		  if (HAVE_64BIT_GPRS
-		      && ! howto->partial_inplace
-		      && (reloc_type[1] == BFD_RELOC_16
-			  || reloc_type[1] == BFD_RELOC_32
-			  || reloc_type[1] == BFD_RELOC_MIPS_JMP
-			  || reloc_type[1] == BFD_RELOC_HI16_S
-			  || reloc_type[1] == BFD_RELOC_LO16
-			  || reloc_type[1] == BFD_RELOC_GPREL16
-			  || reloc_type[1] == BFD_RELOC_MIPS_LITERAL
-			  || reloc_type[1] == BFD_RELOC_GPREL32
-			  || reloc_type[1] == BFD_RELOC_64
-			  || reloc_type[1] == BFD_RELOC_CTOR
-			  || reloc_type[1] == BFD_RELOC_MIPS_SUB
-			  || reloc_type[1] == BFD_RELOC_MIPS_HIGHEST
-			  || reloc_type[1] == BFD_RELOC_MIPS_HIGHER
-			  || reloc_type[1] == BFD_RELOC_MIPS_SCN_DISP
-			  || reloc_type[1] == BFD_RELOC_MIPS_REL16
-			  || reloc_type[1] == BFD_RELOC_MIPS_RELGOT))
-		    fixp[1]->fx_no_overflow = 1;
+		  fixp[1] = fix_new_exp (frag_now, fixp[0]->fx_where,
+					 fixp[0]->fx_size, address_expr,
+					 FALSE, reloc_type[1]);
 
 		  if (reloc_type[2] != BFD_RELOC_UNUSED)
 		    {
@@ -2249,33 +2253,9 @@ append_insn (place, ip, address_expr, re
 		      address_expr->X_add_number = 0;
 
 		      howto = bfd_reloc_type_lookup (stdoutput, reloc_type[2]);
-		      fixp[2] = fix_new_exp (frag_now,
-					     f - frag_now->fr_literal,
-					     bfd_get_reloc_size(howto),
-					     address_expr, FALSE,
-					     reloc_type[2]);
-
-		      /* These relocations can have an addend that won't fit in
-			 4 octets for 64bit assembly.  */
-		      if (HAVE_64BIT_GPRS
-			  && ! howto->partial_inplace
-			  && (reloc_type[2] == BFD_RELOC_16
-			      || reloc_type[2] == BFD_RELOC_32
-			      || reloc_type[2] == BFD_RELOC_MIPS_JMP
-			      || reloc_type[2] == BFD_RELOC_HI16_S
-			      || reloc_type[2] == BFD_RELOC_LO16
-			      || reloc_type[2] == BFD_RELOC_GPREL16
-			      || reloc_type[2] == BFD_RELOC_MIPS_LITERAL
-			      || reloc_type[2] == BFD_RELOC_GPREL32
-			      || reloc_type[2] == BFD_RELOC_64
-			      || reloc_type[2] == BFD_RELOC_CTOR
-			      || reloc_type[2] == BFD_RELOC_MIPS_SUB
-			      || reloc_type[2] == BFD_RELOC_MIPS_HIGHEST
-			      || reloc_type[2] == BFD_RELOC_MIPS_HIGHER
-			      || reloc_type[2] == BFD_RELOC_MIPS_SCN_DISP
-			      || reloc_type[2] == BFD_RELOC_MIPS_REL16
-			      || reloc_type[2] == BFD_RELOC_MIPS_RELGOT))
-			fixp[2]->fx_no_overflow = 1;
+		      fixp[2] = fix_new_exp (frag_now, fixp[0]->fx_where,
+					     fixp[0]->fx_size, address_expr,
+					     FALSE, reloc_type[2]);
 		    }
 		}
 	    }


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