Skip to content

Commit e7c7cf0

Browse files
committed
Implement l2_rename_rvalues(lvalue)
This renames the rvalue components of an lvalue expression to L2, such as the index of an array expression or the offset involved in byte-extract operation. Lvalue components (e.g. symbols) are left alone.
1 parent f620b30 commit e7c7cf0

File tree

2 files changed

+70
-0
lines changed

2 files changed

+70
-0
lines changed

src/goto-symex/goto_symex_state.cpp

Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ Author: Daniel Kroening, [email protected]
1717

1818
#include <util/as_const.h>
1919
#include <util/base_exceptions.h>
20+
#include <util/byte_operators.h>
2021
#include <util/exception_utils.h>
2122
#include <util/expr_util.h>
2223
#include <util/format.h>
@@ -340,6 +341,73 @@ goto_symex_statet::rename(exprt expr, const namespacet &ns)
340341
}
341342
}
342343

344+
exprt goto_symex_statet::l2_rename_rvalues(exprt lvalue, const namespacet &ns)
345+
{
346+
rename(lvalue.type(), irep_idt(), ns);
347+
348+
if(lvalue.id() == ID_symbol)
349+
{
350+
// Nothing to do
351+
}
352+
else if(is_read_only_object(lvalue))
353+
{
354+
// Ignore apparent writes to 'NULL-object' and similar read-only objects
355+
}
356+
else if(lvalue.id() == ID_typecast)
357+
{
358+
auto &typecast_lvalue = to_typecast_expr(lvalue);
359+
typecast_lvalue.op() = l2_rename_rvalues(typecast_lvalue.op(), ns);
360+
}
361+
else if(lvalue.id() == ID_member)
362+
{
363+
auto &member_lvalue = to_member_expr(lvalue);
364+
member_lvalue.compound() = l2_rename_rvalues(member_lvalue.compound(), ns);
365+
}
366+
else if(lvalue.id() == ID_index)
367+
{
368+
// The index is an rvalue:
369+
auto &index_lvalue = to_index_expr(lvalue);
370+
index_lvalue.array() = l2_rename_rvalues(index_lvalue.array(), ns);
371+
index_lvalue.index() = rename(index_lvalue.index(), ns).get();
372+
}
373+
else if(
374+
lvalue.id() == ID_byte_extract_little_endian ||
375+
lvalue.id() == ID_byte_extract_big_endian)
376+
{
377+
// The offset is an rvalue:
378+
auto &byte_extract_lvalue = to_byte_extract_expr(lvalue);
379+
byte_extract_lvalue.op() = l2_rename_rvalues(byte_extract_lvalue.op(), ns);
380+
byte_extract_lvalue.offset() = rename(byte_extract_lvalue.offset(), ns);
381+
}
382+
else if(lvalue.id() == ID_if)
383+
{
384+
// The condition is an rvalue:
385+
auto &if_lvalue = to_if_expr(lvalue);
386+
if_lvalue.cond() = rename(if_lvalue.cond(), ns);
387+
if(!if_lvalue.cond().is_false())
388+
if_lvalue.true_case() = l2_rename_rvalues(if_lvalue.true_case(), ns);
389+
if(!if_lvalue.cond().is_true())
390+
if_lvalue.false_case() = l2_rename_rvalues(if_lvalue.false_case(), ns);
391+
}
392+
else if(lvalue.id() == ID_complex_real)
393+
{
394+
auto &complex_real_lvalue = to_complex_real_expr(lvalue);
395+
complex_real_lvalue.op() = l2_rename_rvalues(complex_real_lvalue.op(), ns);
396+
}
397+
else if(lvalue.id() == ID_complex_imag)
398+
{
399+
auto &complex_imag_lvalue = to_complex_imag_expr(lvalue);
400+
complex_imag_lvalue.op() = l2_rename_rvalues(complex_imag_lvalue.op(), ns);
401+
}
402+
else
403+
{
404+
throw unsupported_operation_exceptiont(
405+
"l2_rename_rvalues case `" + lvalue.id_string() + "' not handled");
406+
}
407+
408+
return lvalue;
409+
}
410+
343411
template renamedt<exprt, L1>
344412
goto_symex_statet::rename<L1>(exprt expr, const namespacet &ns);
345413

src/goto-symex/goto_symex_state.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,8 @@ class goto_symex_statet final : public goto_statet
107107
template <levelt level = L2>
108108
void rename(typet &type, const irep_idt &l1_identifier, const namespacet &ns);
109109

110+
exprt l2_rename_rvalues(exprt lvalue, const namespacet &ns);
111+
110112
/// \return lhs renamed to level 2
111113
renamedt<ssa_exprt, L2> assignment(
112114
ssa_exprt lhs, // L0/L1

0 commit comments

Comments
 (0)