summaryrefslogtreecommitdiff
path: root/bfd/coff-arm.c
diff options
context:
space:
mode:
authorNick Clifton <nickc@redhat.com>1999-12-17 00:42:32 +0000
committerNick Clifton <nickc@redhat.com>1999-12-17 00:42:32 +0000
commitaf74ae991108b49f86a03724bfb401b7363890bd (patch)
tree7d54517001be63af0812b9409036b0d4ebea43ac /bfd/coff-arm.c
parent7d7a673645f1ead2b07a4dac03031068123279f5 (diff)
downloadbinutils-af74ae991108b49f86a03724bfb401b7363890bd.tar.gz
binutils-af74ae991108b49f86a03724bfb401b7363890bd.tar.bz2
binutils-af74ae991108b49f86a03724bfb401b7363890bd.zip
catch bad arm relocs
Diffstat (limited to 'bfd/coff-arm.c')
-rw-r--r--bfd/coff-arm.c36
1 files changed, 26 insertions, 10 deletions
diff --git a/bfd/coff-arm.c b/bfd/coff-arm.c
index a7938257b42..b778017358b 100644
--- a/bfd/coff-arm.c
+++ b/bfd/coff-arm.c
@@ -47,6 +47,10 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#define SET_INTERWORK_FLAG( abfd, flg ) (coff_data (abfd)->flags = \
(coff_data (abfd)->flags & ~ F_INTERWORK) \
| (flg | F_INTERWORK_SET))
+
+#ifndef NUM_ELEM
+#define NUM_ELEM(a) ((sizeof (a)) / sizeof ((a)[0]))
+#endif
typedef enum {bunknown, b9, b12, b23} thumb_pcrel_branchtype;
/* some typedefs for holding instructions */
@@ -402,6 +406,8 @@ static reloc_howto_type aoutarm_std_reloc_howto[] =
PCRELOFFSET),
};
+#define NUM_RELOCS NUM_ELEM (aoutarm_std_reloc_howto)
+
#ifdef COFF_WITH_PE
/* Return true if this relocation should
appear in the output .reloc section. */
@@ -415,9 +421,11 @@ in_reloc_p (abfd, howto)
}
#endif
-
-#define RTYPE2HOWTO(cache_ptr, dst) \
- (cache_ptr)->howto = aoutarm_std_reloc_howto + (dst)->r_type;
+#define RTYPE2HOWTO(cache_ptr, dst) \
+ (cache_ptr)->howto = \
+ (dst)->r_type < NUM_RELOCS \
+ ? aoutarm_std_reloc_howto + (dst)->r_type \
+ : NULL
#define coff_rtype_to_howto coff_arm_rtype_to_howto
@@ -430,17 +438,17 @@ coff_arm_rtype_to_howto (abfd, sec, rel, h, sym, addendp)
struct internal_syment *sym ATTRIBUTE_UNUSED;
bfd_vma *addendp;
{
- reloc_howto_type *howto;
+ reloc_howto_type * howto;
+ if (rel->r_type >= NUM_RELOCS)
+ return NULL;
+
howto = aoutarm_std_reloc_howto + rel->r_type;
if (rel->r_type == ARM_RVA32)
- {
- *addendp -= pe_data(sec->output_section->owner)->pe_opthdr.ImageBase;
- }
+ *addendp -= pe_data(sec->output_section->owner)->pe_opthdr.ImageBase;
return howto;
-
}
/* Used by the assembler. */
@@ -698,7 +706,8 @@ coff_arm_reloc_type_lookup (abfd, code)
bfd * abfd;
bfd_reloc_code_real_type code;
{
-#define ASTD(i,j) case i: return &aoutarm_std_reloc_howto[j]
+#define ASTD(i,j) case i: return aoutarm_std_reloc_howto + j
+
if (code == BFD_RELOC_CTOR)
switch (bfd_get_arch_info (abfd)->bits_per_address)
{
@@ -1900,7 +1909,7 @@ bfd_arm_process_before_allocation (abfd, info, support_old_code)
for (rel = i; rel < i + sec->reloc_count; ++rel)
{
unsigned short r_type = rel->r_type;
- long symndx;
+ unsigned long symndx;
struct coff_link_hash_entry * h;
symndx = rel->r_symndx;
@@ -1909,6 +1918,13 @@ bfd_arm_process_before_allocation (abfd, info, support_old_code)
if (symndx == -1)
continue;
+ if (symndx >= obj_conv_table_size (abfd))
+ {
+ _bfd_error_handler (_("%s: illegal symbol index in reloc: %d"),
+ bfd_get_filename (abfd), symndx);
+ continue;
+ }
+
h = obj_coff_sym_hashes (abfd)[symndx];
/* If the relocation is against a static symbol it must be within