Пример #1
0
void THandler::backtrack( )
{
  // Undoes the state of theory atoms if needed
  while ( (int)stack.size( ) > trail.size( ) )
  {
    Enode * e = stack.back( );
    stack.pop_back( );

    // It was var_True or var_False
    if ( e == NULL )
      continue;

    if ( !e->isTAtom( ) )
      continue;

    core_solver.popBacktrackPoint( );

    assert( e->isTAtom( ) );
    assert( e->hasPolarity( ) );
    assert( e->getPolarity( ) == l_True
         || e->getPolarity( ) == l_False );
    // Reset polarity
    e->resetPolarity( );
    assert( !e->hasPolarity( ) );
  }
  checked_trail_size = stack.size( );
}
Пример #2
0
void THandler::getReason( Lit l, vec< Lit > & reason )
{
#if LAZY_COMMUNICATION
  assert( checked_trail_size == stack.size( ) );
  assert( static_cast< int >( checked_trail_size ) == trail.size( ) );
#else
#endif

  Var v = var(l);
  Enode * e = varToEnode( v );

  // It must be a TAtom and already disabled
  assert( e->isTAtom( ) );
  assert( !e->hasPolarity( ) );
  assert( e->isDeduced( ) );
  assert( e->getDeduced( ) != l_Undef );           // Last assigned deduction
#if LAZY_COMMUNICATION
  assert( e->getPolarity( ) != l_Undef );          // Last assigned polarity
  assert( e->getPolarity( ) == e->getDeduced( ) ); // The two coincide
#else
#endif

  core_solver.pushBacktrackPoint( );

  // Assign reversed polarity temporairly
  e->setPolarity( e->getDeduced( ) == l_True ? l_False : l_True );
  // Compute reason in whatever solver
  const bool res = core_solver.assertLit( e, true ) &&
                   core_solver.check( true );
  // Result must be false
  if ( res )
  {
    cout << endl << "unknown" << endl;
    exit( 1 );
  }

  // Get Explanation
  vector< Enode * > & explanation = core_solver.getConflict( true );

  if ( config.certification_level > 0 )
    verifyExplanationWithExternalTool( explanation );

  // Reserve room for implied lit
  reason.push( lit_Undef );
  // Copy explanation

  while ( !explanation.empty( ) )
  {
    Enode * ei  = explanation.back( );
    explanation.pop_back( );
    assert( ei->hasPolarity( ) );
    assert( ei->getPolarity( ) == l_True
         || ei->getPolarity( ) == l_False );
    bool negate = ei->getPolarity( ) == l_False;
    Var v = enodeToVar( ei );

    // Toggle polarity for deduced literal
    if ( e == ei )
    {
      assert( e->getDeduced( ) != l_Undef );           // But still holds the deduced polarity
      // The deduced literal must have been pushed
      // with the the same polarity that has been deduced
      reason[ 0 ] = Lit( v, !negate );
    }
    else
    {
      assert( ei->hasPolarity( ) );                    // Lit in explanation is active
      // This assertion might fail if in your theory solver
      // you do not skip deduced literals during assertLit
      //
      // TODO: check ! It could be deduced: by another solver
      // For instance BV found conflict and ei was deduced by EUF solver
      //
      // assert( !ei->isDeduced( ) );                     // and not deduced
      Lit l = Lit( v, !negate );
      reason.push( l );
    }
  }

  core_solver.popBacktrackPoint( );

  // Resetting polarity
  e->resetPolarity( );
}