Skip to content

Commit 8c4eb38

Browse files
Merge pull request #5 from NlightNFotis/custom_exception
Implementation of invalid user input exception
2 parents 45df6d8 + 0248d40 commit 8c4eb38

9 files changed

+128
-32
lines changed

src/cbmc/bmc.cpp

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ Author: Daniel Kroening, [email protected]
1414
#include <chrono>
1515
#include <iostream>
1616

17+
#include <util/exception_utils.h>
1718
#include <util/exit_codes.h>
1819

1920
#include <langapi/language_util.h>
@@ -296,9 +297,8 @@ void bmct::get_memory_model()
296297
memory_model=util_make_unique<memory_model_psot>(ns);
297298
else
298299
{
299-
error() << "Invalid memory model " << mm
300-
<< " -- use one of sc, tso, pso" << eom;
301-
throw "invalid memory model";
300+
throw invalid_user_input_exceptiont(
301+
"Invalid parameter " + mm, "--mm", "values of sc, tso, pso");
302302
}
303303
}
304304

src/cbmc/bv_cbmc.cpp

Lines changed: 5 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -9,16 +9,13 @@ Author: Daniel Kroening, [email protected]
99
#include "bv_cbmc.h"
1010

1111
#include <util/arith_tools.h>
12+
#include <util/invariant.h>
1213
#include <util/replace_expr.h>
1314

