51 #define UNEXPECTEDCASE(S) PRECONDITION_WITH_DIAGNOSTICS(false, S);
54 #define SMT2_TODO(S) PRECONDITION_WITH_DIAGNOSTICS(false, "TODO: " S)
58 const std::string &_benchmark,
59 const std::string &_notes,
60 const std::string &_logic,
63 : use_FPA_theory(false),
64 use_array_of_bool(false),
66 use_check_sat_assuming(false),
68 use_lambda_for_array(false),
72 benchmark(_benchmark),
78 no_boolean_variables(0)
169 "variable number shall be within bounds");
175 out <<
"; SMT 2" <<
"\n";
184 out <<
"; Generated for the CPROVER SMT2 solver\n";
break;
194 out <<
"(set-info :source \"" <<
notes <<
"\")" <<
"\n";
196 out <<
"(set-option :produce-models true)" <<
"\n";
202 out <<
"(set-logic " <<
logic <<
")" <<
"\n";
215 out <<
"(check-sat-assuming (";
225 out <<
"; assumptions\n";
236 out <<
"(check-sat)\n";
244 out <<
"(get-value (" <<
id <<
"))"
252 out <<
"; end of SMT2 file"
259 if(type.
id() == ID_empty)
261 else if(type.
id() == ID_struct_tag)
263 else if(type.
id() == ID_union_tag)
265 else if(type.
id() == ID_struct || type.
id() == ID_union)
274 else if(
auto array_type = type_try_dynamic_cast<array_typet>(type))
290 std::size_t number = 0;
291 std::size_t h=pointer_width-1;
296 const typet &type = o.type();
300 (o.id() != ID_symbol && o.id() != ID_string_constant) ||
301 !size_expr.has_value())
308 out <<
"(assert (=> (= "
309 <<
"((_ extract " << h <<
" " << l <<
") ";
312 <<
"(= " <<
id <<
" ";
337 if(expr.
id()==ID_symbol)
344 return it->second.value;
347 else if(expr.
id()==ID_nondet_symbol)
354 return it->second.value;
356 else if(expr.
id() == ID_literal)
364 else if(expr.
id() == ID_not)
369 else if(op.is_false())
374 (!expr.
has_operands() && (expr.
id() == ID_struct || expr.
id() == ID_array)))
386 op = std::move(eval_op);
421 if(s.size()>=2 && s[0]==
'#' && s[1]==
'b')
426 else if(s.size()>=2 && s[0]==
'#' && s[1]==
'x')
437 else if(src.
get_sub().size()==2 &&
442 else if(src.
get_sub().size()==3 &&
445 src.
get_sub()[1].id_string().substr(0, 2)==
"bv")
449 else if(src.
get_sub().size()==4 &&
452 if(type.
id()==ID_floatbv)
461 const auto s1_int = numeric_cast_v<mp_integer>(
s1);
462 const auto s2_int = numeric_cast_v<mp_integer>(
s2);
463 const auto s3_int = numeric_cast_v<mp_integer>(s3);
467 s1_int << (floatbv_type.
get_e() + floatbv_type.
get_f()),
473 else if(src.
get_sub().size()==4 &&
481 else if(src.
get_sub().size()==4 &&
489 else if(src.
get_sub().size()==4 &&
498 if(type.
id()==ID_signedbv ||
499 type.
id()==ID_unsignedbv ||
500 type.
id()==ID_c_enum ||
501 type.
id()==ID_c_bool)
505 else if(type.
id()==ID_c_enum_tag)
511 result.
type() = type;
514 else if(type.
id()==ID_fixedbv ||
515 type.
id()==ID_floatbv)
520 else if(type.
id()==ID_integer ||
527 "smt2_convt::parse_literal should not be of unsupported type " +
535 std::unordered_map<int64_t, exprt> operands_map;
539 auto maybe_default_op = operands_map.find(-1);
541 if(maybe_default_op == operands_map.end())
544 default_op = maybe_default_op->second;
546 auto maybe_size = numeric_cast<std::int64_t>(type.
size());
547 if(maybe_size.has_value())
549 while(i < maybe_size.value())
551 auto found_op = operands_map.find(i);
552 if(found_op != operands_map.end())
553 operands.emplace_back(found_op->second);
555 operands.emplace_back(default_op);
563 auto found_op = operands_map.find(i);
564 while(found_op != operands_map.end())
566 operands.emplace_back(found_op->second);
568 found_op = operands_map.find(i);
570 operands.emplace_back(default_op);
576 std::unordered_map<int64_t, exprt> *operands_map,
589 bool failure =
to_integer(index_constant, tempint);
592 long index = tempint.to_long();
594 operands_map->emplace(index, value);
596 else if(src.
get_sub().size()==2 &&
597 src.
get_sub()[0].get_sub().size()==3 &&
598 src.
get_sub()[0].get_sub()[0].id()==
"as" &&
599 src.
get_sub()[0].get_sub()[1].id()==
"const")
603 operands_map->emplace(-1, default_value);
636 if(components.empty())
644 for(std::size_t i=0; i<components.size(); i++)
654 src.
get_sub().size() > j,
"insufficient number of component values");
671 std::size_t offset=0;
673 for(std::size_t i=0; i<components.size(); i++)
678 std::size_t component_width=
boolbv_width(components[i].type());
681 offset + component_width <= total_width,
682 "struct component bits shall be within struct bit vector");
684 std::string component_binary=
686 total_width-offset-component_width, component_width);
691 offset+=component_width;
705 for(
const auto &binding : src.
get_sub()[1].get_sub())
707 const irep_idt &name = binding.get_sub()[0].id();
718 return parse_rec(bindings_it->second, type);
722 type.
id() == ID_signedbv || type.
id() == ID_unsignedbv ||
723 type.
id() == ID_integer || type.
id() == ID_rational ||
724 type.
id() == ID_real || type.
id() == ID_c_enum ||
725 type.
id() == ID_c_enum_tag || type.
id() == ID_fixedbv ||
726 type.
id() == ID_floatbv || type.
id() == ID_c_bool || type.
id() == ID_range)
730 else if(type.
id()==ID_bool)
732 if(src.
id()==ID_1 || src.
id()==ID_true)
734 else if(src.
id()==ID_0 || src.
id()==ID_false)
737 else if(type.
id()==ID_pointer)
743 mp_integer v = numeric_cast_v<mp_integer>(bv_expr);
752 else if(type.
id()==ID_struct)
756 else if(type.
id() == ID_struct_tag)
761 struct_expr.type() = type;
762 return std::move(struct_expr);
764 else if(type.
id()==ID_union)
768 else if(type.
id() == ID_union_tag)
772 union_expr.type() = type;
775 else if(type.
id()==ID_array)
789 expr.
id() == ID_string_constant || expr.
id() == ID_label)
792 const std::size_t max_objects = std::size_t(1) << object_bits;
795 if(object_id >= max_objects)
798 "too many addressed objects: maximum number of objects is set to 2^n=" +
801 "use the `--object-bits n` option to increase the maximum number"};
804 out <<
"(concat (_ bv" << object_id <<
" " << object_bits <<
")"
805 <<
" (_ bv0 " <<
boolbv_width(result_type) - object_bits <<
"))";
807 else if(expr.
id()==ID_index)
816 if(array.
type().
id()==ID_pointer)
818 else if(array.
type().
id()==ID_array)
838 else if(expr.
id()==ID_member)
843 const typet &struct_op_type = struct_op.
type();
846 struct_op_type.
id() == ID_struct || struct_op_type.
id() == ID_struct_tag,
847 "member expression operand shall have struct type");
850 struct_op_type.
id() == ID_struct_tag
867 else if(expr.
id()==ID_if)
882 "operand of address of expression should not be of kind " +
890 if(node.
id() == ID_exists || node.
id() == ID_forall)
906 else if(expr.
id()==ID_literal)
918 out <<
"; convert\n";
919 out <<
"; Converting var_no " << l.
var_no() <<
" with expr ID of "
929 out <<
"(declare-fun ";
931 out <<
" () Bool)\n";
932 out <<
"(assert (= ";
944 out <<
"(define-fun " << identifier <<
" () Bool ";
972 const auto identifier =
994 for(
auto &assumption : _assumptions)
1005 if(identifier.empty())
1030 std::string result =
"|";
1032 for(
auto ch : identifier)
1057 if(type.
id()==ID_floatbv)
1062 else if(type.
id() == ID_bv)
1066 else if(type.
id()==ID_unsignedbv)
1070 else if(type.
id()==ID_c_bool)
1074 else if(type.
id()==ID_signedbv)
1078 else if(type.
id()==ID_bool)
1082 else if(type.
id()==ID_c_enum_tag)
1086 else if(type.
id() == ID_pointer)
1090 else if(type.
id() == ID_struct_tag)
1097 else if(type.
id() == ID_union_tag)
1101 else if(type.
id() == ID_array)
1122 if(expr.
id()==ID_symbol)
1129 if(expr.
id()==ID_smt2_symbol)
1137 !expr.
operands().empty(),
"non-symbol expressions shall have operands");
1143 for(
const auto &op : expr.
operands())
1171 converter_result->second(expr);
1176 if(expr.
id()==ID_symbol)
1182 else if(expr.
id()==ID_nondet_symbol)
1185 DATA_INVARIANT(!
id.empty(),
"nondet symbol must have identifier");
1188 else if(expr.
id()==ID_smt2_symbol)
1194 else if(expr.
id()==ID_typecast)
1198 else if(expr.
id()==ID_floatbv_typecast)
1202 else if(expr.
id()==ID_struct)
1206 else if(expr.
id()==ID_union)
1214 else if(expr.
id() == ID_concatenation && expr.
operands().size() == 1)
1218 "concatenation over a single operand should have matching types",
1223 else if(expr.
id()==ID_concatenation ||
1224 expr.
id()==ID_bitand ||
1225 expr.
id()==ID_bitor ||
1226 expr.
id()==ID_bitxor ||
1227 expr.
id()==ID_bitnand ||
1228 expr.
id()==ID_bitnor)
1232 "given expression should have at least two operands",
1237 if(expr.
id()==ID_concatenation)
1239 else if(expr.
id()==ID_bitand)
1241 else if(expr.
id()==ID_bitor)
1243 else if(expr.
id()==ID_bitxor)
1245 else if(expr.
id()==ID_bitnand)
1247 else if(expr.
id()==ID_bitnor)
1250 for(
const auto &op : expr.
operands())
1258 else if(expr.
id()==ID_bitnot)
1266 else if(expr.
id()==ID_unary_minus)
1271 unary_minus_expr.
type().
id() == ID_rational ||
1272 unary_minus_expr.
type().
id() == ID_integer ||
1273 unary_minus_expr.
type().
id() == ID_real)
1279 else if(unary_minus_expr.
type().
id() == ID_floatbv)
1298 else if(expr.
id()==ID_unary_plus)
1303 else if(expr.
id()==ID_sign)
1309 if(op_type.
id()==ID_floatbv)
1313 out <<
"(fp.isNegative ";
1320 else if(op_type.
id()==ID_signedbv)
1326 out <<
" (_ bv0 " << op_width <<
"))";
1331 "sign should not be applied to unsupported type",
1334 else if(expr.
id()==ID_if)
1346 else if(expr.
id()==ID_and ||
1352 "logical and, or, and xor expressions should have Boolean type");
1355 "logical and, or, and xor expressions should have at least two operands");
1357 out <<
"(" << expr.
id();
1358 for(
const auto &op : expr.
operands())
1365 else if(expr.
id()==ID_implies)
1370 implies_expr.
is_boolean(),
"implies expression should have Boolean type");
1378 else if(expr.
id()==ID_not)
1383 not_expr.
is_boolean(),
"not expression should have Boolean type");
1389 else if(expr.
id() == ID_equal)
1395 "operands of equal expression shall have same type");
1410 else if(expr.
id() == ID_notequal)
1416 "operands of not equal expression shall have same type");
1424 else if(expr.
id()==ID_ieee_float_equal ||
1425 expr.
id()==ID_ieee_float_notequal)
1432 rel_expr.lhs().type() == rel_expr.rhs().type(),
1433 "operands of float equal and not equal expressions shall have same type");
1438 if(rel_expr.id() == ID_ieee_float_notequal)
1447 if(rel_expr.id() == ID_ieee_float_notequal)
1453 else if(expr.
id()==ID_le ||
1460 else if(expr.
id()==ID_plus)
1464 else if(expr.
id()==ID_floatbv_plus)
1468 else if(expr.
id()==ID_minus)
1472 else if(expr.
id()==ID_floatbv_minus)
1476 else if(expr.
id()==ID_div)
1480 else if(expr.
id()==ID_floatbv_div)
1484 else if(expr.
id()==ID_mod)
1488 else if(expr.
id() == ID_euclidean_mod)
1492 else if(expr.
id()==ID_mult)
1496 else if(expr.
id()==ID_floatbv_mult)
1500 else if(expr.
id() == ID_floatbv_rem)
1504 else if(expr.
id()==ID_address_of)
1510 else if(expr.
id() == ID_array_of)
1515 array_of_expr.type().id() == ID_array,
1516 "array of expression shall have array type");
1520 out <<
"((as const ";
1528 defined_expressionst::const_iterator it =
1534 else if(expr.
id() == ID_array_comprehension)
1539 array_comprehension.type().id() == ID_array,
1540 "array_comprehension expression shall have array type");
1544 out <<
"(lambda ((";
1547 convert_type(array_comprehension.type().size().type());
1559 else if(expr.
id()==ID_index)
1563 else if(expr.
id()==ID_ashr ||
1564 expr.
id()==ID_lshr ||
1570 if(type.
id()==ID_unsignedbv ||
1571 type.
id()==ID_signedbv ||
1574 if(shift_expr.
id() == ID_ashr)
1576 else if(shift_expr.
id() == ID_lshr)
1578 else if(shift_expr.
id() == ID_shl)
1608 if(width_op0==width_op1)
1610 else if(width_op0>width_op1)
1612 out <<
"((_ zero_extend " << width_op0-width_op1 <<
") ";
1618 out <<
"((_ extract " << width_op0-1 <<
" 0) ";
1625 "unsupported distance type for " + shift_expr.
id_string() +
": " +
1632 "unsupported type for " + shift_expr.
id_string() +
": " +
1635 else if(expr.
id() == ID_rol || expr.
id() == ID_ror)
1641 type.
id() == ID_unsignedbv || type.
id() == ID_signedbv ||
1646 if(shift_expr.
id() == ID_rol)
1647 out <<
"((_ rotate_left";
1648 else if(shift_expr.
id() == ID_ror)
1649 out <<
"((_ rotate_right";
1655 auto distance_int_op = numeric_cast<mp_integer>(shift_expr.
distance());
1657 if(distance_int_op.has_value())
1659 out << distance_int_op.value();
1663 "distance type for " + shift_expr.
id_string() +
"must be constant");
1672 "unsupported type for " + shift_expr.
id_string() +
": " +
1675 else if(expr.
id() == ID_named_term)
1679 convert(named_term_expr.value());
1683 else if(expr.
id()==ID_with)
1687 else if(expr.
id()==ID_update)
1691 else if(expr.
id() == ID_update_bit)
1695 else if(expr.
id() == ID_update_bits)
1699 else if(expr.
id() == ID_object_address)
1701 out <<
"(object-address ";
1706 else if(expr.
id() == ID_element_address)
1712 auto element_size_expr_opt =
1722 *element_size_expr_opt, element_address_expr.index().type()));
1725 else if(expr.
id() == ID_field_address)
1734 else if(expr.
id()==ID_member)
1738 else if(expr.
id()==ID_pointer_offset)
1743 op.type().id() == ID_pointer,
1744 "operand of pointer offset expression shall be of pointer type");
1746 std::size_t offset_bits =
1751 if(offset_bits>result_width)
1752 offset_bits=result_width;
1755 if(result_width>offset_bits)
1756 out <<
"((_ zero_extend " << result_width-offset_bits <<
") ";
1758 out <<
"((_ extract " << offset_bits-1 <<
" 0) ";
1762 if(result_width>offset_bits)
1765 else if(expr.
id()==ID_pointer_object)
1770 op.type().id() == ID_pointer,
1771 "pointer object expressions should be of pointer type");
1777 out <<
"((_ zero_extend " << ext <<
") ";
1779 out <<
"((_ extract "
1780 << pointer_width-1 <<
" "
1788 else if(expr.
id() == ID_is_dynamic_object)
1792 else if(expr.
id() == ID_is_invalid_pointer)
1796 out <<
"(= ((_ extract "
1797 << pointer_width-1 <<
" "
1803 else if(expr.
id()==ID_string_constant)
1809 else if(expr.
id()==ID_extractbit)
1818 out <<
"(= ((_ extract " << i <<
" " << i <<
") ";
1824 out <<
"(= ((_ extract 0 0) ";
1834 else if(expr.
id() == ID_onehot)
1838 else if(expr.
id() == ID_onehot0)
1842 else if(expr.
id()==ID_extractbits)
1852 out <<
"((_ extract " << (width + index_i - 1) <<
" " << index_i <<
") ";
1859 out <<
"(= ((_ extract 0 0) ";
1868 SMT2_TODO(
"smt2: extractbits with non-constant index");
1871 else if(expr.
id()==ID_replication)
1875 mp_integer times = numeric_cast_v<mp_integer>(replication_expr.
times());
1877 out <<
"((_ repeat " << times <<
") ";
1881 else if(expr.
id()==ID_byte_extract_little_endian ||
1882 expr.
id()==ID_byte_extract_big_endian)
1885 false,
"byte_extract ops should be lowered in prepare_for_convert_expr");
1887 else if(expr.
id()==ID_byte_update_little_endian ||
1888 expr.
id()==ID_byte_update_big_endian)
1891 false,
"byte_update ops should be lowered in prepare_for_convert_expr");
1893 else if(expr.
id()==ID_abs)
1899 if(type.
id()==ID_signedbv)
1903 out <<
"(ite (bvslt ";
1905 out <<
" (_ bv0 " << result_width <<
")) ";
1912 else if(type.
id()==ID_fixedbv)
1916 out <<
"(ite (bvslt ";
1918 out <<
" (_ bv0 " << result_width <<
")) ";
1925 else if(type.
id()==ID_floatbv)
1939 else if(expr.
id()==ID_isnan)
1945 if(op_type.
id()==ID_fixedbv)
1947 else if(op_type.
id()==ID_floatbv)
1951 out <<
"(fp.isNaN ";
1961 else if(expr.
id()==ID_isfinite)
1967 if(op_type.
id()==ID_fixedbv)
1969 else if(op_type.
id()==ID_floatbv)
1975 out <<
"(not (fp.isNaN ";
1979 out <<
"(not (fp.isInfinite ";
1991 else if(expr.
id()==ID_isinf)
1997 if(op_type.
id()==ID_fixedbv)
1999 else if(op_type.
id()==ID_floatbv)
2003 out <<
"(fp.isInfinite ";
2013 else if(expr.
id()==ID_isnormal)
2019 if(op_type.
id()==ID_fixedbv)
2021 else if(op_type.
id()==ID_floatbv)
2025 out <<
"(fp.isNormal ";
2038 expr.
id() == ID_overflow_result_plus ||
2039 expr.
id() == ID_overflow_result_minus)
2048 "overflow plus and overflow minus expressions shall be of Boolean type");
2051 expr.
id() == ID_overflow_result_minus;
2052 const typet &op_type = op0.type();
2055 if(op_type.
id()==ID_signedbv)
2058 out <<
"(let ((?sum (";
2059 out << (subtract?
"bvsub":
"bvadd");
2060 out <<
" ((_ sign_extend 1) ";
2063 out <<
" ((_ sign_extend 1) ";
2073 out <<
"(mk-" << smt_typename;
2078 out <<
" ((_ extract " << width - 1 <<
" 0) ?sum) ";
2083 "((_ extract " << width <<
" " << width <<
") ?sum) "
2084 "((_ extract " << (width-1) <<
" " << (width-1) <<
") ?sum)";
2094 else if(op_type.
id()==ID_unsignedbv ||
2095 op_type.
id()==ID_pointer)
2098 out <<
"(let ((?sum (" << (subtract ?
"bvsub" :
"bvadd");
2099 out <<
" ((_ zero_extend 1) ";
2102 out <<
" ((_ zero_extend 1) ";
2114 out <<
"(mk-" << smt_typename;
2115 out <<
" ((_ extract " << width - 1 <<
" 0) ?sum) ";
2119 out <<
"((_ extract " << width <<
" " << width <<
") ?sum)";
2130 "overflow check should not be performed on unsupported type",
2135 expr.
id() == ID_overflow_result_mult)
2144 "overflow mult expression shall be of Boolean type");
2149 const typet &op_type = op0.type();
2152 if(op_type.
id()==ID_signedbv)
2154 out <<
"(let ( (prod (bvmul ((_ sign_extend " << width <<
") ";
2156 out <<
") ((_ sign_extend " << width <<
") ";
2166 out <<
"(mk-" << smt_typename;
2171 out <<
" ((_ extract " << width - 1 <<
" 0) prod) ";
2175 out <<
"(or (bvsge prod (_ bv" <<
power(2, width-1) <<
" "
2177 out <<
" (bvslt prod (bvneg (_ bv" <<
power(2, width - 1) <<
" "
2178 << width * 2 <<
"))))";
2187 else if(op_type.
id()==ID_unsignedbv)
2189 out <<
"(let ((prod (bvmul ((_ zero_extend " << width <<
") ";
2191 out <<
") ((_ zero_extend " << width <<
") ";
2201 out <<
"(mk-" << smt_typename;
2206 out <<
" ((_ extract " << width - 1 <<
" 0) prod) ";
2210 out <<
"(bvuge prod (_ bv" <<
power(2, width) <<
" " << width * 2 <<
"))";
2222 "overflow check should not be performed on unsupported type",
2225 else if(expr.
id() == ID_saturating_plus || expr.
id() == ID_saturating_minus)
2227 const bool subtract = expr.
id() == ID_saturating_minus;
2228 const auto &op_type = expr.
type();
2232 if(op_type.id() == ID_signedbv)
2237 out <<
"(let ((?sum (";
2238 out << (subtract ?
"bvsub" :
"bvadd");
2239 out <<
" ((_ sign_extend 1) ";
2242 out <<
" ((_ sign_extend 1) ";
2249 << width <<
" " << width
2252 << (width - 1) <<
" " << (width - 1) <<
") ?sum)";
2256 out <<
"((_ extract " << width - 1 <<
" 0) ?sum) ";
2259 out <<
"(ite (= ((_ extract " << width <<
" " << width <<
") ?sum) #b0) ";
2266 else if(op_type.id() == ID_unsignedbv)
2271 out <<
"(let ((?sum (" << (subtract ?
"bvsub" :
"bvadd");
2272 out <<
" ((_ zero_extend 1) ";
2275 out <<
" ((_ zero_extend 1) ";
2280 out <<
"(ite (= ((_ extract " << width <<
" " << width <<
") ?sum) #b0) ";
2283 out <<
" ((_ extract " << width - 1 <<
" 0) ?sum) ";
2297 "saturating_plus/minus on unsupported type",
2298 op_type.id_string());
2300 else if(expr.
id()==ID_array)
2306 else if(expr.
id()==ID_literal)
2310 else if(expr.
id()==ID_forall ||
2311 expr.
id()==ID_exists)
2317 throw "MathSAT does not support quantifiers";
2319 if(quantifier_expr.
id() == ID_forall)
2321 else if(quantifier_expr.
id() == ID_exists)
2326 for(
const auto &bound : quantifier_expr.
variables())
2345 const auto object_size = expr_try_dynamic_cast<object_size_exprt>(expr))
2349 else if(expr.
id()==ID_let)
2352 const auto &variables = let_expr.
variables();
2353 const auto &values = let_expr.
values();
2358 for(
auto &binding :
make_range(variables).zip(values))
2377 else if(expr.
id()==ID_constraint_select_one)
2380 "smt2_convt::convert_expr: '" + expr.
id_string() +
2381 "' is not yet supported");
2383 else if(expr.
id() == ID_bswap)
2389 "operand of byte swap expression shall have same type as the expression");
2392 out <<
"(let ((bswap_op ";
2397 bswap_expr.
type().
id() == ID_signedbv ||
2398 bswap_expr.
type().
id() == ID_unsignedbv)
2400 const std::size_t width =
2407 width % bits_per_byte == 0,
2408 "bit width indicated by type of bswap expression should be a multiple "
2409 "of the number of bits per byte");
2411 const std::size_t bytes = width / bits_per_byte;
2420 for(std::size_t
byte = 0;
byte < bytes;
byte++)
2424 out <<
"(bswap_byte_" <<
byte <<
' ';
2425 out <<
"((_ extract " << (
byte * bits_per_byte + (bits_per_byte - 1))
2426 <<
" " << (
byte * bits_per_byte) <<
") bswap_op)";
2435 for(std::size_t
byte = 0;
byte < bytes;
byte++)
2436 out <<
" bswap_byte_" <<
byte;
2447 else if(expr.
id() == ID_popcount)
2451 else if(expr.
id() == ID_count_leading_zeros)
2455 else if(expr.
id() == ID_count_trailing_zeros)
2459 else if(expr.
id() == ID_find_first_set)
2463 else if(expr.
id() == ID_bitreverse)
2467 else if(expr.
id() == ID_zero_extend)
2471 else if(expr.
id() == ID_function_application)
2475 if(function_application_expr.arguments().empty())
2483 for(
auto &op : function_application_expr.arguments())
2494 "smt2_convt::convert_expr should not be applied to unsupported type",
2503 if(dest_type.
id()==ID_c_enum_tag)
2507 if(src_type.
id()==ID_c_enum_tag)
2510 if(dest_type.
id()==ID_bool)
2513 if(src_type.
id()==ID_signedbv ||
2514 src_type.
id()==ID_unsignedbv ||
2515 src_type.
id()==ID_c_bool ||
2516 src_type.
id()==ID_fixedbv ||
2517 src_type.
id()==ID_pointer ||
2518 src_type.
id()==ID_integer)
2526 else if(src_type.
id()==ID_floatbv)
2530 out <<
"(not (fp.isZero ";
2542 else if(dest_type.
id()==ID_c_bool)
2551 out <<
" (_ bv1 " << to_width <<
")";
2552 out <<
" (_ bv0 " << to_width <<
")";
2555 else if(dest_type.
id()==ID_signedbv ||
2556 dest_type.
id()==ID_unsignedbv ||
2557 dest_type.
id()==ID_c_enum ||
2558 dest_type.
id()==ID_bv)
2562 if(src_type.
id()==ID_signedbv ||
2563 src_type.
id()==ID_unsignedbv ||
2564 src_type.
id()==ID_c_bool ||
2565 src_type.
id()==ID_c_enum ||
2566 src_type.
id()==ID_bv)
2570 if(from_width==to_width)
2572 else if(from_width<to_width)
2574 if(src_type.
id()==ID_signedbv)
2575 out <<
"((_ sign_extend ";
2577 out <<
"((_ zero_extend ";
2579 out << (to_width-from_width)
2586 out <<
"((_ extract " << (to_width-1) <<
" 0) ";
2591 else if(src_type.
id()==ID_fixedbv)
2595 std::size_t from_width=fixedbv_type.
get_width();
2602 out <<
"(let ((?tcop ";
2608 if(to_width>from_integer_bits)
2610 out <<
"((_ sign_extend "
2611 << (to_width-from_integer_bits) <<
") ";
2612 out <<
"((_ extract " << (from_width-1) <<
" "
2613 << from_fraction_bits <<
") ";
2619 out <<
"((_ extract " << (from_fraction_bits+to_width-1)
2620 <<
" " << from_fraction_bits <<
") ";
2625 out <<
" (ite (and ";
2628 out <<
"(not (= ((_ extract " << (from_fraction_bits-1) <<
" 0) ?tcop) "
2629 "(_ bv0 " << from_fraction_bits <<
")))";
2632 out <<
" (= ((_ extract " << (from_width-1) <<
" " << (from_width-1)
2637 out <<
" (_ bv1 " << to_width <<
") (_ bv0 " << to_width <<
"))";
2641 else if(src_type.
id()==ID_floatbv)
2643 if(dest_type.
id()==ID_bv)
2649 defined_expressionst::const_iterator it =
2660 else if(dest_type.
id()==ID_signedbv)
2664 "typecast unexpected "+src_type.
id_string()+
" -> "+
2667 else if(dest_type.
id()==ID_unsignedbv)
2671 "typecast unexpected "+src_type.
id_string()+
" -> "+
2675 else if(src_type.
id()==ID_bool)
2680 if(dest_type.
id()==ID_fixedbv)
2683 out <<
" (concat (_ bv1 "
2686 "(_ bv0 " << spec.
width <<
")";
2690 out <<
" (_ bv1 " << to_width <<
")";
2691 out <<
" (_ bv0 " << to_width <<
")";
2696 else if(src_type.
id()==ID_pointer)
2700 if(from_width<to_width)
2702 out <<
"((_ sign_extend ";
2703 out << (to_width-from_width)
2710 out <<
"((_ extract " << (to_width-1) <<
" 0) ";
2715 else if(src_type.
id()==ID_integer)
2721 out <<
"(_ bv" << i <<
" " << to_width <<
")";
2724 SMT2_TODO(
"can't convert non-constant integer to bitvector");
2727 src_type.
id() == ID_struct ||
2728 src_type.
id() == ID_struct_tag)
2734 "bit vector with of source and destination type shall be equal");
2741 "bit vector with of source and destination type shall be equal");
2746 src_type.
id() == ID_union ||
2747 src_type.
id() == ID_union_tag)
2751 "bit vector with of source and destination type shall be equal");
2754 else if(src_type.
id()==ID_c_bit_field)
2758 if(from_width==to_width)
2769 std::ostringstream e_str;
2770 e_str << src_type.
id() <<
" -> " << dest_type.
id()
2771 <<
" src == " <<
format(src);
2775 else if(dest_type.
id()==ID_fixedbv)
2781 if(src_type.
id()==ID_unsignedbv ||
2782 src_type.
id()==ID_signedbv ||
2783 src_type.
id()==ID_c_enum)
2790 if(from_width==to_integer_bits)
2792 else if(from_width>to_integer_bits)
2795 out <<
"((_ extract " << (to_integer_bits-1) <<
" 0) ";
2803 from_width < to_integer_bits,
2804 "from_width should be smaller than to_integer_bits as other case "
2805 "have been handled above");
2806 if(dest_type.
id()==ID_unsignedbv)
2808 out <<
"(_ zero_extend "
2809 << (to_integer_bits-from_width) <<
") ";
2815 out <<
"((_ sign_extend "
2816 << (to_integer_bits-from_width) <<
") ";
2822 out <<
"(_ bv0 " << to_fraction_bits <<
")";
2825 else if(src_type.
id()==ID_bool)
2827 out <<
"(concat (concat"
2828 <<
" (_ bv0 " << (to_integer_bits-1) <<
") ";
2834 else if(src_type.
id()==ID_fixedbv)
2839 std::size_t from_width=from_fixedbv_type.
get_width();
2841 out <<
"(let ((?tcop ";
2847 if(to_integer_bits<=from_integer_bits)
2849 out <<
"((_ extract "
2850 << (from_fraction_bits+to_integer_bits-1) <<
" "
2851 << from_fraction_bits
2857 to_integer_bits > from_integer_bits,
2858 "to_integer_bits should be greater than from_integer_bits as the"
2859 "other case has been handled above");
2860 out <<
"((_ sign_extend "
2861 << (to_integer_bits-from_integer_bits)
2863 << (from_width-1) <<
" "
2864 << from_fraction_bits
2870 if(to_fraction_bits<=from_fraction_bits)
2872 out <<
"((_ extract "
2873 << (from_fraction_bits-1) <<
" "
2874 << (from_fraction_bits-to_fraction_bits)
2880 to_fraction_bits > from_fraction_bits,
2881 "to_fraction_bits should be greater than from_fraction_bits as the"
2882 "other case has been handled above");
2883 out <<
"(concat ((_ extract "
2884 << (from_fraction_bits-1) <<
" 0) ";
2887 <<
" (_ bv0 " << to_fraction_bits-from_fraction_bits
2896 else if(dest_type.
id()==ID_pointer)
2900 if(src_type.
id()==ID_pointer)
2906 src_type.
id() == ID_unsignedbv || src_type.
id() == ID_signedbv ||
2907 src_type.
id() == ID_bv)
2913 if(from_width==to_width)
2915 else if(from_width<to_width)
2917 out <<
"((_ sign_extend "
2918 << (to_width-from_width)
2925 out <<
"((_ extract " << to_width <<
" 0) ";
2933 else if(dest_type.
id()==ID_range)
2936 const auto dest_size =
2937 dest_range_type.get_to() - dest_range_type.get_from() + 1;
2939 if(src_type.
id() == ID_range)
2942 const auto src_size =
2943 src_range_type.get_to() - src_range_type.get_from() + 1;
2945 if(src_width < dest_width)
2947 out <<
"((_ zero_extend " << dest_width - src_width <<
") ";
2951 else if(src_width > dest_width)
2953 out <<
"((_ extract " << dest_width - 1 <<
" 0) ";
2965 else if(dest_type.
id()==ID_floatbv)
2974 if(src_type.
id()==ID_bool)
2989 a.
build(significand, exponent);
2997 a.
build(significand, exponent);
3003 else if(src_type.
id()==ID_c_bool)
3009 else if(src_type.
id() == ID_bv)
3018 out <<
"((_ to_fp " << dest_floatbv_type.get_e() <<
" "
3019 << dest_floatbv_type.get_f() + 1 <<
") ";
3029 else if(dest_type.
id()==ID_integer)
3031 if(src_type.
id()==ID_bool)
3040 else if(dest_type.
id()==ID_c_bit_field)
3045 if(from_width==to_width)
3066 if(dest_type.
id()==ID_floatbv)
3068 if(src_type.
id()==ID_floatbv)
3095 out <<
"((_ to_fp " << dst.
get_e() <<
" "
3096 << dst.
get_f() + 1 <<
") ";
3105 else if(src_type.
id()==ID_unsignedbv)
3126 out <<
"((_ to_fp_unsigned " << dst.
get_e() <<
" "
3127 << dst.
get_f() + 1 <<
") ";
3136 else if(src_type.
id()==ID_signedbv)
3144 out <<
"((_ to_fp " << dst.
get_e() <<
" "
3145 << dst.
get_f() + 1 <<
") ";
3154 else if(src_type.
id()==ID_c_enum_tag)
3168 else if(dest_type.
id()==ID_signedbv)
3173 out <<
"((_ fp.to_sbv " << dest_width <<
") ";
3182 else if(dest_type.
id()==ID_unsignedbv)
3187 out <<
"((_ fp.to_ubv " << dest_width <<
") ";
3206 expr.
type().
id() == ID_struct_tag
3214 components.size() == expr.
operands().size(),
3215 "number of struct components as indicated by the struct type shall be equal"
3216 "to the number of operands of the struct expression");
3218 DATA_INVARIANT(!components.empty(),
"struct shall have struct components");
3222 const std::string &smt_typename =
datatype_map.at(struct_type);
3225 out <<
"(mk-" << smt_typename;
3228 for(struct_typet::componentst::const_iterator
3229 it=components.begin();
3230 it!=components.end();
3243 auto convert_operand = [
this](
const exprt &op) {
3247 else if(op.type().id() == ID_bool)
3254 std::size_t n_concat = 0;
3255 for(std::size_t i = components.size(); i > 1; i--)
3265 convert_operand(expr.
operands()[i - 1]);
3271 convert_operand(expr.
op0());
3273 out << std::string(n_concat,
')');
3281 const auto &size_expr = array_type.
size();
3287 out <<
"(let ((?far ";
3295 out <<
"(select ?far ";
3317 if(total_width==member_width)
3325 total_width > member_width,
3326 "total_width should be greater than member_width as member_width can be"
3327 "at most as large as total_width and the other case has been handled "
3331 << (total_width-member_width) <<
") ";
3341 if(expr_type.
id()==ID_unsignedbv ||
3342 expr_type.
id()==ID_signedbv ||
3343 expr_type.
id()==ID_bv ||
3344 expr_type.
id()==ID_c_enum ||
3345 expr_type.
id()==ID_c_enum_tag ||
3346 expr_type.
id()==ID_c_bool ||
3347 expr_type.
id()==ID_c_bit_field)
3353 out <<
"(_ bv" << value
3354 <<
" " << width <<
")";
3356 else if(expr_type.
id()==ID_fixedbv)
3362 out <<
"(_ bv" << v <<
" " << spec.
width <<
")";
3364 else if(expr_type.
id()==ID_floatbv)
3377 size_t e=floatbv_type.
get_e();
3378 size_t f=floatbv_type.
get_f()+1;
3384 out <<
"((_ to_fp " << e <<
" " << f <<
")"
3390 out <<
"(_ NaN " << e <<
" " << f <<
")";
3395 out <<
"(_ -oo " << e <<
" " << f <<
")";
3397 out <<
"(_ +oo " << e <<
" " << f <<
")";
3407 <<
"#b" << binaryString.substr(0, 1) <<
" "
3408 <<
"#b" << binaryString.substr(1, e) <<
" "
3409 <<
"#b" << binaryString.substr(1+e, f-1) <<
")";
3417 out <<
"(_ bv" << v <<
" " << spec.
width() <<
")";
3420 else if(expr_type.
id()==ID_pointer)
3434 out <<
"(_ bv" << value <<
" " << width <<
")";
3437 else if(expr_type.
id()==ID_bool)
3446 else if(expr_type.
id()==ID_array)
3452 else if(expr_type.
id()==ID_rational)
3455 const bool negative =
has_prefix(value,
"-");
3460 size_t pos=value.find(
"/");
3462 if(
pos==std::string::npos)
3463 out << value <<
".0";
3466 out <<
"(/ " << value.substr(0,
pos) <<
".0 "
3467 << value.substr(
pos+1) <<
".0)";
3473 else if(expr_type.
id()==ID_integer)
3479 out <<
"(- " << value.substr(1, std::string::npos) <<
')';
3483 else if(expr_type.
id() == ID_range)
3486 const auto size = range_type.get_to() - range_type.get_from() + 1;
3488 const auto value_int = numeric_cast_v<mp_integer>(expr);
3489 out <<
"(_ bv" << (value_int - range_type.get_from()) <<
" " << width
3498 if(expr.
type().
id() == ID_integer)
3508 "unsupported type for euclidean_mod: " + expr.
type().
id_string());
3513 if(expr.
type().
id()==ID_unsignedbv ||
3514 expr.
type().
id()==ID_signedbv)
3516 if(expr.
type().
id()==ID_unsignedbv)
3532 std::vector<mp_integer> dynamic_objects;
3535 if(dynamic_objects.empty())
3541 out <<
"(let ((?obj ((_ extract "
3542 << pointer_width-1 <<
" "
3547 if(dynamic_objects.size()==1)
3549 out <<
"(= (_ bv" << dynamic_objects.front()
3556 for(
const auto &
object : dynamic_objects)
3557 out <<
" (= (_ bv" <<
object
3571 if(op_type.
id()==ID_unsignedbv ||
3572 op_type.
id()==ID_bv)
3575 if(expr.
id()==ID_le)
3577 else if(expr.
id()==ID_lt)
3579 else if(expr.
id()==ID_ge)
3581 else if(expr.
id()==ID_gt)
3590 else if(op_type.
id()==ID_signedbv ||
3591 op_type.
id()==ID_fixedbv)
3594 if(expr.
id()==ID_le)
3596 else if(expr.
id()==ID_lt)
3598 else if(expr.
id()==ID_ge)
3600 else if(expr.
id()==ID_gt)
3609 else if(op_type.
id()==ID_floatbv)
3614 if(expr.
id()==ID_le)
3616 else if(expr.
id()==ID_lt)
3618 else if(expr.
id()==ID_ge)
3620 else if(expr.
id()==ID_gt)
3632 else if(op_type.
id()==ID_rational ||
3633 op_type.
id()==ID_integer)
3644 else if(op_type.
id() == ID_pointer)
3652 if(expr.
id() == ID_le)
3654 else if(expr.
id() == ID_lt)
3656 else if(expr.
id() == ID_ge)
3658 else if(expr.
id() == ID_gt)
3677 expr.
type().
id() == ID_rational || expr.
type().
id() == ID_integer ||
3678 expr.
type().
id() == ID_real)
3683 for(
const auto &op : expr.
operands())
3692 expr.
type().
id() == ID_unsignedbv || expr.
type().
id() == ID_signedbv ||
3693 expr.
type().
id() == ID_fixedbv || expr.
type().
id() == ID_range)
3710 else if(expr.
type().
id() == ID_floatbv)
3717 else if(expr.
type().
id() == ID_pointer)
3723 if(p.
type().
id() != ID_pointer)
3727 p.
type().
id() == ID_pointer,
3728 "one of the operands should have pointer type");
3732 base_type.id() != ID_empty,
"no pointer arithmetic over void pointers");
3735 CHECK_RETURN(element_size_opt.has_value() && *element_size_opt >= 0);
3739 out <<
"(let ((?pointerop ";
3745 const std::size_t offset_bits =
3749 out <<
"((_ extract " << pointer_width - 1 <<
' ' << offset_bits
3750 <<
") ?pointerop) ";
3751 out <<
"(bvadd ((_ extract " << offset_bits - 1 <<
" 0) ?pointerop) ";
3753 if(element_size >= 2)
3755 out <<
"(bvmul ((_ extract " << offset_bits - 1 <<
" 0) ";
3757 out <<
") (_ bv" << element_size <<
" " << offset_bits <<
"))";
3761 out <<
"((_ extract " << offset_bits - 1 <<
" 0) ";
3797 mp_integer value = numeric_cast_v<mp_integer>(cexpr);
3800 out <<
"roundNearestTiesToEven";
3802 out <<
"roundTowardNegative";
3804 out <<
"roundTowardPositive";
3806 out <<
"roundTowardZero";
3810 "Rounding mode should have value 0, 1, 2, or 3",
3818 out <<
"(ite (= (_ bv0 " << width <<
") ";
3820 out <<
") roundNearestTiesToEven ";
3822 out <<
"(ite (= (_ bv1 " << width <<
") ";
3824 out <<
") roundTowardNegative ";
3826 out <<
"(ite (= (_ bv2 " << width <<
") ";
3828 out <<
") roundTowardPositive ";
3831 out <<
"roundTowardZero";
3842 type.
id() == ID_floatbv ||
3843 (type.
id() == ID_complex &&
3848 if(type.
id()==ID_floatbv)
3858 else if(type.
id()==ID_complex)
3865 "type should not be one of the unsupported types",
3874 if(expr.
type().
id()==ID_integer)
3882 else if(expr.
type().
id()==ID_unsignedbv ||
3883 expr.
type().
id()==ID_signedbv ||
3884 expr.
type().
id()==ID_fixedbv)
3886 if(expr.
op0().
type().
id()==ID_pointer &&
3892 base_type.id() != ID_empty,
"no pointer arithmetic over void pointers");
3894 CHECK_RETURN(element_size_opt.has_value() && *element_size_opt >= 1);
3897 if(element_size >= 2)
3902 "bitvector width of operand shall be equal to the bitvector width of "
3911 if(element_size >= 2)
3924 else if(expr.
type().
id()==ID_floatbv)
3931 else if(expr.
type().
id()==ID_pointer)
3935 (expr.
op1().
type().
id() == ID_unsignedbv ||
3954 expr.
type().
id() == ID_floatbv,
3955 "type of ieee floating point expression shall be floatbv");
3973 if(expr.
type().
id()==ID_unsignedbv ||
3974 expr.
type().
id()==ID_signedbv)
3976 if(expr.
type().
id()==ID_unsignedbv)
3986 else if(expr.
type().
id()==ID_fixedbv)
3991 out <<
"((_ extract " << spec.
width-1 <<
" 0) ";
3996 out <<
" (_ bv0 " << fraction_bits <<
")) ";
3998 out <<
"((_ sign_extend " << fraction_bits <<
") ";
4004 else if(expr.
type().
id()==ID_floatbv)
4018 expr.
type().
id() == ID_floatbv,
4019 "type of ieee floating point expression shall be floatbv");
4050 "expression should have been converted to a variant with two operands");
4052 if(expr.
type().
id()==ID_unsignedbv ||
4053 expr.
type().
id()==ID_signedbv)
4064 else if(expr.
type().
id()==ID_floatbv)
4071 else if(expr.
type().
id()==ID_fixedbv)
4076 out <<
"((_ extract "
4077 << spec.
width+fraction_bits-1 <<
" "
4078 << fraction_bits <<
") ";
4082 out <<
"((_ sign_extend " << fraction_bits <<
") ";
4086 out <<
"((_ sign_extend " << fraction_bits <<
") ";
4092 else if(expr.
type().
id()==ID_rational ||
4093 expr.
type().
id()==ID_integer ||
4094 expr.
type().
id()==ID_real)
4098 for(
const auto &op : expr.
operands())
4113 expr.
type().
id() == ID_floatbv,
4114 "type of ieee floating point expression shall be floatbv");
4133 expr.
type().
id() == ID_floatbv,
4134 "type of ieee floating point expression shall be floatbv");
4148 "smt2_convt::convert_floatbv_rem to be implemented when not using "
4159 std::size_t s=expr.
operands().size();
4174 "with expression should have been converted to a version with three "
4179 if(expr_type.
id()==ID_array)
4203 out <<
"(let ((distance? ";
4204 out <<
"(bvmul (_ bv" << sub_width <<
" " << array_width <<
") ";
4208 if(array_width>index_width)
4210 out <<
"((_ zero_extend " << array_width-index_width <<
") ";
4216 out <<
"((_ extract " << array_width-1 <<
" 0) ";
4226 out <<
"(bvshl (_ bv" <<
power(2, sub_width) - 1 <<
" " << array_width
4228 out <<
"distance?)) ";
4232 out <<
"((_ zero_extend " << array_width-sub_width <<
") ";
4234 out <<
") distance?)))";
4237 else if(expr_type.
id() == ID_struct || expr_type.
id() == ID_struct_tag)
4240 expr_type.
id() == ID_struct_tag
4247 const irep_idt &component_name=index.
get(ID_component_name);
4251 "struct should have accessed component");
4255 const std::string &smt_typename =
datatype_map.at(expr_type);
4257 out <<
"(update-" << smt_typename <<
"." << component_name <<
" ";
4271 out <<
"(let ((?withop ";
4275 if(m.
width==struct_width)
4285 <<
"((_ extract " << (struct_width-1) <<
" "
4286 << m.
width <<
") ?withop) ";
4295 out <<
" ((_ extract " << (m.
offset - 1) <<
" 0) ?withop))";
4300 out <<
"(concat (concat "
4301 <<
"((_ extract " << (struct_width-1) <<
" "
4304 out <<
") ((_ extract " << (m.
offset-1) <<
" 0) ?withop)";
4311 else if(expr_type.
id() == ID_union || expr_type.
id() == ID_union_tag)
4319 if(total_width==member_width)
4326 total_width > member_width,
4327 "total width should be greater than member_width as member_width is at "
4328 "most as large as total_width and the other case has been handled "
4331 out <<
"((_ extract "
4333 <<
" " << member_width <<
") ";
4340 else if(expr_type.
id()==ID_bv ||
4341 expr_type.
id()==ID_unsignedbv ||
4342 expr_type.
id()==ID_signedbv)
4357 "with expects struct, union, or array type, but got "+
4365 SMT2_TODO(
"smt2_convt::convert_update to be implemented");
4382 if(array_op_type.
id()==ID_array)
4417 out <<
"((_ extract " << sub_width-1 <<
" 0) ";
4421 out <<
"(bvmul (_ bv" << sub_width <<
" " << array_width <<
") ";
4425 if(array_width>index_width)
4427 out <<
"((_ zero_extend " << array_width-index_width <<
") ";
4433 out <<
"((_ extract " << array_width-1 <<
" 0) ";
4445 false,
"index with unsupported array type: " + array_op_type.
id_string());
4452 const typet &struct_op_type = struct_op.
type();
4455 if(struct_op_type.
id() == ID_struct || struct_op_type.
id() == ID_struct_tag)
4458 struct_op_type.
id() == ID_struct_tag
4463 struct_type.
has_component(name),
"struct should have accessed component");
4467 const std::string &smt_typename =
datatype_map.at(struct_type);
4469 out <<
"(" << smt_typename <<
"."
4480 if(expr.
type().
id() == ID_bool)
4486 if(expr.
type().
id() == ID_bool)
4491 struct_op_type.
id() == ID_union || struct_op_type.
id() == ID_union_tag)
4495 width != 0,
"failed to get union member width");
4501 out <<
"((_ extract " << (width - 1) <<
" 0) ";
4509 out <<
"((_ extract " << (width - 1) <<
" 0) ";
4516 "convert_member on an unexpected type "+struct_op_type.
id_string());
4523 if(type.
id()==ID_bool)
4529 else if(type.
id()==ID_array)
4540 std::size_t n_concat = 0;
4554 out << std::string(n_concat,
')');
4559 else if(type.
id() == ID_struct || type.
id() == ID_struct_tag)
4572 std::size_t n_concat = 0;
4573 for(std::size_t i=components.size(); i>1; i--)
4593 out << std::string(n_concat,
')');
4598 else if(type.
id()==ID_floatbv)
4602 "floatbv expressions should be flattened when using FPA theory");
4615 if(type.
id()==ID_bool)
4622 else if(type.
id() == ID_array)
4627 out <<
"(let ((?ufop" << nesting <<
" ";
4638 "cannot unflatten arrays of non-constant size");
4645 out <<
"((as const ";
4650 out <<
"((_ extract " << subtype_width - 1 <<
" "
4651 <<
"0) ?ufop" << nesting <<
")";
4655 std::size_t offset = subtype_width;
4656 for(
mp_integer i = 1; i < size; ++i, offset += subtype_width)
4661 out <<
"((_ extract " << offset + subtype_width - 1 <<
" " << offset
4662 <<
") ?ufop" << nesting <<
")";
4670 else if(type.
id() == ID_struct || type.
id() == ID_struct_tag)
4676 out <<
"(let ((?ufop" << nesting <<
" ";
4681 const std::string &smt_typename =
datatype_map.at(type);
4683 out <<
"(mk-" << smt_typename;
4692 std::size_t offset=0;
4695 for(struct_typet::componentst::const_iterator
4696 it=components.begin();
4697 it!=components.end();
4707 out <<
"((_ extract " << offset+member_width-1 <<
" "
4708 << offset <<
") ?ufop" << nesting <<
")";
4710 offset+=member_width;
4731 if(expr.
id()==ID_and && value)
4733 for(
const auto &op : expr.
operands())
4738 if(expr.
id()==ID_or && !value)
4740 for(
const auto &op : expr.
operands())
4745 if(expr.
id()==ID_not)
4755 if(expr.
id() == ID_equal && value)
4764 if(equal_expr.
lhs().
id()==ID_symbol)
4771 equal_expr.
lhs() != equal_expr.
rhs())
4783 out <<
"; set_to true (equal)\n";
4785 if(equal_expr.
lhs().
type().
id() == ID_mathematical_function)
4789 out <<
"(declare-fun " << smt2_identifier;
4791 auto &mathematical_function_type =
4797 for(
auto &t : mathematical_function_type.domain())
4811 out <<
"(assert (= " << smt2_identifier <<
' ';
4813 out <<
')' <<
')' <<
'\n';
4817 out <<
"(define-fun " << smt2_identifier;
4822 equal_expr.
lhs().
type().
id() != ID_array ||
4850 out <<
"; set_to " << (value?
"true":
"false") <<
"\n"
4861 out << found_literal->second;
4884 exprt lowered_expr = expr;
4891 it->id() == ID_byte_extract_little_endian ||
4892 it->id() == ID_byte_extract_big_endian)
4897 it->id() == ID_byte_update_little_endian ||
4898 it->id() == ID_byte_update_big_endian)
4904 return lowered_expr;
4921 "lower_byte_operators should remove all byte operators");
4928 auto prophecy_r_or_w_ok =
4929 expr_try_dynamic_cast<prophecy_r_or_w_ok_exprt>(*it))
4932 it.mutate() = lowered;
4933 it.next_sibling_or_parent();
4936 auto prophecy_pointer_in_range =
4937 expr_try_dynamic_cast<prophecy_pointer_in_range_exprt>(*it))
4940 it.mutate() = lowered;
4941 it.next_sibling_or_parent();
4950 return lowered_expr;
4961 if(expr.
id() == ID_exists || expr.
id() == ID_forall)
4963 std::unordered_map<irep_idt, std::optional<identifiert>> shadowed_syms;
4968 for(
const auto &symbol : q_expr.variables())
4970 const auto identifier = symbol.get_identifier();
4973 shadowed_syms.insert(
4975 id_entry.second ? std::nullopt
4976 : std::optional{id_entry.first->second}});
4979 for(
const auto &[
id, shadowed_val] : shadowed_syms)
4982 if(!shadowed_val.has_value())
4985 previous_entry->second = std::move(*shadowed_val);
4991 for(
const auto &op : expr.
operands())
4994 if(expr.
id()==ID_symbol ||
4995 expr.
id()==ID_nondet_symbol)
4998 if(expr.
type().
id()==ID_code)
5003 if(expr.
id()==ID_symbol)
5006 identifier=
"nondet_"+
5017 out <<
"; find_symbols\n";
5018 out <<
"(declare-fun " << smt2_identifier;
5020 if(expr.
type().
id() == ID_mathematical_function)
5022 auto &mathematical_function_type =
5027 for(
auto &type : mathematical_function_type.domain())
5048 else if(expr.
id() == ID_array_of)
5055 const auto &array_type = array_of.type();
5059 out <<
"; the following is a substitute for lambda i. x\n";
5060 out <<
"(declare-fun " <<
id <<
" () ";
5067 out <<
"(assert (forall ((i ";
5069 out <<
")) (= (select " <<
id <<
" i) ";
5087 else if(expr.
id() == ID_array_comprehension)
5094 const auto &array_type = array_comprehension.type();
5095 const auto &array_size = array_type.size();
5099 out <<
"(declare-fun " <<
id <<
" () ";
5103 out <<
"; the following is a substitute for lambda i . x(i)\n";
5104 out <<
"; universally quantified initialization of the array\n";
5105 out <<
"(assert (forall ((";
5109 out <<
")) (=> (and (bvule (_ bv0 " <<
boolbv_width(array_size.type())
5116 out <<
")) (= (select " <<
id <<
" ";
5135 else if(expr.
id()==ID_array)
5142 out <<
"; the following is a substitute for an array constructor" <<
"\n";
5143 out <<
"(declare-fun " <<
id <<
" () ";
5149 for(std::size_t i = 0; i < expr.
operands().size(); i++)
5151 out <<
"(assert (= (select " <<
id <<
" ";
5172 else if(expr.
id()==ID_string_constant)
5182 out <<
"; the following is a substitute for a string" <<
"\n";
5183 out <<
"(declare-fun " <<
id <<
" () ";
5187 for(std::size_t i=0; i<tmp.
operands().size(); i++)
5189 out <<
"(assert (= (select " <<
id <<
' ';
5193 out <<
"))" <<
"\n";
5200 const auto object_size = expr_try_dynamic_cast<object_size_exprt>(expr))
5206 out <<
"(declare-fun " <<
id <<
" () ";
5217 (expr.
id() == ID_floatbv_plus ||
5218 expr.
id() == ID_floatbv_minus ||
5219 expr.
id() == ID_floatbv_mult ||
5220 expr.
id() == ID_floatbv_div ||
5221 expr.
id() == ID_floatbv_typecast ||
5222 expr.
id() == ID_ieee_float_equal ||
5223 expr.
id() == ID_ieee_float_notequal ||
5224 ((expr.
id() == ID_lt ||
5225 expr.
id() == ID_gt ||
5226 expr.
id() == ID_le ||
5227 expr.
id() == ID_ge ||
5228 expr.
id() == ID_isnan ||
5229 expr.
id() == ID_isnormal ||
5230 expr.
id() == ID_isfinite ||
5231 expr.
id() == ID_isinf ||
5232 expr.
id() == ID_sign ||
5233 expr.
id() == ID_unary_minus ||
5234 expr.
id() == ID_typecast ||
5235 expr.
id() == ID_abs) &&
5242 if(
bvfp_set.insert(
function).second)
5244 out <<
"; this is a model for " << expr.
id() <<
" : "
5247 <<
"(define-fun " <<
function <<
" (";
5249 for(std::size_t i = 0; i < expr.
operands().size(); i++)
5253 out <<
"(op" << i <<
' ';
5263 for(std::size_t i = 0; i < tmp1.
operands().size(); i++)
5279 expr.
type().
id() == ID_bv)
5289 out <<
"(declare-fun " <<
id <<
" () ";
5295 out <<
"(assert (= ";
5296 out <<
"((_ to_fp " << floatbv_type.get_e() <<
" "
5297 << floatbv_type.get_f() + 1 <<
") " <<
id <<
')';
5305 else if(expr.
id() == ID_initial_state)
5307 irep_idt function =
"initial-state";
5311 out <<
"(declare-fun " <<
function <<
" (";
5318 else if(expr.
id() == ID_evaluate)
5324 out <<
"(declare-fun " <<
function <<
" (";
5334 expr.
id() == ID_state_is_cstring ||
5335 expr.
id() == ID_state_is_dynamic_object ||
5336 expr.
id() == ID_state_live_object || expr.
id() == ID_state_writeable_object)
5339 expr.
id() == ID_state_is_cstring ?
"state-is-cstring"
5340 : expr.
id() == ID_state_is_dynamic_object ?
"state-is-dynamic-object"
5341 : expr.
id() == ID_state_live_object ?
"state-live-object"
5342 :
"state-writeable-object";
5346 out <<
"(declare-fun " <<
function <<
" (";
5356 expr.
id() == ID_state_r_ok || expr.
id() == ID_state_w_ok ||
5357 expr.
id() == ID_state_rw_ok)
5359 irep_idt function = expr.
id() == ID_state_r_ok ?
"state-r-ok"
5360 : expr.
id() == ID_state_w_ok ?
"state-w-ok"
5365 out <<
"(declare-fun " <<
function <<
" (";
5376 else if(expr.
id() == ID_update_state)
5383 out <<
"(declare-fun " <<
function <<
" (";
5394 else if(expr.
id() == ID_enter_scope_state)
5401 out <<
"(declare-fun " <<
function <<
" (";
5412 else if(expr.
id() == ID_exit_scope_state)
5419 out <<
"(declare-fun " <<
function <<
" (";
5428 else if(expr.
id() == ID_allocate)
5434 out <<
"(declare-fun " <<
function <<
" (";
5443 else if(expr.
id() == ID_reallocate)
5449 out <<
"(declare-fun " <<
function <<
" (";
5460 else if(expr.
id() == ID_deallocate_state)
5466 out <<
"(declare-fun " <<
function <<
" (";
5475 else if(expr.
id() == ID_object_address)
5477 irep_idt function =
"object-address";
5481 out <<
"(declare-fun " <<
function <<
" (String) ";
5486 else if(expr.
id() == ID_field_address)
5492 out <<
"(declare-fun " <<
function <<
" (";
5501 else if(expr.
id() == ID_element_address)
5507 out <<
"(declare-fun " <<
function <<
" (";
5526 if(expr.
id() == ID_with)
5534 if(type.
id()==ID_array)
5548 out <<
"(_ BitVec 1)";
5554 else if(type.
id()==ID_bool)
5558 else if(type.
id() == ID_struct || type.
id() == ID_struct_tag)
5568 out <<
"(_ BitVec " << width <<
")";
5571 else if(type.
id()==ID_code)
5578 else if(type.
id() == ID_union || type.
id() == ID_union_tag)
5585 union_type.
components().empty() || width != 0,
5586 "failed to get width of union");
5588 out <<
"(_ BitVec " << width <<
")";
5590 else if(type.
id()==ID_pointer)
5595 else if(type.
id()==ID_bv ||
5596 type.
id()==ID_fixedbv ||
5597 type.
id()==ID_unsignedbv ||
5598 type.
id()==ID_signedbv ||
5599 type.
id()==ID_c_bool)
5604 else if(type.
id()==ID_c_enum)
5611 else if(type.
id()==ID_c_enum_tag)
5615 else if(type.
id()==ID_floatbv)
5620 out <<
"(_ FloatingPoint "
5621 << floatbv_type.
get_e() <<
" "
5622 << floatbv_type.
get_f() + 1 <<
")";
5627 else if(type.
id()==ID_rational ||
5630 else if(type.
id()==ID_integer)
5632 else if(type.
id()==ID_complex)
5642 out <<
"(_ BitVec " << width <<
")";
5645 else if(type.
id()==ID_c_bit_field)
5649 else if(type.
id() == ID_state)
5653 else if(type.
id() == ID_range)
5656 mp_integer size = range_type.get_to() - range_type.get_from() + 1;
5669 std::set<irep_idt> recstack;
5675 std::set<irep_idt> &recstack)
5677 if(type.
id()==ID_array)
5683 else if(type.
id()==ID_complex)
5690 const std::string smt_typename =
5694 out <<
"(declare-datatypes ((" << smt_typename <<
" 0)) "
5695 <<
"(((mk-" << smt_typename;
5697 out <<
" (" << smt_typename <<
".imag ";
5701 out <<
" (" << smt_typename <<
".real ";
5708 else if(type.
id() == ID_struct)
5711 bool need_decl=
false;
5715 const std::string smt_typename =
5730 const std::string &smt_typename =
datatype_map.at(type);
5741 out <<
"(declare-datatypes ((" << smt_typename <<
" 0)) "
5742 <<
"(((mk-" << smt_typename <<
" ";
5749 out <<
"(" << smt_typename <<
"." <<
component.get_name()
5755 out <<
"))))" <<
"\n";
5772 for(struct_union_typet::componentst::const_iterator
5773 it=components.begin();
5774 it!=components.end();
5781 out <<
"(define-fun update-" << smt_typename <<
"."
5783 <<
"((s " << smt_typename <<
") "
5786 out <<
")) " << smt_typename <<
" "
5787 <<
"(mk-" << smt_typename
5790 for(struct_union_typet::componentst::const_iterator
5791 it2=components.begin();
5792 it2!=components.end();
5799 out <<
"(" << smt_typename <<
"."
5800 << it2->get_name() <<
" s) ";
5804 out <<
"))" <<
"\n";
5810 else if(type.
id() == ID_union)
5818 else if(type.
id()==ID_code)
5822 for(
const auto ¶m : parameters)
5827 else if(type.
id()==ID_pointer)
5831 else if(type.
id() == ID_struct_tag)
5834 const irep_idt &
id = struct_tag.get_identifier();
5836 if(recstack.find(
id) == recstack.end())
5839 recstack.insert(
id);
5844 else if(type.
id() == ID_union_tag)
5847 const irep_idt &
id = union_tag.get_identifier();
5849 if(recstack.find(
id) == recstack.end())
5851 recstack.insert(
id);
5855 else if(type.
id() == ID_state)
5860 out <<
"(declare-sort state 0)\n";
5863 else if(type.
id() == ID_mathematical_function)
5865 const auto &mathematical_function_type =
5867 for(
auto &d_type : mathematical_function_type.domain())
API to expression classes for bitvectors.
const update_bit_exprt & to_update_bit_expr(const exprt &expr)
Cast an exprt to an update_bit_exprt.
const onehot_exprt & to_onehot_expr(const exprt &expr)
Cast an exprt to a onehot_exprt.
bool can_cast_expr< mult_overflow_exprt >(const exprt &base)
const onehot0_exprt & to_onehot0_expr(const exprt &expr)
Cast an exprt to a onehot0_exprt.
const shift_exprt & to_shift_expr(const exprt &expr)
Cast an exprt to a shift_exprt.
bool can_cast_expr< minus_overflow_exprt >(const exprt &base)
const extractbit_exprt & to_extractbit_expr(const exprt &expr)
Cast an exprt to an extractbit_exprt.
const extractbits_exprt & to_extractbits_expr(const exprt &expr)
Cast an exprt to an extractbits_exprt.
bool can_cast_expr< overflow_result_exprt >(const exprt &base)
const find_first_set_exprt & to_find_first_set_expr(const exprt &expr)
Cast an exprt to a find_first_set_exprt.
const bitreverse_exprt & to_bitreverse_expr(const exprt &expr)
Cast an exprt to a bitreverse_exprt.
const zero_extend_exprt & to_zero_extend_expr(const exprt &expr)
Cast an exprt to a zero_extend_exprt.
const count_trailing_zeros_exprt & to_count_trailing_zeros_expr(const exprt &expr)
Cast an exprt to a count_trailing_zeros_exprt.
bool can_cast_expr< plus_overflow_exprt >(const exprt &base)
const bitnot_exprt & to_bitnot_expr(const exprt &expr)
Cast an exprt to a bitnot_exprt.
const replication_exprt & to_replication_expr(const exprt &expr)
Cast an exprt to a replication_exprt.
const bswap_exprt & to_bswap_expr(const exprt &expr)
Cast an exprt to a bswap_exprt.
const count_leading_zeros_exprt & to_count_leading_zeros_expr(const exprt &expr)
Cast an exprt to a count_leading_zeros_exprt.
const popcount_exprt & to_popcount_expr(const exprt &expr)
Cast an exprt to a popcount_exprt.
const update_bits_exprt & to_update_bits_expr(const exprt &expr)
Cast an exprt to an update_bits_exprt.
const floatbv_typet & to_floatbv_type(const typet &type)
Cast a typet to a floatbv_typet.
const signedbv_typet & to_signedbv_type(const typet &type)
Cast a typet to a signedbv_typet.
const bitvector_typet & to_bitvector_type(const typet &type)
Cast a typet to a bitvector_typet.
const fixedbv_typet & to_fixedbv_type(const typet &type)
Cast a typet to a fixedbv_typet.
const unsignedbv_typet & to_unsignedbv_type(const typet &type)
Cast a typet to an unsignedbv_typet.
const bv_typet & to_bv_type(const typet &type)
Cast a typet to a bv_typet.
bool has_byte_operator(const exprt &src)
Return true iff src or one of its operands contain a byte extract or byte update expression.
Expression classes for byte-level operators.
exprt lower_byte_extract(const byte_extract_exprt &src, const namespacet &ns)
Rewrite a byte extract expression to more fundamental operations.
exprt lower_byte_update(const byte_update_exprt &src, const namespacet &ns)
Rewrite a byte update expression to more fundamental operations.
const byte_update_exprt & to_byte_update_expr(const exprt &expr)
const byte_extract_exprt & to_byte_extract_expr(const exprt &expr)
typet c_bit_field_replacement_type(const c_bit_field_typet &src, const namespacet &ns)
pointer_typet pointer_type(const typet &subtype)
const c_enum_typet & to_c_enum_type(const typet &type)
Cast a typet to a c_enum_typet.
const union_tag_typet & to_union_tag_type(const typet &type)
Cast a typet to a union_tag_typet.
const c_bit_field_typet & to_c_bit_field_type(const typet &type)
Cast a typet to a c_bit_field_typet.
const union_typet & to_union_type(const typet &type)
Cast a typet to a union_typet.
const c_enum_tag_typet & to_c_enum_tag_type(const typet &type)
Cast a typet to a c_enum_tag_typet.
const c_bool_typet & to_c_bool_type(const typet &type)
Cast a typet to a c_bool_typet.
Operator to return the address of an object.
Thrown when an unexpected error occurs during the analysis (e.g., when the SAT solver returns an erro...
Pointer-typed bitvector constant annotated with the pointer expression that the bitvector is the nume...
Array constructor from list of elements.
typet index_type() const
The type of the index expressions into any instance of this type.
const typet & element_type() const
The type of the elements of the array.
const exprt & size() const
A base class for binary expressions.
A base class for relations, i.e., binary predicates whose two operands have the same type.
Bit-wise negation of bit-vectors.
std::size_t get_width() const
const membert & get_member(const struct_typet &type, const irep_idt &member) const
The byte swap expression.
std::size_t get_bits_per_byte() const
std::vector< parametert > parameterst
const parameterst & parameters() const
struct configt::bv_encodingt bv_encoding
A constant literal expression.
const irep_idt & get_value() const
void set_value(const irep_idt &value)
bool is_null_pointer() const
Returns true if expr has a pointer type and a value NULL; it also returns true when expr has value ze...
resultt
Result of running the decision procedure.
dstringt has one field, an unsigned integer no which is an index into a static table of strings.
Boute's Euclidean definition of Modulo – to match SMT-LIB2.
Base class for all expressions.
std::vector< exprt > operandst
bool has_operands() const
Return true if there is at least one operand.
bool is_true() const
Return whether the expression is a constant representing true.
depth_iteratort depth_end()
bool is_boolean() const
Return whether the expression represents a Boolean.
depth_iteratort depth_begin()
bool is_false() const
Return whether the expression is a constant representing false.
bool is_zero() const
Return whether the expression is a constant representing 0.
typet & type()
Return the type of the expression.
bool is_constant() const
Return whether the expression is a constant.
void visit_post(std::function< void(exprt &)>)
These are post-order traversal visitors, i.e., the visitor is executed on a node after its children h...
The Boolean constant false.
std::size_t get_fraction_bits() const
Fixed-width bit-vector with signed fixed-point interpretation.
std::size_t get_fraction_bits() const
std::size_t get_integer_bits() const
Semantic type conversion from/to floating-point formats.
Fixed-width bit-vector with IEEE floating-point interpretation.
std::size_t get_f() const
std::size_t get_e() const
IEEE floating-point operations These have two data operands (op0 and op1) and one rounding mode (op2)...
std::size_t width() const
constant_exprt to_expr() const
static ieee_floatt plus_infinity(const ieee_float_spect &_spec)
static ieee_floatt NaN(const ieee_float_spect &_spec)
static ieee_floatt minus_infinity(const ieee_float_spect &_spec)
void build(const mp_integer &exp, const mp_integer &frac)
The trinary if-then-else operator.
There are a large number of kinds of tree structured or tree-like data in CPROVER.
std::string pretty(unsigned indent=0, unsigned max_indent=0) const
const irep_idt & get(const irep_idt &name) const
const std::string & id_string() const
const irep_idt & id() const
Evaluates to true if the operand is finite.
Evaluates to true if the operand is infinite.
Evaluates to true if the operand is NaN.
Evaluates to true if the operand is a normal number.
exprt & where()
convenience accessor for binding().where()
binding_exprt::variablest & variables()
convenience accessor for binding().variables()
literalt get_literal() const
Extract member of struct or union.
const exprt & struct_op() const
irep_idt get_component_name() const
Modulo defined as lhs-(rhs * truncate(lhs/rhs)).
Binary multiplication Associativity is not specified.
const union_typet & follow_tag(const union_tag_typet &) const
Follow type tag of union type.
A namespacet is essentially one or two symbol tables bound together, to allow for symbol lookups in t...
const irep_idt & get_identifier() const
Expression for finding the size (in bytes) of the object a pointer points to.
The plus expression Associativity is not specified.
const mp_integer & get_invalid_object() const
numberingt< exprt, irep_hash > objects
exprt pointer_expr(const pointert &pointer, const pointer_typet &type) const
Convert an (object,offset) pair to an expression.
void get_dynamic_objects(std::vector< mp_integer > &objects) const
mp_integer add_object(const exprt &expr)
The pointer type These are both 'bitvector_typet' (they have a width) and 'type_with_subtypet' (they ...
const typet & base_type() const
The type of the data what we point to.
A base class for quantifier expressions.
A base class for shift and rotate operators.
Sign of an expression Predicate is true if _op is negative, false otherwise.
const irep_idt & get_identifier() const
void convert_relation(const binary_relation_exprt &)
bool use_lambda_for_array
void convert_type(const typet &)
void unflatten(wheret, const typet &, unsigned nesting=0)
bool use_array_theory(const exprt &)
void find_symbols(const exprt &expr)
std::size_t number_of_solver_calls
void convert_typecast(const typecast_exprt &expr)
void write_footer()
Writes the end of the SMT file to the smt_convt::out stream.
tvt l_get(literalt l) const
void convert_floatbv_rem(const binary_exprt &expr)
std::unordered_map< irep_idt, irept > current_bindings
resultt dec_solve(const exprt &) override
Implementation of the decision procedure.
std::set< irep_idt > bvfp_set
void convert_address_of_rec(const exprt &expr, const pointer_typet &result_type)
void push() override
Unimplemented.
void convert_is_dynamic_object(const unary_exprt &)
void convert_literal(const literalt)
void convert_floatbv_div(const ieee_float_op_exprt &expr)
void convert_string_literal(const std::string &)
std::size_t get_number_of_solver_calls() const override
Return the number of incremental solver calls.
void convert_floatbv_mult(const ieee_float_op_exprt &expr)
boolbv_widtht boolbv_width
void convert_constant(const constant_exprt &expr)
std::string floatbv_suffix(const exprt &) const
void flatten2bv(const exprt &)
void convert_div(const div_exprt &expr)
exprt lower_byte_operators(const exprt &expr)
Lower byte_update and byte_extract operations within expr.
std::string type2id(const typet &) const
void convert_rounding_mode_FPA(const exprt &expr)
Converting a constant or symbolic rounding mode to SMT-LIB.
void convert_floatbv_typecast(const floatbv_typecast_exprt &expr)
struct_exprt parse_struct(const irept &s, const struct_typet &type)
void convert_mult(const mult_exprt &expr)
void convert_update_bit(const update_bit_exprt &)
exprt prepare_for_convert_expr(const exprt &expr)
Perform steps necessary before an expression is passed to convert_expr.
exprt get(const exprt &expr) const override
Return expr with variables replaced by values from satisfying assignment if available.
std::string decision_procedure_text() const override
Return a textual description of the decision procedure.
void convert_floatbv_minus(const ieee_float_op_exprt &expr)
bool use_check_sat_assuming
std::map< object_size_exprt, irep_idt > object_sizes
void define_object_size(const irep_idt &id, const object_size_exprt &expr)
datatype_mapt datatype_map
void convert_mod(const mod_exprt &expr)
static std::string convert_identifier(const irep_idt &identifier)
void convert_floatbv_plus(const ieee_float_op_exprt &expr)
void convert_struct(const struct_exprt &expr)
std::unordered_map< irep_idt, bool > set_values
The values which boolean identifiers have been smt2_convt::set_to or in other words those which are a...
smt2_convt(const namespacet &_ns, const std::string &_benchmark, const std::string &_notes, const std::string &_logic, solvert _solver, std::ostream &_out)
void convert_member(const member_exprt &expr)
void convert_euclidean_mod(const euclidean_mod_exprt &expr)
void convert_index(const index_exprt &expr)
pointer_logict pointer_logic
exprt handle(const exprt &expr) override
Generate a handle, which is an expression that has the same value as the argument in any model that i...
void print_assignment(std::ostream &out) const override
Print satisfying assignment to out.
void walk_array_tree(std::unordered_map< int64_t, exprt > *operands_map, const irept &src, const array_typet &type)
This function walks the SMT output and populates a map with index/value pairs for the array.
void set_to(const exprt &expr, bool value) override
For a Boolean expression expr, add the constraint 'expr' if value is true, otherwise add 'not expr'.
exprt parse_rec(const irept &s, const typet &type)
void convert_union(const union_exprt &expr)
exprt parse_union(const irept &s, const union_typet &type)
exprt parse_array(const irept &s, const array_typet &type)
This function is for parsing array output from SMT solvers when "(get-value |???|)" returns an array ...
std::vector< bool > boolean_assignment
void flatten_array(const exprt &)
produce a flat bit-vector for a given array of fixed size
void convert_with(const with_exprt &expr)
std::vector< literalt > assumptions
void convert_plus(const plus_exprt &expr)
defined_expressionst defined_expressions
void pop() override
Currently, only implements a single stack element (no nested contexts)
void convert_update_bits(const update_bits_exprt &)
void find_symbols_rec(const typet &type, std::set< irep_idt > &recstack)
void convert_update(const update_exprt &)
std::set< irep_idt > state_fkt_declared
identifier_mapt identifier_map
void convert_minus(const minus_exprt &expr)
void convert_expr(const exprt &)
constant_exprt parse_literal(const irept &, const typet &type)
std::size_t no_boolean_variables
smt2_identifierst smt2_identifiers
void convert_floatbv(const exprt &expr)
literalt convert(const exprt &expr)
const smt2_symbolt & to_smt2_symbol(const exprt &expr)
array_exprt to_array_expr() const
convert string into array constant
Struct constructor from list of elements.
Structure type, corresponds to C style structs.
const irep_idt & get_name() const
const componentt & get_component(const irep_idt &component_name) const
Get the reference to a component with given name.
bool has_component(const irep_idt &component_name) const
const componentst & components() const
std::vector< componentt > componentst
const irep_idt & get_identifier() const
The Boolean constant true.
Semantic type conversion.
static exprt conditional_cast(const exprt &expr, const typet &type)
The type of an expression, extends irept.
Generic base class for unary expressions.
The unary minus expression.
Union constructor from single element.
Fixed-width bit-vector with unsigned binary interpretation.
Replaces a sub-range of a bit-vector operand.
exprt lower() const
A lowering to masking, shifting, or.
Replaces a sub-range of a bit-vector operand.
exprt lower() const
A lowering to masking, shifting, or.
Operator to update elements in structs and arrays.
Operator to update elements in structs and arrays.
bool has_prefix(const std::string &s, const std::string &prefix)
Forward depth-first search iterators These iterators' copy operations are expensive,...
exprt make_binary(const exprt &expr)
splits an expression with >=3 operands into nested binary expressions
Deprecated expression utility functions.
exprt float_bv(const exprt &src)
API to expression classes for floating-point arithmetic.
const isnormal_exprt & to_isnormal_expr(const exprt &expr)
Cast an exprt to a isnormal_exprt.
const isnan_exprt & to_isnan_expr(const exprt &expr)
Cast an exprt to a isnan_exprt.
const ieee_float_op_exprt & to_ieee_float_op_expr(const exprt &expr)
Cast an exprt to an ieee_float_op_exprt.
const isfinite_exprt & to_isfinite_expr(const exprt &expr)
Cast an exprt to a isfinite_exprt.
const floatbv_typecast_exprt & to_floatbv_typecast_expr(const exprt &expr)
Cast an exprt to a floatbv_typecast_exprt.
const isinf_exprt & to_isinf_expr(const exprt &expr)
Cast an exprt to a isinf_exprt.
const std::string & id2string(const irep_idt &d)
static std::string binary(const constant_exprt &src)
bool is_true(const literalt &l)
literalt const_literal(bool value)
const literal_exprt & to_literal_expr(const exprt &expr)
Cast a generic exprt to a literal_exprt.
double pow(double x, double y)
API to expression classes for 'mathematical' expressions.
const function_application_exprt & to_function_application_expr(const exprt &expr)
Cast an exprt to a function_application_exprt.
const quantifier_exprt & to_quantifier_expr(const exprt &expr)
Cast an exprt to a quantifier_exprt.
const mathematical_function_typet & to_mathematical_function_type(const typet &type)
Cast a typet to a mathematical_function_typet.
const mp_integer string2integer(const std::string &n, unsigned base)
mp_integer bitwise_or(const mp_integer &a, const mp_integer &b)
bitwise 'or' of two nonnegative integers
const std::string integer2binary(const mp_integer &n, std::size_t width)
const pointer_offset_exprt & to_pointer_offset_expr(const exprt &expr)
Cast an exprt to a pointer_offset_exprt.
const field_address_exprt & to_field_address_expr(const exprt &expr)
Cast an exprt to an field_address_exprt.
const pointer_typet & to_pointer_type(const typet &type)
Cast a typet to a pointer_typet.
const pointer_object_exprt & to_pointer_object_expr(const exprt &expr)
Cast an exprt to a pointer_object_exprt.
const object_address_exprt & to_object_address_expr(const exprt &expr)
Cast an exprt to an object_address_exprt.
const address_of_exprt & to_address_of_expr(const exprt &expr)
Cast an exprt to an address_of_exprt.
const element_address_exprt & to_element_address_expr(const exprt &expr)
Cast an exprt to an element_address_exprt.
std::optional< exprt > size_of_expr(const typet &type, const namespacet &ns)
std::optional< mp_integer > member_offset(const struct_typet &type, const irep_idt &member, const namespacet &ns)
std::optional< mp_integer > pointer_offset_size(const typet &type, const namespacet &ns)
Compute the size of a type in bytes, rounding up to full bytes.
exprt pointer_offset(const exprt &pointer)
exprt object_size(const exprt &pointer)
exprt same_object(const exprt &p1, const exprt &p2)
Various predicates over pointers in programs.
Ranges: pair of begin and end iterators, which can be initialized from containers,...
ranget< iteratort > make_range(iteratort begin, iteratort end)
exprt simplify_expr(exprt src, const namespacet &ns)
static bool has_quantifier(const exprt &expr)
static bool is_zero_width(const typet &type, const namespacet &ns)
Returns true iff type has effective width of zero bits.
static bool is_smt2_simple_identifier(const std::string &identifier)
#define UNEXPECTEDCASE(S)
bool is_smt2_simple_symbol_character(char ch)
void solver(std::vector< framet > &frames, const std::unordered_set< symbol_exprt, irep_hash > &address_taken, const solver_optionst &solver_options, const namespacet &ns, std::vector< propertyt > &properties, std::size_t property_index)
#define CHECK_RETURN(CONDITION)
#define UNREACHABLE
This should be used to mark dead code.
#define DATA_INVARIANT(CONDITION, REASON)
This condition should be used to document that assumptions that are made on goto_functions,...
#define PRECONDITION(CONDITION)
#define INVARIANT_WITH_DIAGNOSTICS(CONDITION, REASON,...)
Same as invariant, with one or more diagnostics attached Diagnostics can be of any type that has a sp...
#define CHECK_RETURN_WITH_DIAGNOSTICS(CONDITION,...)
#define DATA_INVARIANT_WITH_DIAGNOSTICS(CONDITION, REASON,...)
#define UNREACHABLE_BECAUSE(REASON)
auto component(T &struct_expr, const irep_idt &name, const namespacet &ns) -> decltype(struct_expr.op0())
API to expression classes.
const notequal_exprt & to_notequal_expr(const exprt &expr)
Cast an exprt to an notequal_exprt.
const if_exprt & to_if_expr(const exprt &expr)
Cast an exprt to an if_exprt.
const update_exprt & to_update_expr(const exprt &expr)
Cast an exprt to an update_exprt.
const let_exprt & to_let_expr(const exprt &expr)
Cast an exprt to a let_exprt.
const unary_plus_exprt & to_unary_plus_expr(const exprt &expr)
Cast an exprt to a unary_plus_exprt.
const constant_exprt & to_constant_expr(const exprt &expr)
Cast an exprt to a constant_exprt.
const symbol_exprt & to_symbol_expr(const exprt &expr)
Cast an exprt to a symbol_exprt.
const mod_exprt & to_mod_expr(const exprt &expr)
Cast an exprt to a mod_exprt.
const array_comprehension_exprt & to_array_comprehension_expr(const exprt &expr)
Cast an exprt to a array_comprehension_exprt.
const typecast_exprt & to_typecast_expr(const exprt &expr)
Cast an exprt to a typecast_exprt.
const not_exprt & to_not_expr(const exprt &expr)
Cast an exprt to an not_exprt.
const union_exprt & to_union_expr(const exprt &expr)
Cast an exprt to a union_exprt.
const unary_minus_exprt & to_unary_minus_expr(const exprt &expr)
Cast an exprt to a unary_minus_exprt.
const named_term_exprt & to_named_term_expr(const exprt &expr)
Cast an exprt to a named_term_exprt.
const div_exprt & to_div_expr(const exprt &expr)
Cast an exprt to a div_exprt.
const minus_exprt & to_minus_expr(const exprt &expr)
Cast an exprt to a minus_exprt.
const multi_ary_exprt & to_multi_ary_expr(const exprt &expr)
Cast an exprt to a multi_ary_exprt.
const with_exprt & to_with_expr(const exprt &expr)
Cast an exprt to a with_exprt.
const struct_exprt & to_struct_expr(const exprt &expr)
Cast an exprt to a struct_exprt.
const binary_exprt & to_binary_expr(const exprt &expr)
Cast an exprt to a binary_exprt.
const ternary_exprt & to_ternary_expr(const exprt &expr)
Cast an exprt to a ternary_exprt.
const array_of_exprt & to_array_of_expr(const exprt &expr)
Cast an exprt to an array_of_exprt.
const euclidean_mod_exprt & to_euclidean_mod_expr(const exprt &expr)
Cast an exprt to a euclidean_mod_exprt.
const equal_exprt & to_equal_expr(const exprt &expr)
Cast an exprt to an equal_exprt.
const plus_exprt & to_plus_expr(const exprt &expr)
Cast an exprt to a plus_exprt.
const member_exprt & to_member_expr(const exprt &expr)
Cast an exprt to a member_exprt.
const unary_exprt & to_unary_expr(const exprt &expr)
Cast an exprt to a unary_exprt.
const nondet_symbol_exprt & to_nondet_symbol_expr(const exprt &expr)
Cast an exprt to a nondet_symbol_exprt.
const implies_exprt & to_implies_expr(const exprt &expr)
Cast an exprt to a implies_exprt.
const sign_exprt & to_sign_expr(const exprt &expr)
Cast an exprt to a sign_exprt.
const abs_exprt & to_abs_expr(const exprt &expr)
Cast an exprt to a abs_exprt.
const binary_relation_exprt & to_binary_relation_expr(const exprt &expr)
Cast an exprt to a binary_relation_exprt.
const index_exprt & to_index_expr(const exprt &expr)
Cast an exprt to an index_exprt.
const mult_exprt & to_mult_expr(const exprt &expr)
Cast an exprt to a mult_exprt.
const range_typet & to_range_type(const typet &type)
Cast a typet to a range_typet.
const struct_typet & to_struct_type(const typet &type)
Cast a typet to a struct_typet.
const code_typet & to_code_type(const typet &type)
Cast a typet to a code_typet.
const array_typet & to_array_type(const typet &type)
Cast a typet to an array_typet.
const complex_typet & to_complex_type(const typet &type)
Cast a typet to a complex_typet.
const struct_union_typet & to_struct_union_type(const typet &type)
Cast a typet to a struct_union_typet.
const struct_tag_typet & to_struct_tag_type(const typet &type)
Cast a typet to a struct_tag_typet.
std::size_t unsafe_string2size_t(const std::string &str, int base)
const string_constantt & to_string_constant(const exprt &expr)
std::string to_string(const string_not_contains_constraintt &expr)
Used for debug printing.