Skip to content

Commit baec7a1

Browse files
committed
Error handling cleanup in solvers/flattening
Files boolbv_unary_minus.cpp to boolbv_with.cpp
1 parent 087bbbb commit baec7a1

File tree

6 files changed

+56
-75
lines changed

6 files changed

+56
-75
lines changed

src/solvers/flattening/boolbv.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -284,7 +284,7 @@ bvt boolbvt::convert_bitvector(const exprt &expr)
284284
else if(expr.id()==ID_array)
285285
return convert_array(expr);
286286
else if(expr.id()==ID_vector)
287-
return convert_vector(expr);
287+
return convert_vector(to_vector_expr(expr));
288288
else if(expr.id()==ID_complex)
289289
return convert_complex(expr);
290290
else if(expr.id()==ID_complex_real)

src/solvers/flattening/boolbv.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -144,7 +144,7 @@ class boolbvt:public arrayst
144144
virtual bvt convert_if(const if_exprt &expr);
145145
virtual bvt convert_struct(const struct_exprt &expr);
146146
virtual bvt convert_array(const exprt &expr);
147-
virtual bvt convert_vector(const exprt &expr);
147+
virtual bvt convert_vector(const vector_exprt &expr);
148148
virtual bvt convert_complex(const exprt &expr);
149149
virtual bvt convert_complex_real(const complex_real_exprt &expr);
150150
virtual bvt convert_complex_imag(const complex_imag_exprt &expr);

src/solvers/flattening/boolbv_unary_minus.cpp

Lines changed: 24 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@ Author: Daniel Kroening, [email protected]
1212

1313
#include <solvers/floatbv/float_utils.h>
1414

15+
#include <algorithm>
16+
1517
#include "boolbv_type.h"
1618

1719
bvt boolbvt::convert_unary_minus(const unary_exprt &expr)
@@ -23,66 +25,53 @@ bvt boolbvt::convert_unary_minus(const unary_exprt &expr)
2325
if(width==0)
2426
return conversion_failed(expr);
2527

26-
const exprt::operandst &operands=expr.operands();
27-
28-
if(operands.size()!=1)
29-
throw "unary minus takes one operand";
30-
31-
const exprt &op0=expr.op0();
28+
const exprt &op = expr.op();
3229

33-
const bvt &op_bv=convert_bv(op0);
30+
const bvt &op_bv = convert_bv(op, width);
3431

3532
bvtypet bvtype=get_bvtype(type);
36-
bvtypet op_bvtype=get_bvtype(op0.type());
37-
std::size_t op_width=op_bv.size();
33+
bvtypet op_bvtype = get_bvtype(op.type());
3834

3935
bool no_overflow=(expr.id()=="no-overflow-unary-minus");
4036

