Skip to content

Commit f2dfd2e

Browse files
committed
Migrate existing type checks to new framework
This removes the validate_type() methods and moves the checks into a new method check() of the corresponding type.
1 parent 870882c commit f2dfd2e

File tree

3 files changed

+95
-86
lines changed

3 files changed

+95
-86
lines changed

src/util/expr_cast.h

Lines changed: 2 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -48,16 +48,6 @@ inline bool can_cast_type(const typet &base);
4848
/// validate objects in this way at any time.
4949
inline void validate_expr(const exprt &) {}
5050

51-
/// Called after casting. Provides a point to check data invariants on the
52-
/// structure of the typet. By default, this is a no-op, but you can provide an
53-
/// overload to validate particular types. Should always succeed unless the
54-
/// program has entered an invalid state. We validate objects at cast time as
55-
/// that is when these checks have been used historically, but it would be
56-
/// reasonable to validate objects in this way at any time.
57-
inline void validate_type(const typet &)
58-
{
59-
}
60-
6151
namespace detail // NOLINT
6252
{
6353

@@ -129,9 +119,8 @@ auto type_try_dynamic_cast(TType &base) ->
129119
"The template argument T must be derived from typet.");
130120
if(!can_cast_type<typename std::remove_const<T>::type>(base))
131121
return nullptr;
132-
const auto ret = static_cast<returnt>(&base);
133-
validate_type(*ret);
134-
return ret;
122+
TType::check(base);
123+
return static_cast<returnt>(&base);
135124
}
136125

137126
namespace detail // NOLINT

src/util/std_types.h

Lines changed: 71 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -1003,15 +1003,15 @@ inline bool can_cast_type<code_typet>(const typet &type)
10031003
inline const code_typet &to_code_type(const typet &type)
10041004
{
10051005
PRECONDITION(can_cast_type<code_typet>(type));
1006-
validate_type(type);
1006+
code_typet::check(type);
10071007
return static_cast<const code_typet &>(type);
10081008
}
10091009

10101010
/// \copydoc to_code_type(const typet &)
10111011
inline code_typet &to_code_type(typet &type)
10121012
{
10131013
PRECONDITION(can_cast_type<code_typet>(type));
1014-
validate_type(type);
1014+
code_typet::check(type);
10151015
return static_cast<code_typet &>(type);
10161016
}
10171017

@@ -1198,6 +1198,13 @@ class bv_typet:public bitvector_typet
11981198
{
11991199
set_width(width);
12001200
}
1201+
1202+
static void check(
1203+
const typet &type,
1204+
const validation_modet vm = validation_modet::INVARIANT)
1205+
{
1206+
DATA_CHECK(!type.get(ID_width).empty(), "bitvector type must have width");
1207+
}
12011208
};
12021209

12031210
/// Check whether a reference to a typet is a \ref bv_typet.
@@ -1209,11 +1216,6 @@ inline bool can_cast_type<bv_typet>(const typet &type)
12091216
return type.id() == ID_bv;
12101217
}
12111218

1212-
inline void validate_type(const bv_typet &type)
1213-
{
1214-
DATA_INVARIANT(!type.get(ID_width).empty(), "bitvector type must have width");
1215-
}
1216-
12171219
/// \brief Cast a typet to a \ref bv_typet
12181220
///
12191221
/// This is an unchecked conversion. \a type must be known to be \ref
@@ -1225,18 +1227,16 @@ inline void validate_type(const bv_typet &type)
12251227
inline const bv_typet &to_bv_type(const typet &type)
12261228
{
12271229
PRECONDITION(can_cast_type<bv_typet>(type));
1228-
const bv_typet &ret = static_cast<const bv_typet &>(type);
1229-
validate_type(ret);
1230-
return ret;
1230+
bv_typet::check(type);
1231+
return static_cast<const bv_typet &>(type);
12311232
}
12321233

12331234
/// \copydoc to_bv_type(const typet &)
12341235
inline bv_typet &to_bv_type(typet &type)
12351236
{
12361237
PRECONDITION(can_cast_type<bv_typet>(type));
1237-
bv_typet &ret = static_cast<bv_typet &>(type);
1238-
validate_type(ret);
1239-
return ret;
1238+
bv_typet::check(type);
1239+
return static_cast<bv_typet &>(type);
12401240
}
12411241

