* archures.c (bfd_mach_am33): Define.

* bfd-in2.h: Rebuilt.
        * cpu-m10300.c (bfd_am33_arch): Add to the mn103 architecture list
        * elf-m10300.c (mn10300_elf_relax_section): Handle am33 instructions.
        (compute_function_info): Handle additional registers saved by
        movm on the am33.
        (elf_mn10300_mach): Handle E_MN10300_MACH_AM33.
        (_bfd_mn10300_elf_final_write_processing): Handle bfd_mach_am33.
This commit is contained in:
Jeff Law 1999-12-01 10:14:02 +00:00
parent 0ed4f623e6
commit 31f8dc8fce
5 changed files with 189 additions and 3 deletions

View File

@ -1,3 +1,14 @@
Tue Nov 30 22:41:14 1999 Jeffrey A Law (law@cygnus.com)
* archures.c (bfd_mach_am33): Define.
* bfd-in2.h: Rebuilt.
* cpu-m10300.c (bfd_am33_arch): Add to the mn103 architecture list
* elf-m10300.c (mn10300_elf_relax_section): Handle am33 instructions.
(compute_function_info): Handle additional registers saved by
movm on the am33.
(elf_mn10300_mach): Handle E_MN10300_MACH_AM33.
(_bfd_mn10300_elf_final_write_processing): Handle bfd_mach_am33.
1999-11-29 Jim Blandy <jimb@cygnus.com> 1999-11-29 Jim Blandy <jimb@cygnus.com>
* elf.c (bfd_get_elf_phdrs, bfd_get_elf_phdr_upper_bound): New * elf.c (bfd_get_elf_phdrs, bfd_get_elf_phdr_upper_bound): New

View File

@ -188,6 +188,7 @@ DESCRIPTION
. bfd_arch_mn10200, {* Matsushita MN10200 *} . bfd_arch_mn10200, {* Matsushita MN10200 *}
. bfd_arch_mn10300, {* Matsushita MN10300 *} . bfd_arch_mn10300, {* Matsushita MN10300 *}
.#define bfd_mach_mn10300 300 .#define bfd_mach_mn10300 300
.#define bfd_mach_am33 330
. bfd_arch_fr30, . bfd_arch_fr30,
.#define bfd_mach_fr30 0x46523330 .#define bfd_mach_fr30 0x46523330
. bfd_arch_mcore, . bfd_arch_mcore,

View File

@ -1376,6 +1376,7 @@ enum bfd_architecture
bfd_arch_mn10200, /* Matsushita MN10200 */ bfd_arch_mn10200, /* Matsushita MN10200 */
bfd_arch_mn10300, /* Matsushita MN10300 */ bfd_arch_mn10300, /* Matsushita MN10300 */
#define bfd_mach_mn10300 300 #define bfd_mach_mn10300 300
#define bfd_mach_am33 330
bfd_arch_fr30, bfd_arch_fr30,
#define bfd_mach_fr30 0x46523330 #define bfd_mach_fr30 0x46523330
bfd_arch_mcore, bfd_arch_mcore,

View File

@ -21,7 +21,21 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
#include "sysdep.h" #include "sysdep.h"
#include "libbfd.h" #include "libbfd.h"
#define NEXT NULL const bfd_arch_info_type bfd_am33_arch =
{
32, /* 16 bits in a word */
32, /* 16 bits in an address */
8, /* 8 bits in a byte */
bfd_arch_mn10300,
330,
"am33",
"am33",
2,
false,
bfd_default_compatible,
bfd_default_scan ,
0,
};
const bfd_arch_info_type bfd_mn10300_arch = const bfd_arch_info_type bfd_mn10300_arch =
{ {
@ -36,6 +50,5 @@ const bfd_arch_info_type bfd_mn10300_arch =
true, /* the one and only */ true, /* the one and only */
bfd_default_compatible, bfd_default_compatible,
bfd_default_scan , bfd_default_scan ,
NEXT, &bfd_am33_arch,
}; };

View File

