(root)/
gcc-13.2.0/
gcc/
hw-doloop.h
       1  /* Code to analyze doloop loops in order for targets to perform late
       2     optimizations converting doloops to other forms of hardware loops.
       3     Copyright (C) 2011-2023 Free Software Foundation, Inc.
       4  
       5  This file is part of GCC.
       6  
       7  GCC is free software; you can redistribute it and/or modify it under
       8  the terms of the GNU General Public License as published by the Free
       9  Software Foundation; either version 3, or (at your option) any later
      10  version.
      11  
      12  GCC is distributed in the hope that it will be useful, but WITHOUT ANY
      13  WARRANTY; without even the implied warranty of MERCHANTABILITY or
      14  FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
      15  for more details.
      16  
      17  You should have received a copy of the GNU General Public License
      18  along with GCC; see the file COPYING3.  If not see
      19  <http://www.gnu.org/licenses/>.  */
      20  
      21  #ifndef GCC_HW_DOLOOP_H
      22  #define GCC_HW_DOLOOP_H
      23  
      24  /* We need to keep a vector of loops */
      25  typedef struct hwloop_info_d *hwloop_info;
      26  
      27  /* Information about a loop we have found (or are in the process of
      28     finding).  */
      29  struct GTY (()) hwloop_info_d
      30  {
      31    /* loop number, for dumps */
      32    int loop_no;
      33  
      34    /* Next loop in the graph. */
      35    hwloop_info next;
      36  
      37    /* Vector of blocks only within the loop, including those within
      38       inner loops.  */
      39    vec<basic_block> blocks;
      40  
      41    /* Same information in a bitmap.  */
      42    bitmap block_bitmap;
      43  
      44    /* Vector of inner loops within this loop.  Includes loops of every
      45       nesting level.  */
      46    vec<hwloop_info> loops;
      47  
      48    /* All edges that jump into the loop.  */
      49    vec<edge, va_gc> *incoming;
      50  
      51    /* The ports currently using this infrastructure can typically
      52       handle two cases: all incoming edges have the same destination
      53       block, or all incoming edges have the same source block.  These
      54       two members are set to the common source or destination we found,
      55       or NULL if different blocks were found.  If both are NULL the
      56       loop can't be optimized.  */
      57    basic_block incoming_src;
      58    basic_block incoming_dest;
      59  
      60    /* First block in the loop.  This is the one branched to by the loop_end
      61       insn.  */
      62    basic_block head;
      63  
      64    /* Last block in the loop (the one with the loop_end insn).  */
      65    basic_block tail;
      66  
      67    /* The successor block of the loop.  This is the one the loop_end insn
      68       falls into.  */
      69    basic_block successor;
      70  
      71    /* The last instruction in the tail.  */
      72    rtx_insn *last_insn;
      73  
      74    /* The loop_end insn.  */
      75    rtx_insn *loop_end;
      76  
      77    /* The iteration register.  */
      78    rtx iter_reg;
      79  
      80    /* The new label placed at the beginning of the loop. */
      81    rtx_insn *start_label;
      82  
      83    /* The new label placed at the end of the loop. */
      84    rtx end_label;
      85  
      86    /* The length of the loop.  */
      87    int length;
      88  
      89    /* The nesting depth of the loop.  Innermost loops are given a depth
      90       of 1.  Only successfully optimized doloops are counted; if an inner
      91       loop was marked as bad, it does not increase the depth of its parent
      92       loop.
      93       This value is valid when the target's optimize function is called.  */
      94    int depth;
      95  
      96    /* True if we can't optimize this loop.  */
      97    bool bad;
      98  
      99    /* True if we have visited this loop during the optimization phase.  */
     100    bool visited;
     101  
     102    /* The following values are collected before calling the target's optimize
     103       function and are not valid earlier.  */
     104    
     105    /* Record information about control flow: whether the loop has calls
     106       or asm statements, whether it has edges that jump out of the loop,
     107       or edges that jump within the loop.  */
     108    bool has_call;
     109    bool has_asm;
     110    bool jumps_within;
     111    bool jumps_outof;
     112  
     113    /* True if there is an instruction other than the doloop_end which uses the
     114       iteration register.  */
     115    bool iter_reg_used;
     116    /* True if the iteration register lives past the doloop instruction.  */
     117    bool iter_reg_used_outside;
     118  
     119    /* Hard registers set at any point in the loop, except for the loop counter
     120       register's set in the doloop_end instruction.  */
     121    HARD_REG_SET regs_set_in_loop;
     122  };
     123  
     124  /* A set of hooks to be defined by a target that wants to use the reorg_loops
     125     functionality.
     126  
     127     reorg_loops is intended to handle cases where special hardware loop
     128     setup instructions are required before the loop, for example to set
     129     up loop counter registers that are not exposed to the register
     130     allocator, or to inform the hardware about loop bounds.
     131  
     132     reorg_loops performs analysis to discover loop_end patterns created
     133     by the earlier loop-doloop pass, and sets up a hwloop_info
     134     structure for each such insn it finds.  It then tries to discover
     135     the basic blocks containing the loop by tracking the lifetime of
     136     the iteration register.
     137  
     138     If a valid loop can't be found, the FAIL function is called;
     139     otherwise the OPT function is called for each loop, visiting
     140     innermost loops first and ascending.  */
     141  struct hw_doloop_hooks
     142  {
     143    /* Examine INSN.  If it is a suitable doloop_end pattern, return the
     144       iteration register, which should be a single hard register.
     145       Otherwise, return NULL_RTX.  */
     146    rtx (*end_pattern_reg) (rtx_insn *insn);
     147    /* Optimize LOOP.  The target should perform any additional analysis
     148       (e.g. checking that the loop isn't too long), and then perform
     149       its transformations.  Return true if successful, false if the
     150       loop should be marked bad.  If it returns false, the FAIL
     151       function is called.  */
     152    bool (*opt) (hwloop_info loop);
     153    /* Handle a loop that was marked bad for any reason.  This could be
     154       used to split the doloop_end pattern.  */
     155    void (*fail) (hwloop_info loop);
     156  };
     157  
     158  extern void reorg_loops (bool, struct hw_doloop_hooks *);
     159  
     160  #endif /* GCC_HW_DOLOOP_H */