GCC's bacl-end & assemble emission (36)

9.6.4.1.3.           Outputtable(s) for state alternatives

In 9.5.8 Automata generation,it is possible that instruction of different equivalent class can trigger thesame state transition from certain states. These instructions are defined asstate alternatives. To minimize the size of automaton, tegother withtransforming NDFA to DFA, these states will be combined into a compound state,and field state_altsrecords the number of these states. The table and function state alternativesrelated are debugging purpose.

 

7779 static void

7780 output_state_alts_table (automaton_t automaton)                                   ingenautomata.c

7781 {

7782   state_t *state_ptr;

7783   arc_t arc;

7784   vla_hwint_t state_alts_vect;

7785

7786   undefined_vect_el_value = 0; /* no alts when transition is not possible */

7787   automaton->state_alts_table = create_state_ainsn_table (automaton);

7788   /* Create vect ofpointers to states ordered by num of transitions

7789     from the state (state with the maximum numis the first).  */

7790   VLA_PTR_CREATE (output_states_vect, 1500,"output states vector");

7791   pass_states(automaton, add_states_vect_el);

7792   qsort (VLA_PTR_BEGIN (output_states_vect),

7793        VLA_PTR_LENGTH (output_states_vect),

7794        sizeof (state_t), compare_transition_els_num);

7795   /* Create base,comb, and check vectors.  */

7796   VLA_HWINT_CREATE (state_alts_vect, 500,"state alts vector");

7797   for(state_ptr = VLA_PTR_BEGIN (output_states_vect);

7798       state_ptr <= (state_t*) VLA_PTR_LAST (output_states_vect);

7799       state_ptr++)

7800   {

7801     VLA_HWINT_NULLIFY (state_alts_vect);

7802     for (arc = first_out_arc (*state_ptr);

7803         arc != NULL;

7804         arc = next_out_arc (arc))

7805     {

7806       if (arc->insn == NULL)

7807         abort ();

7808       if(arc->insn->first_ainsn_with_given_equialence_num)

7809         add_vect_el(&state_alts_vect, arc->insn, arc->state_alts);

7810     }

7811     add_vect(automaton->state_alts_table, (*state_ptr)->order_state_num,

7812              VLA_HWINT_BEGIN (state_alts_vect),

7813              VLA_HWINT_LENGTH(state_alts_vect));

7814   }

7815   output_state_ainsn_table

7816     (automaton->state_alts_table, (char *)"state insn alternatives",

7817      output_state_alts_full_vect_name, output_state_alts_comb_vect_name,

7818      output_state_alts_check_vect_name, output_state_alts_base_vect_name);

7819   VLA_PTR_DELETE (output_states_vect);

7820   VLA_HWINT_DELETE (state_alts_vect);

7821 }

 

At line 7809, state_alts records the number of alternativereservations which can be used for transition from given state by giveninstruction. The handling of state_alts is very similar with that of asinsnwe have seen previous. Then after outputting code for state_alts, we get following, assumingthis timefull_vect in state_ainsn_table is used, and we have lessthan 2568256 (256*256) effective states.

 

/*Vector translating external insn codes to internal ones.*/

       static const unsigned char translate_0 []ATTRIBUTE_UNUSED = {

         `equivalent class number`  //indescription order

       };

 

/*Comb vector for state transitions */

staticconst unsigned char transitions_0 [] ATTRIBUTE_UNUSED = {

  `content of comb_vect`              //for ainsn, referto add_vect

};

 

/*Check vector for state transitions */

staticconst unsigned char check_0 [] ATTRIBUTE_UNUSED = {

  `content of check_vect`              //for ainsn, refer to add_vect

};

 

/* Basevector for state transitions */

staticconst unsigned char base_0 [] ATTRIBUTE_UNUSED = {

  `content of base_vect`         //for ainsn, referto add_vect

};

 

#if AUTOMATON_STATE_ALTS

/* Vector for state insn alternatives */

staticconst unsigned short state_alts_0 [] ATTRIBUTE_UNUSED = {

  `content of full_vect`          // forstate_alts, refer to add_vect

};

#endif

9.6.4.1.4.           Outputtable for issue delay

To issue instruction with efficiency, we must know the issue delayamong instructions upon certain function unit. In define_function_unit pattern,the issue delay is encoded into the pattern declaration. However, for theautomaton based description, during the generation, we have built all statesand bound them with instruction associated. By traversing the states, we cancollect information for issue delay instead needing encoded into thedeclaration. Obviously, this way is more flexible and powerful.

