diff --git a/jbmc/src/java_bytecode/java_bytecode_convert_method.cpp b/jbmc/src/java_bytecode/java_bytecode_convert_method.cpp index 0393e41f1eb..809ca32ac17 100644 --- a/jbmc/src/java_bytecode/java_bytecode_convert_method.cpp +++ b/jbmc/src/java_bytecode/java_bytecode_convert_method.cpp @@ -2705,15 +2705,19 @@ code_ifthenelset java_bytecode_convert_methodt::convert_ifnull( const mp_integer &number, const source_locationt &location) const { - code_ifthenelset code_branch; const typecast_exprt lhs(op[0], java_reference_type(empty_typet())); const exprt rhs(null_pointer_exprt(to_pointer_type(lhs.type()))); - code_branch.cond() = binary_relation_exprt(lhs, ID_equal, rhs); + const method_offsett label_number = numeric_cast_v(number); - code_branch.then_case() = code_gotot(label(std::to_string(label_number))); + + code_ifthenelset code_branch( + binary_relation_exprt(lhs, ID_equal, rhs), + code_gotot(label(std::to_string(label_number)))); + code_branch.then_case().add_source_location() = address_map.at(label_number).source->source_location; code_branch.add_source_location() = location; + return code_branch; } @@ -2723,15 +2727,19 @@ code_ifthenelset java_bytecode_convert_methodt::convert_ifnonull( const mp_integer &number, const source_locationt &location) const { - code_ifthenelset code_branch; const typecast_exprt lhs(op[0], java_reference_type(empty_typet())); const exprt rhs(null_pointer_exprt(to_pointer_type(lhs.type()))); - code_branch.cond() = binary_relation_exprt(lhs, ID_notequal, rhs); + const method_offsett label_number = numeric_cast_v(number); - code_branch.then_case() = code_gotot(label(std::to_string(label_number))); + + code_ifthenelset code_branch( + binary_relation_exprt(lhs, ID_notequal, rhs), + code_gotot(label(std::to_string(label_number)))); + code_branch.then_case().add_source_location() = address_map.at(label_number).source->source_location; code_branch.add_source_location() = location; + return code_branch; } @@ -2742,18 +2750,20 @@ code_ifthenelset java_bytecode_convert_methodt::convert_if( const mp_integer &number, const source_locationt &location) const { - code_ifthenelset code_branch; - code_branch.cond() = - binary_relation_exprt(op[0], id, from_integer(0, op[0].type())); + const method_offsett label_number = numeric_cast_v(number); + + code_ifthenelset code_branch( + binary_relation_exprt(op[0], id, from_integer(0, op[0].type())), + code_gotot(label(std::to_string(label_number)))); + code_branch.cond().add_source_location() = location; code_branch.cond().add_source_location().set_function(method_id); - const method_offsett label_number = numeric_cast_v(number); - code_branch.then_case() = code_gotot(label(std::to_string(label_number))); code_branch.then_case().add_source_location() = address_map.at(label_number).source->source_location; code_branch.then_case().add_source_location().set_function(method_id); code_branch.add_source_location() = location; code_branch.add_source_location().set_function(method_id); + return code_branch; } @@ -2764,15 +2774,16 @@ code_ifthenelset java_bytecode_convert_methodt::convert_if_cmp( const mp_integer &number, const source_locationt &location) const { - code_ifthenelset code_branch; const irep_idt cmp_op = get_if_cmp_operator(statement); binary_relation_exprt condition( op[0], cmp_op, typecast_exprt::conditional_cast(op[1], op[0].type())); condition.add_source_location() = location; - code_branch.cond() = condition; const method_offsett label_number = numeric_cast_v(number); - code_branch.then_case() = code_gotot(label(std::to_string(label_number))); + + code_ifthenelset code_branch( + std::move(condition), code_gotot(label(std::to_string(label_number)))); + code_branch.then_case().add_source_location() = address_map.at(label_number).source->source_location; code_branch.add_source_location() = location; @@ -2797,15 +2808,16 @@ code_blockt java_bytecode_convert_methodt::convert_ret( c.add(g); else { - code_ifthenelset branch; auto address_ptr = from_integer(jsr_ret_targets[idx], unsignedbv_typet(64)); address_ptr.type() = pointer_type(void_typet()); - branch.cond() = equal_exprt(retvar, address_ptr); + + code_ifthenelset branch(equal_exprt(retvar, address_ptr), std::move(g)); + branch.cond().add_source_location() = location; - branch.then_case() = g; branch.add_source_location() = location; - c.add(branch); + + c.add(std::move(branch)); } } return c; diff --git a/jbmc/src/java_bytecode/java_bytecode_instrument.cpp b/jbmc/src/java_bytecode/java_bytecode_instrument.cpp index 085175ad806..23c9286fab3 100644 --- a/jbmc/src/java_bytecode/java_bytecode_instrument.cpp +++ b/jbmc/src/java_bytecode/java_bytecode_instrument.cpp @@ -127,10 +127,10 @@ code_ifthenelset java_bytecode_instrumentt::throw_exception( side_effect_expr_throwt throw_expr(irept(), typet(), original_loc); throw_expr.copy_to_operands(new_symbol.symbol_expr()); - code_ifthenelset if_code; + code_ifthenelset if_code( + cond, code_blockt({assign_new, code_expressiont(throw_expr)})); + if_code.add_source_location()=original_loc; - if_code.cond()=cond; - if_code.then_case() = code_blockt({assign_new, code_expressiont(throw_expr)}); return if_code; } @@ -250,11 +250,9 @@ code_ifthenelset java_bytecode_instrumentt::check_class_cast( check_code=std::move(assert_class); } - code_ifthenelset conditional_check; - notequal_exprt op_not_null(null_check_op, null_pointer_exprt(voidptr)); - conditional_check.cond()=std::move(op_not_null); - conditional_check.then_case()=std::move(check_code); - return conditional_check; + return code_ifthenelset( + notequal_exprt(std::move(null_check_op), null_pointer_exprt(voidptr)), + std::move(check_code)); } /// Checks whether \p expr is null and throws NullPointerException/ diff --git a/jbmc/src/java_bytecode/java_object_factory.cpp b/jbmc/src/java_bytecode/java_object_factory.cpp index d5725c2d224..cbaf8d37d06 100644 --- a/jbmc/src/java_bytecode/java_object_factory.cpp +++ b/jbmc/src/java_bytecode/java_object_factory.cpp @@ -853,12 +853,12 @@ void java_object_factoryt::gen_nondet_pointer_init( // > // } - code_ifthenelset null_check; - null_check.cond() = side_effect_expr_nondett(bool_typet(), location); - null_check.then_case()=set_null_inst; - null_check.else_case()=non_null_inst; + code_ifthenelset null_check( + side_effect_expr_nondett(bool_typet(), location), + std::move(set_null_inst), + std::move(non_null_inst)); - new_object_assignments.add(null_check); + new_object_assignments.add(std::move(null_check)); } // Similarly to above, maybe use a conditional if both the @@ -872,13 +872,12 @@ void java_object_factoryt::gen_nondet_pointer_init( INVARIANT(update_in_place==update_in_placet::MAY_UPDATE_IN_PLACE, "No-update and must-update should have already been resolved"); - code_ifthenelset update_check; - update_check.cond() = - side_effect_expr_nondett(bool_typet(), expr.source_location()); - update_check.then_case()=update_in_place_assignments; - update_check.else_case()=new_object_assignments; + code_ifthenelset update_check( + side_effect_expr_nondett(bool_typet(), expr.source_location()), + std::move(update_in_place_assignments), + std::move(new_object_assignments)); - assignments.add(update_check); + assignments.add(std::move(update_check)); } } @@ -1461,9 +1460,8 @@ void java_object_factoryt::gen_nondet_array_init( code_labelt init_done_label(done_name, code_skipt()); code_gotot goto_done(done_name); - code_ifthenelset done_test; - done_test.cond()=equal_exprt(counter_expr, length_expr); - done_test.then_case()=goto_done; + const code_ifthenelset done_test( + equal_exprt(counter_expr, length_expr), goto_done); assignments.add(std::move(done_test)); @@ -1471,9 +1469,8 @@ void java_object_factoryt::gen_nondet_array_init( { // Add a redundant if(counter == max_length) break // that is easier for the unwinder to understand. - code_ifthenelset max_test; - max_test.cond()=equal_exprt(counter_expr, max_length_expr); - max_test.then_case()=goto_done; + code_ifthenelset max_test( + equal_exprt(counter_expr, max_length_expr), std::move(goto_done)); assignments.add(std::move(max_test)); } diff --git a/jbmc/src/java_bytecode/java_static_initializers.cpp b/jbmc/src/java_bytecode/java_static_initializers.cpp index bb15d6107a2..89cbe14ab7f 100644 --- a/jbmc/src/java_bytecode/java_static_initializers.cpp +++ b/jbmc/src/java_bytecode/java_static_initializers.cpp @@ -510,12 +510,12 @@ code_blockt get_thread_safe_clinit_wrapper_body( // if(C::__CPROVER_PREFIX_clinit_thread_local_state == INIT_COMPLETE) return; { - code_ifthenelset conditional; - conditional.cond() = gen_clinit_eqexpr( - clinit_thread_local_state_sym.symbol_expr(), - clinit_statest::INIT_COMPLETE); - conditional.then_case() = code_returnt(); - function_body.add(conditional); + code_ifthenelset conditional( + gen_clinit_eqexpr( + clinit_thread_local_state_sym.symbol_expr(), + clinit_statest::INIT_COMPLETE), + code_returnt()); + function_body.add(std::move(conditional)); } // C::__CPROVER_PREFIX_clinit_thread_local_state = INIT_COMPLETE; @@ -550,25 +550,21 @@ code_blockt get_thread_safe_clinit_wrapper_body( // init_complete = true; // } { - code_ifthenelset not_init_conditional; - code_blockt then_block; - not_init_conditional.cond() = gen_clinit_eqexpr( - clinit_state_sym.symbol_expr(), clinit_statest::NOT_INIT); - then_block.add( - gen_clinit_assign( - clinit_state_sym.symbol_expr(), clinit_statest::IN_PROGRESS)); - then_block.add(code_assignt(init_complete.symbol_expr(), false_exprt())); - not_init_conditional.then_case() = then_block; - - code_ifthenelset init_conditional; - code_blockt init_conditional_body; - init_conditional.cond() = gen_clinit_eqexpr( - clinit_state_sym.symbol_expr(), clinit_statest::INIT_COMPLETE); - init_conditional_body.add( - code_assignt(init_complete.symbol_expr(), true_exprt())); - init_conditional.then_case() = init_conditional_body; - not_init_conditional.else_case() = init_conditional; - function_body.add(not_init_conditional); + code_ifthenelset init_conditional( + gen_clinit_eqexpr( + clinit_state_sym.symbol_expr(), clinit_statest::INIT_COMPLETE), + code_blockt({code_assignt(init_complete.symbol_expr(), true_exprt())})); + + code_ifthenelset not_init_conditional( + gen_clinit_eqexpr( + clinit_state_sym.symbol_expr(), clinit_statest::NOT_INIT), + code_blockt( + {gen_clinit_assign( + clinit_state_sym.symbol_expr(), clinit_statest::IN_PROGRESS), + code_assignt(init_complete.symbol_expr(), false_exprt())}), + std::move(init_conditional)); + + function_body.add(std::move(not_init_conditional)); } // ATOMIC_END @@ -578,10 +574,8 @@ code_blockt get_thread_safe_clinit_wrapper_body( // if(init_complete) return; { - code_ifthenelset conditional; - conditional.cond() = init_complete.symbol_expr(); - conditional.then_case() = code_returnt(); - function_body.add(conditional); + code_ifthenelset conditional(init_complete.symbol_expr(), code_returnt()); + function_body.add(std::move(conditional)); } // Initialize the super-class C' and @@ -680,12 +674,6 @@ code_ifthenelset get_clinit_wrapper_body( already_run_symbol.symbol_expr(), false_exprt()); - // the entire body of the function is an if-then-else - code_ifthenelset wrapper_body; - - // add the condition to the if - wrapper_body.cond() = check_already_run; - // add the "already-run = false" statement code_assignt set_already_run(already_run_symbol.symbol_expr(), true_exprt()); code_blockt init_body({set_already_run}); @@ -698,9 +686,8 @@ code_ifthenelset get_clinit_wrapper_body( object_factory_parameters, pointer_type_selector); - wrapper_body.then_case() = init_body; - - return wrapper_body; + // the entire body of the function is an if-then-else + return code_ifthenelset(std::move(check_already_run), std::move(init_body)); } diff --git a/jbmc/src/java_bytecode/java_string_library_preprocess.cpp b/jbmc/src/java_bytecode/java_string_library_preprocess.cpp index 175883cdb48..57daaa1e6e5 100644 --- a/jbmc/src/java_bytecode/java_string_library_preprocess.cpp +++ b/jbmc/src/java_bytecode/java_string_library_preprocess.cpp @@ -1065,12 +1065,11 @@ code_blockt java_string_library_preprocesst::make_float_to_string_code( str, string_expr_list[0], symbol_table, true); for(std::size_t i=1; iguard.is_true()) { - code_ifthenelset i; - - i.cond()=not_exprt(loop_end->guard); + code_ifthenelset i(not_exprt(loop_end->guard), code_breakt()); simplify(i.cond(), ns); - i.then_case()=code_breakt(); copy_source_location(target, i); @@ -1103,11 +1100,6 @@ goto_programt::const_targett goto_program2codet::convert_goto_if( end_if=before_else->get_target(); } - code_ifthenelset i; - i.then_case()=code_blockt(); - - copy_source_location(target, i); - // some nesting of loops and branches we might not be able to deal with if(target->is_backwards_goto() || (upper_bound!=goto_program.instructions.end() && @@ -1119,7 +1111,8 @@ goto_programt::const_targett goto_program2codet::convert_goto_if( return convert_goto_goto(target, dest); } - i.cond()=not_exprt(target->guard); + code_ifthenelset i(not_exprt(target->guard), code_blockt()); + copy_source_location(target, i); simplify(i.cond(), ns); if(has_else) @@ -1182,21 +1175,15 @@ goto_programt::const_targett goto_program2codet::convert_goto_break_continue( if(target->get_target()==loop_end && loop_last_stack.back().second) { - code_continuet cont; - - if(!target->guard.is_true()) - { - code_ifthenelset i; - i.cond()=target->guard; - simplify(i.cond(), ns); - i.then_case().swap(cont); + code_ifthenelset i(target->guard, code_continuet()); + simplify(i.cond(), ns); - copy_source_location(target, i); + copy_source_location(target, i); - dest.move_to_operands(i); - } + if(i.cond().is_true()) + dest.move_to_operands(i.then_case()); else - dest.move_to_operands(cont); + dest.move_to_operands(i); return target; } @@ -1218,12 +1205,8 @@ goto_programt::const_targett goto_program2codet::convert_goto_break_continue( if(target->get_target()==after_loop) { - code_breakt brk; - - code_ifthenelset i; - i.cond()=target->guard; + code_ifthenelset i(target->guard, code_breakt()); simplify(i.cond(), ns); - i.then_case().swap(brk); copy_source_location(target, i); @@ -1285,19 +1268,15 @@ goto_programt::const_targett goto_program2codet::convert_goto_goto( code_gotot goto_code(label.str()); - if(!target->guard.is_true()) - { - code_ifthenelset i; - i.cond()=target->guard; - simplify(i.cond(), ns); - i.then_case().swap(goto_code); + code_ifthenelset i(target->guard, std::move(goto_code)); + simplify(i.cond(), ns); - copy_source_location(target, i); + copy_source_location(target, i); - dest.move_to_operands(i); - } + if(i.cond().is_true()) + dest.move_to_operands(i.then_case()); else - dest.move_to_operands(goto_code); + dest.move_to_operands(i); return target; } diff --git a/src/goto-programs/goto_convert.cpp b/src/goto-programs/goto_convert.cpp index 9738f409ef8..84ac420fa78 100644 --- a/src/goto-programs/goto_convert.cpp +++ b/src/goto-programs/goto_convert.cpp @@ -577,12 +577,12 @@ void goto_convertt::convert_expression( // We do a special treatment for c?t:f // by compiling to if(c) t; else f; const if_exprt &if_expr=to_if_expr(expr); - code_ifthenelset tmp_code; + code_ifthenelset tmp_code( + if_expr.cond(), + code_expressiont(if_expr.true_case()), + code_expressiont(if_expr.false_case())); tmp_code.add_source_location()=expr.source_location(); - tmp_code.cond()=if_expr.cond(); - tmp_code.then_case()=code_expressiont(if_expr.true_case()); tmp_code.then_case().add_source_location()=expr.source_location(); - tmp_code.else_case()=code_expressiont(if_expr.false_case()); tmp_code.else_case().add_source_location()=expr.source_location(); convert_ifthenelse(tmp_code, dest, mode); } @@ -1470,13 +1470,10 @@ void goto_convertt::convert_ifthenelse( !has_else) { // if(a && b) XX --> if(a) if(b) XX - code_ifthenelset new_if0, new_if1; - new_if0.cond()=code.cond().op0(); - new_if1.cond()=code.cond().op1(); - new_if0.add_source_location()=source_location; - new_if1.add_source_location()=source_location; - new_if1.then_case()=code.then_case(); - new_if0.then_case()=new_if1; + code_ifthenelset new_if1(code.cond().op1(), code.then_case()); + new_if1.add_source_location() = source_location; + code_ifthenelset new_if0(code.cond().op0(), std::move(new_if1)); + new_if0.add_source_location() = source_location; return convert_ifthenelse(new_if0, dest, mode); } diff --git a/src/goto-programs/goto_convert_exceptions.cpp b/src/goto-programs/goto_convert_exceptions.cpp index 95bfbc53d98..d8f4791a80a 100644 --- a/src/goto-programs/goto_convert_exceptions.cpp +++ b/src/goto-programs/goto_convert_exceptions.cpp @@ -168,12 +168,10 @@ void goto_convertt::convert_CPROVER_try_catch( targets.set_throw(tmp.instructions.begin()); // now put 'catch' code onto destructor stack - code_ifthenelset catch_code; - catch_code.cond()=exception_flag(); + code_ifthenelset catch_code(exception_flag(), to_code(code.op1())); catch_code.add_source_location()=code.source_location(); - catch_code.then_case()=to_code(code.op1()); - targets.destructor_stack.push_back(catch_code); + targets.destructor_stack.push_back(std::move(catch_code)); // now convert 'try' code convert(to_code(code.op0()), dest, mode); diff --git a/src/jsil/parser.y b/src/jsil/parser.y index 54c277d0a97..f82f5000ceb 100644 --- a/src/jsil/parser.y +++ b/src/jsil/parser.y @@ -235,10 +235,7 @@ instruction: TOK_LABEL TOK_IDENTIFIER code_gotot lt(to_symbol_expr(stack($5)).get_identifier()); code_gotot lf(to_symbol_expr(stack($7)).get_identifier()); - code_ifthenelset ite; - ite.cond().swap(stack($3)); - ite.then_case().swap(lt); - ite.else_case().swap(lf); + code_ifthenelset ite(stack($3), std::move(lt), std::move(lf)); newstack($$).swap(ite); } diff --git a/src/util/std_code.h b/src/util/std_code.h index 921011bb068..f847bcec8c6 100644 --- a/src/util/std_code.h +++ b/src/util/std_code.h @@ -622,6 +622,23 @@ class code_ifthenelset:public codet op2().make_nil(); } + /// An if \p condition then \p then_code else \p else_code statement. + code_ifthenelset( + const exprt &condition, + const codet &then_code, + const codet &else_code) + : codet(ID_ifthenelse) + { + add_to_operands(condition, then_code, else_code); + } + + /// An if \p condition then \p then_code statement (no "else" case). + code_ifthenelset(const exprt &condition, const codet &then_code) + : codet(ID_ifthenelse) + { + add_to_operands(condition, then_code, nil_exprt()); + } + const exprt &cond() const { return op0(); diff --git a/unit/analyses/dependence_graph.cpp b/unit/analyses/dependence_graph.cpp index c26fcfda0ce..bad45358e15 100644 --- a/unit/analyses/dependence_graph.cpp +++ b/unit/analyses/dependence_graph.cpp @@ -68,23 +68,16 @@ SCENARIO("dependence_graph", "[core][analyses][dependence_graph]") code_declt declare_x(x_symbol.symbol_expr()); a_body.move_to_operands(declare_x); - code_ifthenelset if_block; - - if_block.cond() = - equal_exprt( - side_effect_expr_nondett(int_type), - from_integer(0, int_type)); - - code_blockt then_block; code_function_callt call(symbol_exprt("b", void_function_type)); - then_block.move_to_operands(call); code_assignt assign_x( x_symbol.symbol_expr(), from_integer(1, int_type)); - then_block.move_to_operands(assign_x); - if_block.then_case() = then_block; + code_ifthenelset if_block( + equal_exprt( + side_effect_expr_nondett(int_type), from_integer(0, int_type)), + code_blockt({call, assign_x})); - a_body.move_to_operands(if_block); + a_body.add(std::move(if_block)); goto_model.symbol_table.add( create_void_function_symbol(goto_functionst::entry_point(), a_body));