From ba4e4d30c134a148e66d4ade51f2769cfd9fec47 Mon Sep 17 00:00:00 2001 From: Etienne Kneuss <colder@php.net> Date: Fri, 6 Sep 2013 18:03:10 +0200 Subject: [PATCH] Debug sections become implicit --- src/main/scala/leon/Main.scala | 5 ++- src/main/scala/leon/Reporter.scala | 16 +++++-- src/main/scala/leon/solvers/Solver.scala | 2 + .../scala/leon/solvers/SolverFactory.scala | 2 + .../leon/solvers/z3/AbstractZ3Solver.scala | 2 - .../leon/solvers/z3/FairZ3SolverFactory.scala | 42 +++++++++---------- .../leon/verification/AnalysisPhase.scala | 14 +++---- 7 files changed, 46 insertions(+), 37 deletions(-) diff --git a/src/main/scala/leon/Main.scala b/src/main/scala/leon/Main.scala index 10e5c8953..343ed2da4 100644 --- a/src/main/scala/leon/Main.scala +++ b/src/main/scala/leon/Main.scala @@ -163,7 +163,7 @@ object Main { // Create a new reporter taking settings into account val reporter = new DefaultReporter(settings) - reporter.ifDebug(ReportingOptions) { debug => + reporter.whenDebug(ReportingOptions) { debug => debug("Options considered by Leon:") for (lo <- leonOptions) lo match { @@ -235,7 +235,7 @@ object Main { ctx.timers.get("Leon Run") += timer - ctx.reporter.ifDebug(ReportingTimers) { debug => + ctx.reporter.whenDebug(ReportingTimers) { debug => debug("-"*80) debug("Times:") debug("-"*80) @@ -244,6 +244,7 @@ object Main { } debug("-"*80) } + } catch { case LeonFatalError() => sys.exit(1) } diff --git a/src/main/scala/leon/Reporter.scala b/src/main/scala/leon/Reporter.scala index 6b89537c2..98d72ed9f 100644 --- a/src/main/scala/leon/Reporter.scala +++ b/src/main/scala/leon/Reporter.scala @@ -5,6 +5,7 @@ package leon import purescala.Definitions.Definition import purescala.Trees.Expr import purescala.PrettyPrinter +import scala.annotation.implicitNotFound abstract class Reporter(settings: Settings) { def infoFunction(msg: Any) : Unit @@ -36,17 +37,23 @@ abstract class Reporter(settings: Settings) { private val debugMask = settings.debugSections.foldLeft(0){ _ | _.mask } - def ifDebug(section: ReportingSection)(body: (Any => Unit) => Any) { + def ifDebug(body: (Any => Unit) => Any)(implicit section: ReportingSection) = { if ((debugMask & section.mask) == section.mask) { body(debugFunction) } } - def debug(section: ReportingSection)(msg: => Any) { - ifDebug(section) { debug => - debug(msg) + def whenDebug(section: ReportingSection)(body: (Any => Unit) => Any) { + if ((debugMask & section.mask) == section.mask) { + body(debugFunction) } } + + def debug(msg: => Any)(implicit section: ReportingSection) = { + ifDebug{ debug => + debug(msg) + }(section) + } } class DefaultReporter(settings: Settings) extends Reporter(settings) { @@ -82,6 +89,7 @@ class DefaultReporter(settings: Settings) extends Reporter(settings) { } } +@implicitNotFound("No implicit debug section found in scope. You need define an implicit ReportingSection to use debug/ifDebug") sealed abstract class ReportingSection(val name: String, val mask: Int) case object ReportingSolver extends ReportingSection("solver", 1 << 0) diff --git a/src/main/scala/leon/solvers/Solver.scala b/src/main/scala/leon/solvers/Solver.scala index 3fc361a9c..a4fd36aa6 100644 --- a/src/main/scala/leon/solvers/Solver.scala +++ b/src/main/scala/leon/solvers/Solver.scala @@ -16,4 +16,6 @@ trait Solver extends Interruptible { def checkAssumptions(assumptions: Set[Expr]): Option[Boolean] def getModel: Map[Identifier, Expr] def getUnsatCore: Set[Expr] + + implicit val debugSection = ReportingSolver } diff --git a/src/main/scala/leon/solvers/SolverFactory.scala b/src/main/scala/leon/solvers/SolverFactory.scala index c637f1764..237722428 100644 --- a/src/main/scala/leon/solvers/SolverFactory.scala +++ b/src/main/scala/leon/solvers/SolverFactory.scala @@ -36,4 +36,6 @@ trait SolverFactory[S <: Solver] extends Interruptible with LeonComponent { new TimeoutSolverFactory[S](this, ms) } } + + implicit val debugSection = ReportingSolver } diff --git a/src/main/scala/leon/solvers/z3/AbstractZ3Solver.scala b/src/main/scala/leon/solvers/z3/AbstractZ3Solver.scala index 75c828e71..7eb358708 100644 --- a/src/main/scala/leon/solvers/z3/AbstractZ3Solver.scala +++ b/src/main/scala/leon/solvers/z3/AbstractZ3Solver.scala @@ -27,8 +27,6 @@ trait AbstractZ3Solver extends SolverFactory[Solver] { context.interruptManager.registerForInterrupts(this) - val debug = context.reporter.debug(ReportingSolver)_ - private[this] var freed = false val traceE = new Exception() diff --git a/src/main/scala/leon/solvers/z3/FairZ3SolverFactory.scala b/src/main/scala/leon/solvers/z3/FairZ3SolverFactory.scala index 3ece4d56c..b4d187894 100644 --- a/src/main/scala/leon/solvers/z3/FairZ3SolverFactory.scala +++ b/src/main/scala/leon/solvers/z3/FairZ3SolverFactory.scala @@ -133,20 +133,20 @@ class FairZ3SolverFactory(val context : LeonContext, val program: Program) evalResult match { case EvaluationResults.Successful(BooleanLiteral(true)) => - debug("- Model validated.") + reporter.debug("- Model validated.") (true, asMap) case EvaluationResults.Successful(BooleanLiteral(false)) => - debug("- Invalid model.") + reporter.debug("- Invalid model.") (false, asMap) case EvaluationResults.RuntimeError(msg) => - debug("- Model leads to runtime error.") + reporter.debug("- Model leads to runtime error.") (false, asMap) case EvaluationResults.EvaluatorError(msg) => if (silenceErrors) { - debug("- Model leads to evaluator error: " + msg) + reporter.debug("- Model leads to evaluator error: " + msg) } else { reporter.warning("Something went wrong. While evaluating the model, we got this : " + msg) } @@ -207,10 +207,10 @@ class FairZ3SolverFactory(val context : LeonContext, val program: Program) def dumpBlockers = { blockersInfo.groupBy(_._2._1).toSeq.sortBy(_._1).foreach { case (gen, entries) => - debug("--- "+gen) + reporter.debug("--- "+gen) for (((bast), (gen, origGen, ast, fis)) <- entries) { - debug(". "+bast +" ~> "+fis.map(_.funDef.id)) + reporter.debug(". "+bast +" ~> "+fis.map(_.funDef.id)) } } } @@ -431,17 +431,17 @@ class FairZ3SolverFactory(val context : LeonContext, val program: Program) //val blockingSetAsZ3 : Seq[Z3AST] = blockingSet.toSeq.map(toZ3Formula(_).get) // println("Blocking set : " + blockingSet) - debug(" - Running Z3 search...") + reporter.debug(" - Running Z3 search...") - // debug("Searching in:\n"+solver.getAssertions.toSeq.mkString("\nAND\n")) - // debug("Unroll. Assumptions:\n"+unrollingBank.z3CurrentZ3Blockers.mkString(" && ")) - // debug("Userland Assumptions:\n"+assumptionsAsZ3.mkString(" && ")) + // reporter.debug("Searching in:\n"+solver.getAssertions.toSeq.mkString("\nAND\n")) + // reporter.debug("Unroll. Assumptions:\n"+unrollingBank.z3CurrentZ3Blockers.mkString(" && ")) + // reporter.debug("Userland Assumptions:\n"+assumptionsAsZ3.mkString(" && ")) solver.push() // FIXME: remove when z3 bug is fixed val res = solver.checkAssumptions((assumptionsAsZ3 ++ unrollingBank.z3CurrentZ3Blockers) :_*) solver.pop() // FIXME: remove when z3 bug is fixed - debug(" - Finished search with blocked literals") + reporter.debug(" - Finished search with blocked literals") res match { case None => @@ -467,8 +467,8 @@ class FairZ3SolverFactory(val context : LeonContext, val program: Program) val model = modelToMap(z3model, varsInVC) //lazy val modelAsString = model.toList.map(p => p._1 + " -> " + p._2).mkString("\n") - //debug("- Found a model:") - //debug(modelAsString) + //reporter.debug("- Found a model:") + //reporter.debug(modelAsString) foundAnswer(Some(true), model) } @@ -518,9 +518,9 @@ class FairZ3SolverFactory(val context : LeonContext, val program: Program) if (!interrupted) { if (this.feelingLucky) { // we need the model to perform the additional test - debug(" - Running search without blocked literals (w/ lucky test)") + reporter.debug(" - Running search without blocked literals (w/ lucky test)") } else { - debug(" - Running search without blocked literals (w/o lucky test)") + reporter.debug(" - Running search without blocked literals (w/o lucky test)") } solver.push() // FIXME: remove when z3 bug is fixed @@ -529,10 +529,10 @@ class FairZ3SolverFactory(val context : LeonContext, val program: Program) res2 match { case Some(false) => - //debug("UNSAT WITHOUT Blockers") + //reporter.debug("UNSAT WITHOUT Blockers") foundAnswer(Some(false), core = z3CoreToCore(solver.getUnsatCore)) case Some(true) => - //debug("SAT WITHOUT Blockers") + //reporter.debug("SAT WITHOUT Blockers") if (this.feelingLucky && !interrupted) { // we might have been lucky :D val (wereWeLucky, cleanModel) = validateModel(solver.getModel, entireFormula, varsInVC, silenceErrors = true) @@ -552,11 +552,11 @@ class FairZ3SolverFactory(val context : LeonContext, val program: Program) } if(!foundDefinitiveAnswer) { - debug("- We need to keep going.") + reporter.debug("- We need to keep going.") val toRelease = unrollingBank.getZ3BlockersToUnlock - debug(" - more unrollings") + reporter.debug(" - more unrollings") for(id <- toRelease) { val newClauses = unrollingBank.unlock(id) @@ -566,12 +566,12 @@ class FairZ3SolverFactory(val context : LeonContext, val program: Program) } } - debug(" - finished unrolling") + reporter.debug(" - finished unrolling") } } } - //debug(" !! DONE !! ") + //reporter.debug(" !! DONE !! ") if(interrupted) { None diff --git a/src/main/scala/leon/verification/AnalysisPhase.scala b/src/main/scala/leon/verification/AnalysisPhase.scala index 9d6702773..1f2ef2143 100644 --- a/src/main/scala/leon/verification/AnalysisPhase.scala +++ b/src/main/scala/leon/verification/AnalysisPhase.scala @@ -18,6 +18,8 @@ object AnalysisPhase extends LeonPhase[Program,VerificationReport] { val name = "Analysis" val description = "Leon Verification" + implicit val debugSection = ReportingVerification + override val definedOptions : Set[LeonOptionDef] = Set( LeonValueOptionDef("functions", "--functions=f1:f2", "Limit verification to f1,f2,..."), LeonValueOptionDef("timeout", "--timeout=T", "Timeout after T seconds when trying to prove a verification condition.") @@ -61,8 +63,6 @@ object AnalysisPhase extends LeonPhase[Program,VerificationReport] { val reporter = vctx.reporter val solvers = vctx.solvers - val debug = reporter.debug(ReportingVerification)_ - val interruptManager = vctx.context.interruptManager for((funDef, vcs) <- vcs.toSeq.sortWith((a,b) => a._1 < b._1); vcInfo <- vcs if !interruptManager.isInterrupted()) { @@ -70,12 +70,12 @@ object AnalysisPhase extends LeonPhase[Program,VerificationReport] { val vc = vcInfo.condition reporter.info("Now considering '" + vcInfo.kind + "' VC for " + funDef.id + "...") - debug("Verification condition (" + vcInfo.kind + ") for ==== " + funDef.id + " ====") - debug(simplifyLets(vc)) + reporter.debug("Verification condition (" + vcInfo.kind + ") for ==== " + funDef.id + " ====") + reporter.debug(simplifyLets(vc)) // try all solvers until one returns a meaningful answer solvers.find(se => { - debug("Trying with solver: " + se.name) + reporter.debug("Trying with solver: " + se.name) val t1 = System.nanoTime val (satResult, counterexample) = SimpleSolverAPI(se).solveSAT(Not(vc)) val solverResult = satResult.map(!_) @@ -156,10 +156,8 @@ object AnalysisPhase extends LeonPhase[Program,VerificationReport] { val vctx = VerificationContext(ctx, solvers, reporter) - val debug = reporter.debug(ReportingVerification)_ - val report = if(solvers.size >= 1) { - debug("Running verification condition generation...") + reporter.debug("Running verification condition generation...") val vcs = generateVerificationConditions(reporter, program, functionsToAnalyse) checkVerificationConditions(vctx, vcs) } else { -- GitLab