41-
if(op_width==0 || op_width!=width)
42-
return conversion_failed(expr);
43-
4437
if(bvtype==bvtypet::IS_UNKNOWN &&
4538
(type.id()==ID_vector || type.id()==ID_complex))
4639
{
4740
const typet &subtype=ns.follow(type.subtype());
4841

4942
std::size_t sub_width=boolbv_width(subtype);
5043

51-
if(sub_width==0 || width%sub_width!=0)
52-
throw "unary-: unexpected vector operand width";
44+
INVARIANT(
45+
sub_width > 0,
46+
"bitvector representation of type needs to have at least one bit");
47+
48+
INVARIANT(
49+
width % sub_width == 0,
50+
"total bitvector width needs to be a multiple of the component bitvector "
51+
"widths");
5352

54-
std::size_t size=width/sub_width;
5553
bvt bv;
56-
bv.resize(width);
5754

58-
for(std::size_t i=0; i<size; i++)
55+
for(std::size_t sub_idx = 0; sub_idx < width; sub_idx += sub_width)
5956
{
6057
bvt tmp_op;
61-
tmp_op.resize(sub_width);
6258

63-
for(std::size_t j=0; j<tmp_op.size(); j++)
64-
{
65-
assert(i*sub_width+j<op_bv.size());
66-
tmp_op[j]=op_bv[i*sub_width+j];
67-
}
68-
69-
bvt tmp_result;
59+
const auto sub_it = std::next(op_bv.begin(), sub_idx);
60+
std::copy_n(sub_it, sub_width, std::back_inserter(tmp_op));
7061

71-
if(type.subtype().id()==ID_floatbv)
62+
if(type.subtype().id() == ID_floatbv)
7263
{
7364
float_utilst float_utils(prop, to_floatbv_type(subtype));
74-
tmp_result=float_utils.negate(tmp_op);
65+
tmp_op = float_utils.negate(tmp_op);
7566
}
7667
else
77-
tmp_result=bv_utils.negate(tmp_op);
68+
tmp_op = bv_utils.negate(tmp_op);
7869

79-
assert(tmp_result.size()==sub_width);
70+
INVARIANT(
71+
tmp_op.size() == sub_width,
72+
"bitvector after negation shall have same bit width");
8073

81-
for(std::size_t j=0; j<tmp_result.size(); j++)
82-
{
83-
assert(i*sub_width+j<bv.size());
84-
bv[i*sub_width+j]=tmp_result[j];
85-
}
74+
std::copy(tmp_op.begin(), tmp_op.end(), std::back_inserter(bv));
8675
}
8776

8877
return bv;
@@ -96,7 +85,7 @@ bvt boolbvt::convert_unary_minus(const unary_exprt &expr)
9685
}
9786
else if(bvtype==bvtypet::IS_FLOAT && op_bvtype==bvtypet::IS_FLOAT)
9887
{
99-
assert(!no_overflow);
88+
INVARIANT(!no_overflow, "");
10089
float_utilst float_utils(prop, to_floatbv_type(expr.type()));
10190
return float_utils.negate(op_bv);
10291
}

src/solvers/flattening/boolbv_union.cpp

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,10 @@ bvt boolbvt::convert_union(const union_exprt &expr)
2222

2323
const bvt &op_bv=convert_bv(expr.op());
2424

25-
if(width<op_bv.size())
26-
throw "union: unexpected operand op width";
25+
INVARIANT(
26+
op_bv.size() <= width,
27+
"operand bitvector width shall not be larger than the width indicated by "
28+
"the union type");
2729

