From 6bba1048d63e0476b94b9934527defd81c590a13 Mon Sep 17 00:00:00 2001 From: Dave Anglin Date: Thu, 28 Aug 2008 02:33:45 +0000 Subject: [PATCH] * elf-hppa.h (elf_hppa_reloc_final_type): Handle R_PARISC_GPREL64, R_PARISC_SEGREL32 and R_PARISC_SEGREL64. * som.c (som_fixup_formats): Add R_DATA_GPREL fixup. (som_hppa_howto_table): Likewise. (hppa_som_gen_reloc_type): In case R_HPPA_GOTOFF, detect R_DATA_GPREL final type. (som_write_fixups): Handle R_DATA_GPREL. * config/tc-hppa.c (is_SB_relative): New macro. (fix_new_hppa): Remove $segrel$ marker. (cons_fix_new_hppa): Set reloc type R_PARISC_SEGREL32 if expression is segment relative. * config/tc-hppa.h (tc_frob_symbol): Check for $segrel$. --- bfd/ChangeLog | 10 ++++++++++ bfd/elf-hppa.h | 42 +++++++++++++++++++++++++++++++++++++++++- bfd/som.c | 27 ++++++++++++++++++++++++--- gas/ChangeLog | 8 ++++++++ gas/config/tc-hppa.c | 7 +++++++ gas/config/tc-hppa.h | 1 + 6 files changed, 91 insertions(+), 4 deletions(-) diff --git a/bfd/ChangeLog b/bfd/ChangeLog index 6912012628..fbd71321fd 100644 --- a/bfd/ChangeLog +++ b/bfd/ChangeLog @@ -1,3 +1,13 @@ +2008-08-27 John David Anglin + + * elf-hppa.h (elf_hppa_reloc_final_type): Handle R_PARISC_GPREL64, + R_PARISC_SEGREL32 and R_PARISC_SEGREL64. + * som.c (som_fixup_formats): Add R_DATA_GPREL fixup. + (som_hppa_howto_table): Likewise. + (hppa_som_gen_reloc_type): In case R_HPPA_GOTOFF, detect R_DATA_GPREL + final type. + (som_write_fixups): Handle R_DATA_GPREL. + 2008-08-26 Nick Clifton * elf32-arm.c: Fix up comment describing Thumb to ARM interworking diff --git a/bfd/elf-hppa.h b/bfd/elf-hppa.h index d2b5dfd663..0aff4ccc71 100644 --- a/bfd/elf-hppa.h +++ b/bfd/elf-hppa.h @@ -745,6 +745,17 @@ elf_hppa_reloc_final_type (bfd *abfd, } break; + case 64: + switch (field) + { + case e_fsel: + final_type = R_PARISC_GPREL64; + break; + default: + return R_PARISC_NONE; + } + break; + default: return R_PARISC_NONE; } @@ -930,9 +941,38 @@ elf_hppa_reloc_final_type (bfd *abfd, } break; + case R_PARISC_SEGREL32: + switch (format) + { + case 32: + switch (field) + { + case e_fsel: + final_type = R_PARISC_SEGREL32; + break; + default: + return R_PARISC_NONE; + } + break; + + case 64: + switch (field) + { + case e_fsel: + final_type = R_PARISC_SEGREL64; + break; + default: + return R_PARISC_NONE; + } + break; + + default: + return R_PARISC_NONE; + } + break; + case R_PARISC_GNU_VTENTRY: case R_PARISC_GNU_VTINHERIT: - case R_PARISC_SEGREL32: case R_PARISC_SEGBASE: /* The defaults are fine for these cases. */ break; diff --git a/bfd/som.c b/bfd/som.c index f9aed1628b..360819dc68 100644 --- a/bfd/som.c +++ b/bfd/som.c @@ -353,7 +353,7 @@ static const struct fixup_format som_fixup_formats[256] = /* R_DATA_ONE_SYMBOL. */ { 0, "L4=Sb=" }, /* 0x25 */ { 1, "L4=Sd=" }, /* 0x26 */ - /* R_DATA_PLEBEL. */ + /* R_DATA_PLABEL. */ { 0, "L4=Sb=" }, /* 0x27 */ { 1, "L4=Sd=" }, /* 0x28 */ /* R_SPACE_REF. */ @@ -437,8 +437,9 @@ static const struct fixup_format som_fixup_formats[256] = { 31, "L4=SD=" }, /* 0x6f */ { 32, "L4=Sb=" }, /* 0x70 */ { 33, "L4=Sd=" }, /* 0x71 */ + /* R_DATA_GPREL. */ + { 0, "L4=Sd=" }, /* 0x72 */ /* R_RESERVED. */ - { 0, "" }, /* 0x72 */ { 0, "" }, /* 0x73 */ { 0, "" }, /* 0x74 */ { 0, "" }, /* 0x75 */ @@ -825,7 +826,7 @@ static reloc_howto_type som_hppa_howto_table[] = SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"), SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"), SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"), - SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"), + SOM_HOWTO (R_DATA_GPREL, "R_DATA_GPREL"), SOM_HOWTO (R_RESERVED, "R_RESERVED"), SOM_HOWTO (R_RESERVED, "R_RESERVED"), SOM_HOWTO (R_RESERVED, "R_RESERVED"), @@ -1571,6 +1572,8 @@ hppa_som_gen_reloc_type (bfd *abfd, || field == e_lpsel || field == e_rpsel) *final_type = R_DATA_PLABEL; + else if (field == e_fsel && format == 32) + *final_type = R_DATA_GPREL; break; case R_HPPA_COMPLEX: @@ -2799,6 +2802,24 @@ som_write_fixups (bfd *abfd, abort (); break; + case R_DATA_GPREL: + /* Account for any addend. */ + if (bfd_reloc->addend) + p = som_reloc_addend (abfd, bfd_reloc->addend, p, + &subspace_reloc_size, reloc_queue); + + if (sym_num < 0x10000000) + { + bfd_put_8 (abfd, bfd_reloc->howto->type, p); + bfd_put_8 (abfd, sym_num >> 16, p + 1); + bfd_put_16 (abfd, (bfd_vma) sym_num, p + 2); + p = try_prev_fixup (abfd, &subspace_reloc_size, + p, 4, reloc_queue); + } + else + abort (); + break; + case R_DATA_ONE_SYMBOL: case R_DATA_PLABEL: case R_CODE_PLABEL: diff --git a/gas/ChangeLog b/gas/ChangeLog index 5e63625076..d953475d86 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,11 @@ +2008-08-27 John David Anglin + + * config/tc-hppa.c (is_SB_relative): New macro. + (fix_new_hppa): Remove $segrel$ marker. + (cons_fix_new_hppa): Set reloc type R_PARISC_SEGREL32 if expression is + segment relative. + * config/tc-hppa.h (tc_frob_symbol): Check for $segrel$. + 2008-08-27 Jan Beulich * config/tc-i386.c (check_string): Use register_prefix for error diff --git a/gas/config/tc-hppa.c b/gas/config/tc-hppa.c index 5f6efbda6f..da84526fa9 100644 --- a/gas/config/tc-hppa.c +++ b/gas/config/tc-hppa.c @@ -1050,6 +1050,10 @@ static struct default_space_dict pa_def_spaces[] = ((exp).X_op == O_subtract \ && strcmp (S_GET_NAME ((exp).X_op_symbol), "$global$") == 0) +#define is_SB_relative(exp) \ + ((exp).X_op == O_subtract \ + && strcmp (S_GET_NAME ((exp).X_op_symbol), "$segrel$") == 0) + #define is_PC_relative(exp) \ ((exp).X_op == O_subtract \ && strcmp (S_GET_NAME ((exp).X_op_symbol), "$PIC_pcrel$0") == 0) @@ -1233,6 +1237,7 @@ fix_new_hppa (fragS *frag, it now so as not to confuse write.c. Ditto for $PIC_pcrel$0. */ if (new_fix->fx_subsy && (strcmp (S_GET_NAME (new_fix->fx_subsy), "$global$") == 0 + || strcmp (S_GET_NAME (new_fix->fx_subsy), "$segrel$") == 0 || strcmp (S_GET_NAME (new_fix->fx_subsy), "$PIC_pcrel$0") == 0 || strcmp (S_GET_NAME (new_fix->fx_subsy), "$tls_gdidx$") == 0 || strcmp (S_GET_NAME (new_fix->fx_subsy), "$tls_ldidx$") == 0 @@ -1256,6 +1261,8 @@ cons_fix_new_hppa (fragS *frag, int where, int size, expressionS *exp) else if (is_PC_relative (*exp)) rel_type = R_HPPA_PCREL_CALL; #ifdef OBJ_ELF + else if (is_SB_relative (*exp)) + rel_type = R_PARISC_SEGREL32; else if (is_tls_gdidx (*exp)) rel_type = R_PARISC_TLS_GD21L; else if (is_tls_ldidx (*exp)) diff --git a/gas/config/tc-hppa.h b/gas/config/tc-hppa.h index b53527b0c7..393a1440ac 100644 --- a/gas/config/tc-hppa.h +++ b/gas/config/tc-hppa.h @@ -175,6 +175,7 @@ int hppa_fix_adjustable (struct fix *); || (S_GET_SEGMENT (sym) == &bfd_abs_section \ && ! S_IS_EXTERNAL (sym)) \ || strcmp (S_GET_NAME (sym), "$global$") == 0 \ + || strcmp (S_GET_NAME (sym), "$segrel$") == 0 \ || strcmp (S_GET_NAME (sym), "$PIC_pcrel$0") == 0 \ || strcmp (S_GET_NAME (sym), "$tls_gdidx$") == 0 \ || strcmp (S_GET_NAME (sym), "$tls_ldidx$") == 0 \ -- 2.34.1