12421242
/// Fixed-width bit-vector with unsigned binary interpretation
@@ -1308,6 +1308,14 @@ class signedbv_typet:public bitvector_typet
13081308
constant_exprt smallest_expr() const;
13091309
constant_exprt zero_expr() const;
13101310
constant_exprt largest_expr() const;
1311+
1312+
static void check(
1313+
const typet &type,
1314+
const validation_modet vm = validation_modet::INVARIANT)
1315+
{
1316+
DATA_CHECK(
1317+
!type.get(ID_width).empty(), "signed bitvector type must have width");
1318+
}
13111319
};
13121320

13131321
/// Check whether a reference to a typet is a \ref signedbv_typet.
@@ -1319,12 +1327,6 @@ inline bool can_cast_type<signedbv_typet>(const typet &type)
13191327
return type.id() == ID_signedbv;
13201328
}
13211329

1322-
inline void validate_type(const signedbv_typet &type)
1323-
{
1324-
DATA_INVARIANT(
1325-
!type.get(ID_width).empty(), "signed bitvector type must have width");
1326-
}
1327-
13281330
/// \brief Cast a typet to a \ref signedbv_typet
13291331
///
13301332
/// This is an unchecked conversion. \a type must be known to be \ref
@@ -1336,18 +1338,16 @@ inline void validate_type(const signedbv_typet &type)
13361338
inline const signedbv_typet &to_signedbv_type(const typet &type)
13371339
{
13381340
PRECONDITION(can_cast_type<signedbv_typet>(type));
1339-
const signedbv_typet &ret = static_cast<const signedbv_typet &>(type);
1340-
validate_type(ret);
1341-
return ret;
1341+
signedbv_typet::check(type);
1342+
return static_cast<const signedbv_typet &>(type);
13421343
}
13431344

13441345
/// \copydoc to_signedbv_type(const typet &)
13451346
inline signedbv_typet &to_signedbv_type(typet &type)
13461347
{
13471348
PRECONDITION(can_cast_type<signedbv_typet>(type));
1348-
signedbv_typet &ret = static_cast<signedbv_typet &>(type);
1349-
validate_type(ret);
1350-
return ret;
1349+
signedbv_typet::check(type);
1350+
return static_cast<signedbv_typet &>(type);
13511351
}
13521352

13531353
/// Fixed-width bit-vector with signed fixed-point interpretation
@@ -1372,6 +1372,14 @@ class fixedbv_typet:public bitvector_typet
13721372
{
13731373
set(ID_integer_bits, b);
13741374
}
1375+
1376+
static void check(
1377+
const typet &type,
1378+
const validation_modet vm = validation_modet::INVARIANT)
1379+
{
1380+
DATA_CHECK(
1381+
!type.get(ID_width).empty(), "fixed bitvector type must have width");
1382+
}
13751383
};
13761384

13771385
/// Check whether a reference to a typet is a \ref fixedbv_typet.
@@ -1383,12 +1391,6 @@ inline bool can_cast_type<fixedbv_typet>(const typet &type)
13831391
return type.id() == ID_fixedbv;
13841392
}
13851393

1386-
inline void validate_type(const fixedbv_typet &type)
1387-
{
1388-
DATA_INVARIANT(
1389-
!type.get(ID_width).empty(), "fixed bitvector type must have width");
1390-
}
1391-
13921394
/// \brief Cast a typet to a \ref fixedbv_typet
13931395
///
13941396
/// This is an unchecked conversion. \a type must be known to be \ref
@@ -1400,18 +1402,16 @@ inline void validate_type(const fixedbv_typet &type)
14001402
inline const fixedbv_typet &to_fixedbv_type(const typet &type)
14011403
{
14021404
PRECONDITION(can_cast_type<fixedbv_typet>(type));
1403-
const fixedbv_typet &ret = static_cast<const fixedbv_typet &>(type);
1404-
validate_type(ret);
1405-
return ret;
1405+
fixedbv_typet::check(type);
1406+
return static_cast<const fixedbv_typet &>(type);
14061407
}
14071408