Here is the function.

 

7892 static void

7893 output_min_issue_delay_table (automaton_t automaton)                         ingenautomata.c

7894 {

7895   vla_hwint_t min_issue_delay_vect;

7896   vla_hwint_t compressed_min_issue_delay_vect;

7897  vect_el_t min_delay;

7898  ainsn_t ainsn;

7899   state_t *state_ptr;

7900   int i;

7901

7902   /* Create vect ofpointers to states ordered by num of transitions

7903     from the state (state with the maximum numis the first).  */

7904   VLA_PTR_CREATE (output_states_vect, 1500,"output states vector");

7905   pass_states(automaton, add_states_vect_el);

7906   VLA_HWINT_CREATE (min_issue_delay_vect, 1500,"min issue delay vector");

7907   VLA_HWINT_EXPAND (min_issue_delay_vect,

7908                         VLA_HWINT_LENGTH (output_states_vect)

7909                         *automaton->insn_equiv_classes_num);

7910   for (i = 0;

7911       i < ((int) VLA_HWINT_LENGTH (output_states_vect)

7912          *automaton->insn_equiv_classes_num);

7913       i++)

7914     VLA_HWINT (min_issue_delay_vect, i) = 0;

7915   automaton->max_min_delay = 0;

7916   for (ainsn =automaton->ainsn_list; ainsn != NULL; ainsn = ainsn->next_ainsn)

7917     if(ainsn->first_ainsn_with_given_equialence_num)

7918     {

7919       for (state_ptr =VLA_PTR_BEGIN (output_states_vect);

7920           state_ptr <= (state_t*) VLA_PTR_LAST (output_states_vect);

7921           state_ptr++)

7922         (*state_ptr)->min_insn_issue_delay =-1;

7923       for (state_ptr =VLA_PTR_BEGIN (output_states_vect);

7924           state_ptr <= (state_t*) VLA_PTR_LAST (output_states_vect);

7925           state_ptr++)

7926       {

7927         min_delay = min_issue_delay(*state_ptr, ainsn);

7928         if (automaton->max_min_delay <min_delay)

7929           automaton->max_min_delay =min_delay;

7930         VLA_HWINT (min_issue_delay_vect,

7931                     (*state_ptr)->order_state_num

7932                        *automaton->insn_equiv_classes_num

7933                        +ainsn->insn_equiv_class_num) = min_delay;

7934       }

7935     }

7936   fprintf (output_file, "/* Vector of min issue delayof insns.  */\n");

7937   fprintf (output_file, "static const ");

7938   output_range_type(output_file,0, automaton->max_min_delay);

7939   fprintf (output_file, " ");

7940   output_min_issue_delay_vect_name (output_file,automaton);

7941   fprintf (output_file, "[] ATTRIBUTE_UNUSED ={\n");

7942   /* Compress thevector.  */

7943   if (automaton->max_min_delay < 2)

7944    automaton->min_issue_delay_table_compression_factor = 8;

7945   else if (automaton->max_min_delay < 4)

7946     automaton->min_issue_delay_table_compression_factor= 4;

7947   else if (automaton->max_min_delay < 16)

7948    automaton->min_issue_delay_table_compression_factor = 2;

7949   else

7950    automaton->min_issue_delay_table_compression_factor = 1;

7951   VLA_HWINT_CREATE (compressed_min_issue_delay_vect,1500,

7952                        "compressed minissue delay vector");

7953   VLA_HWINT_EXPAND(compressed_min_issue_delay_vect,

7954                         (VLA_HWINT_LENGTH(min_issue_delay_vect)

7955                           + automaton->min_issue_delay_table_compression_factor

7956                           - 1)

7957                           /automaton->min_issue_delay_table_compression_factor);

7958   for (i = 0;

7959       i < (int) VLA_HWINT_LENGTH(compressed_min_issue_delay_vect);

7960       i++)

7961     VLA_HWINT (compressed_min_issue_delay_vect,i) = 0;

7962   for (i = 0; i< (int) VLA_HWINT_LENGTH (min_issue_delay_vect); i++)

7963     VLA_HWINT (compressed_min_issue_delay_vect,

7964                  i / automaton->min_issue_delay_table_compression_factor)

7965                  |= (VLA_HWINT(min_issue_delay_vect, i)

7966                   << (8 - (i %automaton->min_issue_delay_table_compression_factor

7967                       + 1)

7968                   * (8 / automaton->min_issue_delay_table_compression_factor)));

7969   output_vect(VLA_HWINT_BEGIN (compressed_min_issue_delay_vect),

7970              VLA_HWINT_LENGTH(compressed_min_issue_delay_vect));

7971   fprintf (output_file, "};\n\n");

7972   VLA_PTR_DELETE (output_states_vect);

7973   VLA_HWINT_DELETE (min_issue_delay_vect);

7974   VLA_HWINT_DELETE(compressed_min_issue_delay_vect);

7975 }

 

