@@ -20,66 +20,6 @@ Author: Diffblue Ltd.
20
20
21
21
namespace
22
22
{
23
- void typecheck_function_pointer_restrictions (
24
- const goto_modelt &goto_model,
25
- const function_pointer_restrictionst &restrictions)
26
- {
27
- const std::string options =
28
- " --" RESTRICT_FUNCTION_POINTER_OPT " /"
29
- " --" RESTRICT_FUNCTION_POINTER_FROM_FILE_OPT " /"
30
- " --" RESTRICT_FUNCTION_POINTER_BY_NAME_OPT;
31
-
32
- for (auto const &restriction : restrictions.restrictions )
33
- {
34
- auto const function_pointer_sym =
35
- goto_model.symbol_table .lookup (restriction.first );
36
- if (function_pointer_sym == nullptr )
37
- {
38
- throw invalid_command_line_argument_exceptiont{
39
- id2string (restriction.first ) + " not found in the symbol table" ,
40
- options};
41
- }
42
- auto const &function_pointer_type = function_pointer_sym->type ;
43
- if (function_pointer_type.id () != ID_pointer)
44
- {
45
- throw invalid_command_line_argument_exceptiont{
46
- " not a function pointer: " + id2string (restriction.first ),
47
- options};
48
- }
49
- auto const &function_type =
50
- to_pointer_type (function_pointer_type).subtype ();
51
- if (function_type.id () != ID_code)
52
- {
53
- throw invalid_command_line_argument_exceptiont{
54
- " not a function pointer: " + id2string (restriction.first ),
55
- options};
56
- }
57
- auto const &ns = namespacet{goto_model.symbol_table };
58
- for (auto const &function_pointer_target : restriction.second )
59
- {
60
- auto const function_pointer_target_sym =
61
- goto_model.symbol_table .lookup (function_pointer_target);
62
- if (function_pointer_target_sym == nullptr )
63
- {
64
- throw invalid_command_line_argument_exceptiont{
65
- " symbol not found: " + id2string (function_pointer_target),
66
- options};
67
- }
68
- auto const &function_pointer_target_type =
69
- function_pointer_target_sym->type ;
70
- if (function_type != function_pointer_target_type)
71
- {
72
- throw invalid_command_line_argument_exceptiont{
73
- " type mismatch: `" + id2string (restriction.first ) + " ' points to `" +
74
- type2c (function_type, ns) + " ', but restriction `" +
75
- id2string (function_pointer_target) + " ' has type `" +
76
- type2c (function_pointer_target_type, ns) + " '" ,
77
- options};
78
- }
79
- }
80
- }
81
- }
82
-
83
23
source_locationt make_function_pointer_restriction_assertion_source_location (
84
24
source_locationt source_location,
85
25
const function_pointer_restrictionst::restrictiont restriction)
@@ -200,12 +140,83 @@ void restrict_function_pointer(
200
140
}
201
141
} // namespace
202
142
143
+ function_pointer_restrictionst::invalid_restriction_exceptiont::
144
+ invalid_restriction_exceptiont (std::string reason, std::string correct_format)
145
+ : reason(std::move(reason)), correct_format(std::move(correct_format))
146
+ {
147
+
148
+ }
149
+
150
+ std::string
151
+ function_pointer_restrictionst::invalid_restriction_exceptiont::what () const
152
+ {
153
+ std::string res;
154
+
155
+ res += " Invalid restriction" ;
156
+ res += " \n Reason: " + reason;
157
+
158
+ if (!correct_format.empty ())
159
+ {
160
+ res += " \n Format: " + correct_format;
161
+ }
162
+
163
+ return res;
164
+ }
165
+
166
+ void function_pointer_restrictionst::typecheck_function_pointer_restrictions (
167
+ const goto_modelt &goto_model,
168
+ const function_pointer_restrictionst::restrictionst &restrictions)
169
+ {
170
+ for (auto const &restriction : restrictions)
171
+ {
172
+ auto const function_pointer_sym =
173
+ goto_model.symbol_table .lookup (restriction.first );
174
+ if (function_pointer_sym == nullptr )
175
+ {
176
+ throw invalid_restriction_exceptiont{
177
+ id2string (restriction.first ) + " not found in the symbol table" };
178
+ }
179
+ auto const &function_pointer_type = function_pointer_sym->type ;
180
+ if (function_pointer_type.id () != ID_pointer)
181
+ {
182
+ throw invalid_restriction_exceptiont{
183
+ " not a function pointer: " + id2string (restriction.first )};
184
+ }
185
+ auto const &function_type =
186
+ to_pointer_type (function_pointer_type).subtype ();
187
+ if (function_type.id () != ID_code)
188
+ {
189
+ throw invalid_restriction_exceptiont{
190
+ " not a function pointer: " + id2string (restriction.first )};
191
+ }
192
+ auto const &ns = namespacet{goto_model.symbol_table };
193
+ for (auto const &function_pointer_target : restriction.second )
194
+ {
195
+ auto const function_pointer_target_sym =
196
+ goto_model.symbol_table .lookup (function_pointer_target);
197
+ if (function_pointer_target_sym == nullptr )
198
+ {
199
+ throw invalid_restriction_exceptiont{
200
+ " symbol not found: " + id2string (function_pointer_target)};
201
+ }
202
+ auto const &function_pointer_target_type =
203
+ function_pointer_target_sym->type ;
204
+ if (function_type != function_pointer_target_type)
205
+ {
206
+ throw invalid_restriction_exceptiont{
207
+ " type mismatch: `" + id2string (restriction.first ) + " ' points to `" +
208
+ type2c (function_type, ns) + " ', but restriction `" +
209
+ id2string (function_pointer_target) + " ' has type `" +
210
+ type2c (function_pointer_target_type, ns) + " '" };
211
+ }
212
+ }
213
+ }
214
+ }
215
+
203
216
void restrict_function_pointers (
204
217
goto_modelt &goto_model,
205
218
const function_pointer_restrictionst &restrictions)
206
219
{
207
- typecheck_function_pointer_restrictions (goto_model, restrictions);
208
-
209
220
for (auto &function_item : goto_model.goto_functions .function_map )
210
221
{
211
222
goto_functiont &goto_function = function_item.second ;
@@ -283,10 +294,9 @@ function_pointer_restrictionst::parse_function_pointer_restrictions(
283
294
284
295
if (!inserted)
285
296
{
286
- throw invalid_command_line_argument_exceptiont {
297
+ throw invalid_restriction_exceptiont {
287
298
" function pointer restriction for `" + id2string (restriction.first ) +
288
- " ' was specified twice" ,
289
- option};
299
+ " ' was specified twice" };
290
300
}
291
301
}
292
302
@@ -335,25 +345,22 @@ function_pointer_restrictionst::parse_function_pointer_restriction(
335
345
336
346
if (pointer_name_end == std::string::npos)
337
347
{
338
- throw invalid_command_line_argument_exceptiont {
348
+ throw invalid_restriction_exceptiont {
339
349
" couldn't find '/' in `" + restriction_opt + " '" ,
340
- option,
341
350
restriction_format_message};
342
351
}
343
352
344
353
if (pointer_name_end == restriction_opt.size ())
345
354
{
346
- throw invalid_command_line_argument_exceptiont {
355
+ throw invalid_restriction_exceptiont {
347
356
" couldn't find names of targets after '/' in `" + restriction_opt + " '" ,
348
- option,
349
357
restriction_format_message};
350
358
}
351
359
352
360
if (pointer_name_end == 0 )
353
361
{
354
- throw invalid_command_line_argument_exceptiont{
355
- " couldn't find target name before '/' in `" + restriction_opt + " '" ,
356
- option};
362
+ throw invalid_restriction_exceptiont{
363
+ " couldn't find target name before '/' in `" + restriction_opt + " '" };
357
364
}
358
365
359
366
auto const pointer_name = restriction_opt.substr (0 , pointer_name_end);
@@ -363,9 +370,8 @@ function_pointer_restrictionst::parse_function_pointer_restriction(
363
370
364
371
if (target_name_strings.size () == 1 && target_name_strings[0 ].empty ())
365
372
{
366
- throw invalid_command_line_argument_exceptiont {
373
+ throw invalid_restriction_exceptiont {
367
374
" missing target list for function pointer restriction " + pointer_name,
368
- option,
369
375
restriction_format_message};
370
376
}
371
377
@@ -376,9 +382,8 @@ function_pointer_restrictionst::parse_function_pointer_restriction(
376
382
{
377
383
if (target_name == ID_empty_string)
378
384
{
379
- throw invalid_command_line_argument_exceptiont (
385
+ throw invalid_restriction_exceptiont (
380
386
" leading or trailing comma in restrictions for `" + pointer_name + " '" ,
381
- option,
382
387
restriction_format_message);
383
388
}
384
389
}
@@ -436,18 +441,49 @@ function_pointer_restrictionst function_pointer_restrictionst::from_options(
436
441
{
437
442
auto const restriction_opts =
438
443
options.get_list_option (RESTRICT_FUNCTION_POINTER_OPT);
439
- auto const commandline_restrictions =
440
- parse_function_pointer_restrictions_from_command_line (restriction_opts);
441
-
442
- auto const restriction_file_opts =
443
- options.get_list_option (RESTRICT_FUNCTION_POINTER_FROM_FILE_OPT);
444
- auto const file_restrictions = parse_function_pointer_restrictions_from_file (
445
- restriction_file_opts, message_handler);
446
-
447
- auto const restriction_name_opts =
448
- options.get_list_option (RESTRICT_FUNCTION_POINTER_BY_NAME_OPT);
449
- auto const name_restrictions = get_function_pointer_by_name_restrictions (
450
- restriction_name_opts, goto_model);
444
+
445
+ restrictionst commandline_restrictions;
446
+ try
447
+ {
448
+ commandline_restrictions =
449
+ parse_function_pointer_restrictions_from_command_line (restriction_opts);
450
+ typecheck_function_pointer_restrictions (
451
+ goto_model, commandline_restrictions);
452
+ }
453
+ catch (const invalid_restriction_exceptiont &e)
454
+ {
455
+ throw invalid_command_line_argument_exceptiont{
456
+ e.reason , " --" RESTRICT_FUNCTION_POINTER_OPT, e.correct_format };
457
+ }
458
+
459
+ restrictionst file_restrictions;
460
+ try
461
+ {
462
+ auto const restriction_file_opts =
463
+ options.get_list_option (RESTRICT_FUNCTION_POINTER_FROM_FILE_OPT);
464
+ file_restrictions = parse_function_pointer_restrictions_from_file (
465
+ restriction_file_opts, message_handler);
466
+ typecheck_function_pointer_restrictions (goto_model, file_restrictions);
467
+ }
468
+ catch (const invalid_restriction_exceptiont &e)
469
+ {
470
+ throw deserialization_exceptiont{e.what ()};
471
+ }
472
+
473
+ restrictionst name_restrictions;
474
+ try
475
+ {
476
+ auto const restriction_name_opts =
477
+ options.get_list_option (RESTRICT_FUNCTION_POINTER_BY_NAME_OPT);
478
+ name_restrictions = get_function_pointer_by_name_restrictions (
479
+ restriction_name_opts, goto_model);
480
+ typecheck_function_pointer_restrictions (goto_model, name_restrictions);
481
+ }
482
+ catch (const invalid_restriction_exceptiont &e)
483
+ {
484
+ throw invalid_command_line_argument_exceptiont{
485
+ e.reason , " --" RESTRICT_FUNCTION_POINTER_BY_NAME_OPT, e.correct_format };
486
+ }
451
487
452
488
return {merge_function_pointer_restrictions (
453
489
commandline_restrictions,
0 commit comments