This is the mail archive of the binutils-cvs@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]

[binutils-gdb] [binutils, ARM, 8/16] BFL infrastructure with new global reloc R_ARM_THM_BF18


https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=1caf72a5849abf9a717ed3e0232abf591ff933e7

commit 1caf72a5849abf9a717ed3e0232abf591ff933e7
Author: Andre Vieira <andre.simoesdiasvieira@arm.com>
Date:   Mon Apr 15 11:37:51 2019 +0100

    [binutils, ARM, 8/16] BFL infrastructure with new global reloc R_ARM_THM_BF18
    
    This patch is part of a series of patches to add support for Armv8.1-M Mainline instructions to binutils.
    This adds infrastructure for the BFL instructions which is one of the first instructions in Arm that have more than one relocations in them.
    
    This adds a new relocation R_ARM_THM_BF18.
    
    The inconsistency between external R_ARM_THM_BF18 and internal
    BFD_RELOC_ARM_THUMB_BF19 is because internally we count the static bit-0 of the immediate and we don't externally.
    
    ChangeLog entries are as follows :
    
    *** bfd/ChangeLog ***
    
    2019-04-15  Sudakshina Das  <sudi.das@arm.com>
    
    	* reloc.c (BFD_RELOC_ARM_THUMB_BF19): New
    	* libbfd.h: Regenerated.
    	* bfd-in2.h: Regenerated.
    	* bfd-elf32-arm.c (elf32_arm_howto_table_1): New entry for R_ARM_THM_BF18.
    	(elf32_arm_reloc_map elf32_arm_reloc_map): Map BFD_RELOC_ARM_THUMB_BF19
    	and R_ARM_THM_BF18 together.
    	(elf32_arm_final_link_relocate): New switch case for R_ARM_THM_BF19.
    
    *** elfcpp/ChangeLog ***
    
    2019-04-15  Sudakshina Das  <sudi.das@arm.com>
    
    	* arm.h (R_ARM_THM_BF18): New relocation code.
    
    *** gas/ChangeLog ***
    
    2019-04-15  Sudakshina Das  <sudi.das@arm.com>
    
    	* config/tc-arm.c (md_pcrel_from_section): New switch case for
    	BFD_RELOC_ARM_THUMB_BF19.
    	(md_appdy_fix): Likewise.
    	(tc_gen_reloc): Likewise.
    
    *** include/ChangeLog ***
    
    2019-04-15  Sudakshina Das  <sudi.das@arm.com>
    
    	* elf/arm.h (START_RELOC_NUMBERS): New entry for R_ARM_THM_BF18.
    
    *** opcodes/ChangeLog ***
    
    2019-04-15  Sudakshina Das  <sudi.das@arm.com>
    
    	* arm-dis.c (print_insn_thumb32): Updated to accept new %Y pattern.

Diff:
---
 bfd/ChangeLog       | 10 +++++++++
 bfd/bfd-in2.h       |  3 +++
 bfd/elf32-arm.c     | 62 ++++++++++++++++++++++++++++++++++++++++++++++++++++-
 bfd/libbfd.h        |  1 +
 bfd/reloc.c         |  5 +++++
 elfcpp/ChangeLog    |  4 ++++
 elfcpp/arm.h        |  1 +
 gas/ChangeLog       |  7 ++++++
 gas/config/tc-arm.c | 35 ++++++++++++++++++++++++++++++
 include/ChangeLog   |  4 ++++
 include/elf/arm.h   |  1 +
 opcodes/ChangeLog   |  4 ++++
 opcodes/arm-dis.c   | 18 ++++++++++++++++
 13 files changed, 154 insertions(+), 1 deletion(-)

diff --git a/bfd/ChangeLog b/bfd/ChangeLog
index 992e570..59bb64d 100644
--- a/bfd/ChangeLog
+++ b/bfd/ChangeLog
@@ -1,5 +1,15 @@
 2019-04-15  Sudakshina Das  <sudi.das@arm.com>
 
