This is the mail archive of the binutils@sources.redhat.com mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

Re: Changes To Fixup Saving, Restoring and Swapping


Committed.

John


>
>
>   ------------------------------------------------------------------------
> [gas]
>
> 2001-07-05  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
>         for 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.
>
>   ------------------------------------------------------------------------
> Index: gas/cgen.c
> ===================================================================
> RCS file: /cvs/src/src/gas/cgen.c,v
> retrieving revision 1.12
> diff -c -3 -p -r1.12 cgen.c
> *** cgen.c      2001/05/16 23:06:02     1.12
> --- cgen.c      2001/07/05 17:24:01
> *************** queue_fixup (opindex, opinfo, expP)
> *** 94,155 ****
>     ++ 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.  */
>
> ! static struct fixup saved_fixups[GAS_CGEN_MAX_FIXUPS];
> ! static int saved_num_fixups;
>
> ! void
> ! gas_cgen_save_fixups ()
>   {
> !   saved_num_fixups = num_fixups;
> !
> !   memcpy (saved_fixups, fixups, sizeof (fixups[0]) * num_fixups);
> !
> !   num_fixups = 0;
>   }
>
> ! void
> ! gas_cgen_restore_fixups ()
>   {
> !   num_fixups = saved_num_fixups;
> !
> !   memcpy (fixups, saved_fixups, sizeof (fixups[0]) * num_fixups);
>
> !   saved_num_fixups = 0;
>   }
>
> ! void
> ! gas_cgen_swap_fixups ()
>   {
> !   int tmp;
> !   struct fixup tmp_fixup;
>
> !   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;
> !
> !       for (tmp = GAS_CGEN_MAX_FIXUPS; tmp--;)
> !       {
> !         tmp_fixup          = saved_fixups [tmp];
> !         saved_fixups [tmp] = fixups [tmp];
> !         fixups [tmp]       = tmp_fixup;
> !       }
>       }
>   }
>
> --- 94,208 ----
>     ++ num_fixups;
>   }
>
> ! /* 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.
> !
> !    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.
> !
> !    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()
>   {
> !    int i = 0;
> !    while (i < MAX_SAVED_FIXUP_CHAINS)
> !       stored_fixups[i++].num_fixups_in_chain = 0;
>   }
>
> ! void
> ! gas_cgen_save_fixups (int i)
>   {
> !       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_restore_fixups(int i)
> ! {
> !       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;
>   }
>
> ! void
> ! gas_cgen_swap_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;
> !      }
> !
> !      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;
> !        }
>       }
>   }
>
> Index: gas/cgen.h
> ===================================================================
> RCS file: /cvs/src/src/gas/cgen.h,v
> retrieving revision 1.7
> diff -c -3 -p -r1.7 cgen.h
> *** cgen.h      2001/03/08 23:24:22     1.7
> --- cgen.h      2001/07/05 17:24:01
> *************** extern const char * gas_cgen_parse_opera
> *** 53,61 ****
>   /* 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));
>
>   /* Add a register to the assembler's hash table.
>      This makes lets GAS parse registers for us.
> --- 53,64 ----
>   /* Call this from md_assemble to initialize the assembler callback.  */
>   extern void gas_cgen_init_parse 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.
> Index: gas/config/tc-m32r.c
> ===================================================================
> RCS file: /cvs/src/src/gas/config/tc-m32r.c,v
> retrieving revision 1.19
> diff -c -3 -p -r1.19 tc-m32r.c
> *** tc-m32r.c   2001/05/10 11:32:51     1.19
> --- tc-m32r.c   2001/07/05 17:24:02
> *************** md_begin ()
> *** 554,559 ****
> --- 554,561 ----
>     scom_symbol.section         = &scom_section;
>
>     allow_m32rx (enable_m32rx);
> +
> +   gas_cgen_initialize_saved_fixups_array();
>   }
>
>   #define OPERAND_IS_COND_BIT(operand, indices, index) \
> *************** assemble_two_insns (str, str2, parallel_
> *** 832,838 ****
>
>     /* Preserve any fixups that have been generated and reset the list
>        to empty.  */
> !   gas_cgen_save_fixups ();
>
>     /* Get the indices of the operands of the instruction.  */
>     /* FIXME: CGEN_FIELDS is already recorded, but relying on that fact
> --- 834,840 ----
>
>     /* Preserve any fixups that have been generated and reset the list
>        to empty.  */
> !   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
> *************** assemble_two_insns (str, str2, parallel_
> *** 941,947 ****
>         || (errmsg = (char *) can_make_parallel (&first, &second)) == NULL)
>       {
>         /* Get the fixups for the first instruction.  */
> !       gas_cgen_swap_fixups ();
>
>         /* Write it out.  */
>         expand_debug_syms (first.debug_sym_link, 1);
> --- 943,949 ----
>         || (errmsg = (char *) can_make_parallel (&first, &second)) == NULL)
>       {
>         /* Get the fixups for the first instruction.  */
> !       gas_cgen_swap_fixups (0);
>
>         /* Write it out.  */
>         expand_debug_syms (first.debug_sym_link, 1);
> *************** assemble_two_insns (str, str2, parallel_
> *** 953,959 ****
>         make_parallel (second.buffer);
>
>         /* Get its fixups.  */
> !       gas_cgen_restore_fixups ();
>
>         /* Write it out.  */
>         expand_debug_syms (second.debug_sym_link, 1);
> --- 955,961 ----
>         make_parallel (second.buffer);
>
>         /* Get its fixups.  */
> !       gas_cgen_restore_fixups (0);
>
>         /* Write it out.  */
>         expand_debug_syms (second.debug_sym_link, 1);
> *************** assemble_two_insns (str, str2, parallel_
> *** 972,978 ****
>         make_parallel (first.buffer);
>
>         /* Get the fixups for the first instruction.  */
> !       gas_cgen_restore_fixups ();
>
>         /* Write out the first instruction.  */
>         expand_debug_syms (first.debug_sym_link, 1);
> --- 974,980 ----
>         make_parallel (first.buffer);
>
>         /* Get the fixups for the first instruction.  */
> !       gas_cgen_restore_fixups (0);
>
>         /* Write out the first instruction.  */
>         expand_debug_syms (first.debug_sym_link, 1);


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]