2001-07-06 John Healy <jhealy@redhat.com>

* cgen.c (gas_cgen_save_fixups): Modified to allow more than one
        set of fixups to be stored.
        (gas_cgen_restore_fixups): Modified to allow the fixup chain to be
        restored to be chosen from any that are saved.
        (gas_cgen_swap_fixups): Modified to allow the current set of
        fixups to be swapped with any other set that has been saved.
        (gas_cgen_initialize_saved_fixups_array): New routine.
        * cgen.h: Modifed prototypes for gas_cgen_save_fixups,
        gas_cgen_restore_fixups, and gas_cgen_swap_fixups.  Added definitions
        or MAX_SAVED_FIXUP_CHAINS.
        * config/tc-m32r.c (assemble_two_insns): Changed calls to fixup
        store, swap and restore fuctions to reflect the new interface.
This commit is contained in:
John Healy 2001-07-06 19:09:23 +00:00
parent b1aeb4c5a3
commit 002de68b31
4 changed files with 125 additions and 52 deletions

View File

@ -1,3 +1,18 @@
2001-07-06 John Healy <jhealy@redhat.com>
* cgen.c (gas_cgen_save_fixups): Modified to allow more than one
set of fixups to be stored.
(gas_cgen_restore_fixups): Modified to allow the fixup chain to be
restored to be chosen from any that are saved.
(gas_cgen_swap_fixups): Modified to allow the current set of
fixups to be swapped with any other set that has been saved.
(gas_cgen_initialize_saved_fixups_array): New routine.
* cgen.h: Modifed prototypes for gas_cgen_save_fixups,
gas_cgen_restore_fixups, and gas_cgen_swap_fixups. Added definitions
or MAX_SAVED_FIXUP_CHAINS.
* config/tc-m32r.c (assemble_two_insns): Changed calls to fixup
store, swap and restore fuctions to reflect the new interface.
2001-07-06 Nick Clifton <nickc@cambridge.redhat.com>
* config/tc-m68k.c (md_estimate_size_before_relax): Catch and

View File