As we know instructions are grouped according to the resourcereserved, and only the first instruction found in one group, has field first_ainsn_with_given_equialence_numbeen set. For instructions belong to same equivalent class, their can be issuedfrom the same states, that is if one of them can be issued from certain state,so the other.

Then FOR loop at line7916, tries to find out the minimum issue delays to specified state amonginstruction groups.

 

7873 static int

7874 min_issue_delay (state_tstate, ainsn_t ainsn)                                         ingenautomata.c

7875 {

7876   curr_state_pass_num++;

7877   state->min_insn_issue_delay = min_issue_delay_pass_states (state,ainsn);

7878   returnstate->min_insn_issue_delay;

7879 }

 

See parameter state firstly has min_insn_issue_delay set as -1 toprevent muliple process.

 

7831 static int

7832 min_issue_delay_pass_states (state_t state, ainsn_t ainsn)

7833 {

7834   arc_t arc;

7835   int min_insn_issue_delay, insn_issue_delay;

7836

7837   if (state->state_pass_num == curr_state_pass_num

7838     || state->min_insn_issue_delay != -1)

7839     /* We've enteredinto a loop or already have the correct value for

7840       given state and ainsn.  */

7841     returnstate->min_insn_issue_delay;

7842   state->state_pass_num = curr_state_pass_num;

7843   min_insn_issue_delay = -1;

7844   for (arc =first_out_arc (state); arc != NULL; arc = next_out_arc (arc))

7845     if (arc->insn == ainsn)

7846     {

7847       min_insn_issue_delay = 0;

7848       break;

7849     }

7850    else

7851     {

7852       insn_issue_delay = min_issue_delay_pass_states(arc->to_state, ainsn);

7853       if (insn_issue_delay != -1)

7854       {

7855         if (arc->insn->insn_reserv_decl

7856            == DECL_INSN_RESERV (advance_cycle_insn_decl))

7857           insn_issue_delay++;

7858         if (min_insn_issue_delay == -1

7859            || min_insn_issue_delay >insn_issue_delay)

7860         {

7861           min_insn_issue_delay = insn_issue_delay;

7862           if (insn_issue_delay == 0)

7863             break;

7864         }

7865       }

7866     }

7867   returnmin_insn_issue_delay;

7868 }

 

At line 7847, the function is recursed until the target instructionis found, then during returning from the nested invocation, every advance_cycle_insn_declencountered causes the delay increased. Notice that other instructions in thesame group except the first one have no effect on the searching, they willalways return -1.

Back to output_min_issue_delay_table,at line 7929, max_min_delayrecords the max value of the whole states set. According to this value we cancompress the vector of issue delay by saving several values teogther into adata of int type.

Then we get output code as following (content in red is not output by tool).

 

/* Vector translating external insn codes tointernal ones.*/

       static const unsigned char translate_0 []ATTRIBUTE_UNUSED = {

         `equivalent class number`  // descriptionorder

       };

 

/*Comb vector for state transitions */

staticconst unsigned char transitions_0 [] ATTRIBUTE_UNUSED = {

  `content of comb_vect`              // for ainsn,refer to add_vect

};

 

/*Check vector for state transitions */

static constunsigned char check_0 [] ATTRIBUTE_UNUSED = {

  `content of check_vect`              // for ainsn, refer to add_vect

};

 

/* Basevector for state transitions */

staticconst unsigned char base_0 [] ATTRIBUTE_UNUSED = {

  `content of base_vect`         //for ainsn, referto add_vect

};

 

#if AUTOMATON_STATE_ALTS

/* Vector for state insn alternatives */

staticconst unsigned short state_alts_0 [] ATTRIBUTE_UNUSED = {

  `content of full_vect`          // forstate_alts, refer to add_vect

};

#endif

 

/* Vector of min issue delay of insns.  */

staticconst unsigned char min_issue_delay_0 = []ATTRIBUTE_UNUSED = {

  `content of compressed_min_issue_delay_vect` // refer to output_min_issue_delay_table

};

