/** Partially evaluate the right-hand side and the conditions of a specified rule. */
  private static Rule evaluateRule(Rule rule, TermContext termContext) {
    try {
      // TODO(AndreiS): some evaluation is required in the LHS as well
      // TODO(YilongL): cannot simply uncomment the following code because it
      // may evaluate the LHS using the rule itself
      // Term leftHandSide = rule.leftHandSide().evaluate(termContext);

      Rule origRule = rule;
      Term rightHandSide = rule.rightHandSide().evaluate(termContext);
      List<Term> requires = new ArrayList<>();
      for (Term term : rule.requires()) {
        requires.add(term.evaluate(termContext));
      }
      List<Term> ensures = new ArrayList<>();
      for (Term term : rule.ensures()) {
        ensures.add(term.evaluate(termContext));
      }
      ConjunctiveFormula lookups = ConjunctiveFormula.of(termContext);
      for (Equality equality : rule.lookups().equalities()) {
        lookups =
            lookups.add(
                equality.leftHandSide().evaluate(termContext),
                equality.rightHandSide().evaluate(termContext));
      }

      Map<CellLabel, Term> rhsOfWriteCell = null;
      if (rule.isCompiledForFastRewriting()) {
        rhsOfWriteCell = new HashMap<>();
        for (Map.Entry<CellLabel, Term> entry : rule.rhsOfWriteCell().entrySet()) {
          rhsOfWriteCell.put(entry.getKey(), entry.getValue().evaluate(termContext));
        }
      }

      Rule newRule =
          new Rule(
              rule.label(),
              rule.leftHandSide(),
              rightHandSide,
              requires,
              ensures,
              rule.freshConstants(),
              rule.freshVariables(),
              lookups,
              rule.isCompiledForFastRewriting(),
              rule.lhsOfReadCell(),
              rhsOfWriteCell,
              rule.cellsToCopy(),
              rule.matchingInstructions(),
              rule,
              termContext);
      return newRule.equals(rule) ? origRule : newRule;
    } catch (KEMException e) {
      e.exception.addTraceFrame(
          "while compiling rule at location " + rule.getSource() + rule.getLocation());
      throw e;
    }
  }
示例#2
0
 @Override
 public void visit(Rule rule) {
   rule.leftHandSide().accept(this);
   rule.rightHandSide().accept(this);
   rule.lookups().accept(this);
   for (Term term : rule.requires()) {
     term.accept(this);
   }
   for (Term term : rule.ensures()) {
     term.accept(this);
   }
   for (Variable variable : rule.freshVariables()) {
     variable.accept(this);
   }
 }
示例#3
0
  private void narrowByRule(ConstrainedTerm constrainedTerm, Rule rule) {
    stopwatch.reset();
    stopwatch.start();

    constrainedTermResults = new ArrayList<ConstrainedTerm>();

    SymbolicConstraint leftHandSideConstraint =
        new SymbolicConstraint(constrainedTerm.termContext());
    leftHandSideConstraint.addAll(rule.requires());
    for (Variable variable : rule.freshVariables()) {
      leftHandSideConstraint.add(variable, IntToken.fresh());
    }

    ConstrainedTerm leftHandSide =
        new ConstrainedTerm(
            rule.leftHandSide(),
            rule.lookups().getSymbolicConstraint(constrainedTerm.termContext()),
            leftHandSideConstraint,
            constrainedTerm.termContext());

    for (SymbolicConstraint constraint : constrainedTerm.unify(leftHandSide)) {
      constraint.addAll(rule.ensures());
      /* rename rule variables in the constraints */
      Map<Variable, Variable> freshSubstitution = constraint.rename(rule.variableSet());

      Term result = rule.rightHandSide();
      /* rename rule variables in the rule RHS */
      result = result.substituteWithBinders(freshSubstitution, constrainedTerm.termContext());
      /* apply the constraints substitution on the rule RHS */
      result =
          result.substituteWithBinders(constraint.substitution(), constrainedTerm.termContext());
      /* evaluate pending functions in the rule RHS */
      result = result.evaluate(constrainedTerm.termContext());
      /* eliminate anonymous variables */
      constraint.eliminateAnonymousVariables();

      /* compute all results */
      constrainedTermResults.add(
          new ConstrainedTerm(result, constraint, constrainedTerm.termContext()));
    }

    stopwatch.stop();
  }
示例#4
0
  @Override
  public KRunProofResult<Set<org.kframework.kil.Term>> prove(Module module)
      throws KRunExecutionException {
    TermContext termContext = TermContext.of(globalContext);
    List<Rule> rules = new ArrayList<Rule>();
    for (org.kframework.kil.ModuleItem moduleItem : module.getItems()) {
      if (!(moduleItem instanceof org.kframework.kil.Rule)) {
        continue;
      }

      Rule rule = transformer.transformAndEval((org.kframework.kil.Rule) moduleItem);
      Rule freshRule = rule.getFreshRule(termContext);
      rules.add(freshRule);
    }

    CounterGetter counterGetter = new CounterGetter(context);
    counterGetter.visitNode(module);
    BigInteger counter = counterGetter.counter.add(BigInteger.ONE);

    SymbolicRewriter symbolicRewriter = executor.getSymbolicRewriter();
    List<ConstrainedTerm> proofResults = new ArrayList<>();
    for (org.kframework.kil.ModuleItem moduleItem : module.getItems()) {
      if (!(moduleItem instanceof org.kframework.kil.Rule)
          || moduleItem.containsAttribute(Attribute.TRUSTED_KEY)) {
        continue;
      }

      termContext.setCounter(counter);
      Rule rule = transformer.transformAndEval((org.kframework.kil.Rule) moduleItem);
      ConstrainedTerm initialTerm =
          new ConstrainedTerm(
              rule.leftHandSide(), ConjunctiveFormula.of(termContext).addAll(rule.requires()));
      ConstrainedTerm targetTerm =
          new ConstrainedTerm(
              rule.rightHandSide(), ConjunctiveFormula.of(termContext).addAll(rule.ensures()));
      proofResults.addAll(symbolicRewriter.proveRule(initialTerm, targetTerm, rules));
    }

    return new KRunProofResult<>(
        proofResults.isEmpty(), Collections.<org.kframework.kil.Term>emptySet());
  }