@ -1903,6 +1903,79 @@ mn10300_elf_relax_section (abfd, sec, link_info, again)
*again = true; *again = true;
} }
/* Try to turn a 24 immediate, displacement or absolute address
into a 8 immediate, displacement or absolute address. */
if (ELF32_R_TYPE (irel->r_info) == (int) R_MN10300_24)
{
bfd_vma value = symval;
value += irel->r_addend;
/* See if the value will fit in 8 bits. */
if ((long)value < 0x7f && (long)value > -0x80)
{
unsigned char code;
/* AM33 insns which have 24 operands are 6 bytes long and
will have 0xfd as the first byte. */
/* Get the first opcode. */
code = bfd_get_8 (abfd, contents + irel->r_offset - 3);
if (code == 0xfd)
{
/* Get the second opcode. */
code = bfd_get_8 (abfd, contents + irel->r_offset - 2);
/* We can not relax 0x6b, 0x7b, 0x8b, 0x9b as no 24bit
equivalent instructions exists. */
if (code != 0x6b && code != 0x7b
&& code != 0x8b && code != 0x9b
&& ((code & 0x0f) == 0x09 || (code & 0x0f) == 0x08
|| (code & 0x0f) == 0x0a || (code & 0x0f) == 0x0b
|| (code & 0x0f) == 0x0e))
{
/* Not safe if the high bit is on as relaxing may
move the value out of high mem and thus not fit
in a signed 8bit value. This is currently over
conservative. */
if ((value & 0x80) == 0)
{
/* Note that we've changed the relocation contents,
etc. */
elf_section_data (sec)->relocs = internal_relocs;
free_relocs = NULL;
elf_section_data (sec)->this_hdr.contents = contents;
free_contents = NULL;
symtab_hdr->contents = (bfd_byte *) extsyms;
free_extsyms = NULL;
/* Fix the opcode. */
bfd_put_8 (abfd, 0xfb, contents + irel->r_offset - 3);
bfd_put_8 (abfd, code, contents + irel->r_offset - 2);
/* Fix the relocation's type. */
irel->r_info
= ELF32_R_INFO (ELF32_R_SYM (irel->r_info),
R_MN10300_8);
/* Delete two bytes of data. */
if (!mn10300_elf_relax_delete_bytes (abfd, sec,
irel->r_offset + 1, 2))
goto error_return;
/* That will change things, so, we should relax
again. Note that this is not required, and it
may be slow. */
*again = true;
break;
}
}
}
}
}
/* Try to turn a 32bit immediate, displacement or absolute address /* Try to turn a 32bit immediate, displacement or absolute address
into a 16bit immediate, displacement or absolute address. */ into a 16bit immediate, displacement or absolute address. */
@ -1911,6 +1984,74 @@ mn10300_elf_relax_section (abfd, sec, link_info, again)
bfd_vma value = symval; bfd_vma value = symval;
value += irel->r_addend; value += irel->r_addend;
/* See if the value will fit in 24 bits.
We allow any 16bit match here. We prune those we can't
handle below. */
if ((long)value < 0x7fffff && (long)value > -0x800000)
{
unsigned char code;
/* AM33 insns which have 32bit operands are 7 bytes long and
will have 0xfe as the first byte. */
/* Get the first opcode. */
code = bfd_get_8 (abfd, contents + irel->r_offset - 3);
if (code == 0xfe)
{
/* Get the second opcode. */
code = bfd_get_8 (abfd, contents + irel->r_offset - 2);
/* All the am33 32 -> 24 relaxing possibilities. */
/* We can not relax 0x6b, 0x7b, 0x8b, 0x9b as no 24bit
equivalent instructions exists. */
if (code != 0x6b && code != 0x7b
&& code != 0x8b && code != 0x9b
&& ((code & 0x0f) == 0x09 || (code & 0x0f) == 0x08
|| (code & 0x0f) == 0x0a || (code & 0x0f) == 0x0b
|| (code & 0x0f) == 0x0e))
{
/* Not safe if the high bit is on as relaxing may
move the value out of high mem and thus not fit
in a signed 16bit value. This is currently over
conservative. */
if ((value & 0x8000) == 0)
{
/* Note that we've changed the relocation contents,
etc. */
elf_section_data (sec)->relocs = internal_relocs;
free_relocs = NULL;
elf_section_data (sec)->this_hdr.contents = contents;
free_contents = NULL;
symtab_hdr->contents = (bfd_byte *) extsyms;
free_extsyms = NULL;
/* Fix the opcode. */
bfd_put_8 (abfd, 0xfd, contents + irel->r_offset - 3);
bfd_put_8 (abfd, code, contents + irel->r_offset - 2);
/* Fix the relocation's type. */
irel->r_info
= ELF32_R_INFO (ELF32_R_SYM (irel->r_info),
R_MN10300_24);
/* Delete one byte of data. */
if (!mn10300_elf_relax_delete_bytes (abfd, sec,
irel->r_offset + 3, 1))
goto error_return;
/* That will change things, so, we should relax
again. Note that this is not required, and it
may be slow. */
*again = true;
break;
}
}
}
}
/* See if the value will fit in 16 bits. /* See if the value will fit in 16 bits.
We allow any 16bit match here. We prune those we can't We allow any 16bit match here. We prune those we can't
@ -2333,6 +2474,20 @@ compute_function_info (abfd, hash, addr, contents)
if (hash->movm_args & 0x08) if (hash->movm_args & 0x08)
hash->movm_stack_size += 8 * 4; hash->movm_stack_size += 8 * 4;
if (bfd_get_mach (abfd) == bfd_mach_am33)
{
/* "exother" space. e0, e1, mdrq, mcrh, mcrl, mcvf */
if (hash->movm_args & 0x1)
hash->movm_stack_size += 6 * 4;
/* exreg1 space. e4, e5, e6, e7 */
if (hash->movm_args & 0x2)
hash->movm_stack_size += 4 * 4;
/* exreg0 space. e2, e3 */
if (hash->movm_args & 0x4)
hash->movm_stack_size += 2 * 4;
}
} }
/* Now look for the two stack adjustment variants. */ /* Now look for the two stack adjustment variants. */
@ -2724,6 +2879,8 @@ elf_mn10300_mach (flags)
default: default:
return bfd_mach_mn10300; return bfd_mach_mn10300;
case E_MN10300_MACH_AM33:
return bfd_mach_am33;
} }
} }
@ -2746,6 +2903,9 @@ _bfd_mn10300_elf_final_write_processing (abfd, linker)
val = E_MN10300_MACH_MN10300; val = E_MN10300_MACH_MN10300;
break; break;
case bfd_mach_am33:
val = E_MN10300_MACH_AM33;
break;
} }
elf_elfheader (abfd)->e_flags &= ~ (EF_MN10300_MACH); elf_elfheader (abfd)->e_flags &= ~ (EF_MN10300_MACH);