+	* reloc.c (BFD_RELOC_ARM_THUMB_BF19): New
+	* libbfd.h: Regenerated.
+	* bfd-in2.h: Regenerated.
+	* bfd-elf32-arm.c (elf32_arm_howto_table_1): New entry for R_ARM_THM_BF18.
+	(elf32_arm_reloc_map elf32_arm_reloc_map): Map BFD_RELOC_ARM_THUMB_BF19
+	and R_ARM_THM_BF18 together.
+	(elf32_arm_final_link_relocate): New switch case for R_ARM_THM_BF19.
+
+2019-04-15  Sudakshina Das  <sudi.das@arm.com>
+
 	* reloc.c (BFD_RELOC_ARM_THUMB_BF17): New enum.
 	* bfd-in2.h: Regenerated.
 	* libbfd.h: Regenerated.
diff --git a/bfd/bfd-in2.h b/bfd/bfd-in2.h
index b5922ff..99b0db4 100644
--- a/bfd/bfd-in2.h
+++ b/bfd/bfd-in2.h
@@ -3570,6 +3570,9 @@ field in the instruction.  */
 /* ARM 17-bit pc-relative branch for Branch Future instructions.  */
   BFD_RELOC_ARM_THUMB_BF17,
 
+/* ARM 19-bit pc-relative branch for Branch Future Link instruction.  */
+  BFD_RELOC_ARM_THUMB_BF19,
+
 /* Thumb 7-, 9-, 12-, 20-, 23-, and 25-bit pc-relative branches.
 The lowest bit must be zero and is not stored in the instruction.
 Note that the corresponding ELF R_ARM_THM_JUMPnn constant has an
diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c
index 2a209da..456dc9d 100644
--- a/bfd/elf32-arm.c
+++ b/bfd/elf32-arm.c
@@ -1756,6 +1756,20 @@ static reloc_howto_type elf32_arm_howto_table_1[] =
 	 0x001f0ffe,		/* src_mask.  */
 	 0x001f0ffe,		/* dst_mask.  */
 	 TRUE),			/* pcrel_offset.  */
+  EMPTY_HOWTO (137),
+  HOWTO (R_ARM_THM_BF18,	/* type.  */
+	 0,			/* rightshift.  */
+	 1,			/* size (0 = byte, 1 = short, 2 = long).  */
+	 18,			/* bitsize.  */
+	 TRUE,			/* pc_relative.  */
+	 0,			/* bitpos.  */
+	 complain_overflow_dont,/* do not complain_on_overflow.  */
+	 bfd_elf_generic_reloc,	/* special_function.  */
+	 "R_ARM_THM_BF18",	/* name.  */
+	 FALSE,			/* partial_inplace.  */
+	 0x007f0ffe,		/* src_mask.  */
+	 0x007f0ffe,		/* dst_mask.  */
+	 TRUE),			/* pcrel_offset.  */
 };
 
 /* 160 onwards: */
@@ -2068,7 +2082,8 @@ static const struct elf32_arm_reloc_map elf32_arm_reloc_map[] =
     {BFD_RELOC_ARM_THUMB_ALU_ABS_G2_NC, R_ARM_THM_ALU_ABS_G2_NC},
     {BFD_RELOC_ARM_THUMB_ALU_ABS_G1_NC, R_ARM_THM_ALU_ABS_G1_NC},
     {BFD_RELOC_ARM_THUMB_ALU_ABS_G0_NC, R_ARM_THM_ALU_ABS_G0_NC},
-    {BFD_RELOC_ARM_THUMB_BF17, R_ARM_THM_BF16}
+    {BFD_RELOC_ARM_THUMB_BF17, R_ARM_THM_BF16},
+    {BFD_RELOC_ARM_THUMB_BF19, R_ARM_THM_BF18}
   };
 
 static reloc_howto_type *
@@ -12969,6 +12984,51 @@ elf32_arm_final_link_relocate (reloc_howto_type *	    howto,
 	return bfd_reloc_ok;
       }
 
