33#include < util/arith_tools.h>
44#include < util/bitvector_expr.h>
55#include < util/bitvector_types.h>
6+ #include < util/byte_operators.h>
67#include < util/c_types.h>
78#include < util/config.h>
89#include < util/expr_initializer.h>
@@ -142,7 +143,7 @@ std::string to_hex(unsigned int value)
142143}
143144
144145TEST_CASE (
145- " duplicate_per_byte on unsigned_bv with constant" ,
146+ " duplicate_per_byte on bitvector types with constant" ,
146147 " [core][util][duplicate_per_byte]" )
147148{
148149 auto test = expr_initializer_test_environmentt::make ();
@@ -161,34 +162,73 @@ TEST_CASE(
161162 rowt{0xAB , 8 , 0xABAB , 16 }, // smaller-type constant gets replicated
162163 rowt{0xAB , 8 , 0xBABAB , 20 }); // smaller-type constant gets replicated
163164 SECTION (
164- " Testing with output size " + std::to_string (output_size ) + " init value " +
165- to_hex (init_expr_value) + " of size " + std::to_string (init_expr_size))
165+ " Testing with init value " + to_hex (init_expr_value ) + " of size " +
166+ std::to_string (init_expr_size))
166167 {
167- typet output_type = unsignedbv_typet{output_size};
168- const auto result = duplicate_per_byte (
169- from_integer (init_expr_value, unsignedbv_typet{init_expr_size}),
170- output_type);
171- const auto expected =
172- from_integer (output_expected_value, unsignedbv_typet{output_size});
173- REQUIRE (result == expected);
174-
175- // Check that signed-bv values are replicated including the sign bit.
176- const auto result_with_signed_init_type = duplicate_per_byte (
177- from_integer (init_expr_value, signedbv_typet{init_expr_size}),
178- output_type);
179- REQUIRE (result_with_signed_init_type == result);
180-
181- // Check that replicating a pointer_value is same as unsigned_bv.
182- const pointer_typet pointer_type{bool_typet{}, output_size};
183- const auto result_with_pointer_type = duplicate_per_byte (
184- from_integer (init_expr_value, signedbv_typet{init_expr_size}),
185- pointer_type);
186- auto pointer_typed_expected =
187- from_integer (output_expected_value, unsignedbv_typet{output_size});
188- // Forcing the type to be pointer_typet otherwise from_integer fails when
189- // the init value is not 0 (NULL).
190- pointer_typed_expected.type () = pointer_type;
191- REQUIRE (result_with_pointer_type == pointer_typed_expected);
168+ SECTION (" filling unsignedbv of size " + std::to_string (output_size))
169+ {
170+ typet output_type = unsignedbv_typet{output_size};
171+ const auto result = duplicate_per_byte (
172+ from_integer (init_expr_value, unsignedbv_typet{init_expr_size}),
173+ output_type);
174+ const auto expected =
175+ from_integer (output_expected_value, unsignedbv_typet{output_size});
176+ REQUIRE (result == expected);
177+
178+ // Check that signed-bv values are replicated including the sign bit.
179+ const auto result_with_signed_init_type = duplicate_per_byte (
180+ from_integer (init_expr_value, signedbv_typet{init_expr_size}),
181+ output_type);
182+ REQUIRE (result_with_signed_init_type == result);
183+ }
184+
185+ SECTION (" filling signedbv of size " + std::to_string (output_size))
186+ {
187+ typet output_type = signedbv_typet{output_size};
188+ const auto result = duplicate_per_byte (
189+ from_integer (init_expr_value, unsignedbv_typet{init_expr_size}),
190+ output_type);
191+ const auto expected =
192+ from_integer (output_expected_value, signedbv_typet{output_size});
193+ REQUIRE (result == expected);
194+
195+ // Check that signed-bv values are replicated including the sign bit.
196+ const auto result_with_signed_init_type = duplicate_per_byte (
197+ from_integer (init_expr_value, signedbv_typet{init_expr_size}),
198+ output_type);
199+ REQUIRE (result_with_signed_init_type == result);
200+ }
201+
202+ SECTION (" filling pointer of size " + std::to_string (output_size))
203+ {
204+ // Check that replicating a pointer_value is same as unsigned_bv.
205+ const pointer_typet output_type{bool_typet{}, output_size};
206+ const auto result = duplicate_per_byte (
207+ from_integer (init_expr_value, signedbv_typet{init_expr_size}),
208+ output_type);
209+ auto expected =
210+ from_integer (output_expected_value, unsignedbv_typet{output_size});
211+ // Forcing the type to be pointer_typet otherwise from_integer fails when
212+ // the init value is not 0 (NULL).
213+ expected.type () = output_type;
214+ REQUIRE (result == expected);
215+ }
216+
217+ SECTION (" filling float" )
218+ {
219+ // Check that replicating to a float_value is same as unsigned_bv.
220+ const auto result = duplicate_per_byte (
221+ from_integer (init_expr_value, unsignedbv_typet{init_expr_size}),
222+ float_type ());
223+ const auto expected_unsigned_value =
224+ expr_try_dynamic_cast<constant_exprt>(duplicate_per_byte (
225+ from_integer (init_expr_value, unsignedbv_typet{init_expr_size}),
226+ unsignedbv_typet{float_type ().get_width ()}));
227+ REQUIRE (expected_unsigned_value);
228+ const auto expected =
229+ constant_exprt{expected_unsigned_value->get_value (), float_type ()};
230+ REQUIRE (result == expected);
231+ }
192232 }
193233}
194234
@@ -207,38 +247,78 @@ TEST_CASE(
207247 rowt{8 , 2 , 1 }, // bigger type gets truncated
208248 rowt{8 , 16 , 2 }, // replicated twice
209249 rowt{8 , 20 , 3 }); // replicated three times and truncated
210- SECTION (
211- " Testing with output size " + std::to_string (output_size) + " init size " +
212- std::to_string (init_expr_size))
250+ SECTION (" Testing with init size " + std::to_string (init_expr_size))
213251 {
214- typet output_type = signedbv_typet{output_size};
215-
216252 const auto init_expr = plus_exprt{
217253 from_integer (1 , unsignedbv_typet{init_expr_size}),
218254 from_integer (2 , unsignedbv_typet{init_expr_size})};
219- const auto result = duplicate_per_byte (init_expr, output_type);
255+ SECTION (" filling signedbv of size " + std::to_string (output_size))
256+ {
257+ typet output_type = signedbv_typet{output_size};
220258
221- const auto casted_init_expr =
222- typecast_exprt::conditional_cast (init_expr, output_type);
223- const auto expected =
224- replicate_expression (casted_init_expr, output_type, replication_count);
259+ const auto result = duplicate_per_byte (init_expr, output_type);
225260
226- REQUIRE (result == expected);
261+ const auto casted_init_expr =
262+ typecast_exprt::conditional_cast (init_expr, output_type);
263+ const auto expected =
264+ replicate_expression (casted_init_expr, output_type, replication_count);
265+
266+ REQUIRE (result == expected);
267+ }
227268
228- // Check that replicating a pointer_value is same as unsigned_bv modulo a
229- // typecast outside.
230- const pointer_typet pointer_type{bool_typet{}, output_size};
231- const auto pointer_typed_result =
232- duplicate_per_byte (init_expr, pointer_type);
233- const auto pointer_unsigned_corr_type = unsignedbv_typet{output_size};
234- const auto pointer_init_expr =
235- typecast_exprt::conditional_cast (init_expr, pointer_unsigned_corr_type);
236- const auto pointer_expected = typecast_exprt::conditional_cast (
237- replicate_expression (
238- pointer_init_expr, pointer_unsigned_corr_type, replication_count),
239- pointer_type);
269+ SECTION (" filling unsignedbv of size " + std::to_string (output_size))
270+ {
271+ typet output_type = unsignedbv_typet{output_size};
272+ const auto result = duplicate_per_byte (init_expr, output_type);
240273
241- REQUIRE (pointer_typed_result == pointer_expected);
274+ const auto casted_init_expr =
275+ typecast_exprt::conditional_cast (init_expr, output_type);
276+ const auto expected =
277+ replicate_expression (casted_init_expr, output_type, replication_count);
278+
279+ REQUIRE (result == expected);
280+ }
281+
282+ SECTION (" filling pointer of size " + std::to_string (output_size))
283+ {
284+ // Check that replicating a pointer_value is same as unsigned_bv modulo a
285+ // byte_extract outside.
286+ const pointer_typet output_type{bool_typet{}, output_size};
287+ const auto result = duplicate_per_byte (init_expr, output_type);
288+ const auto unsigned_corr_type = unsignedbv_typet{output_size};
289+ const auto unsigned_init_expr =
290+ typecast_exprt::conditional_cast (init_expr, unsigned_corr_type);
291+ const auto expected = make_byte_extract (
292+ replicate_expression (
293+ unsigned_init_expr, unsigned_corr_type, replication_count),
294+ from_integer (0 , char_type ()),
295+ output_type);
296+
297+ REQUIRE (result == expected);
298+ }
299+
300+ SECTION (" filling float" )
301+ {
302+ // Check that replicating a float is same as unsigned_bv modulo a
303+ // byte_extract outside.
304+ // We ignore the output size and replication_count passed above as float
305+ // size is constant
306+ const std::size_t float_replication_count =
307+ (float_type ().get_width () + config.ansi_c .char_width - 1 ) /
308+ config.ansi_c .char_width ;
309+ const auto result = duplicate_per_byte (init_expr, float_type ());
310+ const auto unsigned_corr_type =
311+ unsignedbv_typet{float_type ().get_width ()};
312+ const auto unsigned_init_expr =
313+ typecast_exprt::conditional_cast (init_expr, unsigned_corr_type);
314+ const auto expected = make_byte_extract (
315+ replicate_expression (
316+ unsigned_init_expr, unsigned_corr_type, float_replication_count),
317+ from_integer (0 , char_type ()),
318+ float_type ());
319+
320+ REQUIRE (result == expected);
321+ }
242322 }
243323}
244324
@@ -386,6 +466,45 @@ TEST_CASE(
386466 }
387467}
388468
469+ TEST_CASE (" expr_initializer on float type" , " [core][util][expr_initializer]" )
470+ {
471+ auto test = expr_initializer_test_environmentt::make ();
472+ SECTION (" Testing with expected type as float" )
473+ {
474+ const typet input_type = float_type ();
475+ SECTION (" nondet_initializer works" )
476+ {
477+ const auto result = nondet_initializer (input_type, test.loc , test.ns );
478+ REQUIRE (result.has_value ());
479+ const auto expected = side_effect_expr_nondett{float_type (), test.loc };
480+ REQUIRE (result.value () == expected);
481+ const auto expr_result =
482+ expr_initializer (input_type, test.loc , test.ns , exprt (ID_nondet));
483+ REQUIRE (expr_result == result);
484+ }
485+ SECTION (" zero_initializer works" )
486+ {
487+ const auto result = zero_initializer (input_type, test.loc , test.ns );
488+ REQUIRE (result.has_value ());
489+ auto expected = from_integer (0 , float_type ());
490+ REQUIRE (result.value () == expected);
491+ const auto expr_result = expr_initializer (
492+ input_type, test.loc , test.ns , constant_exprt (ID_0, char_type ()));
493+ REQUIRE (expr_result == result);
494+ }
495+ SECTION (" expr_initializer calls duplicate_per_byte" )
496+ {
497+ const exprt init_value =
498+ from_integer (0x0A , unsignedbv_typet{config.ansi_c .char_width });
499+ const auto result =
500+ expr_initializer (input_type, test.loc , test.ns , init_value);
501+ REQUIRE (result.has_value ());
502+ const auto expected = duplicate_per_byte (init_value, float_type ());
503+ REQUIRE (result.value () == expected);
504+ }
505+ }
506+ }
507+
389508TEST_CASE (
390509 " expr_initializer on c_enum and c_enum_tag" ,
391510 " [core][util][expr_initializer]" )
0 commit comments