Skip to content

Commit fc4b5cc

Browse files
authored
Merge pull request #4302 from romainbrenguier/refactor/symex_call_stack2
Extract call_stackt class from goto_symex_statet [depends-on: #4294]
2 parents 17e53d6 + 52eb5c7 commit fc4b5cc

16 files changed

+92
-72
lines changed

jbmc/src/java_bytecode/java_bmc_util.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ void java_setup_symex(
2828
// for some reason)
2929
symex.add_loop_unwind_handler(
3030
[&goto_model](
31-
const goto_symex_statet::call_stackt &context,
31+
const call_stackt &context,
3232
unsigned loop_num,
3333
unsigned unwind,
3434
unsigned &max_unwind)

jbmc/src/java_bytecode/java_enum_static_init_unwind_handler.cpp

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -24,8 +24,7 @@ Author: Chris Smowton, [email protected]
2424
/// \param context: the current call stack
2525
/// \return the name of an enclosing function that may be defined on the
2626
/// relevant enum type, or an empty string if we don't find one.
27-
static irep_idt
28-
find_enum_function_on_stack(const goto_symex_statet::call_stackt &context)
27+
static irep_idt find_enum_function_on_stack(const call_stackt &context)
2928
{
3029
static irep_idt reference_array_clone_id =
3130
"java::array[reference].clone:()Ljava/lang/Object;";
@@ -64,7 +63,7 @@ find_enum_function_on_stack(const goto_symex_statet::call_stackt &context)
6463
/// unwind_count is <= the enumeration size, or unknown (defer / no decision)
6564
/// otherwise.
6665
tvt java_enum_static_init_unwind_handler(
67-
const goto_symex_statet::call_stackt &context,
66+
const call_stackt &context,
6867
unsigned loop_number,
6968
unsigned unwind_count,
7069
unsigned &unwind_max,

jbmc/src/java_bytecode/java_enum_static_init_unwind_handler.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ Author: Chris Smowton, [email protected]
1818
#include <util/threeval.h>
1919

2020
tvt java_enum_static_init_unwind_handler(
21-
const goto_symex_statet::call_stackt &context,
21+
const call_stackt &context,
2222
unsigned loop_number,
2323
unsigned unwind_count,
2424
unsigned &unwind_max,

jbmc/src/jbmc/jbmc_parse_options.cpp

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -511,17 +511,17 @@ int jbmc_parse_optionst::doit()
511511
std::function<void(bmct &, const symbol_tablet &)> configure_bmc = nullptr;
512512
if(options.get_bool_option("java-unwind-enum-static"))
513513
{
514-
configure_bmc = [](bmct &bmc, const symbol_tablet &symbol_table) {
515-
bmc.add_loop_unwind_handler(
516-
[&symbol_table](
517-
const goto_symex_statet::call_stackt &context,
518-
unsigned loop_number,
519-
unsigned unwind,
520-
unsigned &max_unwind) {
514+
configure_bmc =
515+
[](bmct &bmc, const symbol_tablet &symbol_table) {
516+
bmc.add_loop_unwind_handler([&symbol_table](
517+
const call_stackt &context,
518+
unsigned loop_number,
519+
unsigned unwind,
520+
unsigned &max_unwind) {
521521
return java_enum_static_init_unwind_handler(
522522
context, loop_number, unwind, max_unwind, symbol_table);
523523
});
524-
};
524+
};
525525
}
526526

527527
object_factory_params.set(options);

src/goto-checker/symex_bmc.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -105,7 +105,7 @@ void symex_bmct::merge_goto(goto_statet &&goto_state, statet &state)
105105

106106
bool symex_bmct::should_stop_unwind(
107107
const symex_targett::sourcet &source,
108-
const goto_symex_statet::call_stackt &context,
108+
const call_stackt &context,
109109
unsigned unwind)
110110
{
111111
const irep_idt id = goto_programt::loop_id(source.function_id, *source.pc);

src/goto-checker/symex_bmc.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,7 @@ class symex_bmct : public goto_symext
4242
/// enforced. They return true to halt unwinding, false to authorise
4343
/// unwinding, or Unknown to indicate they have no opinion.
4444
typedef std::function<
45-
tvt(const goto_symex_statet::call_stackt &, unsigned, unsigned, unsigned &)>
45+
tvt(const call_stackt &, unsigned, unsigned, unsigned &)>
4646
loop_unwind_handlert;
4747

4848
/// Recursion unwind handlers take the function ID, the unwind count so far,
@@ -98,7 +98,7 @@ class symex_bmct : public goto_symext
9898

9999
bool should_stop_unwind(
100100
const symex_targett::sourcet &source,
101-
const goto_symex_statet::call_stackt &context,
101+
const call_stackt &context,
102102
unsigned unwind) override;
103103

104104
bool get_unwind_recursion(

src/goto-symex/call_stack.h

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
/*******************************************************************\
2+
3+
Module: Symbolic Execution
4+
5+
Author: Romain Brenguier, [email protected]
6+
7+
\*******************************************************************/
8+
9+
#ifndef CPROVER_GOTO_SYMEX_CALL_STACK_H
10+
#define CPROVER_GOTO_SYMEX_CALL_STACK_H
11+
12+
#include "frame.h"
13+
14+
class call_stackt : public std::vector<framet>
15+
{
16+
public:
17+
framet &top()
18+
{
19+
PRECONDITION(!empty());
20+
return back();
21+
}
22+
23+
const framet &top() const
24+
{
25+
PRECONDITION(!empty());
26+
return back();
27+
}
28+
29+
framet &new_frame(symex_targett::sourcet calling_location)
30+
{
31+
emplace_back(calling_location);
32+
return back();
33+
}
34+
35+
void pop()
36+
{
37+
PRECONDITION(!empty());
38+
pop_back();
39+
}
40+
41+
const framet &previous_frame()
42+
{
43+
return *(--(--end()));
44+
}
45+
};
46+
47+
#endif // CPROVER_GOTO_SYMEX_CALL_STACK_H

src/goto-symex/goto_symex.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -345,7 +345,7 @@ class goto_symext
345345
/// \return true indicates abort, with false we continue
346346
virtual bool should_stop_unwind(
347347
const symex_targett::sourcet &source,
348-
const goto_symex_statet::call_stackt &context,
348+
const call_stackt &context,
349349
unsigned unwind);
350350

351351
virtual void loop_bound_exceeded(statet &state, const exprt &guard);

src/goto-symex/goto_symex_state.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ goto_symex_statet::goto_symex_statet(const symex_targett::sourcet &_source)
3333
: goto_statet(_source), symex_target(nullptr), record_events(true), dirty()
3434
{
3535
threads.resize(1);
36-
new_frame();
36+
call_stack().new_frame(source);
3737
}
3838

3939
goto_symex_statet::~goto_symex_statet()=default;

src/goto-symex/goto_symex_state.h

Lines changed: 1 addition & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ Author: Daniel Kroening, [email protected]
2424
#include <util/make_unique.h>
2525
#include <goto-programs/goto_function.h>
2626

27+
#include "call_stack.h"
2728
#include "frame.h"
2829
#include "goto_state.h"
2930
#include "renaming_level.h"
@@ -126,18 +127,13 @@ class goto_symex_statet final : public goto_statet
126127
l1_typest l1_types;
127128

128129
public:
129-
// gotos
130-
typedef std::list<goto_statet> goto_state_listt;
131-
132130
// guards
133131
static irep_idt guard_identifier()
134132
{
135133
static irep_idt id = "goto_symex::\\guard";
136134
return id;
137135
}
138136

139-
typedef std::vector<framet> call_stackt;
140-
141137
call_stackt &call_stack()
142138
{
143139
PRECONDITION(source.thread_nr < threads.size());
@@ -150,28 +146,6 @@ class goto_symex_statet final : public goto_statet
150146
return threads[source.thread_nr].call_stack;
151147
}
152148

153-
framet &top()
154-
{
155-
PRECONDITION(!call_stack().empty());
156-
return call_stack().back();
157-
}
158-
159-
const framet &top() const
160-
{
161-
PRECONDITION(!call_stack().empty());
162-
return call_stack().back();
163-
}
164-
165-
framet &new_frame()
166-
{
167-
call_stack().emplace_back(source);
168-
return top();
169-
}
170-
171-
void pop_frame() { call_stack().pop_back(); }
172-
173-
const framet &previous_frame() { return *(--(--call_stack().end())); }
174-
175149
void print_backtrace(std::ostream &) const;
176150

177151
// threads

src/goto-symex/symex_assign.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,7 @@ void goto_symext::symex_assign(statet &state, const code_assignt &code)
6565
assignment_type=symex_targett::assignment_typet::HIDDEN;
6666

6767
// We hide if we are in a hidden function.
68-
if(state.top().hidden_function)
68+
if(state.call_stack().top().hidden_function)
6969
assignment_type=symex_targett::assignment_typet::HIDDEN;
7070

7171
// We hide if we are executing a hidden instruction.

src/goto-symex/symex_decl.cpp

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -78,10 +78,9 @@ void goto_symext::symex_decl(statet &state, const symbol_exprt &expr)
7878

7979
// we hide the declaration of auxiliary variables
8080
// and if the statement itself is hidden
81-
bool hidden=
82-
ns.lookup(expr.get_identifier()).is_auxiliary ||
83-
state.top().hidden_function ||
84-
state.source.pc->source_location.get_hide();
81+
bool hidden = ns.lookup(expr.get_identifier()).is_auxiliary ||
82+
state.call_stack().top().hidden_function ||
83+
state.source.pc->source_location.get_hide();
8584

8685
target.decl(
8786
state.guard.as_expr(),

src/goto-symex/symex_function_call.cpp

Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -124,7 +124,7 @@ void goto_symext::parameter_assignments(
124124
assignment_typet assignment_type;
125125

126126
// We hide if we are in a hidden function.
127-
if(state.top().hidden_function)
127+
if(state.call_stack().top().hidden_function)
128128
assignment_type =
129129
symex_targett::assignment_typet::HIDDEN_ACTUAL_PARAMETER;
130130
else
@@ -243,10 +243,10 @@ void goto_symext::symex_function_call_code(
243243
if(emplace_safe_pointers_result.second)
244244
emplace_safe_pointers_result.first->second(goto_function.body);
245245

246-
const bool stop_recursing=get_unwind_recursion(
246+
const bool stop_recursing = get_unwind_recursion(
247247
identifier,
248248
state.source.thread_nr,
249-
state.top().loop_iterations[identifier].count);
249+
state.call_stack().top().loop_iterations[identifier].count);
250250

251251
// see if it's too much
252252
if(stop_recursing)
@@ -274,7 +274,8 @@ void goto_symext::symex_function_call_code(
274274
a = state.rename(std::move(a), ns);
275275

276276
// we hide the call if the caller and callee are both hidden
277-
const bool hidden = state.top().hidden_function && goto_function.is_hidden();
277+
const bool hidden =
278+
state.call_stack().top().hidden_function && goto_function.is_hidden();
278279

279280
// record the call
280281
target.function_call(
@@ -302,7 +303,7 @@ void goto_symext::symex_function_call_code(
302303

303304
// produce a new frame
304305
PRECONDITION(!state.call_stack().empty());
305-
framet &frame = state.new_frame();
306+
framet &frame = state.call_stack().new_frame(state.source);
306307

307308
// preserve locality of local variables
308309
locality(identifier, state, goto_function, ns);
@@ -315,7 +316,7 @@ void goto_symext::symex_function_call_code(
315316
frame.function_identifier=identifier;
316317
frame.hidden_function=goto_function.is_hidden();
317318

318-
const framet &p_frame = state.previous_frame();
319+
const framet &p_frame = state.call_stack().previous_frame();
319320
for(const auto &pair : p_frame.loop_iterations)
320321
{
321322
if(pair.second.is_recursion)
@@ -336,7 +337,7 @@ static void pop_frame(goto_symext::statet &state)
336337
PRECONDITION(!state.call_stack().empty());
337338

338339
{
339-
framet &frame = state.top();
340+
const framet &frame = state.call_stack().top();
340341

341342
// restore program counter
342343
symex_transition(state, frame.calling_location.pc, false);
@@ -365,13 +366,13 @@ static void pop_frame(goto_symext::statet &state)
365366
}
366367
}
367368

368-
state.pop_frame();
369+
state.call_stack().pop();
369370
}
370371

371372
/// do function call by inlining
372373
void goto_symext::symex_end_of_function(statet &state)
373374
{
374-
const bool hidden = state.top().hidden_function;
375+
const bool hidden = state.call_stack().top().hidden_function;
375376

376377
// first record the return
377378
target.function_return(
@@ -397,7 +398,7 @@ static void locality(
397398

398399
get_local_identifiers(goto_function, local_identifiers);
399400

400-
framet &frame = state.top();
401+
framet &frame = state.call_stack().top();
401402

402403
for(std::set<irep_idt>::const_iterator
403404
it=local_identifiers.begin();

src/goto-symex/symex_goto.cpp

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,6 @@ Author: Daniel Kroening, [email protected]
2525
void goto_symext::symex_goto(statet &state)
2626
{
2727
const goto_programt::instructiont &instruction=*state.source.pc;
28-
framet &frame = state.top();
2928

3029
exprt new_guard = instruction.get_condition();
3130
clean_expr(new_guard, state, false);
@@ -80,7 +79,7 @@ void goto_symext::symex_goto(statet &state)
8079
const auto loop_id =
8180
goto_programt::loop_id(state.source.function_id, *state.source.pc);
8281

83-
unsigned &unwind = frame.loop_iterations[loop_id].count;
82+
unsigned &unwind = state.call_stack().top().loop_iterations[loop_id].count;
8483
unwind++;
8584

8685
if(should_stop_unwind(state.source, state.call_stack(), unwind))
@@ -210,7 +209,7 @@ void goto_symext::symex_goto(statet &state)
210209
// put a copy of the current state into the state-queue, to be used by
211210
// merge_gotos when we visit new_state_pc
212211
framet::goto_state_listt &goto_state_list =
213-
state.top().goto_state_map[new_state_pc];
212+
state.call_stack().top().goto_state_map[new_state_pc];
214213
goto_state_list.emplace_back(state);
215214

216215
symex_transition(state, state_pc, backward);
@@ -288,7 +287,7 @@ void goto_symext::symex_goto(statet &state)
288287

289288
void goto_symext::merge_gotos(statet &state)
290289
{
291-
framet &frame = state.top();
290+
framet &frame = state.call_stack().top();
292291

293292
// first, see if this is a target at all
294293
auto state_map_it = frame.goto_state_map.find(state.source.pc);
@@ -563,7 +562,7 @@ void goto_symext::loop_bound_exceeded(
563562

564563
bool goto_symext::should_stop_unwind(
565564
const symex_targett::sourcet &,
566-
const goto_symex_statet::call_stackt &,
565+
const call_stackt &,
567566
unsigned)
568567
{
569568
// by default, we keep going

src/goto-symex/symex_main.cpp

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ void symex_transition(
5353
// 1. the transition from state.source.pc to "to" is not a backwards goto
5454
// or
5555
// 2. we are arriving from an outer loop
56-
framet &frame = state.top();
56+
framet &frame = state.call_stack().top();
5757
const goto_programt::instructiont &instruction=*to;
5858
for(const auto &i_e : instruction.incoming_edges)
5959
if(i_e->is_goto() && i_e->is_backwards_goto() &&
@@ -257,7 +257,7 @@ void goto_symext::symex_with_state(
257257
// as state.symbol_table might go out of scope
258258
reset_namespacet reset_ns(ns);
259259

260-
PRECONDITION(state.top().end_of_function->is_end_function());
260+
PRECONDITION(state.call_stack().top().end_of_function->is_end_function());
261261

262262
symex_threaded_step(state, get_goto_function);
263263
if(should_pause_symex)
@@ -323,9 +323,10 @@ std::unique_ptr<goto_symext::statet> goto_symext::initialize_entry_point_state(
323323

324324
goto_programt::const_targett limit =
325325
std::prev(start_function->body.instructions.end());
326-
state->top().end_of_function = limit;
327-
state->top().calling_location.pc = state->top().end_of_function;
328-
state->top().hidden_function = start_function->is_hidden();
326+
state->call_stack().top().end_of_function = limit;
327+
state->call_stack().top().calling_location.pc =
328+
state->call_stack().top().end_of_function;
329+
state->call_stack().top().hidden_function = start_function->is_hidden();
329330

330331
state->symex_target = &target;
331332

0 commit comments

Comments
 (0)