+    case R_ARM_THM_BF18:
+      {
+	bfd_vma relocation;
+	bfd_vma upper_insn = bfd_get_16 (input_bfd, hit_data);
+	bfd_vma lower_insn = bfd_get_16 (input_bfd, hit_data + 2);
+
+	if (globals->use_rel)
+	  {
+	    bfd_vma immA  = (upper_insn & 0x007f);
+	    bfd_vma immB  = (lower_insn & 0x07fe) >> 1;
+	    bfd_vma immC  = (lower_insn & 0x0800) >> 11;
+	    addend  = (immA << 12);
+	    addend |= (immB << 2);
+	    addend |= (immC << 1);
+	    addend |= 1;
+	    /* Sign extend.  */
+	    addend = (addend & 0x40000) ? addend - (1 << 19) : addend;
+	  }
+
+	value = get_value_helper (plt_offset, splt, input_section, sym_sec, h,
+				  info, input_bfd, rel, sym_name, st_type,
+				  globals, unresolved_reloc_p);
+
+	relocation  = value + addend;
+	relocation -= (input_section->output_section->vma
+		       + input_section->output_offset
+		       + rel->r_offset);
+
+	/* Put RELOCATION back into the insn.  */
+	{
+	  bfd_vma immA = (relocation & 0x0007f000) >> 12;
+	  bfd_vma immB = (relocation & 0x00000ffc) >> 2;
+	  bfd_vma immC = (relocation & 0x00000002) >> 1;
+
+	  upper_insn = (upper_insn & 0xff80) | immA;
+	  lower_insn = (lower_insn & 0xf001) | (immC << 11) | (immB << 1);
+	}
+
+	/* Put the relocated value back in the object file:  */
+	bfd_put_16 (input_bfd, upper_insn, hit_data);
+	bfd_put_16 (input_bfd, lower_insn, hit_data + 2);
+
+	return bfd_reloc_ok;
+      }
+
     default:
       return bfd_reloc_notsupported;
     }
