/*
* See LICENSE file in distribution for copyright and licensing information.
*/
package ioke.lang;
import java.io.InputStreamReader;
import java.io.StringReader;
import java.util.List;
import java.util.ArrayList;
import java.util.Properties;
import ioke.lang.exceptions.ControlFlow;
import ioke.lang.coverage.Coverage;
import ioke.lang.coverage.CoverageInterpreter;
/**
* @author <a href="mailto:ola.bini@gmail.com">Ola Bini</a>
*/
public class Main {
private final static String HELP =
"Usage: ioke [switches] -- [programfile] [arguments]\n" +
" -Cdirectory execute with directory as CWD\n" +
" -d debug, set debug flag\n" +
" -e script execute the script. if provided, no program file is necessary.\n" +
" -c, --coverage collects coverage information and gives that to IKover after program run.\n" +
" there can be many of these provided on the same command line.\n" +
" -h, --help help, this message\n" +
" -Idir add directory to 'System loadPath'. May be used more than once\n" +
" --copyright print the copyright\n" +
" --version print current version\n";
public static void main(String[] args) throws Throwable {
boolean debug = false;
String cwd = null;
boolean coverage = false;
String argError = null;
List<String> scripts = new ArrayList<String>();
List<String> loadDirs = new ArrayList<String>();
int start = 0;
boolean done = false;
boolean readStdin = false;
boolean printedSomething = false;
for(;!done && start<args.length;start++) {
String arg = args[start];
if(arg.length() > 0) {
if(arg.charAt(0) != '-') {
done = true;
break;
} else {
if(arg.equals("--")) {
done = true;
} else if(arg.equals("-d")) {
debug = true;
} else if(arg.startsWith("-e")) {
if(arg.length() == 2) {
scripts.add(args[++start]);
} else {
scripts.add(arg.substring(2));
}
} else if(arg.startsWith("-I")) {
if(arg.length() == 2) {
loadDirs.add(args[++start]);
} else {
loadDirs.add(arg.substring(2));
}
} else if(arg.equals("-h") || arg.equals("--help")) {
System.err.print(HELP);
return;
} else if(arg.equals("-c") || arg.equals("--coverage")) {
coverage = true;
} else if(arg.equals("--version")) {
System.err.println(getVersion());
printedSomething = true;
} else if(arg.equals("--copyright")) {
System.err.print(COPYRIGHT);
printedSomething = true;
} else if(arg.equals("-")) {
readStdin = true;
} else if(arg.charAt(1) == 'C') {
if(arg.length() == 2) {
cwd = args[++start];
} else {
cwd = arg.substring(2);
}
} else {
argError = arg;
}
}
}
}
CoverageInterpreter citer = null;
Interpreter iter = null;
if(coverage) {
citer = new CoverageInterpreter();
iter = citer;
} else {
iter = new Interpreter();
}
Runtime r = new Runtime(iter);
try {
r.init();
final IokeObject context = r.ground;
final Message mx = new Message(r, ".", null, true);
mx.setLine(0);
mx.setPosition(0);
final IokeObject message = r.createMessage(mx);
if(debug) {
r.debug = true;
}
if(argError != null) {
final IokeObject condition = IokeObject.as(IokeObject.getCellChain(r.condition,
message,
context,
"Error",
"CommandLine",
"DontUnderstandOption"), null).mimic(message, context);
condition.setCell("message", message);
condition.setCell("context", context);
condition.setCell("receiver", context);
condition.setCell("option", r.newText(argError));
r.errorCondition(condition);
}
if(cwd != null) {
r.setCurrentWorkingDirectory(cwd);
}
((IokeSystem)IokeObject.data(r.system)).setCurrentProgram("-e");
((IokeSystem)IokeObject.data(r.system)).addLoadPath(System.getProperty("ioke.lib", ".") + "/ioke");
((IokeSystem)IokeObject.data(r.system)).addLoadPath("lib/ioke");
for(String ss : loadDirs) {
((IokeSystem)IokeObject.data(r.system)).addLoadPath(ss);
}
for(String script : scripts) {
r.evaluateStream("-e", new StringReader(script), message, context);
}
if(readStdin) {
((IokeSystem)IokeObject.data(r.system)).setCurrentProgram("<stdin>");
r.evaluateStream("<stdin>", new InputStreamReader(System.in, "UTF-8"), message, context);
}
if(args.length > start) {
if(args.length > (start+1)) {
for(int i=start+1,j=args.length; i<j; i++) {
r.addArgument(args[i]);
}
}
String file = args[start];
if(file.startsWith("\"")) {
file = file.substring(1, file.length());
}
if(file.length() > 1 && file.charAt(file.length()-1) == '"') {
file = file.substring(0, file.length()-1);
}
((IokeSystem)IokeObject.data(r.system)).setCurrentProgram(file);
r.evaluateFile(file, message, context);
} else {
if(!readStdin && scripts.size() == 0 && !printedSomething) {
r.evaluateString("use(\"builtin/iik\"). IIk mainLoop", message, context);
}
}
if(coverage) {
citer.stopCovering();
Coverage.processCoverage(r, citer);
}
r.tearDown();
} catch(ControlFlow.Exit e) {
int exitVal = e.getExitValue();
try {
if(coverage) {
citer.stopCovering();
Coverage.processCoverage(r, citer);
}
r.tearDown();
} catch(ControlFlow.Exit e2) {
exitVal = e2.getExitValue();
}
System.exit(exitVal);
} catch(ControlFlow e) {
String name = e.getClass().getName();
System.err.println("unexpected control flow: " + name.substring(name.indexOf("$") + 1).toLowerCase());
if(debug) {
e.printStackTrace(System.err);
}
System.exit(1);
}
}
public static String getVersion() {
try {
Properties props = new Properties();
props.load(Main.class.getResourceAsStream("/ioke/lang/version.properties"));
String version = props.getProperty("ioke.build.versionString");
String date = props.getProperty("ioke.build.date");
String commit = props.getProperty("ioke.build.commit");
return version + " [" + date + " -- " + commit + "]";
} catch(Exception e) {
}
return "";
}
private final static String COPYRIGHT =
"Copyright (c) 2008 Ola Bini, ola.bini@gmail.com\n"+
"\n"+
"Permission is hereby granted, free of charge, to any person obtaining a copy\n"+
"of this software and associated documentation files (the \"Software\"), to deal\n"+
"in the Software without restriction, including without limitation the rights\n"+
"to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\n"+
"copies of the Software, and to permit persons to whom the Software is\n"+
"furnished to do so, subject to the following conditions:\n"+
"\n"+
"The above copyright notice and this permission notice shall be included in\n"+
"all copies or substantial portions of the Software.\n"+
"\n"+
"THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n"+
"IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n"+
"FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\n"+
"AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\n"+
"LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\n"+
"OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN\n"+
"THE SOFTWARE.\n";
}// Main