14081409
/// \copydoc to_fixedbv_type(const typet &)
14091410
inline fixedbv_typet &to_fixedbv_type(typet &type)
14101411
{
14111412
PRECONDITION(can_cast_type<fixedbv_typet>(type));
1412-
fixedbv_typet &ret = static_cast<fixedbv_typet &>(type);
1413-
validate_type(ret);
1414-
return ret;
1413+
fixedbv_typet::check(type);
1414+
return static_cast<fixedbv_typet &>(type);
14151415
}
14161416

14171417
/// Fixed-width bit-vector with IEEE floating-point interpretation
@@ -1434,6 +1434,14 @@ class floatbv_typet:public bitvector_typet
14341434
{
14351435
set(ID_f, b);
14361436
}
1437+
1438+
static void check(
1439+
const typet &type,
1440+
const validation_modet vm = validation_modet::INVARIANT)
1441+
{
1442+
DATA_CHECK(
1443+
!type.get(ID_width).empty(), "float bitvector type must have width");
1444+
}
14371445
};
14381446

14391447
/// Check whether a reference to a typet is a \ref floatbv_typet.
@@ -1445,12 +1453,6 @@ inline bool can_cast_type<floatbv_typet>(const typet &type)
14451453
return type.id() == ID_floatbv;
14461454
}
14471455

1448-
inline void validate_type(const floatbv_typet &type)
1449-
{
1450-
DATA_INVARIANT(
1451-
!type.get(ID_width).empty(), "float bitvector type must have width");
1452-
}
1453-
14541456
/// \brief Cast a typet to a \ref floatbv_typet
14551457
///
14561458
/// This is an unchecked conversion. \a type must be known to be \ref
@@ -1462,18 +1464,16 @@ inline void validate_type(const floatbv_typet &type)
14621464
inline const floatbv_typet &to_floatbv_type(const typet &type)
14631465
{
14641466
PRECONDITION(can_cast_type<floatbv_typet>(type));
1465-
const floatbv_typet &ret = static_cast<const floatbv_typet &>(type);
1466-
validate_type(ret);
1467-
return ret;
1467+
floatbv_typet::check(type);
1468+
return static_cast<const floatbv_typet &>(type);
14681469
}
14691470

14701471
/// \copydoc to_floatbv_type(const typet &)
14711472
inline floatbv_typet &to_floatbv_type(typet &type)
14721473
{
14731474
PRECONDITION(can_cast_type<floatbv_typet>(type));
1474-
floatbv_typet &ret = static_cast<floatbv_typet &>(type);
1475-
validate_type(ret);
1476-
return ret;
1475+
floatbv_typet::check(type);
1476+
return static_cast<floatbv_typet &>(type);
14771477
}
14781478

14791479
/// Type for C bit fields
@@ -1537,6 +1537,13 @@ class pointer_typet:public bitvector_typet
15371537
{
15381538
return signedbv_typet(get_width());
15391539
}
1540+
1541+
static void check(
1542+
const typet &type,
1543+
const validation_modet vm = validation_modet::INVARIANT)
1544+
{
1545+
DATA_CHECK(!type.get(ID_width).empty(), "pointer must have width");
1546+
}
15401547
};
15411548

15421549
/// Check whether a reference to a typet is a \ref pointer_typet.
@@ -1548,11 +1555,6 @@ inline bool can_cast_type<pointer_typet>(const typet &type)
15481555
return type.id() == ID_pointer;
15491556
}
15501557

1551-
inline void validate_type(const pointer_typet &type)
1552-
{
1553-
DATA_INVARIANT(!type.get(ID_width).empty(), "pointer must have width");
1554-
}
1555-
15561558
/// \brief Cast a typet to a \ref pointer_typet
15571559
///
15581560
/// This is an unchecked conversion. \a type must be known to be \ref
@@ -1564,18 +1566,16 @@ inline void validate_type(const pointer_typet &type)
15641566
inline const pointer_typet &to_pointer_type(const typet &type)
15651567
{
15661568
PRECONDITION(can_cast_type<pointer_typet>(type));
1567-
const pointer_typet &ret = static_cast<const pointer_typet &>(type);
1568-
validate_type(ret);
1569-
return ret;
1569+
pointer_typet::check(type);
1570+
return static_cast<const pointer_typet &>(type);
15701571
}
15711572

