31
31
string_constraint_generatort::string_constraint_generatort (
32
32
const string_constraint_generatort::infot &info,
33
33
const namespacet &ns)
34
- : max_string_length(info.string_max_length),
35
- ns(ns)
34
+ : array_pool(fresh_symbol), max_string_length(info.string_max_length), ns(ns)
36
35
{
37
36
}
38
37
@@ -157,13 +156,12 @@ plus_exprt string_constraint_generatort::plus_exprt_with_overflow_check(
157
156
// / Associate an actual finite length to infinite arrays
158
157
// / \param s: array expression representing a string
159
158
// / \return expression for the length of `s`
160
- exprt string_constraint_generatort::get_length_of_string_array (
161
- const array_string_exprt &s) const
159
+ exprt array_poolt::get_length (const array_string_exprt &s) const
162
160
{
163
161
if (s.length () == infinity_exprt (s.length ().type ()))
164
162
{
165
- auto it = length_of_array_ .find (s);
166
- if (it != length_of_array_ .end ())
163
+ auto it = length_of_array .find (s);
164
+ if (it != length_of_array .end ())
167
165
return it->second ;
168
166
}
169
167
return s.length ();
@@ -185,10 +183,9 @@ array_string_exprt string_constraint_generatort::fresh_string(
185
183
return str;
186
184
}
187
185
188
- // Associate a char array to a char pointer. The size of the char array is a
186
+ // Make a new char array for a char pointer. The size of the char array is a
189
187
// variable with no constraint.
190
- array_string_exprt
191
- string_constraint_generatort::associate_char_array_to_char_pointer (
188
+ array_string_exprt array_poolt::make_char_array_for_char_pointer (
192
189
const exprt &char_pointer,
193
190
const typet &char_array_type)
194
191
{
@@ -214,10 +211,10 @@ string_constraint_generatort::associate_char_array_to_char_pointer(
214
211
else if (char_pointer.id () == ID_if)
215
212
{
216
213
const if_exprt &if_expr = to_if_expr (char_pointer);
217
- const array_string_exprt t = associate_char_array_to_char_pointer (
218
- if_expr.true_case (), char_array_type);
219
- const array_string_exprt f = associate_char_array_to_char_pointer (
220
- if_expr.false_case (), char_array_type);
214
+ const array_string_exprt t =
215
+ make_char_array_for_char_pointer ( if_expr.true_case (), char_array_type);
216
+ const array_string_exprt f =
217
+ make_char_array_for_char_pointer ( if_expr.false_case (), char_array_type);
221
218
array_typet array_type (
222
219
char_array_type.subtype (),
223
220
if_exprt (
@@ -247,15 +244,32 @@ string_constraint_generatort::associate_char_array_to_char_pointer(
247
244
array_string_exprt array_sym =
248
245
to_array_string_expr (fresh_symbol (symbol_name, char_array_type));
249
246
auto insert_result =
250
- arrays_of_pointers_ .insert (std::make_pair (char_pointer, array_sym));
247
+ arrays_of_pointers .insert (std::make_pair (char_pointer, array_sym));
251
248
array_string_exprt result = to_array_string_expr (insert_result.first ->second );
252
249
return result;
253
250
}
254
251
252
+ void array_poolt::insert (
253
+ const exprt &pointer_expr,
254
+ array_string_exprt &array_expr)
255
+ {
256
+ const exprt &length = array_expr.length ();
257
+ if (length == infinity_exprt (length.type ()))
258
+ {
259
+ auto pair = length_of_array.insert (
260
+ std::make_pair (array_expr, fresh_symbol (" string_length" , length.type ())));
261
+ array_expr.length () = pair.first ->second ;
262
+ }
263
+
264
+ const auto it_bool =
265
+ arrays_of_pointers.insert (std::make_pair (pointer_expr, array_expr));
266
+ INVARIANT (
267
+ it_bool.second , " should not associate two arrays to the same pointer" );
268
+ }
269
+
255
270
// / Associate a char array to a char pointer.
256
- // / Insert in `arrays_of_pointers_` a binding from `ptr` to `arr`.
257
- // / If the length of `arr` is infinite, we create a new integer symbol and add
258
- // / a binding from `arr` to this length in `length_of_array_`.
271
+ // / Insert in `array_pool` a binding from `ptr` to `arr`. If the length of `arr`
272
+ // / is infinite, a new integer symbol is created and stored in `array_pool`.
259
273
// / This also adds the default axioms for `arr`.
260
274
// / \param f: a function application with argument a character array `arr` and
261
275
// / a character pointer `ptr`.
@@ -271,21 +285,7 @@ exprt string_constraint_generatort::associate_array_to_pointer(
271
285
: f.arguments ()[0 ]);
272
286
273
287
const exprt &pointer_expr = f.arguments ()[1 ];
274
-
275
- const auto &length = array_expr.length ();
276
- if (length == infinity_exprt (length.type ()))
277
- {
278
- auto pair = length_of_array_.insert (
279
- std::make_pair (array_expr, fresh_symbol (" string_length" , length.type ())));
280
- array_expr.length () = pair.first ->second ;
281
- }
282
-
283
- // / \todo We should use a function for inserting the correspondance
284
- // / between array and pointers.
285
- const auto it_bool =
286
- arrays_of_pointers_.insert (std::make_pair (pointer_expr, array_expr));
287
- INVARIANT (
288
- it_bool.second , " should not associate two arrays to the same pointer" );
288
+ array_pool.insert (pointer_expr, array_expr);
289
289
add_default_axioms (to_array_string_expr (array_expr));
290
290
return from_integer (0 , f.type ());
291
291
}
@@ -302,7 +302,7 @@ exprt string_constraint_generatort::associate_length_to_array(
302
302
array_string_exprt array_expr = to_array_string_expr (f.arguments ()[0 ]);
303
303
const exprt &new_length = f.arguments ()[1 ];
304
304
305
- const auto &length = get_length_of_string_array (array_expr);
305
+ const auto &length = array_pool. get_length (array_expr);
306
306
lemmas.push_back (equal_exprt (length, new_length));
307
307
return from_integer (0 , f.type ());
308
308
}
@@ -400,19 +400,36 @@ exprt string_constraint_generatort::add_axioms_for_constrain_characters(
400
400
return from_integer (0 , get_return_code_type ());
401
401
}
402
402
403
+ // / Creates a new array if the pointer is not pointing to an array
404
+ // / \todo This should be replaced by make_char_array_for_char_pointer
405
+ array_string_exprt array_poolt::find (const exprt &pointer, const exprt &length)
406
+ {
407
+ const array_typet array_type (pointer.type ().subtype (), length);
408
+ return make_char_array_for_char_pointer (pointer, array_type);
409
+ }
410
+
403
411
// / Adds creates a new array if it does not already exists
404
412
// / \todo This should be replaced by associate_char_array_to_char_pointer
405
413
array_string_exprt string_constraint_generatort::char_array_of_pointer (
406
414
const exprt &pointer,
407
415
const exprt &length)
408
416
{
409
- const array_typet array_type (pointer.type ().subtype (), length);
410
- const array_string_exprt array =
411
- associate_char_array_to_char_pointer (pointer, array_type);
417
+ const array_string_exprt array = array_pool.find (pointer, length);
412
418
add_default_axioms (array);
413
419
return array;
414
420
}
415
421
422
+ array_string_exprt array_poolt::find (const refined_string_exprt &str)
423
+ {
424
+ return find (str.content (), str.length ());
425
+ }
426
+
427
+ array_string_exprt array_poolt::of_argument (const exprt &arg)
428
+ {
429
+ const auto string_argument = expr_checked_cast<struct_exprt>(arg);
430
+ return find (string_argument.op1 (), string_argument.op0 ());
431
+ }
432
+
416
433
// / strings contained in this call are converted to objects of type
417
434
// / `string_exprt`, through adding axioms. Axioms are then added to enforce that
418
435
// / the result corresponds to the function application.
0 commit comments