CBMC
c_expr.h
Go to the documentation of this file.
1 /*******************************************************************\
2 
3 Module: API to expression classes that are internal to the C frontend
4 
5 Author: Daniel Kroening, kroening@kroening.com
6 
7 \*******************************************************************/
8 
9 #ifndef CPROVER_ANSI_C_C_EXPR_H
10 #define CPROVER_ANSI_C_C_EXPR_H
11 
14 
15 #include <util/std_code.h>
16 
20 {
21 public:
23  exprt vector1,
26 
27  const vector_typet &type() const
28  {
29  return static_cast<const vector_typet &>(multi_ary_exprt::type());
30  }
31 
33  {
34  return static_cast<vector_typet &>(multi_ary_exprt::type());
35  }
36 
37  const exprt &vector1() const
38  {
39  return op0();
40  }
41 
43  {
44  return op0();
45  }
46 
47  const exprt &vector2() const
48  {
49  return op1();
50  }
51 
53  {
54  return op1();
55  }
56 
57  bool has_two_input_vectors() const
58  {
59  return vector2().is_not_nil();
60  }
61 
62  const exprt::operandst &indices() const
63  {
64  return op2().operands();
65  }
66 
68  {
69  return op2().operands();
70  }
71 
72  vector_exprt lower() const;
73 };
74 
75 template <>
77 {
78  return base.id() == ID_shuffle_vector;
79 }
80 
81 inline void validate_expr(const shuffle_vector_exprt &value)
82 {
83  validate_operands(value, 3, "shuffle_vector must have three operands");
84 }
85 
93 {
94  PRECONDITION(expr.id() == ID_shuffle_vector);
95  const shuffle_vector_exprt &ret =
96  static_cast<const shuffle_vector_exprt &>(expr);
97  validate_expr(ret);
98  return ret;
99 }
100 
103 {
104  PRECONDITION(expr.id() == ID_shuffle_vector);
105  shuffle_vector_exprt &ret = static_cast<shuffle_vector_exprt &>(expr);
106  validate_expr(ret);
107  return ret;
108 }
109 
117 {
118 public:
120  const irep_idt &kind,
121  exprt _lhs,
122  exprt _rhs,
123  exprt _result,
124  const source_locationt &loc)
126  "overflow-" + id2string(kind),
127  {std::move(_lhs), std::move(_rhs), std::move(_result)},
128  bool_typet{},
129  loc)
130  {
131  }
132 
134  {
135  return op0();
136  }
137 
138  const exprt &lhs() const
139  {
140  return op0();
141  }
142 
144  {
145  return op1();
146  }
147 
148  const exprt &rhs() const
149  {
150  return op1();
151  }
152 
154  {
155  return op2();
156  }
157 
158  const exprt &result() const
159  {
160  return op2();
161  }
162 };
163 
164 template <>
166 {
167  if(base.id() != ID_side_effect)
168  return false;
169 
170  const irep_idt &statement = to_side_effect_expr(base).get_statement();
171  return statement == ID_overflow_plus || statement == ID_overflow_mult ||
172  statement == ID_overflow_minus;
173 }
174 
181 inline const side_effect_expr_overflowt &
183 {
184  const auto &side_effect_expr = to_side_effect_expr(expr);
185  PRECONDITION(
186  side_effect_expr.get_statement() == ID_overflow_plus ||
187  side_effect_expr.get_statement() == ID_overflow_mult ||
188  side_effect_expr.get_statement() == ID_overflow_minus);
189  return static_cast<const side_effect_expr_overflowt &>(side_effect_expr);
190 }
191 
194 {
195  auto &side_effect_expr = to_side_effect_expr(expr);
196  PRECONDITION(
197  side_effect_expr.get_statement() == ID_overflow_plus ||
198  side_effect_expr.get_statement() == ID_overflow_mult ||
199  side_effect_expr.get_statement() == ID_overflow_minus);
200  return static_cast<side_effect_expr_overflowt &>(side_effect_expr);
201 }
202 
205 {
206 public:
207  explicit history_exprt(exprt variable, const irep_idt &id)
208  : unary_exprt(id, std::move(variable))
209  {
210  }
211 
212  const exprt &expression() const
213  {
214  return op0();
215  }
216 };
217 
218 inline const history_exprt &
219 to_history_expr(const exprt &expr, const irep_idt &id)
220 {
221  PRECONDITION(id == ID_old || id == ID_loop_entry);
222  PRECONDITION(expr.id() == id);
223  auto &ret = static_cast<const history_exprt &>(expr);
224  validate_expr(ret);
225  return ret;
226 }
227 
232 {
233 public:
234  explicit conditional_target_group_exprt(exprt _condition, exprt _target_list)
235  : exprt(ID_conditional_target_group, empty_typet{})
236  {
237  add_to_operands(std::move(_condition));
238  add_to_operands(std::move(_target_list));
239  }
240 
241  static void check(
242  const exprt &expr,
244  {
245  DATA_CHECK(
246  vm,
247  expr.operands().size() == 2,
248  "conditional target expression must have two operands");
249 
250  DATA_CHECK(
251  vm,
252  expr.operands()[1].id() == ID_expression_list,
253  "conditional target second operand must be an ID_expression_list "
254  "expression, found " +
255  id2string(expr.operands()[1].id()));
256  }
257 
258  static void validate(
259  const exprt &expr,
260  const namespacet &,
262  {
263  check(expr, vm);
264  }
265 
266  const exprt &condition() const
267  {
268  return op0();
269  }
270 
272  {
273  return op0();
274  }
275 
276  const exprt::operandst &targets() const
277  {
278  return op1().operands();
279  }
280 
282  {
283  return op1().operands();
284  }
285 };
286 
288 {
290 }
291 
292 template <>
294 {
295  return base.id() == ID_conditional_target_group;
296 }
297 
304 inline const conditional_target_group_exprt &
306 {
307  PRECONDITION(expr.id() == ID_conditional_target_group);
308  auto &ret = static_cast<const conditional_target_group_exprt &>(expr);
309  validate_expr(ret);
310  return ret;
311 }
312 
316 {
317  PRECONDITION(expr.id() == ID_conditional_target_group);
318  auto &ret = static_cast<conditional_target_group_exprt &>(expr);
319  validate_expr(ret);
320  return ret;
321 }
322 
328 {
329 public:
331  exprt _function_pointer,
332  exprt _contract)
333  : exprt(ID_function_pointer_obeys_contract, empty_typet{})
334  {
335  add_to_operands(std::move(_function_pointer));
336  add_to_operands(std::move(_contract));
337  }
338 
339  static void check(
340  const exprt &expr,
342  {
343  DATA_CHECK(
344  vm,
345  expr.operands().size() == 2,
346  "function pointer obeys contract expression must have two operands");
347  }
348 
349  static void validate(
350  const exprt &expr,
351  const namespacet &,
353  {
354  check(expr, vm);
355  }
356 
357  const exprt &function_pointer() const
358  {
359  return op0();
360  }
361 
363  {
364  return op0();
365  }
366 
368  {
369  return to_symbol_expr(op1().operands().at(0));
370  }
371 
373  {
374  return to_symbol_expr(op1().operands().at(0));
375  }
376 
377  const exprt &address_of_contract() const
378  {
379  return op1();
380  }
381 
383  {
384  return op1();
385  }
386 };
387 
389 {
391 }
392 
393 template <>
394 inline bool
396 {
397  return base.id() == ID_function_pointer_obeys_contract;
398 }
399 
408 {
409  PRECONDITION(expr.id() == ID_function_pointer_obeys_contract);
410  auto &ret = static_cast<const function_pointer_obeys_contract_exprt &>(expr);
411  validate_expr(ret);
412  return ret;
413 }
414 
418 {
419  PRECONDITION(expr.id() == ID_function_pointer_obeys_contract);
420  auto &ret = static_cast<function_pointer_obeys_contract_exprt &>(expr);
421  validate_expr(ret);
422  return ret;
423 }
424 
425 #endif // CPROVER_ANSI_C_C_EXPR_H
exprt::op2
exprt & op2()
Definition: expr.h:131
dstringt
dstringt has one field, an unsigned integer no which is an index into a static table of strings.
Definition: dstring.h:36
multi_ary_exprt
A base class for multi-ary expressions Associativity is not specified.
Definition: std_expr.h:856
DATA_CHECK
#define DATA_CHECK(vm, condition, message)
This macro takes a condition which denotes a well-formedness criterion on goto programs,...
Definition: validate.h:22
can_cast_expr< function_pointer_obeys_contract_exprt >
bool can_cast_expr< function_pointer_obeys_contract_exprt >(const exprt &base)
Definition: c_expr.h:395
to_side_effect_expr_overflow
const side_effect_expr_overflowt & to_side_effect_expr_overflow(const exprt &expr)
Cast an exprt to a side_effect_expr_overflowt.
Definition: c_expr.h:182
conditional_target_group_exprt::validate
static void validate(const exprt &expr, const namespacet &, const validation_modet vm=validation_modet::INVARIANT)
Definition: c_expr.h:258
to_history_expr
const history_exprt & to_history_expr(const exprt &expr, const irep_idt &id)
Definition: c_expr.h:219
side_effect_expr_overflowt::rhs
exprt & rhs()
Definition: c_expr.h:143
function_pointer_obeys_contract_exprt::address_of_contract
exprt & address_of_contract()
Definition: c_expr.h:382
shuffle_vector_exprt
Shuffle elements of one or two vectors, modelled after Clang's __builtin_shufflevector.
Definition: c_expr.h:19
validate_operands
void validate_operands(const exprt &value, exprt::operandst::size_type number, const char *message, bool allow_more=false)
Definition: expr_cast.h:250
side_effect_expr_overflowt::lhs
const exprt & lhs() const
Definition: c_expr.h:138
exprt
Base class for all expressions.
Definition: expr.h:55
unary_exprt
Generic base class for unary expressions.
Definition: std_expr.h:313
exprt::op0
exprt & op0()
Definition: expr.h:125
vector_typet
The vector type.
Definition: std_types.h:1007
bool_typet
The Boolean type.
Definition: std_types.h:35
shuffle_vector_exprt::type
const vector_typet & type() const
Definition: c_expr.h:27
vector_exprt
Vector constructor from list of elements.
Definition: std_expr.h:1671
to_side_effect_expr
side_effect_exprt & to_side_effect_expr(exprt &expr)
Definition: std_code.h:1506
symbol_exprt
Expression to hold a symbol (variable)
Definition: std_expr.h:112
multi_ary_exprt::op2
exprt & op2()
Definition: std_expr.h:889
shuffle_vector_exprt::vector2
const exprt & vector2() const
Definition: c_expr.h:47
validate_expr
void validate_expr(const shuffle_vector_exprt &value)
Definition: c_expr.h:81
shuffle_vector_exprt::type
vector_typet & type()
Definition: c_expr.h:32
namespacet
A namespacet is essentially one or two symbol tables bound together, to allow for symbol lookups in t...
Definition: namespace.h:90
exprt::type
typet & type()
Return the type of the expression.
Definition: expr.h:84
irept::is_not_nil
bool is_not_nil() const
Definition: irep.h:380
side_effect_expr_overflowt::lhs
exprt & lhs()
Definition: c_expr.h:133
conditional_target_group_exprt::condition
exprt & condition()
Definition: c_expr.h:271
shuffle_vector_exprt::vector2
exprt & vector2()
Definition: c_expr.h:52
empty_typet
The empty type.
Definition: std_types.h:50
id2string
const std::string & id2string(const irep_idt &d)
Definition: irep.h:47
function_pointer_obeys_contract_exprt::function_pointer
const exprt & function_pointer() const
Definition: c_expr.h:357
function_pointer_obeys_contract_exprt::address_of_contract
const exprt & address_of_contract() const
Definition: c_expr.h:377
PRECONDITION
#define PRECONDITION(CONDITION)
Definition: invariant.h:463
multi_ary_exprt::op1
exprt & op1()
Definition: std_expr.h:883
function_pointer_obeys_contract_exprt::contract_symbol_expr
symbol_exprt & contract_symbol_expr()
Definition: c_expr.h:372
function_pointer_obeys_contract_exprt::check
static void check(const exprt &expr, const validation_modet vm=validation_modet::INVARIANT)
Definition: c_expr.h:339
exprt::op1
exprt & op1()
Definition: expr.h:128
side_effect_expr_overflowt::side_effect_expr_overflowt
side_effect_expr_overflowt(const irep_idt &kind, exprt _lhs, exprt _rhs, exprt _result, const source_locationt &loc)
Definition: c_expr.h:119
conditional_target_group_exprt::conditional_target_group_exprt
conditional_target_group_exprt(exprt _condition, exprt _target_list)
Definition: c_expr.h:234
to_symbol_expr
const symbol_exprt & to_symbol_expr(const exprt &expr)
Cast an exprt to a symbol_exprt.
Definition: std_expr.h:222
validation_modet
validation_modet
Definition: validation_mode.h:12
to_shuffle_vector_expr
const shuffle_vector_exprt & to_shuffle_vector_expr(const exprt &expr)
Cast an exprt to a shuffle_vector_exprt.
Definition: c_expr.h:92
irept::id
const irep_idt & id() const
Definition: irep.h:396
exprt::operandst
std::vector< exprt > operandst
Definition: expr.h:58
function_pointer_obeys_contract_exprt::validate
static void validate(const exprt &expr, const namespacet &, const validation_modet vm=validation_modet::INVARIANT)
Definition: c_expr.h:349
to_conditional_target_group_expr
const conditional_target_group_exprt & to_conditional_target_group_expr(const exprt &expr)
Cast an exprt to a conditional_target_group_exprt.
Definition: c_expr.h:305
std_code.h
optionalt
nonstd::optional< T > optionalt
Definition: optional.h:35
conditional_target_group_exprt
A class for an expression that represents a conditional target or a list of targets sharing a common ...
Definition: c_expr.h:231
can_cast_expr< shuffle_vector_exprt >
bool can_cast_expr< shuffle_vector_exprt >(const exprt &base)
Definition: c_expr.h:76
function_pointer_obeys_contract_exprt
A class for expressions representing a requires_contract(fptr, contract) clause or an ensures_contrac...
Definition: c_expr.h:327
conditional_target_group_exprt::condition
const exprt & condition() const
Definition: c_expr.h:266
conditional_target_group_exprt::targets
const exprt::operandst & targets() const
Definition: c_expr.h:276
shuffle_vector_exprt::lower
vector_exprt lower() const
Definition: c_expr.cpp:34
side_effect_exprt::get_statement
const irep_idt & get_statement() const
Definition: std_code.h:1472
shuffle_vector_exprt::indices
exprt::operandst & indices()
Definition: c_expr.h:67
source_locationt
Definition: source_location.h:18
can_cast_expr< side_effect_expr_overflowt >
bool can_cast_expr< side_effect_expr_overflowt >(const exprt &base)
Definition: c_expr.h:165
shuffle_vector_exprt::indices
const exprt::operandst & indices() const
Definition: c_expr.h:62
history_exprt
A class for an expression that indicates a history variable.
Definition: c_expr.h:204
side_effect_expr_overflowt::result
exprt & result()
Definition: c_expr.h:153
conditional_target_group_exprt::check
static void check(const exprt &expr, const validation_modet vm=validation_modet::INVARIANT)
Definition: c_expr.h:241
exprt::add_to_operands
void add_to_operands(const exprt &expr)
Add the given argument to the end of exprt's operands.
Definition: expr.h:162
function_pointer_obeys_contract_exprt::function_pointer_obeys_contract_exprt
function_pointer_obeys_contract_exprt(exprt _function_pointer, exprt _contract)
Definition: c_expr.h:330
shuffle_vector_exprt::vector1
const exprt & vector1() const
Definition: c_expr.h:37
history_exprt::history_exprt
history_exprt(exprt variable, const irep_idt &id)
Definition: c_expr.h:207
side_effect_expr_overflowt
A Boolean expression returning true, iff the result of performing operation kind on operands a and b ...
Definition: c_expr.h:116
exprt::operands
operandst & operands()
Definition: expr.h:94
can_cast_expr< conditional_target_group_exprt >
bool can_cast_expr< conditional_target_group_exprt >(const exprt &base)
Definition: c_expr.h:293
side_effect_expr_overflowt::rhs
const exprt & rhs() const
Definition: c_expr.h:148
function_pointer_obeys_contract_exprt::contract_symbol_expr
const symbol_exprt & contract_symbol_expr() const
Definition: c_expr.h:367
shuffle_vector_exprt::has_two_input_vectors
bool has_two_input_vectors() const
Definition: c_expr.h:57
function_pointer_obeys_contract_exprt::function_pointer
exprt & function_pointer()
Definition: c_expr.h:362
multi_ary_exprt::op0
exprt & op0()
Definition: std_expr.h:877
conditional_target_group_exprt::targets
exprt::operandst & targets()
Definition: c_expr.h:281
history_exprt::expression
const exprt & expression() const
Definition: c_expr.h:212
side_effect_expr_overflowt::result
const exprt & result() const
Definition: c_expr.h:158
shuffle_vector_exprt::shuffle_vector_exprt
shuffle_vector_exprt(exprt vector1, optionalt< exprt > vector2, exprt::operandst indices)
Definition: c_expr.cpp:13
side_effect_exprt
An expression containing a side effect.
Definition: std_code.h:1449
validation_modet::INVARIANT
@ INVARIANT
to_function_pointer_obeys_contract_expr
const function_pointer_obeys_contract_exprt & to_function_pointer_obeys_contract_expr(const exprt &expr)
Cast an exprt to a function_pointer_obeys_contract_exprt.
Definition: c_expr.h:407
shuffle_vector_exprt::vector1
exprt & vector1()
Definition: c_expr.h:42