15721573
/// \copydoc to_pointer_type(const typet &)
15731574
inline pointer_typet &to_pointer_type(typet &type)
15741575
{
15751576
PRECONDITION(can_cast_type<pointer_typet>(type));
1576-
pointer_typet &ret = static_cast<pointer_typet &>(type);
1577-
validate_type(ret);
1578-
return ret;
1577+
pointer_typet::check(type);
1578+
return static_cast<pointer_typet &>(type);
15791579
}
15801580

15811581
/// The reference type
@@ -1635,6 +1635,13 @@ class c_bool_typet:public bitvector_typet
16351635
bitvector_typet(ID_c_bool, width)
16361636
{
16371637
}
1638+
1639+
static void check(
1640+
const typet &type,
1641+
const validation_modet vm = validation_modet::INVARIANT)
1642+
{
1643+
DATA_CHECK(!type.get(ID_width).empty(), "C bool type must have width");
1644+
}
16381645
};
16391646

16401647
/// Check whether a reference to a typet is a \ref c_bool_typet.
@@ -1646,11 +1653,6 @@ inline bool can_cast_type<c_bool_typet>(const typet &type)
16461653
return type.id() == ID_c_bool;
16471654
}
16481655

1649-
inline void validate_type(const c_bool_typet &type)
1650-
{
1651-
DATA_INVARIANT(!type.get(ID_width).empty(), "C bool type must have width");
1652-
}
1653-
16541656
/// \brief Cast a typet to a \ref c_bool_typet
16551657
///
16561658
/// This is an unchecked conversion. \a type must be known to be \ref
@@ -1662,18 +1664,16 @@ inline void validate_type(const c_bool_typet &type)
16621664
inline const c_bool_typet &to_c_bool_type(const typet &type)
16631665
{
16641666
PRECONDITION(can_cast_type<c_bool_typet>(type));
1665-
const c_bool_typet &ret = static_cast<const c_bool_typet &>(type);
1666-
validate_type(ret);
1667-
return ret;
1667+
c_bool_typet::check(type);
1668+
return static_cast<const c_bool_typet &>(type);
16681669
}
16691670

16701671
/// \copydoc to_c_bool_type(const typet &)
16711672
inline c_bool_typet &to_c_bool_type(typet &type)
16721673
{
16731674
PRECONDITION(can_cast_type<c_bool_typet>(type));
1674-
c_bool_typet &ret = static_cast<c_bool_typet &>(type);
1675-
validate_type(ret);
1676-
return ret;
1675+
c_bool_typet::check(type);
1676+
return static_cast<c_bool_typet &>(type);
16771677
}
16781678

16791679
/// String type

src/util/validate_types.cpp

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,14 +24,34 @@ Author: Daniel Poetzl
2424
template <template <typename, typename> class C, typename... Args>
2525
void call_on_type(const typet &type, Args &&... args)
2626
{
27-
if(type.id() == ID_signedbv)
27+
if(type.id() == ID_bv)
2828
{
29-
CALL_ON_TYPE(signedbv_typet);
29+
CALL_ON_TYPE(bv_typet);
3030
}
3131
else if(type.id() == ID_unsignedbv)
3232
{
3333
CALL_ON_TYPE(unsignedbv_typet);
3434
}
35+
else if(type.id() == ID_signedbv)
36+
{
37+
CALL_ON_TYPE(signedbv_typet);
38+
}
39+
else if(type.id() == ID_fixedbv)
40+
{
41+
CALL_ON_TYPE(fixedbv_typet);
42+
}
43+
else if(type.id() == ID_floatbv)
44+
{
45+
CALL_ON_TYPE(floatbv_typet);
46+
}
47+
else if(type.id() == ID_pointer)
48+
{
49+
CALL_ON_TYPE(pointer_typet);
50+
}
51+
else if(type.id() == ID_c_bool)
52+
{
53+
CALL_ON_TYPE(c_bool_typet);
54+
}
3555
else
3656
{
3757
#ifdef REPORT_UNIMPLEMENTED_TYPE_CHECKS

0 commit comments

Comments
 (0)