Line data Source code
1 : /* Iterator routines for manipulating GENERIC tree statement list. -*- C++ -*- 2 : Copyright (C) 2003-2023 Free Software Foundation, Inc. 3 : Contributed by Andrew MacLeod <amacleod@redhat.com> 4 : 5 : This file is part of GCC. 6 : 7 : GCC is free software; you can redistribute it and/or modify 8 : it under the terms of the GNU General Public License as published by 9 : the Free Software Foundation; either version 3, or (at your option) 10 : any later version. 11 : 12 : GCC is distributed in the hope that it will be useful, 13 : but WITHOUT ANY WARRANTY; without even the implied warranty of 14 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 : GNU General Public License 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 : 22 : /* This file is dependent upon the implementation of tree's. It provides an 23 : abstract interface to the tree objects such that if all tree creation and 24 : manipulations are done through this interface, we can easily change the 25 : implementation of tree's, and not impact other code. */ 26 : 27 : #ifndef GCC_TREE_ITERATOR_H 28 : #define GCC_TREE_ITERATOR_H 1 29 : 30 : /* Iterator object for GENERIC or GIMPLE TREE statements. */ 31 : 32 : struct tree_stmt_iterator { 33 : struct tree_statement_list_node *ptr; 34 : tree container; 35 : 36 : /* No need for user-defined constructors, the implicit definitions (or 37 : aggregate initialization) are fine. */ 38 : 39 679128980 : bool operator== (tree_stmt_iterator b) const 40 153527167 : { return b.ptr == ptr && b.container == container; } 41 774082067 : bool operator!= (tree_stmt_iterator b) const { return !(*this == b); } 42 532559708 : tree_stmt_iterator &operator++ () { ptr = ptr->next; return *this; } 43 4470 : tree_stmt_iterator &operator-- () { ptr = ptr->prev; return *this; } 44 : tree_stmt_iterator operator++ (int) 45 : { tree_stmt_iterator x = *this; ++*this; return x; } 46 : tree_stmt_iterator operator-- (int) 47 : { tree_stmt_iterator x = *this; --*this; return x; } 48 10932120 : tree &operator* () { return ptr->stmt; } 49 : tree operator* () const { return ptr->stmt; } 50 : }; 51 : 52 : inline tree_stmt_iterator 53 189709613 : tsi_start (tree t) 54 : { 55 189709613 : tree_stmt_iterator i; 56 : 57 189709613 : i.ptr = STATEMENT_LIST_HEAD (t); 58 189709613 : i.container = t; 59 : 60 189709613 : return i; 61 : } 62 : 63 : inline tree_stmt_iterator 64 7632807 : tsi_last (tree t) 65 : { 66 7632807 : tree_stmt_iterator i; 67 : 68 7632807 : i.ptr = STATEMENT_LIST_TAIL (t); 69 7632807 : i.container = t; 70 : 71 7632807 : return i; 72 : } 73 : 74 : inline bool 75 27150327 : tsi_end_p (tree_stmt_iterator i) 76 : { 77 27150327 : return i.ptr == NULL; 78 : } 79 : 80 : inline bool 81 6980603 : tsi_one_before_end_p (tree_stmt_iterator i) 82 : { 83 6980603 : return i.ptr != NULL && i.ptr->next == NULL; 84 : } 85 : 86 : inline void 87 1014659 : tsi_next (tree_stmt_iterator *i) 88 : { 89 678158 : ++(*i); 90 349278 : } 91 : 92 : inline void 93 4470 : tsi_prev (tree_stmt_iterator *i) 94 : { 95 4470 : --(*i); 96 4470 : } 97 : 98 : inline tree * 99 3210 : tsi_stmt_ptr (tree_stmt_iterator i) 100 : { 101 3210 : return &(*i); 102 : } 103 : 104 : inline tree 105 16261939 : tsi_stmt (tree_stmt_iterator i) 106 : { 107 16261939 : return *i; 108 : } 109 : 110 : /* Make tree_stmt_iterator work as a C++ range, e.g. 111 : for (tree stmt : tsi_range (stmt_list)) { ... } */ 112 : class tsi_range 113 : { 114 : tree t; 115 : public: 116 154327226 : tsi_range (tree t): t(t) { } 117 154327226 : tree_stmt_iterator begin() const { return tsi_start (t); } 118 154327226 : tree_stmt_iterator end() const { return { nullptr, t }; } 119 : }; 120 : 121 : enum tsi_iterator_update 122 : { 123 : TSI_NEW_STMT, /* Only valid when single statement is added, move 124 : iterator to it. */ 125 : TSI_SAME_STMT, /* Leave the iterator at the same statement. */ 126 : TSI_CHAIN_START, /* Only valid when chain of statements is added, move 127 : iterator to the first statement in the chain. */ 128 : TSI_CHAIN_END, /* Only valid when chain of statements is added, move 129 : iterator to the last statement in the chain. */ 130 : TSI_CONTINUE_LINKING /* Move iterator to whatever position is suitable for 131 : linking other statements/chains of statements in 132 : the same direction. */ 133 : }; 134 : 135 : extern void tsi_link_before (tree_stmt_iterator *, tree, 136 : enum tsi_iterator_update); 137 : extern void tsi_link_after (tree_stmt_iterator *, tree, 138 : enum tsi_iterator_update); 139 : 140 : extern void tsi_delink (tree_stmt_iterator *); 141 : 142 : extern tree alloc_stmt_list (void); 143 : extern void free_stmt_list (tree); 144 : extern void append_to_statement_list (tree, tree *); 145 : extern void append_to_statement_list_force (tree, tree *); 146 : extern tree expr_first (tree); 147 : extern tree expr_last (tree); 148 : extern tree expr_single (tree); 149 : 150 : #endif /* GCC_TREE_ITERATOR_H */