2005-08-12 Dmitry Diky <diwil@spec.ru>
* config/tc-msp430.c (msp430_enable_relax): New flag. (msp430_enable_polys): Likewise. (OPTION_RELAX): New option. (OPTION_POLYMORPHS): Likewise. (md_longopts): New long options. (md_show_usage): Updated. (md_parse_option): Add new options handler. (msp430_operands): Add check if polymorph insns are enabled. (msp430_force_relocation_local): New function. (md_apply_fix): Now delete relocs according to new flags combination. (msp430_relax_frag): Convert long branches to short branches only if flag msp430_enable_relax is set. * config/tc-msp430.h (TC_FORCE_RELOCATION_LOCAL): Defined. (msp430_force_relocation_local): Likewise. * doc/c-msp430.texi: Describe new options.
This commit is contained in:
parent
fa9ee72b80
commit
77592908ee
@ -1,3 +1,20 @@
|
||||
2005-08-12 Dmitry Diky <diwil@spec.ru>
|
||||
* config/tc-msp430.c (msp430_enable_relax): New flag.
|
||||
(msp430_enable_polys): Likewise.
|
||||
(OPTION_RELAX): New option.
|
||||
(OPTION_POLYMORPHS): Likewise.
|
||||
(md_longopts): New long options.
|
||||
(md_show_usage): Updated.
|
||||
(md_parse_option): Add new options handler.
|
||||
(msp430_operands): Add check if polymorph insns are enabled.
|
||||
(msp430_force_relocation_local): New function.
|
||||
(md_apply_fix): Now delete relocs according to new flags combination.
|
||||
(msp430_relax_frag): Convert long branches to short branches only if
|
||||
flag msp430_enable_relax is set.
|
||||
* config/tc-msp430.h (TC_FORCE_RELOCATION_LOCAL): Defined.
|
||||
(msp430_force_relocation_local): Likewise.
|
||||
* doc/c-msp430.texi: Describe new options.
|
||||
|
||||
2005-08-11 Ian Lance Taylor <ian@airs.com>
|
||||
|
||||
* Makefile.am ($(srcdir)/make-gas.com): Remove target.
|
||||
|
@ -31,6 +31,49 @@
|
||||
#include "opcode/msp430.h"
|
||||
#include "safe-ctype.h"
|
||||
|
||||
/*
|
||||
We will disable polymorphs by default because it is dangerous.
|
||||
The potencial problem here is the following: assume we got the
|
||||
following code:
|
||||
|
||||
jump .l1
|
||||
nop
|
||||
jump subroutine ; external symbol
|
||||
.l1:
|
||||
nop
|
||||
ret
|
||||
|
||||
In case of assembly time relaxation we'll get:
|
||||
0: jmp .l1 <.text +0x08> (reloc deleted)
|
||||
2: nop
|
||||
4: br subroutine
|
||||
.l1:
|
||||
8: nop
|
||||
10: ret
|
||||
|
||||
If the 'subroutine' wiys thin +-1024 bytes range then linker
|
||||
will produce
|
||||
0: jmp .text +0x08
|
||||
2: nop
|
||||
4: jmp subroutine
|
||||
.l1:
|
||||
6: nop
|
||||
8: ret ; 'jmp .text +0x08' will land here. WRONG!!!
|
||||
|
||||
|
||||
The workaround is the following:
|
||||
1. Declare global var enable_polymorphs which set to 1 via option -mP.
|
||||
2. Declare global var enable_relax which set to 1 via option -mQ.
|
||||
|
||||
If polymorphs are enabled, and relax isn't, treat all jumps as long jumps,
|
||||
do not delete any relocs and leave them for linker.
|
||||
|
||||
If relax is enabled, relax at assembly time and kill relocs as necessary.
|
||||
*/
|
||||
|
||||
int msp430_enable_relax;
|
||||
int msp430_enable_polys;
|
||||
|
||||
/* GCC uses the some condition codes which we'll
|
||||
implement as new polymorph instructions.
|
||||
|
||||
@ -660,6 +703,8 @@ extract_word (char * from, char * to, int limit)
|
||||
}
|
||||
|
||||
#define OPTION_MMCU 'm'
|
||||
#define OPTION_RELAX 'Q'
|
||||
#define OPTION_POLYMORPHS 'P'
|
||||
|
||||
static void
|
||||
msp430_set_arch (int dummy ATTRIBUTE_UNUSED)
|
||||
@ -709,6 +754,17 @@ md_parse_option (int c, char * arg)
|
||||
as_fatal (_("redefinition of mcu type %s' to %s'"),
|
||||
msp430_mcu->name, mcu_types[i].name);
|
||||
return 1;
|
||||
break;
|
||||
|
||||
case OPTION_RELAX:
|
||||
msp430_enable_relax = 1;
|
||||
return 1;
|
||||
break;
|
||||
|
||||
case OPTION_POLYMORPHS:
|
||||
msp430_enable_polys = 1;
|
||||
return 1;
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
@ -727,6 +783,8 @@ const char *md_shortopts = "m:";
|
||||
struct option md_longopts[] =
|
||||
{
|
||||
{"mmcu", required_argument, NULL, OPTION_MMCU},
|
||||
{"mP", no_argument, NULL, OPTION_POLYMORPHS},
|
||||
{"mQ", no_argument, NULL, OPTION_RELAX},
|
||||
{NULL, no_argument, NULL, 0}
|
||||
};
|
||||
|
||||
@ -758,6 +816,9 @@ md_show_usage (FILE * stream)
|
||||
" msp430xG437 msp430xG438 msp430G439\n"
|
||||
" msp430x435 msp430x436 msp430x437\n"
|
||||
" msp430x447 msp430x448 msp430x449\n"));
|
||||
fprintf (stream,
|
||||
_(" -mQ - enable relaxation at assembly time. DANGEROUS!\n"
|
||||
" -mP - enable polymorph instructions\n"));
|
||||
|
||||
show_mcu_list (stream);
|
||||
}
|
||||
@ -1683,6 +1744,12 @@ msp430_operands (struct msp430_opcode_s * opcode, char * line)
|
||||
break;
|
||||
|
||||
case 4: /* Extended jumps. */
|
||||
if (!msp430_enable_polys)
|
||||
{
|
||||
as_bad(_("polymorphs are not enabled. Use -mP option to enable."));
|
||||
break;
|
||||
}
|
||||
|
||||
line = extract_operand (line, l1, sizeof (l1));
|
||||
if (l1[0])
|
||||
{
|
||||
@ -1714,6 +1781,11 @@ msp430_operands (struct msp430_opcode_s * opcode, char * line)
|
||||
break;
|
||||
|
||||
case 5: /* Emulated extended branches. */
|
||||
if (!msp430_enable_polys)
|
||||
{
|
||||
as_bad(_("polymorphs are not enabled. Use -mP option to enable."));
|
||||
break;
|
||||
}
|
||||
line = extract_operand (line, l1, sizeof (l1));
|
||||
if (l1[0])
|
||||
{
|
||||
@ -1820,9 +1892,24 @@ md_pcrel_from_section (fixS * fixp, segT sec)
|
||||
return fixp->fx_frag->fr_address + fixp->fx_where;
|
||||
}
|
||||
|
||||
/* Replaces standard TC_FORCE_RELOCATION_LOCAL.
|
||||
Now it handles the situation when relocations
|
||||
have to be passed to linker. */
|
||||
int
|
||||
msp430_force_relocation_local(fixS *fixp)
|
||||
{
|
||||
if (msp430_enable_polys
|
||||
&& !msp430_enable_relax)
|
||||
return 1;
|
||||
else
|
||||
return (!fixp->fx_pcrel
|
||||
|| fixp->fx_plt
|
||||
|| generic_force_reloc(fixp));
|
||||
}
|
||||
|
||||
|
||||
/* GAS will call this for each fixup. It should store the correct
|
||||
value in the object file. */
|
||||
|
||||
void
|
||||
md_apply_fix (fixS * fixp, valueT * valuep, segT seg)
|
||||
{
|
||||
@ -1879,13 +1966,18 @@ md_apply_fix (fixS * fixp, valueT * valuep, segT seg)
|
||||
}
|
||||
}
|
||||
|
||||
switch (fixp->fx_r_type)
|
||||
fixp->fx_no_overflow = 1;
|
||||
|
||||
/* if polymorphs are enabled and relax disabled.
|
||||
do not kill any relocs and pass them to linker. */
|
||||
if (msp430_enable_polys
|
||||
&& !msp430_enable_relax)
|
||||
{
|
||||
default:
|
||||
fixp->fx_no_overflow = 1;
|
||||
break;
|
||||
case BFD_RELOC_MSP430_10_PCREL:
|
||||
break;
|
||||
if (!fixp->fx_addsy || (fixp->fx_addsy
|
||||
&& S_GET_SEGMENT (fixp->fx_addsy) == absolute_section))
|
||||
fixp->fx_done = 1; /* it is ok to kill 'abs' reloc */
|
||||
else
|
||||
fixp->fx_done = 0;
|
||||
}
|
||||
|
||||
if (fixp->fx_done)
|
||||
@ -2185,6 +2277,13 @@ msp430_relax_frag (segT seg ATTRIBUTE_UNUSED, fragS * fragP,
|
||||
aim = S_GET_VALUE (symbolP) - fragP->fr_address - fragP->fr_fix;
|
||||
}
|
||||
|
||||
if (!msp430_enable_relax)
|
||||
{
|
||||
/* Relaxation is not enabled. So, make all jump as long ones
|
||||
by setting 'aim' to quite high value. */
|
||||
aim = 0x7fff;
|
||||
}
|
||||
|
||||
this_state = fragP->fr_subtype;
|
||||
start_type = this_type = table + this_state;
|
||||
|
||||
|
@ -112,3 +112,11 @@ extern long md_pcrel_from_section (struct fix *, segT);
|
||||
#define md_relax_frag(SEG, FRAGP, STRETCH) \
|
||||
msp430_relax_frag (SEG, FRAGP, STRETCH)
|
||||
extern long msp430_relax_frag (segT, fragS *, long);
|
||||
|
||||
#define TC_FORCE_RELOCATION_LOCAL(FIX) \
|
||||
msp430_force_relocation_local(FIX)
|
||||
extern int msp430_force_relocation_local(struct fix *);
|
||||
|
||||
|
||||
extern int msp430_enable_relax;
|
||||
extern int msp430_enable_polys;
|
||||
|
@ -26,8 +26,17 @@
|
||||
@section Options
|
||||
@cindex MSP 430 options (none)
|
||||
@cindex options for MSP430 (none)
|
||||
@code{@value{AS}} has only -m flag which selects the mpu arch. Currently has
|
||||
no effect.
|
||||
@table @code
|
||||
|
||||
@item -m
|
||||
select the mpu arch. Currently has no effect.
|
||||
@item -mP
|
||||
enables polymorph instructions handler.
|
||||
|
||||
@item -mQ
|
||||
enables relaxation at assembly time. DANGEROUS!
|
||||
|
||||
@end table
|
||||
|
||||
@node MSP430 Syntax
|
||||
@section Syntax
|
||||
@ -214,7 +223,7 @@ This directive instructs assembler to add new profile entry to the object file.
|
||||
additional pseudo-instructions are needed on this family.
|
||||
|
||||
For information on the 430 machine instruction set, see @cite{MSP430
|
||||
User's Manual, document slau049b}, Texas Instrument, Inc.
|
||||
User's Manual, document slau049d}, Texas Instrument, Inc.
|
||||
|
||||
@node MSP430 Profiling Capability
|
||||
@section Profiling Capability
|
||||
|
Loading…
Reference in New Issue
Block a user