// execute krun in debug mode (i.e. step by step execution) // isSwitch variable is true if we enter in debug execution from normal // execution (we use the search command with --graph option) @SuppressWarnings("unchecked") public static void debugExecution( Term kast, String lang, KRunResult<SearchResults> state, org.kframework.kil.loader.Context context) { try { // adding autocompletion and history feature to the stepper internal // commandline by using the JLine library ConsoleReader reader = new ConsoleReader(); reader.setBellEnabled(false); List<Completor> argCompletor = new LinkedList<Completor>(); argCompletor.add( new SimpleCompletor( new String[] { "help", "abort", "resume", "step", "step-all", "select", "show-search-graph", "show-node", "show-edge", "save", "load", "read" })); argCompletor.add(new FileNameCompletor()); List<Completor> completors = new LinkedList<Completor>(); completors.add(new ArgumentCompletor(argCompletor)); reader.addCompletor(new MultiCompletor(completors)); new File(K.compiled_def + K.fileSeparator + "main.maude").getCanonicalPath(); RunProcess rp = new RunProcess(); KRun krun = obtainKRun(context); krun.setBackendOption("io", false); KRunDebugger debugger; try { if (state == null) { Term t = makeConfiguration(kast, "", rp, (K.term != null), context); debugger = krun.debug(t); System.out.println("After running one step of execution the result is:"); AnsiConsole.out.println(debugger.printState(debugger.getCurrentState())); } else { debugger = krun.debug(state.getResult().getGraph()); } } catch (UnsupportedBackendOptionException e) { Error.report("Backend \"" + K.backend + "\" does not support option " + e.getMessage()); throw e; // unreachable } while (true) { System.out.println(); String input = reader.readLine("Command > "); if (input == null) { // probably pressed ^D System.out.println(); System.exit(0); } // construct the right command line input when we specify the // "step" option with an argument (i.e. step=3) input = input.trim(); String[] tokens = input.split(" "); // store the tokens that are not a blank space List<String> items = new ArrayList<String>(); for (int i = 0; i < tokens.length; i++) { if ((!(tokens[i].equals(" ")) && (!tokens[i].equals("")))) { items.add(tokens[i]); } } StringBuilder aux = new StringBuilder(); // excepting the case of a command like: help if (items.size() > 1) { for (int i = 0; i < items.size(); i++) { if (i > 0) { aux.append("="); aux.append(items.get(i)); } else if (i == 0) { aux.append(items.get(i)); } } input = aux.toString(); } // apply trim to remove possible blank spaces from the inserted // command String[] cmds = new String[] {"--" + input}; CommandlineOptions cmd_options = new CommandlineOptions(); CommandLine cmd = cmd_options.parse(cmds); // when an error occurred during parsing the commandline // continue the execution of the stepper if (cmd == null) { continue; } else { if (cmd.hasOption("help")) { printDebugUsage(cmd_options); } if (cmd.hasOption("abort")) { System.exit(0); } if (cmd.hasOption("resume")) { try { debugger.resume(); AnsiConsole.out.println(debugger.printState(debugger.getCurrentState())); } catch (IllegalStateException e) { Error.silentReport( "Wrong command: If you previously used the step-all command you must" + K.lineSeparator + "seletc first a solution with step command before executing steps of rewrites!"); } } // one step execution (by default) or more if you specify an // argument if (cmd.hasOption("step")) { // by default execute only one step at a time String arg = new String("1"); String[] remainingArguments = null; remainingArguments = cmd.getArgs(); if (remainingArguments.length > 0) { arg = remainingArguments[0]; } try { int steps = Integer.parseInt(arg); debugger.step(steps); AnsiConsole.out.println(debugger.printState(debugger.getCurrentState())); } catch (NumberFormatException e) { Error.silentReport("Argument to step must be an integer."); } catch (IllegalStateException e) { Error.silentReport( "Wrong command: If you previously used the step-all command you must" + K.lineSeparator + "select first a solution with step command before executing steps of rewrites!"); } } if (cmd.hasOption("step-all")) { // by default compute all successors in one transition String arg = new String("1"); String[] remainingArguments = null; remainingArguments = cmd.getArgs(); if (remainingArguments.length > 0) { arg = remainingArguments[0]; } try { int steps = Integer.parseInt(arg); SearchResults states = debugger.stepAll(steps); AnsiConsole.out.println(states); } catch (NumberFormatException e) { Error.silentReport("Argument to step-all must be an integer."); } catch (IllegalStateException e) { Error.silentReport( "Wrong command: If you previously used the step-all command you must" + K.lineSeparator + "select first a solution with step command before executing steps of rewrites!"); } } // "select n7" or "select 3" are both valid commands if (cmd.hasOption("select")) { String arg = new String(); arg = cmd.getOptionValue("select").trim(); try { int stateNum = Integer.parseInt(arg); debugger.setCurrentState(stateNum); AnsiConsole.out.println(debugger.printState(debugger.getCurrentState())); } catch (NumberFormatException e) { Error.silentReport("Argument to select must bean integer."); } catch (IllegalArgumentException e) { System.out.println( "A node with the specified state number could not be found in the" + K.lineSeparator + "search graph"); } } if (cmd.hasOption("show-search-graph")) { System.out.println(K.lineSeparator + "The search graph is:" + K.lineSeparator); System.out.println(debugger.getGraph()); } if (cmd.hasOption("show-node")) { String nodeId = cmd.getOptionValue("show-node").trim(); try { int stateNum = Integer.parseInt(nodeId); AnsiConsole.out.println(debugger.printState(stateNum)); } catch (NumberFormatException e) { Error.silentReport("Argument to select node to show must be an integer."); } catch (IllegalArgumentException e) { System.out.println( "A node with the specified state number could not be found in the" + K.lineSeparator + "search graph"); } } if (cmd.hasOption("show-edge")) { String[] vals = cmd.getOptionValues("show-edge"); vals = vals[0].split("=", 2); try { int state1 = Integer.parseInt(vals[0].trim()); int state2 = Integer.parseInt(vals[1].trim()); AnsiConsole.out.println(debugger.printEdge(state1, state2)); } catch (ArrayIndexOutOfBoundsException e) { Error.silentReport("Must specify two nodes with an edge between them."); } catch (NumberFormatException e) { Error.silentReport("Arguments to select edge to show must be integers."); } catch (IllegalArgumentException e) { System.out.println( "An edge with the specified endpoints could not be found in the" + K.lineSeparator + "search graph"); } } DirectedGraph<KRunState, Transition> savedGraph = null; if (cmd.hasOption("save")) { BinaryLoader.save( new File(cmd.getOptionValue("save")).getCanonicalPath(), debugger.getGraph()); System.out.println("File successfully saved."); } if (cmd.hasOption("load")) { savedGraph = (DirectedGraph<KRunState, Transition>) BinaryLoader.load(cmd.getOptionValue("load")); krun = new MaudeKRun(context); debugger = krun.debug(savedGraph); debugger.setCurrentState(1); System.out.println("File successfully loaded."); } if (cmd.hasOption("read")) { try { debugger.readFromStdin( StringBuiltin.valueOf("\"" + cmd.getOptionValue("read") + "\"").stringValue()); AnsiConsole.out.println(debugger.printState(debugger.getCurrentState())); } catch (IllegalStateException e) { Error.silentReport(e.getMessage()); } } } } } catch (Exception e) { e.printStackTrace(); System.exit(1); } }
// execute krun in normal mode (i.e. not in debug mode) public static void normalExecution( Term KAST, String lang, RunProcess rp, CommandlineOptions cmd_options, Context context) { try { CommandLine cmd = cmd_options.getCommandLine(); KRun krun = obtainKRun(context); KRunResult<?> result = null; // Set<String> varNames = null; Rule patternRule = null; RuleCompilerSteps steps; steps = new RuleCompilerSteps(K.definition, context); try { if (cmd.hasOption("pattern") || "search".equals(K.maude_cmd)) { org.kframework.parser.concrete.KParser.ImportTbl(K.compiled_def + "/def/Concrete.tbl"); ASTNode pattern = DefinitionLoader.parsePattern(K.pattern, "Command line pattern", context); CollectVariablesVisitor vars = new CollectVariablesVisitor(context); pattern.accept(vars); // varNames = vars.getVars().keySet(); try { pattern = steps.compile(new Rule((Sentence) pattern), null); } catch (CompilerStepDone e) { pattern = (ASTNode) e.getResult(); } patternRule = new Rule((Sentence) pattern); if (GlobalSettings.verbose) sw.printIntermediate("Parsing search pattern"); } if (K.do_search) { if ("search".equals(K.maude_cmd)) { BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); String buffer = ""; // detect if the input comes from console or redirected // from a pipeline Console c = System.console(); if (c == null && br.ready()) { try { buffer = br.readLine(); } catch (IOException ioe) { ioe.printStackTrace(); } finally { if (br != null) { try { br.close(); } catch (IOException e) { e.printStackTrace(); } } } } Integer depth = null; Integer bound = null; if (cmd.hasOption("bound") && cmd.hasOption("depth")) { bound = Integer.parseInt(K.bound); depth = Integer.parseInt(K.depth); } else if (cmd.hasOption("bound")) { bound = Integer.parseInt(K.bound); } else if (cmd.hasOption("depth")) { depth = Integer.parseInt(K.depth); } if (K.do_testgen) { result = krun.generate( bound, depth, K.searchType, patternRule, makeConfiguration(KAST, buffer, rp, (K.term != null), context), steps); } else { result = krun.search( bound, depth, K.searchType, patternRule, makeConfiguration(KAST, buffer, rp, (K.term != null), context), steps); } if (GlobalSettings.verbose) sw.printTotal("Search total"); } else { Error.report("For the search option you must specify that --maude-cmd=search"); } } else if (K.model_checking.length() > 0) { // run kast for the formula to be verified File formulaFile = new File(K.model_checking); Term KAST1 = null; if (!formulaFile.exists()) { // Error.silentReport("\nThe specified argument does not exist as a file on the disc; it // may represent a direct formula: " // + K.model_checking); // assume that the specified argument is not a file and // maybe represents a formula KAST1 = rp.runParserOrDie("kast -e", K.model_checking, false, "LtlFormula", context); } else { // the specified argument represents a file KAST1 = rp.runParserOrDie("kast", K.model_checking, false, "LtlFormula", context); } result = krun.modelCheck(KAST1, makeConfiguration(KAST, null, rp, (K.term != null), context)); if (GlobalSettings.verbose) sw.printTotal("Model checking total"); } else if (K.prove.length() > 0) { File proofFile = new File(K.prove); if (!proofFile.exists()) { Error.report("Cannot find the file containing rules to prove"); } String content = FileUtil.getFileContent(proofFile.getAbsoluteFile().toString()); Definition parsed = DefinitionLoader.parseString(content, proofFile.getAbsolutePath(), context); Module mod = parsed.getSingletonModule(); try { mod = new SpecificationCompilerSteps(context).compile(mod, null); } catch (CompilerStepDone e) { assert false : "dead code"; } result = krun.prove(mod); } else if (cmd.hasOption("depth")) { int depth = Integer.parseInt(K.depth); result = krun.step(makeConfiguration(KAST, null, rp, (K.term != null), context), depth); if (GlobalSettings.verbose) sw.printTotal("Bounded execution total"); } else { result = krun.run(makeConfiguration(KAST, null, rp, (K.term != null), context)); if (GlobalSettings.verbose) sw.printTotal("Normal execution total"); } if (cmd.hasOption("pattern") && !K.do_search) { Object krs = result.getResult(); if (krs instanceof KRunState) { Term res = ((KRunState) krs).getRawResult(); krun.setBackendOption("io", false); result = krun.search(null, null, K.searchType, patternRule, res, steps); } else { Error.report( "Pattern matching after execution is not supported by search\nand model checking"); } } } catch (KRunExecutionException e) { rp.printError(e.getMessage(), lang, context); System.exit(1); } catch (TransformerException e) { e.report(); } catch (UnsupportedBackendOptionException e) { Error.report("Backend \"" + K.backend + "\" does not support option " + e.getMessage()); } if ("pretty".equals(K.output_mode)) { String output = result.toString(); if (!cmd.hasOption("output")) { AnsiConsole.out.println(output); } else { writeStringToFile(new File(K.output), output); } // print search graph if ("search".equals(K.maude_cmd) && K.do_search && K.showSearchGraph) { System.out.println(K.lineSeparator + "The search graph is:" + K.lineSeparator); @SuppressWarnings("unchecked") KRunResult<SearchResults> searchResult = (KRunResult<SearchResults>) result; AnsiConsole.out.println(searchResult.getResult().getGraph()); // offer the user the possibility to turn execution into // debug mode while (true) { System.out.print(K.lineSeparator + "Do you want to enter in debug mode? (y/n):"); BufferedReader stdin = new BufferedReader(new InputStreamReader(System.in)); String input = stdin.readLine(); if (input == null) { K.debug = false; K.guidebug = false; System.out.println(); break; } if (input.equals("y")) { K.debug = true; debugExecution(KAST, lang, searchResult, context); } else if (input.equals("n")) { K.debug = false; K.guidebug = false; break; } else { System.out.println("You should specify one of the possible answers:y or n"); } } } } else if ("raw".equals(K.output_mode)) { String output = result.getRawOutput(); ; if (!cmd.hasOption("output")) { System.out.println(output); } else { writeStringToFile(new File(K.output), output); } } else if ("none".equals(K.output_mode)) { System.out.print(""); } else if ("binary".equals(K.output_mode)) { Object krs = result.getResult(); if (krs instanceof KRunState) { Term res = ((KRunState) krs).getRawResult(); if (!cmd.hasOption("output")) { Error.silentReport( "Did not specify an output file. Cannot print output-mode binary to\nstandard out. Saving to .k/krun/krun_output"); BinaryLoader.save(K.krun_output, res); } else { BinaryLoader.save(K.output, res); } } else { Error.report("binary output mode is not supported by search and model\nchecking"); } } else { Error.report(K.output_mode + " is not a valid value for output-mode option"); } System.exit(0); } catch (IOException e) { e.printStackTrace(); System.exit(1); } }