LCOV - code coverage report
Current view: top level - gcc/config/i386 - x86-tune-sched-core.cc (source / functions) Coverage Total Hit
Test: gcc.info Lines: 100.0 % 93 93
Test Date: 2026-03-28 14:25:54 Functions: 100.0 % 9 9
Legend: Lines:     hit not hit

            Line data    Source code
       1              : /* Scheduler hooks for IA-32 which implement Core 2 specific logic.
       2              :    Copyright (C) 1988-2026 Free Software Foundation, Inc.
       3              : 
       4              : This file is part of GCC.
       5              : 
       6              : GCC is free software; you can redistribute it and/or modify
       7              : it under the terms of the GNU General Public License as published by
       8              : the Free Software Foundation; either version 3, or (at your option)
       9              : any later version.
      10              : 
      11              : GCC is distributed in the hope that it will be useful,
      12              : but WITHOUT ANY WARRANTY; without even the implied warranty of
      13              : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      14              : GNU General Public License for more details.
      15              : 
      16              : You should have received a copy of the GNU General Public License
      17              : along with GCC; see the file COPYING3.  If not see
      18              : <http://www.gnu.org/licenses/>.  */
      19              : 
      20              : #define IN_TARGET_CODE 1
      21              : 
      22              : #include "config.h"
      23              : #include "system.h"
      24              : #include "coretypes.h"
      25              : #include "backend.h"
      26              : #include "rtl.h"
      27              : #include "tree.h"
      28              : #include "cfghooks.h"
      29              : #include "tm_p.h"
      30              : #include "insn-config.h"
      31              : #include "insn-attr.h"
      32              : #include "recog.h"
      33              : #include "target.h"
      34              : #include "rtl-iter.h"
      35              : #include "regset.h"
      36              : #include "sched-int.h"
      37              : 
      38              : 
      39              : /* Model decoder of Core 2/i7.
      40              :    Below hooks for multipass scheduling (see haifa-sched.cc:max_issue)
      41              :    track the instruction fetch block boundaries and make sure that long
      42              :    (9+ bytes) instructions are assigned to D0.  */
      43              : 
      44              : /* Maximum length of an insn that can be handled by
      45              :    a secondary decoder unit.  '8' for Core 2/i7.  */
      46              : static int core2i7_secondary_decoder_max_insn_size;
      47              : 
      48              : /* Ifetch block size, i.e., number of bytes decoder reads per cycle.
      49              :    '16' for Core 2/i7.  */
      50              : static int core2i7_ifetch_block_size;
      51              : 
      52              : /* Maximum number of instructions decoder can handle per cycle.
      53              :    '6' for Core 2/i7.  */
      54              : static int core2i7_ifetch_block_max_insns;
      55              : 
      56              : typedef struct ix86_first_cycle_multipass_data_ *
      57              :   ix86_first_cycle_multipass_data_t;
      58              : typedef const struct ix86_first_cycle_multipass_data_ *
      59              :   const_ix86_first_cycle_multipass_data_t;
      60              : 
      61              : /* A variable to store target state across calls to max_issue within
      62              :    one cycle.  */
      63              : static struct ix86_first_cycle_multipass_data_ _ix86_first_cycle_multipass_data,
      64              :   *ix86_first_cycle_multipass_data = &_ix86_first_cycle_multipass_data;
      65              : 
      66              : /* Initialize DATA.  */
      67              : static void
      68    118138187 : core2i7_first_cycle_multipass_init (void *_data)
      69              : {
      70    118138187 :   ix86_first_cycle_multipass_data_t data
      71              :     = (ix86_first_cycle_multipass_data_t) _data;
      72              : 
      73    118138187 :   data->ifetch_block_len = 0;
      74    118138187 :   data->ifetch_block_n_insns = 0;
      75    118138187 :   data->ready_try_change = NULL;
      76    118138187 :   data->ready_try_change_size = 0;
      77    118138187 : }
      78              : 
      79              : /* Advancing the cycle; reset ifetch block counts.  */
      80              : static void
      81     45729005 : core2i7_dfa_post_advance_cycle (void)
      82              : {
      83     45729005 :   ix86_first_cycle_multipass_data_t data = ix86_first_cycle_multipass_data;
      84              : 
      85     45729005 :   gcc_assert (data->ifetch_block_n_insns <= core2i7_ifetch_block_max_insns);
      86              : 
      87     45729005 :   data->ifetch_block_len = 0;
      88     45729005 :   data->ifetch_block_n_insns = 0;
      89     45729005 : }
      90              : 
      91              : /* Filter out insns from ready_try that the core will not be able to issue
      92              :    on current cycle due to decoder.  */
      93              : static void
      94    166173498 : core2i7_first_cycle_multipass_filter_ready_try
      95              : (const_ix86_first_cycle_multipass_data_t data,
      96              :  signed char *ready_try, int n_ready, bool first_cycle_insn_p)
      97              : {
      98    645503118 :   while (n_ready--)
      99              :     {
     100    479329620 :       rtx_insn *insn;
     101    479329620 :       int insn_size;
     102              : 
     103    479329620 :       if (ready_try[n_ready])
     104    209718554 :         continue;
     105              : 
     106    269611066 :       insn = get_ready_element (n_ready);
     107    269611066 :       insn_size = ix86_min_insn_size (insn);
     108              : 
     109    269611066 :       if (/* If this is a too long an insn for a secondary decoder ...  */
     110              :           (!first_cycle_insn_p
     111    212928100 :            && insn_size > core2i7_secondary_decoder_max_insn_size)
     112              :           /* ... or it would not fit into the ifetch block ...  */
     113    244590820 :           || data->ifetch_block_len + insn_size > core2i7_ifetch_block_size
     114              :           /* ... or the decoder is full already ...  */
     115    166301609 :           || data->ifetch_block_n_insns + 1 > core2i7_ifetch_block_max_insns)
     116              :         /* ... mask the insn out.  */
     117              :         {
     118    103309529 :           ready_try[n_ready] = 1;
     119              : 
     120    103309529 :           if (data->ready_try_change)
     121     95703720 :             bitmap_set_bit (data->ready_try_change, n_ready);
     122              :         }
     123              :     }
     124    166173498 : }
     125              : 
     126              : /* Prepare for a new round of multipass lookahead scheduling.  */
     127              : static void
     128     54891261 : core2i7_first_cycle_multipass_begin (void *_data,
     129              :                                      signed char *ready_try, int n_ready,
     130              :                                      bool first_cycle_insn_p)
     131              : {
     132     54891261 :   ix86_first_cycle_multipass_data_t data
     133              :     = (ix86_first_cycle_multipass_data_t) _data;
     134     54891261 :   const_ix86_first_cycle_multipass_data_t prev_data
     135              :     = ix86_first_cycle_multipass_data;
     136              : 
     137              :   /* Restore the state from the end of the previous round.  */
     138     54891261 :   data->ifetch_block_len = prev_data->ifetch_block_len;
     139     54891261 :   data->ifetch_block_n_insns = prev_data->ifetch_block_n_insns;
     140              : 
     141              :   /* Filter instructions that cannot be issued on current cycle due to
     142              :      decoder restrictions.  */
     143     54891261 :   core2i7_first_cycle_multipass_filter_ready_try (data, ready_try, n_ready,
     144              :                                                   first_cycle_insn_p);
     145     54891261 : }
     146              : 
     147              : /* INSN is being issued in current solution.  Account for its impact on
     148              :    the decoder model.  */
     149              : static void
     150    111282237 : core2i7_first_cycle_multipass_issue (void *_data,
     151              :                                      signed char *ready_try, int n_ready,
     152              :                                      rtx_insn *insn, const void *_prev_data)
     153              : {
     154    111282237 :   ix86_first_cycle_multipass_data_t data
     155              :     = (ix86_first_cycle_multipass_data_t) _data;
     156    111282237 :   const_ix86_first_cycle_multipass_data_t prev_data
     157              :     = (const_ix86_first_cycle_multipass_data_t) _prev_data;
     158              : 
     159    111282237 :   int insn_size = ix86_min_insn_size (insn);
     160              : 
     161    111282237 :   data->ifetch_block_len = prev_data->ifetch_block_len + insn_size;
     162    111282237 :   data->ifetch_block_n_insns = prev_data->ifetch_block_n_insns + 1;
     163    111282237 :   gcc_assert (data->ifetch_block_len <= core2i7_ifetch_block_size
     164              :               && data->ifetch_block_n_insns <= core2i7_ifetch_block_max_insns);
     165              : 
     166              :   /* Allocate or resize the bitmap for storing INSN's effect on ready_try.  */
     167    111282237 :   if (!data->ready_try_change)
     168              :     {
     169     16096077 :       data->ready_try_change = sbitmap_alloc (n_ready);
     170     16096077 :       data->ready_try_change_size = n_ready;
     171              :     }
     172     95186160 :   else if (data->ready_try_change_size < n_ready)
     173              :     {
     174      1061899 :       data->ready_try_change = sbitmap_resize (data->ready_try_change,
     175              :                                                n_ready, 0);
     176      1061899 :       data->ready_try_change_size = n_ready;
     177              :     }
     178    111282237 :   bitmap_clear (data->ready_try_change);
     179              : 
     180              :   /* Filter out insns from ready_try that the core will not be able to issue
     181              :      on current cycle due to decoder.  */
     182    111282237 :   core2i7_first_cycle_multipass_filter_ready_try (data, ready_try, n_ready,
     183              :                                                   false);
     184    111282237 : }
     185              : 
     186              : /* Revert the effect on ready_try.  */
     187              : static void
     188     56629558 : core2i7_first_cycle_multipass_backtrack (const void *_data,
     189              :                                          signed char *ready_try,
     190              :                                          int n_ready ATTRIBUTE_UNUSED)
     191              : {
     192     56629558 :   const_ix86_first_cycle_multipass_data_t data
     193              :     = (const_ix86_first_cycle_multipass_data_t) _data;
     194     56629558 :   unsigned int i = 0;
     195     56629558 :   sbitmap_iterator sbi;
     196              : 
     197     56629558 :   gcc_assert (bitmap_last_set_bit (data->ready_try_change) < n_ready);
     198    207507711 :   EXECUTE_IF_SET_IN_BITMAP (data->ready_try_change, 0, i, sbi)
     199              :     {
     200     94248595 :       ready_try[i] = 0;
     201              :     }
     202     56629558 : }
     203              : 
     204              : /* Save the result of multipass lookahead scheduling for the next round.  */
     205              : static void
     206     54891261 : core2i7_first_cycle_multipass_end (const void *_data)
     207              : {
     208     54891261 :   const_ix86_first_cycle_multipass_data_t data
     209              :     = (const_ix86_first_cycle_multipass_data_t) _data;
     210     54891261 :   ix86_first_cycle_multipass_data_t next_data
     211              :     = ix86_first_cycle_multipass_data;
     212              : 
     213     54891261 :   if (data != NULL)
     214              :     {
     215     52718903 :       next_data->ifetch_block_len = data->ifetch_block_len;
     216     52718903 :       next_data->ifetch_block_n_insns = data->ifetch_block_n_insns;
     217              :     }
     218     54891261 : }
     219              : 
     220              : /* Deallocate target data.  */
     221              : static void
     222    118138187 : core2i7_first_cycle_multipass_fini (void *_data)
     223              : {
     224    118138187 :   ix86_first_cycle_multipass_data_t data
     225              :     = (ix86_first_cycle_multipass_data_t) _data;
     226              : 
     227    118138187 :   if (data->ready_try_change)
     228              :     {
     229     16096077 :       sbitmap_free (data->ready_try_change);
     230     16096077 :       data->ready_try_change = NULL;
     231     16096077 :       data->ready_try_change_size = 0;
     232              :     }
     233    118138187 : }
     234              : 
     235              : void
     236       913829 : ix86_core2i7_init_hooks (void)
     237              : {
     238       913829 :   targetm.sched.dfa_post_advance_cycle
     239       913829 :     = core2i7_dfa_post_advance_cycle;
     240       913829 :   targetm.sched.first_cycle_multipass_init
     241       913829 :     = core2i7_first_cycle_multipass_init;
     242       913829 :   targetm.sched.first_cycle_multipass_begin
     243       913829 :     = core2i7_first_cycle_multipass_begin;
     244       913829 :   targetm.sched.first_cycle_multipass_issue
     245       913829 :     = core2i7_first_cycle_multipass_issue;
     246       913829 :   targetm.sched.first_cycle_multipass_backtrack
     247       913829 :     = core2i7_first_cycle_multipass_backtrack;
     248       913829 :   targetm.sched.first_cycle_multipass_end
     249       913829 :     = core2i7_first_cycle_multipass_end;
     250       913829 :   targetm.sched.first_cycle_multipass_fini
     251       913829 :     = core2i7_first_cycle_multipass_fini;
     252              : 
     253              :   /* Set decoder parameters.  */
     254       913829 :   core2i7_secondary_decoder_max_insn_size = 8;
     255       913829 :   core2i7_ifetch_block_size = 16;
     256       913829 :   core2i7_ifetch_block_max_insns = 6;
     257       913829 : }
        

Generated by: LCOV version 2.4-beta

LCOV profile is generated on x86_64 machine using following configure options: configure --disable-bootstrap --enable-coverage=opt --enable-languages=c,c++,fortran,go,jit,lto,rust,m2 --enable-host-shared. GCC test suite is run with the built compiler.