diff --git a/bfd/libbfd.h b/bfd/libbfd.h
index 4a3fa14..7f775ac 100644
--- a/bfd/libbfd.h
+++ b/bfd/libbfd.h
@@ -1531,6 +1531,7 @@ static const char *const bfd_reloc_code_real_names[] = { "@@uninitialized@@",
   "BFD_RELOC_ARM_PCREL_JUMP",
   "BFD_RELOC_THUMB_PCREL_BRANCH5",
   "BFD_RELOC_ARM_THUMB_BF17",
+  "BFD_RELOC_ARM_THUMB_BF19",
   "BFD_RELOC_THUMB_PCREL_BRANCH7",
   "BFD_RELOC_THUMB_PCREL_BRANCH9",
   "BFD_RELOC_THUMB_PCREL_BRANCH12",
diff --git a/bfd/reloc.c b/bfd/reloc.c
index b351d12..9e3899a 100644
--- a/bfd/reloc.c
+++ b/bfd/reloc.c
@@ -3025,6 +3025,11 @@ ENUMDOC
   ARM 17-bit pc-relative branch for Branch Future instructions.
 
 ENUM
+  BFD_RELOC_ARM_THUMB_BF19
+ENUMDOC
+  ARM 19-bit pc-relative branch for Branch Future Link instruction.
+
+ENUM
   BFD_RELOC_THUMB_PCREL_BRANCH7
 ENUMX
   BFD_RELOC_THUMB_PCREL_BRANCH9
diff --git a/elfcpp/ChangeLog b/elfcpp/ChangeLog
index 7770f7e..fab2744 100644
--- a/elfcpp/ChangeLog
+++ b/elfcpp/ChangeLog
@@ -1,5 +1,9 @@
 2019-04-15  Sudakshina Das  <sudi.das@arm.com>
 
+	* arm.h (R_ARM_THM_BF18): New relocation code.
+
+2019-04-15  Sudakshina Das  <sudi.das@arm.com>
+
 	* arm.h (R_ARM_THM_BF16): New relocation code.
 
 2018-06-24  Nick Clifton  <nickc@redhat.com>
diff --git a/elfcpp/arm.h b/elfcpp/arm.h
index b4cd67f..bc5e0cc 100644
--- a/elfcpp/arm.h
+++ b/elfcpp/arm.h
@@ -197,6 +197,7 @@ enum
   // 131 - 135			Unallocated
   // Relocations for Armv8.1-M Mainline (BF/BFL)
   R_ARM_THM_BF16 = 136,		// Static       Thumb32 ((S + A) | T) â?? P
+  R_ARM_THM_BF18 = 138,		// Static       Thumb32 ((S + A) | T) â?? P
   // 139			Unallocated
   // 140 - 159			Dynamic		Reserved for future allocation
   R_ARM_IRELATIVE = 160,	// Dynamic
diff --git a/gas/ChangeLog b/gas/ChangeLog
index 10aa757..2602aa3 100644
--- a/gas/ChangeLog
+++ b/gas/ChangeLog
@@ -1,5 +1,12 @@
 2019-04-15  Sudakshina Das  <sudi.das@arm.com>
 
+	* config/tc-arm.c (md_pcrel_from_section): New switch case for
+	BFD_RELOC_ARM_THUMB_BF19.
+	(md_appdy_fix): Likewise.
+	(tc_gen_reloc): Likewise.
+
+2019-04-15  Sudakshina Das  <sudi.das@arm.com>
+
 	* config/tc-arm.c (T16_32_TAB): New entries for bfx and bflx.
 	(do_t_v8_1_branch): New switch cases for bfx and bflx.
 	(insns): New instruction for bfx and bflx.
diff --git a/gas/config/tc-arm.c b/gas/config/tc-arm.c
index c7c1a82..177d90f 100644
--- a/gas/config/tc-arm.c
+++ b/gas/config/tc-arm.c
@@ -22924,6 +22924,7 @@ md_pcrel_from_section (fixS * fixP, segT seg)
     case BFD_RELOC_THUMB_PCREL_BRANCH20:
     case BFD_RELOC_THUMB_PCREL_BRANCH25:
     case BFD_RELOC_ARM_THUMB_BF17:
+    case BFD_RELOC_ARM_THUMB_BF19:
       return base + 4;
 
     case BFD_RELOC_THUMB_PCREL_BRANCH23:
@@ -24854,6 +24855,39 @@ md_apply_fix (fixS *	fixP,
 	}
       break;
 
+    case BFD_RELOC_ARM_THUMB_BF19:
+      if (fixP->fx_addsy
+	  && (S_GET_SEGMENT (fixP->fx_addsy) == seg)
+	  && !S_FORCE_RELOC (fixP->fx_addsy, TRUE)
+	  && ARM_IS_FUNC (fixP->fx_addsy)
+	  && ARM_CPU_HAS_FEATURE (selected_cpu, arm_ext_v8_1m_main))
+	{
+	  /* Force a relocation for a branch 19 bits wide.  */
+	  fixP->fx_done = 0;
+	}
+
+      if (v8_1_branch_value_check (value, 19, TRUE) == FAIL)
+	as_bad_where (fixP->fx_file, fixP->fx_line,
+		      BAD_BRANCH_OFF);
+
+      if (fixP->fx_done || !seg->use_rela_p)
+	{
+	  offsetT newval2;
+	  addressT immA, immB, immC;
+
+	  immA = (value & 0x0007f000) >> 12;
+	  immB = (value & 0x00000ffc) >> 2;
+	  immC = (value & 0x00000002) >> 1;
+
+	  newval   = md_chars_to_number (buf, THUMB_SIZE);
+	  newval2  = md_chars_to_number (buf + THUMB_SIZE, THUMB_SIZE);
+	  newval  |= immA;
+	  newval2 |= (immC << 11) | (immB << 1);
+	  md_number_to_chars (buf, newval, THUMB_SIZE);
+	  md_number_to_chars (buf + THUMB_SIZE, newval2, THUMB_SIZE);
+	}
+      break;
+
     case BFD_RELOC_ARM_V4BX:
       /* This will need to go in the object file.  */
       fixP->fx_done = 0;
@@ -25037,6 +25071,7 @@ tc_gen_reloc (asection *section, fixS *fixp)
     case BFD_RELOC_ARM_GOTOFFFUNCDESC:
     case BFD_RELOC_ARM_FUNCDESC:
     case BFD_RELOC_ARM_THUMB_BF17:
+    case BFD_RELOC_ARM_THUMB_BF19:
       code = fixp->fx_r_type;
       break;
 
diff --git a/include/ChangeLog b/include/ChangeLog
index f60e7a3..65bbac7 100644
--- a/include/ChangeLog
+++ b/include/ChangeLog
@@ -1,5 +1,9 @@
 2019-04-15  Sudakshina Das  <sudi.das@arm.com>
 
+	* elf/arm.h (START_RELOC_NUMBERS): New entry for R_ARM_THM_BF18.
+
+2019-04-15  Sudakshina Das  <sudi.das@arm.com>
+
 	* elf/arm.h (START_RELOC_NUMBERS): New entry for R_ARM_THM_BF16.
 
 2019-04-15  Thomas Preud'homme  <thomas.preudhomme@arm.com>
diff --git a/include/elf/arm.h b/include/elf/arm.h
index 2c6d4ef..b8f2d2f 100644
--- a/include/elf/arm.h
+++ b/include/elf/arm.h
@@ -242,6 +242,7 @@ START_RELOC_NUMBERS (elf_arm_reloc_type)
   RELOC_NUMBER (R_ARM_THM_ALU_ABS_G2_NC,134)
   RELOC_NUMBER (R_ARM_THM_ALU_ABS_G3_NC,135)
   RELOC_NUMBER (R_ARM_THM_BF16,		136)
+  RELOC_NUMBER (R_ARM_THM_BF18,		138)
 
   RELOC_NUMBER (R_ARM_IRELATIVE,      	160)
   RELOC_NUMBER (R_ARM_GOTFUNCDESC,    	161)
diff --git a/opcodes/ChangeLog b/opcodes/ChangeLog
index e4de1d7..edd03f8 100644
--- a/opcodes/ChangeLog
+++ b/opcodes/ChangeLog
@@ -1,5 +1,9 @@
 2019-04-15  Sudakshina Das  <sudi.das@arm.com>
 
+	* arm-dis.c (print_insn_thumb32): Updated to accept new %Y pattern.
+
+2019-04-15  Sudakshina Das  <sudi.das@arm.com>
+
 	* arm-dis.c (print_insn_thumb32): Add '%<bitfield>S' to print an
 	Arm register with r13 and r15 unpredictable.
 	(thumb32_opcodes): New instructions for bfx and bflx.
diff --git a/opcodes/arm-dis.c b/opcodes/arm-dis.c
index 08af171..b32ff32 100644
--- a/opcodes/arm-dis.c
+++ b/opcodes/arm-dis.c
@@ -2715,6 +2715,7 @@ static const struct opcode16 thumb_opcodes[] =
        %F		print the lsb and width fields of a sbfx/ubfx instruction
        %G		print a fallback offset for Branch Future instructions
        %W		print an offset for BF instruction
+       %Y		print an offset for BFL instruction
        %b		print a conditional branch offset
        %B		print an unconditional branch offset
        %s		print the shift field of an SSAT instruction
@@ -5898,6 +5899,23 @@ print_insn_thumb32 (bfd_vma pc, struct disassemble_info *info, long given)
 		}
 		break;
 
+	      case 'Y':
+		{
+		  unsigned int immA = (given & 0x007f0000u) >> 16;
+		  unsigned int immB = (given & 0x000007feu) >> 1;
+		  unsigned int immC = (given & 0x00000800u) >> 11;
+		  bfd_vma offset = 0;
+
+		  offset |= immA << 12;
+		  offset |= immB << 2;
+		  offset |= immC << 1;
+		  /* Sign extend.  */
+		  offset = (offset & 0x40000) ? offset - (1 << 19) : offset;
+
+		  info->print_address_func (pc + 4 + offset, info);
+		}
+		break;
+
 	      case 'b':
 		{
 		  unsigned int S = (given & 0x04000000u) >> 26;


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