9.6.4.1.5.           Outputtable for locked states

There may be states that no other instruction can be issued except advance_cycle_insn_decl– that is CPU heading for next cycle. output_dead_lock_vectfinds out these states and create table for them. At line 8007 ~8009, see the judgmentof these states.

 

7985 static void

7986 output_dead_lock_vect (automaton_t automaton)                                   ingenautomata.c

7987 {

7988   state_t *state_ptr;

7989   arc_t arc;

7990   vla_hwint_t dead_lock_vect;

7991

7992   /* Create vect ofpointers to states ordered by num of

7993     transitions from the state (state with themaximum num is the

7994     first). */

7995   VLA_PTR_CREATE (output_states_vect, 1500,"output states vector");

7996   pass_states(automaton, add_states_vect_el);

7997   VLA_HWINT_CREATE (dead_lock_vect, 1500,"is dead locked vector");

7998   VLA_HWINT_EXPAND (dead_lock_vect,VLA_HWINT_LENGTH (output_states_vect));

7999   for(state_ptr = VLA_PTR_BEGIN (output_states_vect);

8000       state_ptr <= (state_t*) VLA_PTR_LAST (output_states_vect);

8001       state_ptr++)

8002   {

8003     arc = first_out_arc (*state_ptr);

8004     if (arc == NULL)

8005       abort ();

8006     VLA_HWINT (dead_lock_vect,(*state_ptr)->order_state_num)

8007          = (next_out_arc (arc) == NULL

8008            &&(arc->insn->insn_reserv_decl

8009                == DECL_INSN_RESERV (advance_cycle_insn_decl))? 1 : 0);

8010 #ifndef NDEBUG

8011     if (VLA_HWINT (dead_lock_vect,(*state_ptr)->order_state_num))

8012       locked_states_num++;

8013 #endif

8014   }

8015   fprintf (output_file, "/* Vector for locked stateflags.  */\n");

8016   fprintf (output_file, "static const ");

8017   output_range_type(output_file,0, 1);

8018   fprintf (output_file, " ");

8019   output_dead_lock_vect_name (output_file,automaton);

8020   fprintf (output_file, "[] = {\n");

8021   output_vect(VLA_HWINT_BEGIN (dead_lock_vect),

8022              VLA_HWINT_LENGTH (dead_lock_vect));

8023   fprintf (output_file, "};\n\n");

8024   VLA_HWINT_DELETE (dead_lock_vect);

8025   VLA_PTR_DELETE (output_states_vect);

8026 }

 

From line 8009 above, we can see that the content of dead_lock_vectis only 1 or 0, with 1 indicates no meaningful instruction can be issued, with0 vice versa.

Then output_tableswill output table for define_query_cpu_unit. We omit it here. However, theproducing very resembles that of other tables. Now in output file we getfollowing (content in red is not output by the tool).And assuming we don’t have the reserved unit for automaton (i.e., nodefine_query_cpu_unit)

 

/* Vector translating external insn codes tointernal ones.*/

       static const unsigned char translate_0 []ATTRIBUTE_UNUSED = {

         `equivalent class number`  // indescription order

       };

 

/*Comb vector for state transitions */

staticconst unsigned char transitions_0 [] ATTRIBUTE_UNUSED = {

  `content of comb_vect`              // for ainsn,refer to add_vect

};

 

/*Check vector for state transitions */

staticconst unsigned char check_0 [] ATTRIBUTE_UNUSED = {

  `content of check_vect`              // for ainsn, refer to add_vect

};

 

/* Basevector for state transitions */

staticconst unsigned char base_0 [] ATTRIBUTE_UNUSED = {

  `content of base_vect`         // for ainsn, referto add_vect

};

 

#if AUTOMATON_STATE_ALTS

/* Vector for state insn alternatives */

staticconst unsigned short state_alts_0 [] ATTRIBUTE_UNUSED = {

  `content of full_vect`          // forstate_alts, refer to add_vect

};

#endif

 

/* Vector of min issue delay of insns.  */

staticconst unsigned char min_issue_delay_0 = []ATTRIBUTE_UNUSED = {

  `content of compressed_min_issue_delay_vect` // refer to output_min_issue_delay_table

};

 

 /* Vector for locked state flags.  */

    staticconst unsigned char dead_lock_0 = []ATTRIBUTE_UNUSED = {

    `content of dead_lock_vect`       // refer to output_dead_lock_vect

 }

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值