@ -94,62 +94,115 @@ queue_fixup (opindex, opinfo, expP)
++ num_fixups;
}
/* The following three functions allow a backup of the fixup chain to be made,
and to have this backup be swapped with the current chain. This allows
certain ports, eg the m32r, to swap two instructions and swap their fixups
at the same time. */
/* ??? I think with cgen_asm_finish_insn (or something else) there is no
more need for this. */
/* The following functions allow fixup chains to be stored, retrieved,
and swapped. They are a generalization of a pre-existing scheme
for storing, restoring and swapping fixup chains that was used by
the m32r port. The functionality is essentially the same, only
instead of only being able to store a single fixup chain, an entire
array of fixup chains can be stored. It is the user's responsibility
to keep track of how many fixup chains have been stored and which
elements of the array they are in.
static struct fixup saved_fixups[GAS_CGEN_MAX_FIXUPS];
static int saved_num_fixups;
The algorithms used are the same as in the old scheme. Other than the
"array-ness" of the whole thing, the functionality is identical to the
old scheme.
void
gas_cgen_save_fixups ()
gas_cgen_initialize_saved_fixups_array():
Sets num_fixups_in_chain to 0 for each element. Call this from
md_begin() if you plan to use these functions and you want the
fixup count in each element to be set to 0 intially. This is
not necessary, but it's included just in case. It performs
the same function for each element in the array of fixup chains
that gas_init_parse() performs for the current fixups.
gas_cgen_save_fixups (element):
element - element number of the array you wish to store the fixups
to. No mechanism is built in for tracking what element
was last stored to.
gas_cgen_restore_fixups (element):
element - element number of the array you wish to restore the fixups
from.
gas_cgen_swap_fixups(int element):
element - swap the current fixups with those in this element number.
*/
struct saved_fixups {
struct fixup fixup_chain[GAS_CGEN_MAX_FIXUPS];
int num_fixups_in_chain;
};
static struct saved_fixups stored_fixups[MAX_SAVED_FIXUP_CHAINS];
void
gas_cgen_initialize_saved_fixups_array ()
{
saved_num_fixups = num_fixups;
memcpy (saved_fixups, fixups, sizeof (fixups[0]) * num_fixups);
num_fixups = 0;
int i = 0;
while (i < MAX_SAVED_FIXUP_CHAINS)
stored_fixups[i++].num_fixups_in_chain = 0;
}
void
gas_cgen_restore_fixups ()
void
gas_cgen_save_fixups (int i)
{
num_fixups = saved_num_fixups;
memcpy (fixups, saved_fixups, sizeof (fixups[0]) * num_fixups);
saved_num_fixups = 0;
if (i < 0 || i >= MAX_SAVED_FIXUP_CHAINS)
{
as_fatal("Index into stored_fixups[] out of bounds.");
return;
}
stored_fixups[i].num_fixups_in_chain = num_fixups;
memcpy(stored_fixups[i].fixup_chain, fixups,
sizeof (fixups[0])*num_fixups);
num_fixups = 0;
}
void
gas_cgen_swap_fixups ()
void
gas_cgen_restore_fixups (int i)
{
int tmp;
struct fixup tmp_fixup;
if (i < 0 || i >= MAX_SAVED_FIXUP_CHAINS)
{
as_fatal("Index into stored_fixups[] out of bounds.");
return;
}
num_fixups = stored_fixups[i].num_fixups_in_chain;
memcpy(fixups,stored_fixups[i].fixup_chain,
(sizeof (stored_fixups[i].fixup_chain[0]))*num_fixups);
stored_fixups[i].num_fixups_in_chain = 0;
}
if (num_fixups == 0)
{
gas_cgen_restore_fixups ();
}
else if (saved_num_fixups == 0)
{
gas_cgen_save_fixups ();
}
else
{
tmp = saved_num_fixups;
saved_num_fixups = num_fixups;
num_fixups = tmp;
void
gas_cgen_swap_fixups (int i)
{
int tmp;
struct fixup tmp_fixup;
for (tmp = GAS_CGEN_MAX_FIXUPS; tmp--;)
{
tmp_fixup = saved_fixups [tmp];
saved_fixups [tmp] = fixups [tmp];
fixups [tmp] = tmp_fixup;
}
if (i < 0 || i >= MAX_SAVED_FIXUP_CHAINS)
{
as_fatal("Index into stored_fixups[] out of bounds.");
return;
}
if (num_fixups == 0)
{
gas_cgen_restore_fixups (i);
}
else if (stored_fixups[i].num_fixups_in_chain == 0)
{
gas_cgen_save_fixups (i);
}
else
{
tmp = stored_fixups[i].num_fixups_in_chain;
stored_fixups[i].num_fixups_in_chain = num_fixups;
num_fixups = tmp;
for (tmp = GAS_CGEN_MAX_FIXUPS; tmp--;)
{
tmp_fixup = stored_fixups[i].fixup_chain [tmp];
stored_fixups[i].fixup_chain[tmp] = fixups [tmp];
fixups [tmp] = tmp_fixup;
}
}
}

View File

@ -53,9 +53,12 @@ extern const char * gas_cgen_parse_operand
/* Call this from md_assemble to initialize the assembler callback. */
extern void gas_cgen_init_parse PARAMS ((void));
extern void gas_cgen_save_fixups PARAMS ((void));
extern void gas_cgen_restore_fixups PARAMS ((void));
extern void gas_cgen_swap_fixups PARAMS ((void));
/* Routines and macros for saving fixup chains. */
extern void gas_cgen_save_fixups PARAMS ((int));
extern void gas_cgen_restore_fixups PARAMS ((int));
extern void gas_cgen_swap_fixups PARAMS ((int));
extern void gas_cgen_initialize_saved_fixups_array PARAMS ((void));
#define MAX_SAVED_FIXUP_CHAINS 50
/* Add a register to the assembler's hash table.
This makes lets GAS parse registers for us.

View File

@ -554,6 +554,8 @@ md_begin ()
scom_symbol.section = &scom_section;
allow_m32rx (enable_m32rx);
gas_cgen_initialize_saved_fixups_array();
}
#define OPERAND_IS_COND_BIT(operand, indices, index) \
@ -832,7 +834,7 @@ assemble_two_insns (str, str2, parallel_p)
/* Preserve any fixups that have been generated and reset the list
to empty. */
gas_cgen_save_fixups ();
gas_cgen_save_fixups (0);
/* Get the indices of the operands of the instruction. */
/* FIXME: CGEN_FIELDS is already recorded, but relying on that fact
@ -941,7 +943,7 @@ assemble_two_insns (str, str2, parallel_p)
|| (errmsg = (char *) can_make_parallel (&first, &second)) == NULL)
{
/* Get the fixups for the first instruction. */
gas_cgen_swap_fixups ();
gas_cgen_swap_fixups (0);
/* Write it out. */
expand_debug_syms (first.debug_sym_link, 1);
@ -953,7 +955,7 @@ assemble_two_insns (str, str2, parallel_p)
make_parallel (second.buffer);
/* Get its fixups. */
gas_cgen_restore_fixups ();
gas_cgen_restore_fixups (0);
/* Write it out. */
expand_debug_syms (second.debug_sym_link, 1);
@ -972,7 +974,7 @@ assemble_two_insns (str, str2, parallel_p)
make_parallel (first.buffer);
/* Get the fixups for the first instruction. */
gas_cgen_restore_fixups ();
gas_cgen_restore_fixups (0);
/* Write out the first instruction. */
expand_debug_syms (first.debug_sym_link, 1);