@@ -30,6 +30,7 @@ Date: February 2016
30
30
#include < langapi/language_util.h>
31
31
32
32
#include < util/c_types.h>
33
+ #include < util/exception_utils.h>
33
34
#include < util/expr_util.h>
34
35
#include < util/find_symbols.h>
35
36
#include < util/format_expr.h>
@@ -47,7 +48,6 @@ Date: February 2016
47
48
#include " instrument_spec_assigns.h"
48
49
#include " memory_predicates.h"
49
50
#include " utils.h"
50
-
51
51
// / Decorator for \ref message_handlert that keeps track of warnings
52
52
// / occuring when inlining a function.
53
53
// /
@@ -729,7 +729,7 @@ code_contractst::create_ensures_instruction(
729
729
return std::make_pair (std::move (ensures_program), std::move (history));
730
730
}
731
731
732
- bool code_contractst::apply_function_contract (
732
+ void code_contractst::apply_function_contract (
733
733
const irep_idt &function,
734
734
const source_locationt &location,
735
735
goto_programt &function_body,
@@ -932,7 +932,6 @@ bool code_contractst::apply_function_contract(
932
932
933
933
// Add this function to the set of replaced functions.
934
934
summarized.insert (target_function);
935
- return false ;
936
935
}
937
936
938
937
void code_contractst::apply_loop_contract (
@@ -1225,17 +1224,14 @@ goto_functionst &code_contractst::get_goto_functions()
1225
1224
return goto_functions;
1226
1225
}
1227
1226
1228
- bool code_contractst::check_frame_conditions_function (const irep_idt &function)
1227
+ void code_contractst::check_frame_conditions_function (const irep_idt &function)
1229
1228
{
1230
1229
// Get the function object before instrumentation.
1231
1230
auto function_obj = goto_functions.function_map .find (function);
1232
- if (function_obj == goto_functions.function_map .end ())
1233
- {
1234
- log .error () << " Could not find function '" << function
1235
- << " ' in goto-program; not enforcing contracts."
1236
- << messaget::eom;
1237
- return true ;
1238
- }
1231
+
1232
+ INVARIANT (
1233
+ function_obj != goto_functions.function_map .end (),
1234
+ " Function '" + id2string (function) + " 'must exist in the goto program" );
1239
1235
1240
1236
const auto &goto_function = function_obj->second ;
1241
1237
auto &function_body = function_obj->second .body ;
@@ -1316,11 +1312,9 @@ bool code_contractst::check_frame_conditions_function(const irep_idt &function)
1316
1312
function_body.instructions .end (),
1317
1313
skip_function_paramst::YES,
1318
1314
cfg_info_opt);
1319
-
1320
- return false ;
1321
1315
}
1322
1316
1323
- bool code_contractst::enforce_contract (const irep_idt &function)
1317
+ void code_contractst::enforce_contract (const irep_idt &function)
1324
1318
{
1325
1319
// Add statements to the source function
1326
1320
// to ensure assigns clause is respected.
@@ -1333,13 +1327,9 @@ bool code_contractst::enforce_contract(const irep_idt &function)
1333
1327
const irep_idt original (function);
1334
1328
1335
1329
auto old_function = goto_functions.function_map .find (original);
1336
- if (old_function == goto_functions.function_map .end ())
1337
- {
1338
- log .error () << " Could not find function '" << function
1339
- << " ' in goto-program; not enforcing contracts."
1340
- << messaget::eom;
1341
- return true ;
1342
- }
1330
+ INVARIANT (
1331
+ old_function != goto_functions.function_map .end (),
1332
+ " Function to replace must exist in the program." );
1343
1333
1344
1334
std::swap (goto_functions.function_map [mangled], old_function->second );
1345
1335
goto_functions.function_map .erase (old_function);
@@ -1379,8 +1369,6 @@ bool code_contractst::enforce_contract(const irep_idt &function)
1379
1369
wrapper.parameter_identifiers = mangled_fun->second .parameter_identifiers ;
1380
1370
wrapper.body .add (goto_programt::make_end_function (sl));
1381
1371
add_contract_check (original, mangled, wrapper.body );
1382
-
1383
- return false ;
1384
1372
}
1385
1373
1386
1374
void code_contractst::add_contract_check (
@@ -1536,12 +1524,29 @@ void code_contractst::add_contract_check(
1536
1524
dest.destructive_insert (dest.instructions .begin (), check);
1537
1525
}
1538
1526
1539
- bool code_contractst::replace_calls (const std::set<std::string> &to_replace)
1527
+ void code_contractst::check_all_functions_found (
1528
+ const std::set<std::string> &functions) const
1529
+ {
1530
+ for (const auto &function : functions)
1531
+ {
1532
+ if (
1533
+ goto_functions.function_map .find (function) ==
1534
+ goto_functions.function_map .end ())
1535
+ {
1536
+ throw invalid_input_exceptiont (
1537
+ " Function '" + function + " ' was not found in the GOTO program." );
1538
+ }
1539
+ }
1540
+ }
1541
+
1542
+ void code_contractst::replace_calls (const std::set<std::string> &to_replace)
1540
1543
{
1541
1544
if (to_replace.empty ())
1542
- return false ;
1545
+ return ;
1546
+
1547
+ log .status () << " Replacing function calls with contracts" << messaget::eom;
1543
1548
1544
- bool fail = false ;
1549
+ check_all_functions_found (to_replace) ;
1545
1550
1546
1551
for (auto &goto_function : goto_functions.function_map )
1547
1552
{
@@ -1559,7 +1564,7 @@ bool code_contractst::replace_calls(const std::set<std::string> &to_replace)
1559
1564
if (found == to_replace.end ())
1560
1565
continue ;
1561
1566
1562
- fail |= apply_function_contract (
1567
+ apply_function_contract (
1563
1568
goto_function.first ,
1564
1569
ins->source_location (),
1565
1570
goto_function.second .body ,
@@ -1568,15 +1573,10 @@ bool code_contractst::replace_calls(const std::set<std::string> &to_replace)
1568
1573
}
1569
1574
}
1570
1575
1571
- if (fail)
1572
- return true ;
1573
-
1574
1576
for (auto &goto_function : goto_functions.function_map )
1575
1577
remove_skip (goto_function.second .body );
1576
1578
1577
1579
goto_functions.update ();
1578
-
1579
- return false ;
1580
1580
}
1581
1581
1582
1582
void code_contractst::apply_loop_contracts ()
@@ -1585,27 +1585,15 @@ void code_contractst::apply_loop_contracts()
1585
1585
apply_loop_contract (goto_function.first , goto_function.second );
1586
1586
}
1587
1587
1588
- bool code_contractst::enforce_contracts (const std::set<std::string> &to_enforce)
1588
+ void code_contractst::enforce_contracts (const std::set<std::string> &to_enforce)
1589
1589
{
1590
1590
if (to_enforce.empty ())
1591
- return false ;
1591
+ return ;
1592
1592
1593
- bool fail = false ;
1593
+ log . status () << " Enforcing contracts " << messaget ::eom ;
1594
1594
1595
- for (const auto &function : to_enforce)
1596
- {
1597
- auto goto_function = goto_functions.function_map .find (function);
1598
- if (goto_function == goto_functions.function_map .end ())
1599
- {
1600
- fail = true ;
1601
- log .error () << " Could not find function '" << function
1602
- << " ' in goto-program; not enforcing contracts."
1603
- << messaget::eom;
1604
- continue ;
1605
- }
1595
+ check_all_functions_found (to_enforce);
1606
1596
1607
- if (!fail)
1608
- fail = enforce_contract (function);
1609
- }
1610
- return fail;
1597
+ for (const auto &function : to_enforce)
1598
+ enforce_contract (function);
1611
1599
}
0 commit comments