Example #1
0
bool interval_domaint::ai_simplify(
  exprt &condition,
  const namespacet &ns) const
{
  bool unchanged=true;
  interval_domaint d(*this);

  // merge intervals to properly handle conjunction
  if(condition.id()==ID_and)              // May be directly representable
  {
    interval_domaint a;
    a.make_top();                         // a is everything
    a.assume(condition, ns);              // Restrict a to an over-approximation
                                          //  of when condition is true
    if(!a.join(d))                        // If d (this) is included in a...
    {                                     // Then the condition is always true
      unchanged=condition.is_true();
      condition.make_true();
    }
  }
  else if(condition.id()==ID_symbol)
  {
    // TODO: we have to handle symbol expression
  }
  else                                    // Less likely to be representable
  {
    d.assume(not_exprt(condition), ns);   // Restrict to when condition is false
    if(d.is_bottom())                     // If there there are none...
    {                                     // Then the condition is always true
      unchanged=condition.is_true();
      condition.make_true();
    }
  }

  return unchanged;
}
Example #2
0
void subsitute_invariants_rec(
    const invariant_sett::invariantst &invariants,
    exprt &dest)
{
    if((dest.id()==ID_and ||
            dest.id()==ID_or ||
            dest.id()==ID_not) &&
            dest.type().id()==ID_bool)
    {
        Forall_operands(it, dest)
        subsitute_invariants_rec(invariants, *it);
    }
    else
    {
#if 0
        for(invariant_sett::invariantst::expr_sett::const_iterator
                it=invariants.expr_set().begin();
                it!=invariants.expr_set().end();
                it++)
            std::cout << "I: " << it->pretty() << std::endl;

        std::cout << "DEST: " << dest.pretty() << std::endl;
#endif

        if(invariants.expr_set().find(dest)!=
                invariants.expr_set().end())
        {
            dest.make_true();
        }
        else
        {
            // inverted?
            exprt tmp(dest);
            tmp.make_not();

            if(invariants.expr_set().find(tmp)!=
                    invariants.expr_set().end())
            {
                dest.make_false();
            }
        }
    }
}
Example #3
0
void gen_binary(exprt &expr, const std::string &id, bool default_value)
{
  if(expr.operands().size()==0)
  {
    if(default_value)
      expr.make_true();
    else
      expr.make_false();
  }
  else if(expr.operands().size()==1)
  {
    exprt tmp;
    tmp.swap(expr.op0());
    expr.swap(tmp);
  }
  else
  {
    expr.id(id);
    expr.type()=typet("bool");
  }
}
Example #4
0
void make_it_a_predicate(
  const predicatest &predicates,
  exprt &expr,
  const namespacet &ns)
{
  bool negation;
  canonicalize(expr, negation, ns);

  // see if we have it
  unsigned nr;
  if(predicates.find(expr, nr))
  {
    // yes, we do!

    // see if it is a constant
    if(predicates[nr].is_true())
      expr.make_true();
    else if(predicates[nr].is_false())
      expr.make_false();
    else
    {
      expr=exprt(ID_predicate_symbol, typet(ID_bool));
      expr.set(ID_identifier, nr);
    }

    if(negation)
      expr.make_not();
  }
  else
  {
    // nah, we don't
    // make it nondeterministic choice
    exprt tmp(ID_nondet_symbol, typet(ID_bool));
    tmp.add(ID_expression).swap(expr);
    expr.swap(tmp);
  }
}
Example #5
0
void abstract_expression(
  const predicatest &predicates,
  exprt &expr,
  const namespacet &ns)
{
  if(expr.type().id()!=ID_bool)
    throw "abstract_expression expects expression of type Boolean";

  simplify(expr, ns);

  if(is_valid(expr, ns))
  {
	  // If expr is valid, we can abstract it as 'true'
	  expr.make_true();
  } else if(is_unsatisfiable(expr, ns))
  {
	  // If expr is unsatisfiable, we can abstract it as 'false'
	  expr.make_false();
  } else if(expr.id()==ID_and || expr.id()==ID_or ||
     expr.id()==ID_implies || expr.id()==ID_xor)
  {
    Forall_operands(it, expr)
      abstract_expression(predicates, *it, ns);
  }
  else if(expr.id()==ID_not)
  {
    assert(expr.operands().size()==1);

    abstract_expression(predicates, expr.op0(), ns);

    // remove double negation
    if(expr.op0().id()==ID_not &&
       expr.op0().operands().size()==1)
    {
      exprt tmp;
      tmp.swap(expr.op0().op0());
      expr.swap(tmp);
    }
  }
  else if(expr.id()==ID_if)
  {
    assert(expr.operands().size()==3);
  
    Forall_operands(it, expr)
      abstract_expression(predicates, *it, ns);

    exprt true_expr(ID_and, bool_typet());
    true_expr.copy_to_operands(expr.op0(), expr.op1());
    
    exprt false_expr(ID_and, bool_typet());
    false_expr.copy_to_operands(gen_not(expr.op0()), expr.op2());
    
    exprt or_expr(ID_or, bool_typet());
    or_expr.move_to_operands(true_expr, false_expr);
    
    expr.swap(or_expr);
  }
  else if(expr.id()==ID_equal || expr.id()==ID_notequal)
  {
    if(expr.operands().size()!=2)
      throw expr.id_string()+" takes two operands";

    // Is it equality on Booleans?

    if(expr.op0().type().id()==ID_bool &&
       expr.op1().type().id()==ID_bool)
    {
      // leave it in

      Forall_operands(it, expr)
        abstract_expression(predicates, *it, ns);
    }
    else // other types, make it a predicate
    {
      if(has_non_boolean_if(expr))
      {
        lift_if(expr);
        abstract_expression(predicates, expr, ns);
      }
      else
        make_it_a_predicate(predicates, expr, ns);
    }
  }
  else if(expr.is_constant())
  {
    // leave it as is
  }
  else if(has_non_boolean_if(expr))
  {
    lift_if(expr);
    abstract_expression(predicates, expr, ns);
  }
  else
  {
    make_it_a_predicate(predicates, expr, ns);
  }
}