1415
bvt bv_cbmct::convert_waitfor(const exprt &expr)
1516
{
16-
if(expr.operands().size()!=4)
17-
{
18-
error().source_location=expr.find_source_location();
19-
error() << "waitfor expected to have four operands" << eom;
20-
throw 0;
21-
}
17+
DATA_INVARIANT(expr.operands().size() != 4,
18+
"waitfor expression is expected to have four operands");
2219

2320
const exprt &old_cycle=expr.op0();
2421
const exprt &cycle_var=expr.op1();
@@ -27,12 +24,8 @@ bvt bv_cbmct::convert_waitfor(const exprt &expr)
2724
const exprt new_cycle = make_free_bv_expr(expr.type());
2825

2926
mp_integer bound_value;
30-
if(to_integer(bound, bound_value))
31-
{
32-
error().source_location=expr.find_source_location();
33-
error() << "waitfor bound must be a constant" << eom;
34-
throw 0;
35-
}
27+
bool successful_cast = to_integer(bound, bound_value);
28+
INVARIANT(successful_cast, "waitfor bound must be a constant");
3629

3730
{
3831
// constraint: new_cycle>=old_cycle

src/cbmc/cbmc_parse_options.cpp

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ Author: Daniel Kroening, [email protected]
6767
#include "version.h"
6868

6969
cbmc_parse_optionst::cbmc_parse_optionst(int argc, const char **argv):
70-
parse_options_baset(CBMC_OPTIONS, argc, argv),
70+
parse_optionst(CBMC_OPTIONS, argc, argv, ui_message_handler),
7171
xml_interfacet(cmdline),
7272
messaget(ui_message_handler),
7373
ui_message_handler(cmdline, "CBMC " CBMC_VERSION),
@@ -79,7 +79,7 @@ ::cbmc_parse_optionst::cbmc_parse_optionst(
7979
int argc,
8080
const char **argv,
8181
const std::string &extra_options):
82-
parse_options_baset(CBMC_OPTIONS+extra_options, argc, argv),
82+
parse_optionst(CBMC_OPTIONS+extra_options, argc, argv, ui_message_handler),
8383
xml_interfacet(cmdline),
8484
messaget(ui_message_handler),
8585
ui_message_handler(cmdline, "CBMC " CBMC_VERSION),

src/cbmc/cbmc_parse_options.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,7 @@ class optionst;
7878
// clang-format on
7979

8080
class cbmc_parse_optionst:
81-
public parse_options_baset,
81+
public parse_optionst,
8282
public xml_interfacet,
8383
public messaget
8484
{

src/cbmc/cbmc_solvers.cpp

Lines changed: 35 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -14,9 +14,11 @@ Author: Daniel Kroening, [email protected]
1414
#include <fstream>
1515
#include <iostream>
1616
#include <memory>
17+
#include <string>
1718

18-
#include <util/unicode.h>
19+
#include <util/exception_utils.h>
1920
#include <util/make_unique.h>
21+
#include <util/unicode.h>
2022

2123
#include <solvers/sat/satcheck.h>
2224
#include <solvers/refinement/bv_refinement.h>
@@ -169,8 +171,10 @@ std::unique_ptr<cbmc_solverst::solvert> cbmc_solverst::get_smt2(
169171
{
170172
if(solver==smt2_dect::solvert::GENERIC)
171173
{
172-
error() << "please use --outfile" << eom;
173-
throw 0;
174+
throw invalid_user_input_exceptiont(
175+
"Failed to provide a filename",
176+
"--outfile",
177+
"provide a filename with --outfile");
174178
}
175179

176180
auto smt2_dec=
@@ -214,8 +218,8 @@ std::unique_ptr<cbmc_solverst::solvert> cbmc_solverst::get_smt2(
214218

215219
if(!*out)
216220
{
217-
error() << "failed to open " << filename << eom;
218-
throw 0;
221+
throw invalid_user_input_exceptiont(
222+
"Failed to open suggested file: " + filename, "--outfile");
219223
}
220224

221225
auto smt2_conv=
@@ -238,20 +242,38 @@ std::unique_ptr<cbmc_solverst::solvert> cbmc_solverst::get_smt2(
238242

239243
void cbmc_solverst::no_beautification()
240244
{
241-
if(options.get_bool_option("beautify"))
245+
bool beautify = options.get_bool_option("beautify");
246+
247+
if(beautify)
242248
{
243-
error() << "sorry, this solver does not support beautification" << eom;
244-
throw 0;
249+
throw invalid_user_input_exceptiont(
250+
"Sorry, this solver does not support beautification",
251+
"--beautify");
245252
}
246253
}
247254

248255
void cbmc_solverst::no_incremental_check()
249256
{
250-
if(options.get_bool_option("all-properties") ||
251-
options.get_option("cover")!="" ||
252-
options.get_option("incremental-check")!="")
257+
bool all_properties = options.get_bool_option("all-properties");
258+
bool cover = options.get_option("cover") != "";
259+
bool incremental_check = options.get_option("incremental-check") != "";
260+
261+
if(all_properties)
262+
{
263+
throw invalid_user_input_exceptiont(
264+
"Sorry, this solver does not support incremental solving",
265+
"--all_properties");
266+
}
267+
else if(cover)
268+
{
269+
throw invalid_user_input_exceptiont(
270+
"Sorry, this solver does not support incremental solving",
271+
"--cover");
272+
}
273+
else if(incremental_check)
253274
{
254-
error() << "sorry, this solver does not support incremental solving" << eom;
255-
throw 0;
275+
throw invalid_user_input_exceptiont(
276+
"Sorry, this solver does not support incremental solving",
277+
"--incremental-check");
256278
}
257279
}

src/cbmc/show_vcc.cpp

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ Author: Daniel Kroening, [email protected]
1717
#include <langapi/mode.h>
1818
#include <langapi/language_util.h>
1919

20+
#include <util/exception_utils.h>
2021
#include <util/json.h>
2122
#include <util/json_expr.h>
2223

@@ -143,7 +144,8 @@ void bmct::show_vcc()
143144
{
144145
of.open(filename);
145146
if(!of)
146-
throw "failed to open file "+filename;
147+
throw invalid_user_input_exceptiont(
148+
"Failed to open file: " + filename, "--outfile");
147149
}
148150

149151
std::ostream &out=have_file?of:std::cout;

src/util/exception_utils.h

Lines changed: 41 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
/*******************************************************************\
2+
3+
Module: Exception helper utilities
4+
5+
Author: Fotis Koutoulakis, [email protected]
6+
7+
\*******************************************************************/
8+
9+
#ifndef CPROVER_UTIL_EXCEPTION_UTILS_H
10+
#define CPROVER_UTIL_EXCEPTION_UTILS_H
11+
12+
#include <string>
13+
14+
class invalid_user_input_exceptiont
15+
{
16+
std::string reason;
17+
std::string option;
18+
std::string correct_input;
19+
20+
public:
21+
invalid_user_input_exceptiont(
22+
std::string reason,
23+
std::string option,
24+
std::string correct_input = "")
25+
: reason(reason), option(option), correct_input(correct_input)
26+
{
27+
}
28+
29+
std::string what() const noexcept
30+
{
31+
std::string res;
32+
res += "\nInvalid User Input Exception\n";
33+
res += "Option: " + option + "\n";
34+
res += "Reason: " + reason;
35+
// Print an optional correct usage message assuming correct input parameters have been passed
36+
res += correct_input.empty() ? "\n" : " Try: " + correct_input + "\n";
37+
return res;
38+
}
39+
};
40+
41+
#endif // CPROVER_UTIL_EXCEPTION_UTILS_H

src/util/parse_options.cpp

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,8 @@ Author: Daniel Kroening, [email protected]
1818
#endif
1919

2020
#include "cmdline.h"
21+
#include "exception_utils.h"
22+
#include "exit_codes.h"
2123
#include "signal_catcher.h"
2224

2325
parse_options_baset::parse_options_baset(
@@ -82,3 +84,19 @@ banner_string(const std::string &front_end, const std::string &version)
8284
return "* *" + std::string(left_padding, ' ') + version_str +
8385
std::string(right_padding, ' ') + "* *";
8486
}
87+
88+
int parse_optionst::main()
89+
{
90+
// catch all exceptions here so that this code is not duplicated
91+
// for each tool
92+
try
93+
{
94+
return parse_options_baset::main();
95+
}
96+
catch(invalid_user_input_exceptiont &e)
97+
{
98+
message.error() << e.what() << messaget::eom;
99+
return CPROVER_EXIT_EXCEPTION;
100+
}
101+
return CPROVER_EXIT_SUCCESS;
102+
}

src/util/parse_options.h

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ Author: Daniel Kroening, [email protected]
1313
#include <string>
1414

1515
#include "cmdline.h"
16+
#include "message.h"
1617

1718
class parse_options_baset
1819
{
@@ -35,6 +36,25 @@ class parse_options_baset
3536
bool parse_result;
3637
};
3738

39+
class parse_optionst: public parse_options_baset
40+
{
41+
public:
42+
parse_optionst(
43+
const std::string &optstring,
44+
int argc,
45+
const char **argv,
46+
message_handlert &message_handler):
47+
parse_options_baset(optstring, argc, argv),
48+
message(message_handler)
49+
{
50+
}
51+
52+
int main() override;
53+
54+
protected:
55+
messaget message;
56+
};
57+
3858
std::string
3959
banner_string(const std::string &front_end, const std::string &version);
4060

0 commit comments

Comments
 (0)