12
12
#ifndef CPROVER_GOTO_PROGRAMS_CFG_H
13
13
#define CPROVER_GOTO_PROGRAMS_CFG_H
14
14
15
- #include < util/std_expr .h>
15
+ #include < util/dense_integer_map .h>
16
16
#include < util/graph.h>
17
+ #include < util/std_expr.h>
17
18
18
19
#include " goto_functions.h"
19
20
@@ -31,6 +32,29 @@ struct cfg_base_nodet:public graph_nodet<empty_edget>, public T
31
32
I PC;
32
33
};
33
34
35
+ // / Functor to convert cfg nodes into dense integers, used by \ref cfg_baset.
36
+ // / Default implementation: the identity function.
37
+ template <class T >
38
+ class cfg_instruction_to_dense_integert
39
+ {
40
+ public:
41
+ std::size_t operator ()(T &&t) const
42
+ {
43
+ return std::forward<T>(identity_functort{}(t));
44
+ }
45
+ };
46
+
47
+ // / GOTO-instruction to location number functor.
48
+ template <>
49
+ class cfg_instruction_to_dense_integert <goto_programt::const_targett>
50
+ {
51
+ public:
52
+ std::size_t operator ()(const goto_programt::const_targett &t) const
53
+ {
54
+ return t->location_number ;
55
+ }
56
+ };
57
+
34
58
// / A multi-procedural control flow graph (CFG) whose nodes store references to
35
59
// / instructions in a GOTO program.
36
60
// /
@@ -69,7 +93,11 @@ class cfg_baset:public grapht< cfg_base_nodet<T, I> >
69
93
70
94
class entry_mapt final
71
95
{
72
- typedef std::map<goto_programt::const_targett, entryt> data_typet;
96
+ typedef dense_integer_mapt<
97
+ goto_programt::const_targett,
98
+ entryt,
99
+ cfg_instruction_to_dense_integert<goto_programt::const_targett>>
100
+ data_typet;
73
101
data_typet data;
74
102
75
103
public:
@@ -114,6 +142,12 @@ class cfg_baset:public grapht< cfg_base_nodet<T, I> >
114
142
{
115
143
return data.at (t);
116
144
}
145
+
146
+ template <class Iter >
147
+ void setup_for_keys (Iter begin, Iter end)
148
+ {
149
+ data.setup_for_keys (begin, end);
150
+ }
117
151
};
118
152
entry_mapt entry_map;
119
153
@@ -173,12 +207,30 @@ class cfg_baset:public grapht< cfg_base_nodet<T, I> >
173
207
void operator ()(
174
208
const goto_functionst &goto_functions)
175
209
{
210
+ std::vector<goto_programt::const_targett> possible_keys;
211
+ for (const auto &id_and_function : goto_functions.function_map )
212
+ {
213
+ const auto &instructions = id_and_function.second .body .instructions ;
214
+ possible_keys.reserve (
215
+ possible_keys.size () +
216
+ std::distance (instructions.begin (), instructions.end ()));
217
+ for (auto it = instructions.begin (); it != instructions.end (); ++it)
218
+ possible_keys.push_back (it);
219
+ }
220
+ entry_map.setup_for_keys (possible_keys.begin (), possible_keys.end ());
176
221
compute_edges (goto_functions);
177
222
}
178
223
179
224
void operator ()(P &goto_program)
180
225
{
181
226
goto_functionst goto_functions;
227
+ std::vector<goto_programt::const_targett> possible_keys;
228
+ const auto &instructions = goto_program.instructions ;
229
+ possible_keys.reserve (
230
+ std::distance (instructions.begin (), instructions.end ()));
231
+ for (auto it = instructions.begin (); it != instructions.end (); ++it)
232
+ possible_keys.push_back (it);
233
+ entry_map.setup_for_keys (possible_keys.begin (), possible_keys.end ());
182
234
compute_edges (goto_functions, goto_program);
183
235
}
184
236
0 commit comments