1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
|
/* Support for simple predicate analysis.
Copyright (C) 2021-2022 Free Software Foundation, Inc.
Contributed by Martin Sebor <msebor@redhat.com>
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.
GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#ifndef GIMPLE_PREDICATE_ANALYSIS_H_INCLUDED
#define GIMPLE_PREDICATE_ANALYSIS_H_INCLUDED
/* Represents a simple Boolean predicate. */
struct pred_info
{
tree pred_lhs;
tree pred_rhs;
enum tree_code cond_code;
bool invert;
};
/* The type to represent a sequence of predicates grouped
with .AND. operation. */
typedef vec<pred_info, va_heap, vl_ptr> pred_chain;
/* The type to represent a sequence of pred_chains grouped
with .OR. operation. */
typedef vec<pred_chain, va_heap, vl_ptr> pred_chain_union;
/* Represents a complex Boolean predicate expression. */
class predicate
{
public:
/* Construct with the specified EVAL object. */
predicate () : m_preds (vNULL) { }
/* Copy. */
predicate (const predicate &rhs) : m_preds (vNULL) { *this = rhs; }
~predicate ();
/* Assign. */
predicate& operator= (const predicate &);
bool is_empty () const
{
return m_preds.is_empty ();
}
const pred_chain_union chain () const
{
return m_preds;
}
void init_from_control_deps (const vec<edge> *, unsigned, bool);
void dump (gimple *, const char *) const;
void normalize (gimple * = NULL, bool = false);
void simplify (gimple * = NULL, bool = false);
bool superset_of (const predicate &) const;
private:
bool includes (const pred_chain &) const;
void push_pred (const pred_info &);
/* Normalization functions. */
void normalize (pred_chain *, pred_info, tree_code, pred_chain *,
hash_set<tree> *);
void normalize (const pred_info &);
void normalize (const pred_chain &);
/* Simplification functions. */
bool simplify_2 ();
bool simplify_3 ();
bool simplify_4 ();
/* Representation of the predicate expression(s). */
pred_chain_union m_preds;
};
/* Represents a complex Boolean predicate expression. */
class uninit_analysis
{
public:
/* Base function object type used to determine whether an expression
is of interest. */
struct func_t
{
typedef unsigned phi_arg_set_t;
/* Return a bitset of PHI arguments of interest. By default returns
bitset with a bit set for each argument. Should be called in
the overriden function first and, if nonzero, the result then
refined as appropriate. */
virtual phi_arg_set_t phi_arg_set (gphi *);
/* Maximum number of PHI arguments supported by phi_arg_set(). */
static constexpr unsigned max_phi_args =
sizeof (phi_arg_set_t) * CHAR_BIT;
};
/* Construct with the specified EVAL object. */
uninit_analysis (func_t &eval)
: m_phi_def_preds (), m_eval (eval) { }
/* Copy. */
uninit_analysis (const uninit_analysis &rhs) = delete;
/* Assign. */
uninit_analysis& operator= (const uninit_analysis&) = delete;
/* Return true if the use by a statement in the basic block of
a PHI operand is ruled out (i.e., guarded) by *THIS. */
bool is_use_guarded (gimple *, basic_block, gphi *, unsigned);
private:
bool is_use_guarded (gimple *, basic_block, gphi *, unsigned,
hash_set<gphi *> *);
bool prune_phi_opnds (gphi *, unsigned, gphi *, tree, tree_code,
hash_set<gphi *> *, bitmap *);
bool overlap (gphi *, unsigned, hash_set<gphi *> *, const predicate &);
void collect_phi_def_edges (gphi *, basic_block, vec<edge> *,
hash_set<gimple *> *);
bool init_from_phi_def (gphi *);
bool init_use_preds (predicate &, basic_block, basic_block);
/* Representation of the predicate expression(s). */
predicate m_phi_def_preds;
/* Callback to evaluate an operand. Return true if it's interesting. */
func_t &m_eval;
};
/* Bit mask handling macros. */
#define MASK_SET_BIT(mask, pos) mask |= (1 << pos)
#define MASK_TEST_BIT(mask, pos) (mask & (1 << pos))
#define MASK_EMPTY(mask) (mask == 0)
#endif // GIMPLE_PREDICATE_ANALYSIS_H_INCLUDED
|