CBMC
string_instrumentation.cpp
Go to the documentation of this file.
1 /*******************************************************************\
2 
3 Module: String Abstraction
4 
5 Author: Daniel Kroening, kroening@kroening.com
6 
7 \*******************************************************************/
8 
11 
12 #include "string_instrumentation.h"
13 
14 #include <algorithm>
15 
16 #include <util/arith_tools.h>
17 #include <util/c_types.h>
18 #include <util/config.h>
19 #include <util/pointer_expr.h>
20 #include <util/std_code.h>
21 #include <util/string_constant.h>
22 
26 
27 exprt is_zero_string(const exprt &what, bool write)
28 {
29  unary_exprt result{"is_zero_string", what, c_bool_type()};
30  result.copy_to_operands(what);
31  result.set("lhs", write);
32  return notequal_exprt{result, from_integer(0, c_bool_type())};
33 }
34 
36  const exprt &what,
37  bool write)
38 {
39  exprt result("zero_string_length", size_type());
40  result.copy_to_operands(what);
41  result.set("lhs", write);
42  return result;
43 }
44 
45 exprt buffer_size(const exprt &what)
46 {
47  exprt result("buffer_size", size_type());
48  result.copy_to_operands(what);
49  return result;
50 }
51 
53 {
54 public:
56  : symbol_table(_symbol_table), ns(_symbol_table)
57  {
58  }
59 
60  void operator()(goto_programt &dest);
61  void operator()(goto_functionst &dest);
62 
63 protected:
66 
69 
70  // strings
71  void do_sprintf(
72  goto_programt &dest,
74  const exprt &lhs,
75  const exprt::operandst &arguments);
76  void do_snprintf(
77  goto_programt &dest,
79  const exprt &lhs,
80  const exprt::operandst &arguments);
81  void do_strcat(
82  goto_programt &dest,
84  const exprt &lhs,
85  const exprt::operandst &arguments);
86  void do_strncmp(
87  goto_programt &dest,
89  const exprt &lhs,
90  const exprt::operandst &arguments);
91  void do_strchr(
92  goto_programt &dest,
94  const exprt &lhs,
95  const exprt::operandst &arguments);
96  void do_strrchr(
97  goto_programt &dest,
99  const exprt &lhs,
100  const exprt::operandst &arguments);
101  void do_strstr(
102  goto_programt &dest,
103  goto_programt::targett target,
104  const exprt &lhs,
105  const exprt::operandst &arguments);
106  void do_strtok(
107  goto_programt &dest,
108  goto_programt::targett target,
109  const exprt &lhs,
110  const exprt::operandst &arguments);
111  void do_strerror(
112  goto_programt &dest,
114  const exprt &lhs,
115  const exprt::operandst &arguments);
116  void do_fscanf(
117  goto_programt &dest,
118  goto_programt::targett target,
119  const exprt &lhs,
120  const exprt::operandst &arguments);
121 
123  goto_programt &dest,
125  const code_function_callt::argumentst &arguments,
126  std::size_t format_string_inx,
127  std::size_t argument_start_inx,
128  const std::string &function_name);
129 
131  goto_programt &dest,
133  const code_function_callt::argumentst &arguments,
134  std::size_t format_string_inx,
135  std::size_t argument_start_inx,
136  const std::string &function_name);
137 
138  bool is_string_type(const typet &t) const
139  {
140  return (t.id() == ID_pointer || t.id() == ID_array) &&
141  (to_type_with_subtype(t).subtype().id() == ID_signedbv ||
142  to_type_with_subtype(t).subtype().id() == ID_unsignedbv) &&
145  }
146 
147  void invalidate_buffer(
148  goto_programt &dest,
150  const exprt &buffer,
151  const typet &buf_type,
152  const mp_integer &limit);
153 };
154 
156  symbol_table_baset &symbol_table,
157  goto_programt &dest)
158 {
161 }
162 
164  symbol_table_baset &symbol_table,
165  goto_functionst &dest)
166 {
169 }
170 
172 {
174  goto_model.symbol_table,
175  goto_model.goto_functions);
176 }
177 
179 {
180  for(goto_functionst::function_mapt::iterator
181  it=dest.function_map.begin();
182  it!=dest.function_map.end();
183  it++)
184  {
185  (*this)(it->second.body);
186  }
187 }
188 
190 {
192  instrument(dest, it);
193 }
194 
196  goto_programt &dest,
198 {
199  if(it->is_function_call())
200  do_function_call(dest, it);
201 }
202 
204  goto_programt &dest,
205  goto_programt::targett target)
206 {
207  const exprt &lhs = as_const(*target).call_lhs();
208  const exprt &function = as_const(*target).call_function();
209  const auto &arguments = as_const(*target).call_arguments();
210 
211  if(function.id()==ID_symbol)
212  {
213  const irep_idt &identifier=
214  to_symbol_expr(function).get_identifier();
215 
216  if(identifier=="strcoll")
217  {
218  }
219  else if(identifier=="strncmp")
220  do_strncmp(dest, target, lhs, arguments);
221  else if(identifier=="strxfrm")
222  {
223  }
224  else if(identifier=="strchr")
225  do_strchr(dest, target, lhs, arguments);
226  else if(identifier=="strcspn")
227  {
228  }
229  else if(identifier=="strpbrk")
230  {
231  }
232  else if(identifier=="strrchr")
233  do_strrchr(dest, target, lhs, arguments);
234  else if(identifier=="strspn")
235  {
236  }
237  else if(identifier=="strerror")
238  do_strerror(dest, target, lhs, arguments);
239  else if(identifier=="strstr")
240  do_strstr(dest, target, lhs, arguments);
241  else if(identifier=="strtok")
242  do_strtok(dest, target, lhs, arguments);
243  else if(identifier=="sprintf")
244  do_sprintf(dest, target, lhs, arguments);
245  else if(identifier=="snprintf")
246  do_snprintf(dest, target, lhs, arguments);
247  else if(identifier == "fscanf" || identifier == "__isoc99_fscanf")
248  do_fscanf(dest, target, lhs, arguments);
249 
250  remove_skip(dest);
251  }
252 }
253 
255  goto_programt &dest,
256  goto_programt::targett target,
257  const exprt &lhs,
258  const exprt::operandst &arguments)
259 {
260  if(arguments.size()<2)
261  {
263  "sprintf expected to have two or more arguments",
264  target->source_location());
265  }
266 
267  goto_programt tmp;
268 
269  // in the abstract model, we have to report a
270  // (possibly false) positive here
271  source_locationt annotated_location = target->source_location();
272  annotated_location.set_property_class("string");
273  annotated_location.set_comment("sprintf buffer overflow");
274  tmp.add(goto_programt::make_assertion(false_exprt(), annotated_location));
275 
276  do_format_string_read(tmp, target, arguments, 1, 2, "sprintf");
277 
278  if(lhs.is_not_nil())
279  {
280  exprt rhs = side_effect_expr_nondett(lhs.type(), target->source_location());
281 
282  tmp.add(
283  goto_programt::make_assignment(lhs, rhs, target->source_location()));
284  }
285 
286  target->turn_into_skip();
287  dest.insert_before_swap(target, tmp);
288 }
289 
291  goto_programt &dest,
292  goto_programt::targett target,
293  const exprt &lhs,
294  const exprt::operandst &arguments)
295 {
296  if(arguments.size()<3)
297  {
299  "snprintf expected to have three or more arguments",
300  target->source_location());
301  }
302 
303  goto_programt tmp;
304 
305  exprt bufsize = buffer_size(arguments[0]);
306 
307  source_locationt annotated_location = target->source_location();
308  annotated_location.set_property_class("string");
309  annotated_location.set_comment("snprintf buffer overflow");
311  binary_relation_exprt(bufsize, ID_ge, arguments[1]), annotated_location));
312 
313  do_format_string_read(tmp, target, arguments, 2, 3, "snprintf");
314 
315  if(lhs.is_not_nil())
316  {
317  exprt rhs = side_effect_expr_nondett(lhs.type(), target->source_location());
318 
319  tmp.add(
320  goto_programt::make_assignment(lhs, rhs, target->source_location()));
321  }
322 
323  target->turn_into_skip();
324  dest.insert_before_swap(target, tmp);
325 }
326 
328  goto_programt &dest,
329  goto_programt::targett target,
330  const exprt &lhs,
331  const exprt::operandst &arguments)
332 {
333  if(arguments.size()<2)
334  {
336  "fscanf expected to have two or more arguments",
337  target->source_location());
338  }
339 
340  goto_programt tmp;
341 
342  do_format_string_write(tmp, target, arguments, 1, 2, "fscanf");
343 
344  if(lhs.is_not_nil())
345  {
346  exprt rhs = side_effect_expr_nondett(lhs.type(), target->source_location());
347 
348  tmp.add(
349  goto_programt::make_assignment(lhs, rhs, target->source_location()));
350  }
351 
352  target->turn_into_skip();
353  dest.insert_before_swap(target, tmp);
354 }
355 
357  goto_programt &dest,
359  const code_function_callt::argumentst &arguments,
360  std::size_t format_string_inx,
361  std::size_t argument_start_inx,
362  const std::string &function_name)
363 {
364  const exprt &format_arg=arguments[format_string_inx];
365 
366  if(
367  format_arg.id() == ID_address_of &&
368  to_address_of_expr(format_arg).object().id() == ID_index &&
369  to_index_expr(to_address_of_expr(format_arg).object()).array().id() ==
370  ID_string_constant)
371  {
374  to_index_expr(to_address_of_expr(format_arg).object()).array())
375  .value()));
376 
377  std::size_t args=0;
378 
379  for(const auto &token : token_list)
380  {
381  if(token.type==format_tokent::token_typet::STRING)
382  {
383  const exprt &arg=arguments[argument_start_inx+args];
384 
385  if(arg.id()!=ID_string_constant) // we don't need to check constants
386  {
387  exprt temp(arg);
388 
389  if(arg.type().id() != ID_pointer)
390  {
391  index_exprt index(temp, from_integer(0, c_index_type()));
392  temp=address_of_exprt(index);
393  }
394 
395  source_locationt annotated_location = target->source_location();
396  annotated_location.set_property_class("string");
397  std::string comment("zero-termination of string argument of ");
398  comment += function_name;
399  annotated_location.set_comment(comment);
401  is_zero_string(temp), annotated_location));
402  }
403  }
404 
405  if(token.type!=format_tokent::token_typet::TEXT &&
406  token.type!=format_tokent::token_typet::UNKNOWN) args++;
407 
408  if(find(
409  token.flags.begin(),
410  token.flags.end(),
412  token.flags.end())
413  args++; // just eat the additional argument
414  }
415  }
416  else // non-const format string
417  {
418  source_locationt annotated_location = target->source_location();
419  annotated_location.set_property_class("string");
420  annotated_location.set_comment(
421  "zero-termination of format string of " + function_name);
423  is_zero_string(arguments[1]), annotated_location));
424 
425  for(std::size_t i=2; i<arguments.size(); i++)
426  {
427  const exprt &arg=arguments[i];
428 
429  if(arguments[i].id() != ID_string_constant && is_string_type(arg.type()))
430  {
431  exprt temp(arg);
432 
433  if(arg.type().id() != ID_pointer)
434  {
435  index_exprt index(temp, from_integer(0, c_index_type()));
436  temp=address_of_exprt(index);
437  }
438 
439  source_locationt annotated_location = target->source_location();
440  annotated_location.set_property_class("string");
441  annotated_location.set_comment(
442  "zero-termination of string argument of " + function_name);
444  is_zero_string(temp), annotated_location));
445  }
446  }
447  }
448 }
449 
451  goto_programt &dest,
453  const code_function_callt::argumentst &arguments,
454  std::size_t format_string_inx,
455  std::size_t argument_start_inx,
456  const std::string &function_name)
457 {
458  const exprt &format_arg=arguments[format_string_inx];
459 
460  if(
461  format_arg.id() == ID_address_of &&
462  to_address_of_expr(format_arg).object().id() == ID_index &&
463  to_index_expr(to_address_of_expr(format_arg).object()).array().id() ==
464  ID_string_constant) // constant format
465  {
468  to_index_expr(to_address_of_expr(format_arg).object()).array())
469  .value()));
470 
471  std::size_t args=0;
472 
473  for(const auto &token : token_list)
474  {
475  if(find(
476  token.flags.begin(),
477  token.flags.end(),
479  token.flags.end())
480  continue; // asterisk means `ignore this'
481 
482  switch(token.type)
483  {
485  {
486  const exprt &argument=arguments[argument_start_inx+args];
487  const typet &arg_type = argument.type();
488 
489  exprt condition;
490 
491  if(token.field_width!=0)
492  {
493  exprt fwidth=from_integer(token.field_width, unsigned_int_type());
495  const plus_exprt fw_1(fwidth, one); // +1 for 0-char
496 
497  exprt fw_lt_bs;
498 
499  if(arg_type.id()==ID_pointer)
500  fw_lt_bs=
501  binary_relation_exprt(fw_1, ID_le, buffer_size(argument));
502  else
503  {
504  const index_exprt index(
505  argument, from_integer(0, unsigned_int_type()));
506  address_of_exprt aof(index);
507  fw_lt_bs=binary_relation_exprt(fw_1, ID_le, buffer_size(aof));
508  }
509 
510  condition = fw_lt_bs;
511  }
512  else
513  {
514  // this is a possible overflow.
515  condition = false_exprt();
516  }
517 
518  source_locationt annotated_location = target->source_location();
519  annotated_location.set_property_class("string");
520  std::string comment("format string buffer overflow in ");
521  comment += function_name;
522  annotated_location.set_comment(comment);
523  dest.add(
524  goto_programt::make_assertion(condition, annotated_location));
525 
526  // now kill the contents
528  dest, target, argument, arg_type, token.field_width);
529 
530  args++;
531  break;
532  }
535  {
536  // nothing
537  break;
538  }
543  {
544  const exprt &argument=arguments[argument_start_inx+args];
545  const dereference_exprt lhs{argument};
546 
547  side_effect_expr_nondett rhs(lhs.type(), target->source_location());
548 
550  lhs, rhs, target->source_location()));
551 
552  args++;
553  break;
554  }
555  }
556  }
557  }
558  else // non-const format string
559  {
560  for(std::size_t i=argument_start_inx; i<arguments.size(); i++)
561  {
562  const typet &arg_type = arguments[i].type();
563 
564  // Note: is_string_type() is a `good guess' here. Actually
565  // any of the pointers could point into an array. But it
566  // would suck if we had to invalidate all variables.
567  // Luckily this case isn't needed too often.
568  if(is_string_type(arg_type))
569  {
570  // as we don't know any field width for the %s that
571  // should be here during runtime, we just report a
572  // possibly false positive
573  source_locationt annotated_location = target->source_location();
574  annotated_location.set_property_class("string");
575  std::string comment("format string buffer overflow in ");
576  comment += function_name;
577  annotated_location.set_comment(comment);
578  dest.add(
579  goto_programt::make_assertion(false_exprt(), annotated_location));
580 
581  invalidate_buffer(dest, target, arguments[i], arg_type, 0);
582  }
583  else
584  {
585  dereference_exprt lhs{arguments[i]};
586 
587  side_effect_expr_nondett rhs(lhs.type(), target->source_location());
588 
589  dest.add(
590  goto_programt::make_assignment(lhs, rhs, target->source_location()));
591  }
592  }
593  }
594 }
595 
597  goto_programt &,
599  const exprt &,
600  const exprt::operandst &)
601 {
602 }
603 
605  goto_programt &dest,
606  goto_programt::targett target,
607  const exprt &lhs,
608  const exprt::operandst &arguments)
609 {
610  if(arguments.size()!=2)
611  {
613  "strchr expected to have two arguments", target->source_location());
614  }
615 
616  source_locationt annotated_location = target->source_location();
617  annotated_location.set_property_class("string");
618  annotated_location.set_comment(
619  "zero-termination of string argument of strchr");
621  is_zero_string(arguments[0]), annotated_location);
622 
623  target->turn_into_skip();
624  dest.insert_before_swap(target, assertion);
625 }
626 
628  goto_programt &dest,
629  goto_programt::targett target,
630  const exprt &lhs,
631  const exprt::operandst &arguments)
632 {
633  if(arguments.size()!=2)
634  {
636  "strrchr expected to have two arguments", target->source_location());
637  }
638 
639  source_locationt annotated_location = target->source_location();
640  annotated_location.set_property_class("string");
641  annotated_location.set_comment(
642  "zero-termination of string argument of strrchr");
644  is_zero_string(arguments[0]), annotated_location);
645 
646  target->turn_into_skip();
647  dest.insert_before_swap(target, assertion);
648 }
649 
651  goto_programt &dest,
652  goto_programt::targett target,
653  const exprt &lhs,
654  const exprt::operandst &arguments)
655 {
656  if(arguments.size()!=2)
657  {
659  "strstr expected to have two arguments", target->source_location());
660  }
661 
662  goto_programt tmp;
663 
664  source_locationt annotated_location = target->source_location();
665  annotated_location.set_property_class("string");
666  annotated_location.set_comment(
667  "zero-termination of 1st string argument of strstr");
669  is_zero_string(arguments[0]), annotated_location));
670 
671  annotated_location.set_property_class("string");
672  annotated_location.set_comment(
673  "zero-termination of 2nd string argument of strstr");
675  is_zero_string(arguments[1]), annotated_location));
676 
677  target->turn_into_skip();
678  dest.insert_before_swap(target, tmp);
679 }
680 
682  goto_programt &dest,
683  goto_programt::targett target,
684  const exprt &lhs,
685  const exprt::operandst &arguments)
686 {
687  if(arguments.size()!=2)
688  {
690  "strtok expected to have two arguments", target->source_location());
691  }
692 
693  goto_programt tmp;
694 
695  source_locationt annotated_location = target->source_location();
696  annotated_location.set_property_class("string");
697  annotated_location.set_comment(
698  "zero-termination of 1st string argument of strtok");
700  is_zero_string(arguments[0]), annotated_location));
701 
702  annotated_location.set_property_class("string");
703  annotated_location.set_comment(
704  "zero-termination of 2nd string argument of strtok");
706  is_zero_string(arguments[1]), annotated_location));
707 
708  target->turn_into_skip();
709  dest.insert_before_swap(target, tmp);
710 }
711 
713  goto_programt &dest,
715  const exprt &lhs,
716  const exprt::operandst &arguments)
717 {
718  if(lhs.is_nil())
719  {
720  it->turn_into_skip();
721  return;
722  }
723 
724  irep_idt identifier_buf="__strerror_buffer";
725  irep_idt identifier_size="__strerror_buffer_size";
726 
727  if(symbol_table.symbols.find(identifier_buf)==symbol_table.symbols.end())
728  {
729  symbolt new_symbol_size{identifier_size, size_type(), ID_C};
730  new_symbol_size.base_name = identifier_size;
731  new_symbol_size.pretty_name=new_symbol_size.base_name;
732  new_symbol_size.is_state_var=true;
733  new_symbol_size.is_lvalue=true;
734  new_symbol_size.is_static_lifetime=true;
735 
736  array_typet type(char_type(), new_symbol_size.symbol_expr());
737  symbolt new_symbol_buf{identifier_buf, type, ID_C};
738  new_symbol_buf.is_state_var=true;
739  new_symbol_buf.is_lvalue=true;
740  new_symbol_buf.is_static_lifetime=true;
741  new_symbol_buf.base_name = identifier_buf;
742  new_symbol_buf.pretty_name=new_symbol_buf.base_name;
743 
744  symbol_table.insert(std::move(new_symbol_buf));
745  symbol_table.insert(std::move(new_symbol_size));
746  }
747 
748  const symbolt &symbol_size=ns.lookup(identifier_size);
749  const symbolt &symbol_buf=ns.lookup(identifier_buf);
750 
751  goto_programt tmp;
752 
753  {
754  exprt nondet_size =
755  side_effect_expr_nondett(size_type(), it->source_location());
757  code_assignt(symbol_size.symbol_expr(), nondet_size),
758  it->source_location()));
759 
762  symbol_size.symbol_expr(),
763  ID_notequal,
764  from_integer(0, symbol_size.type)),
765  it->source_location()));
766  }
767 
768  // return a pointer to some magic buffer
769  index_exprt index(
770  symbol_buf.symbol_expr(), from_integer(0, c_index_type()), char_type());
771 
772  address_of_exprt ptr(index);
773 
774  // make that zero-terminated
776  unary_exprt{"is_zero_string", ptr, c_bool_type()},
778  it->source_location()));
779 
780  // assign address
781  {
782  exprt rhs = typecast_exprt::conditional_cast(ptr, lhs.type());
784  code_assignt(lhs, rhs), it->source_location()));
785  }
786 
787  it->turn_into_skip();
788  dest.insert_before_swap(it, tmp);
789 }
790 
792  goto_programt &dest,
794  const exprt &buffer,
795  const typet &buf_type,
796  const mp_integer &limit)
797 {
798  irep_idt cntr_id="string_instrumentation::$counter";
799 
800  if(symbol_table.symbols.find(cntr_id)==symbol_table.symbols.end())
801  {
802  symbolt new_symbol{cntr_id, size_type(), ID_C};
803  new_symbol.base_name="$counter";
804  new_symbol.pretty_name=new_symbol.base_name;
805  new_symbol.is_state_var=true;
806  new_symbol.is_lvalue=true;
807  new_symbol.is_static_lifetime=true;
808 
809  symbol_table.insert(std::move(new_symbol));
810  }
811 
812  const symbolt &cntr_sym=ns.lookup(cntr_id);
813 
814  // create a loop that runs over the buffer
815  // and invalidates every element
816 
818  cntr_sym.symbol_expr(),
819  from_integer(0, cntr_sym.type),
820  target->source_location()));
821 
822  exprt bufp;
823 
824  if(buf_type.id()==ID_pointer)
825  bufp=buffer;
826  else
827  {
828  index_exprt index(
829  buffer,
831  to_type_with_subtype(buf_type).subtype());
832  bufp=address_of_exprt(index);
833  }
834 
835  exprt condition;
836 
837  if(limit==0)
838  condition =
839  binary_relation_exprt(cntr_sym.symbol_expr(), ID_ge, buffer_size(bufp));
840  else
841  condition = binary_relation_exprt(
842  cntr_sym.symbol_expr(), ID_gt, from_integer(limit, unsigned_int_type()));
843 
844  goto_programt::targett check = dest.add(
846 
847  const plus_exprt b_plus_i(bufp, cntr_sym.symbol_expr());
848  const dereference_exprt deref(
849  b_plus_i, to_type_with_subtype(buf_type).subtype());
850 
851  const side_effect_expr_nondett nondet(
852  to_type_with_subtype(buf_type).subtype(), target->source_location());
853 
854  // invalidate
855  dest.add(
856  goto_programt::make_assignment(deref, nondet, target->source_location()));
857 
858  const plus_exprt plus(
859  cntr_sym.symbol_expr(), from_integer(1, unsigned_int_type()));
860 
862  cntr_sym.symbol_expr(), plus, target->source_location()));
863 
864  dest.add(
866 
868  dest.add(goto_programt::make_skip(target->source_location()));
869 
870  check->complete_goto(exit);
871 }
configt config
Definition: config.cpp:25
constant_exprt from_integer(const mp_integer &int_value, const typet &type)
const T & as_const(T &value)
Return a reference to the same object but ensures the type is const.
Definition: as_const.h:14
const bitvector_typet & to_bitvector_type(const typet &type)
Cast a typet to a bitvector_typet.
unsignedbv_typet unsigned_int_type()
Definition: c_types.cpp:36
bitvector_typet char_type()
Definition: c_types.cpp:106
typet c_bool_type()
Definition: c_types.cpp:100
bitvector_typet c_index_type()
Definition: c_types.cpp:16
Operator to return the address of an object.
Definition: pointer_expr.h:540
Arrays with given size.
Definition: std_types.h:807
A base class for relations, i.e., binary predicates whose two operands have the same type.
Definition: std_expr.h:762
std::size_t get_width() const
Definition: std_types.h:920
A goto_instruction_codet representing an assignment in the program.
exprt::operandst argumentst
struct configt::ansi_ct ansi_c
Operator to dereference a pointer.
Definition: pointer_expr.h:834
dstringt has one field, an unsigned integer no which is an index into a static table of strings.
Definition: dstring.h:38
Base class for all expressions.
Definition: expr.h:56
std::vector< exprt > operandst
Definition: expr.h:58
void copy_to_operands(const exprt &expr)
Copy the given argument to the end of exprt's operands.
Definition: expr.h:163
const source_locationt & source_location() const
Definition: expr.h:231
typet & type()
Return the type of the expression.
Definition: expr.h:84
The Boolean constant false.
Definition: std_expr.h:3064
A collection of goto functions.
function_mapt function_map
symbol_tablet symbol_table
Symbol table.
Definition: goto_model.h:31
goto_functionst goto_functions
GOTO functions.
Definition: goto_model.h:34
This class represents an instruction in the GOTO intermediate representation.
Definition: goto_program.h:181
A generic container class for the GOTO intermediate representation of one function.
Definition: goto_program.h:73
static instructiont make_assumption(const exprt &g, const source_locationt &l=source_locationt::nil())
Definition: goto_program.h:945
void insert_before_swap(targett target)
Insertion that preserves jumps to "target".
Definition: goto_program.h:643
instructionst::iterator targett
Definition: goto_program.h:614
instructionst::const_iterator const_targett
Definition: goto_program.h:615
static instructiont make_assignment(const code_assignt &_code, const source_locationt &l=source_locationt::nil())
Create an assignment instruction.
static instructiont make_skip(const source_locationt &l=source_locationt::nil())
Definition: goto_program.h:891
targett add(instructiont &&instruction)
Adds a given instruction at the end.
Definition: goto_program.h:739
static instructiont make_goto(targett _target, const source_locationt &l=source_locationt::nil())
static instructiont make_assertion(const exprt &g, const source_locationt &l=source_locationt::nil())
Definition: goto_program.h:933
static instructiont make_incomplete_goto(const exprt &_cond, const source_locationt &l=source_locationt::nil())
Array index operator.
Definition: std_expr.h:1465
Thrown when we can't handle something in an input source file.
void set(const irep_idt &name, const irep_idt &value)
Definition: irep.h:408
bool is_not_nil() const
Definition: irep.h:368
const irep_idt & id() const
Definition: irep.h:384
bool is_nil() const
Definition: irep.h:364
A namespacet is essentially one or two symbol tables bound together, to allow for symbol lookups in t...
Definition: namespace.h:94
bool lookup(const irep_idt &name, const symbolt *&symbol) const override
See documentation for namespace_baset::lookup().
Definition: namespace.cpp:148
Disequality.
Definition: std_expr.h:1420
The plus expression Associativity is not specified.
Definition: std_expr.h:1002
A side_effect_exprt that returns a non-deterministically chosen value.
Definition: std_code.h:1520
void set_comment(const irep_idt &comment)
void set_property_class(const irep_idt &property_class)
void do_strtok(goto_programt &dest, goto_programt::targett target, const exprt &lhs, const exprt::operandst &arguments)
void do_function_call(goto_programt &dest, goto_programt::targett target)
bool is_string_type(const typet &t) const
void operator()(goto_programt &dest)
void do_snprintf(goto_programt &dest, goto_programt::targett target, const exprt &lhs, const exprt::operandst &arguments)
string_instrumentationt(symbol_table_baset &_symbol_table)
void do_format_string_read(goto_programt &dest, goto_programt::const_targett target, const code_function_callt::argumentst &arguments, std::size_t format_string_inx, std::size_t argument_start_inx, const std::string &function_name)
symbol_table_baset & symbol_table
void do_strncmp(goto_programt &dest, goto_programt::targett it, const exprt &lhs, const exprt::operandst &arguments)
void do_sprintf(goto_programt &dest, goto_programt::targett target, const exprt &lhs, const exprt::operandst &arguments)
void do_strstr(goto_programt &dest, goto_programt::targett target, const exprt &lhs, const exprt::operandst &arguments)
void do_strerror(goto_programt &dest, goto_programt::targett it, const exprt &lhs, const exprt::operandst &arguments)
void do_format_string_write(goto_programt &dest, goto_programt::const_targett target, const code_function_callt::argumentst &arguments, std::size_t format_string_inx, std::size_t argument_start_inx, const std::string &function_name)
void do_fscanf(goto_programt &dest, goto_programt::targett target, const exprt &lhs, const exprt::operandst &arguments)
void instrument(goto_programt &dest, goto_programt::targett it)
void do_strcat(goto_programt &dest, goto_programt::targett it, const exprt &lhs, const exprt::operandst &arguments)
void do_strrchr(goto_programt &dest, goto_programt::targett target, const exprt &lhs, const exprt::operandst &arguments)
void invalidate_buffer(goto_programt &dest, goto_programt::const_targett target, const exprt &buffer, const typet &buf_type, const mp_integer &limit)
void do_strchr(goto_programt &dest, goto_programt::targett target, const exprt &lhs, const exprt::operandst &arguments)
const irep_idt & get_identifier() const
Definition: std_expr.h:160
The symbol table base class interface.
const symbolst & symbols
Read-only field, used to look up symbols given their names.
virtual std::pair< symbolt &, bool > insert(symbolt symbol)=0
Move or copy a new symbol to the symbol table.
Symbol table entry.
Definition: symbol.h:28
class symbol_exprt symbol_expr() const
Produces a symbol_exprt for a symbol.
Definition: symbol.cpp:121
typet type
Type of symbol.
Definition: symbol.h:31
The Boolean constant true.
Definition: std_expr.h:3055
const typet & subtype() const
Definition: type.h:187
static exprt conditional_cast(const exprt &expr, const typet &type)
Definition: std_expr.h:2076
The type of an expression, extends irept.
Definition: type.h:29
const source_locationt & source_location() const
Definition: type.h:72
Generic base class for unary expressions.
Definition: std_expr.h:361
format_token_listt parse_format_string(const std::string &arg_string)
Format String Parser.
std::list< format_tokent > format_token_listt
Symbol Table + CFG.
#define Forall_goto_program_instructions(it, program)
const std::string & id2string(const irep_idt &d)
Definition: irep.h:40
API to expression classes for Pointers.
const address_of_exprt & to_address_of_expr(const exprt &expr)
Cast an exprt to an address_of_exprt.
Definition: pointer_expr.h:577
static std::string comment(const rw_set_baset::entryt &entry, bool write)
Definition: race_check.cpp:108
void remove_skip(goto_programt &goto_program, goto_programt::targett begin, goto_programt::targett end)
remove unnecessary skip statements
Definition: remove_skip.cpp:87
Program Transformation.
BigInt mp_integer
Definition: smt_terms.h:17
const symbol_exprt & to_symbol_expr(const exprt &expr)
Cast an exprt to a symbol_exprt.
Definition: std_expr.h:272
const index_exprt & to_index_expr(const exprt &expr)
Cast an exprt to an index_exprt.
Definition: std_expr.h:1533
void exit(int status)
Definition: stdlib.c:102
const string_constantt & to_string_constant(const exprt &expr)
void string_instrumentation(symbol_table_baset &symbol_table, goto_programt &dest)
exprt buffer_size(const exprt &what)
exprt is_zero_string(const exprt &what, bool write)
exprt zero_string_length(const exprt &what, bool write)
String Abstraction.
std::size_t char_width
Definition: config.h:140
const type_with_subtypet & to_type_with_subtype(const typet &type)
Definition: type.h:208
ssize_t write(int fildes, const void *buf, size_t nbyte)
Definition: unistd.c:195
#define size_type
Definition: unistd.c:347