2830
bvt bv;
2931
bv.resize(width);
@@ -39,8 +41,9 @@ bvt boolbvt::convert_union(const union_exprt &expr)
3941
}
4042
else
4143
{
42-
assert(
43-
config.ansi_c.endianness==configt::ansi_ct::endiannesst::IS_BIG_ENDIAN);
44+
INVARIANT(
45+
config.ansi_c.endianness == configt::ansi_ct::endiannesst::IS_BIG_ENDIAN,
46+
"endianness should be set to either little endian or big endian");
4447

4548
bv_endianness_mapt map_u(expr.type(), false, ns, boolbv_width);
4649
bv_endianness_mapt map_op(expr.op0().type(), false, ns, boolbv_width);

src/solvers/flattening/boolbv_vector.cpp

Lines changed: 13 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -9,38 +9,30 @@ Author: Daniel Kroening, [email protected]
99

1010
#include "boolbv.h"
1111

12-
bvt boolbvt::convert_vector(const exprt &expr)
12+
bvt boolbvt::convert_vector(const vector_exprt &expr)
1313
{
1414
std::size_t width=boolbv_width(expr.type());
1515

1616
if(width==0)
1717
return conversion_failed(expr);
1818

19-
if(expr.type().id()==ID_vector)
20-
{
21-
const exprt::operandst &operands=expr.operands();
22-
23-
bvt bv;
24-
bv.reserve(width);
19+
const exprt::operandst &operands = expr.operands();
2520

26-
if(!operands.empty())
27-
{
28-
std::size_t op_width=width/operands.size();
21+
bvt bv;
22+
bv.reserve(width);
2923

30-
forall_expr(it, operands)
31-
{
32-
const bvt &tmp=convert_bv(*it);
24+
if(!operands.empty())
25+
{
26+
std::size_t op_width = width / operands.size();
3327

34-
if(tmp.size()!=op_width)
35-
throw "convert_vector: unexpected operand width";
28+
forall_expr(it, operands)
29+
{
30+
const bvt &tmp = convert_bv(*it, op_width);
3631

37-
forall_literals(it2, tmp)
38-
bv.push_back(*it2);
39-
}
32+
forall_literals(it2, tmp)
33+
bv.push_back(*it2);
4034
}
41-
42-
return bv;
4335
}
4436

45-
return conversion_failed(expr);
37+
return bv;
4638
}

src/solvers/flattening/boolbv_width.cpp

Lines changed: 10 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ Author: Daniel Kroening, [email protected]
1111
#include <algorithm>
1212

1313
#include <util/arith_tools.h>
14+
#include <util/exception_utils.h>
1415
#include <util/invariant.h>
1516
#include <util/std_types.h>
1617

@@ -79,39 +80,35 @@ const boolbv_widtht::entryt &boolbv_widtht::get_entry(const typet &type) const
7980
else if(type_id==ID_c_bool)
8081
{
8182
entry.total_width=to_c_bool_type(type).get_width();
82-
assert(entry.total_width!=0);
8383
}
8484
else if(type_id==ID_signedbv)
8585
{
8686
entry.total_width=to_signedbv_type(type).get_width();
87-
assert(entry.total_width!=0);
8887
}
8988
else if(type_id==ID_unsignedbv)
9089
{
9190
entry.total_width=to_unsignedbv_type(type).get_width();
92-
assert(entry.total_width!=0);
9391
}
9492
else if(type_id==ID_floatbv)
9593
{
9694
entry.total_width=to_floatbv_type(type).get_width();
97-
assert(entry.total_width!=0);
9895
}
9996
else if(type_id==ID_fixedbv)
10097
{
10198
entry.total_width=to_fixedbv_type(type).get_width();
102-
assert(entry.total_width!=0);
10399
}
104100
else if(type_id==ID_bv)
105101
{
106102
entry.total_width=to_bv_type(type).get_width();
107-
assert(entry.total_width!=0);
108103
}
109104
else if(type_id==ID_verilog_signedbv ||
110105
type_id==ID_verilog_unsignedbv)
111106
{
112107
// we encode with two bits
113-
entry.total_width = type.get_size_t(ID_width) * 2;
114-
assert(entry.total_width!=0);
108+
std::size_t size = type.get_size_t(ID_width);
109+
DATA_INVARIANT(
110+
size > 0, "verilog bitvector width shall be greater than zero");
111+
entry.total_width = size * 2;
115112
}
116113
else if(type_id==ID_range)
117114
{
@@ -123,7 +120,7 @@ const boolbv_widtht::entryt &boolbv_widtht::get_entry(const typet &type) const
123120
if(size>=1)
124121
{
125122
entry.total_width = address_bits(size);
126-
assert(entry.total_width!=0);
123+
CHECK_RETURN(entry.total_width > 0);
127124
}
128125
}
129126
else if(type_id==ID_array)
@@ -142,7 +139,7 @@ const boolbv_widtht::entryt &boolbv_widtht::get_entry(const typet &type) const
142139
{
143140
mp_integer total=array_size*sub_width;
144141
if(total>(1<<30)) // realistic limit
145-
throw "array too large for flattening";
142+
throw analysis_exceptiont("array too large for flattening");
146143

147144
entry.total_width=integer2unsigned(total);
148145
}
@@ -163,7 +160,7 @@ const boolbv_widtht::entryt &boolbv_widtht::get_entry(const typet &type) const
163160
{
164161
mp_integer total=vector_size*sub_width;
165162
if(total>(1<<30)) // realistic limit
166-
throw "vector too large for flattening";
163+
analysis_exceptiont("vector too large for flattening");
167164

168165
entry.total_width=integer2unsigned(vector_size*sub_width);
169166
}
@@ -181,13 +178,13 @@ const boolbv_widtht::entryt &boolbv_widtht::get_entry(const typet &type) const
181178
// get number of necessary bits
182179
std::size_t size=to_enumeration_type(type).elements().size();
183180
entry.total_width = address_bits(size);
184-
assert(entry.total_width!=0);
181+
CHECK_RETURN(entry.total_width > 0);
185182
}
186183
else if(type_id==ID_c_enum)
187184
{
188185
// these have a subtype
189186
entry.total_width = type.subtype().get_size_t(ID_width);
190-
assert(entry.total_width!=0);
187+
CHECK_RETURN(entry.total_width > 0);
191188
}
192189
else if(type_id==ID_incomplete_c_enum)
193190
{

0 commit comments

Comments
 (0)