summaryrefslogtreecommitdiff
path: root/sources/scalac/util/OptionParser.java
diff options
context:
space:
mode:
Diffstat (limited to 'sources/scalac/util/OptionParser.java')
-rw-r--r--sources/scalac/util/OptionParser.java546
1 files changed, 546 insertions, 0 deletions
diff --git a/sources/scalac/util/OptionParser.java b/sources/scalac/util/OptionParser.java
new file mode 100644
index 0000000000..01eecb2208
--- /dev/null
+++ b/sources/scalac/util/OptionParser.java
@@ -0,0 +1,546 @@
+/* ____ ____ ____ ____ ______ *\
+** / __// __ \/ __// __ \/ ____/ SOcos COmpiles Scala **
+** __\_ \/ /_/ / /__/ /_/ /\_ \ (c) 2002, LAMP/EPFL **
+** /_____/\____/\___/\____/____/ **
+\* */
+
+// $Id$
+
+package scalac.util;
+
+import java.text.Format;
+import java.text.MessageFormat;
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Iterator;
+import java.util.StringTokenizer;
+
+import scalac.Main;
+import scalac.PhaseDescriptor;
+//import scalac.optimizer.OptimizePhase;
+
+public class CommandParser {
+
+ private final String product;
+ private final String version;
+ private final String syntax;
+ private final Reporter reporter;
+ private final List/*<ArgumentParser>*/ parsers;
+
+ public CommandParser(String product, String version, String syntax,
+ Reporter reporter)
+ {
+ this.product = product;
+ this.version = version;
+ this.syntax = syntax;
+ this.reporter = reporter;
+ this.parsers = new ArrayList();
+ }
+
+ public String product() {
+ return product;
+ }
+
+ public String version() {
+ return version;
+ }
+
+ public String syntax() {
+ return syntax;
+ }
+
+ public Reporter reporter() {
+ return reporter;
+ }
+
+ public boolean add(ArgumentParser parser) {
+ return parsers.add(parser);
+ }
+
+ public void add(int index, ArgumentParser parser) {
+ parsers.add(index, parser);
+ }
+
+ public boolean remove(ArgumentParser parser) {
+ return parsers.remove(parser);
+ }
+
+ public List parsers() {
+ return parsers;
+ }
+
+ public boolean parse(String[] args) {
+ int errors = reporter.errors();
+ for (int i = 0; i < args.length; ) {
+ for (int j = 0; j < parsers.size(); j++) {
+ ArgumentParser parser = (ArgumentParser)parsers.get(j);
+ if (parser.matches(args, i)) {
+ i = parser.consume(args, i);
+ break;
+ }
+ }
+ }
+ return reporter.errors() == errors;
+ }
+
+ public String getHelpMessage() {
+ Format format = new MessageFormat(" {0}\t {1}");
+ List options = new ArrayList(parsers.size());
+ for (int i = 0; i < parsers.size(); i++) {
+ if (!(parsers.get(i) instanceof OptionParser)) continue;
+ OptionParser parser = (OptionParser)parsers.get(i);
+ String option = parser.getHelpMessage(format);
+ if (option != null) options.add(option);
+ }
+ StringBuffer buffer = new StringBuffer();
+ buffer.append("usage: ").append(product());
+ if (options.size() > 0) buffer.append(" <options>");
+ if (syntax != null) buffer.append(' ').append(syntax);
+ buffer.append(Strings.EOL);
+ if (options.size() > 0) {
+ buffer.append("where possible options include:");
+ buffer.append(Strings.EOL);
+ buffer.append(Strings.format(options));
+ }
+ return buffer.toString();
+ }
+
+ public void error(String message) {
+ reporter.error(product + ": " + message);
+ }
+
+ public void warning(String message) {
+ reporter.warning(product + ": " + message);
+ }
+
+ public void note(String message) {
+ reporter.note(product + ": " + message);
+ }
+}
+
+public abstract class ArgumentParser {
+
+ public final CommandParser command;
+
+ public ArgumentParser(CommandParser command) {
+ this.command = command;
+ }
+
+ public abstract boolean matches(String[] args, int index);
+ public abstract int consume(String[] args, int index);
+
+}
+
+public class UnknownArgumentParser extends ArgumentParser {
+
+ public UnknownArgumentParser(CommandParser command) {
+ super(command);
+ }
+
+ public boolean matches(String[] args, int index) {
+ return true;
+ }
+
+ public int consume(String[] args, int index) {
+ command.error("don't known what to do with '" + args[index] + "'");
+ return index + 1;
+ }
+}
+
+public class ScalaFileArgumentParser extends ArgumentParser {
+
+ public final List list;
+
+ public ScalaFileArgumentParser(CommandParser command) {
+ super(command);
+ this.list = new ArrayList();
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].endsWith(".scala");
+ }
+
+ public int consume(String[] args, int index) {
+ list.add(args[index]);
+ return index + 1;
+ }
+
+ public String[] toArray() {
+ return (String[])list.toArray(new String[list.size()]);
+ }
+}
+
+public class ScalaProgramArgumentParser extends ArgumentParser {
+
+ public String main;
+ public String[] args;
+
+ public ScalaProgramArgumentParser(CommandParser command) {
+ super(command);
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].equals("--");
+ }
+
+ public int consume(String[] args, int index) {
+ if (index + 1 < args.length) {
+ this.main = args[index + 1];
+ this.args = new String[args.length - index - 2];
+ System.arraycopy(args, index + 2, this.args, 0, this.args.length);
+ return args.length;
+ } else {
+ command.error("option --: missing module name");
+ return args.length;
+ }
+ }
+}
+
+public abstract class OptionParser extends ArgumentParser {
+
+ public final String option;
+ public final String description;
+
+ public OptionParser(CommandParser command, String option,
+ String description)
+ {
+ super(command);
+ this.option = option;
+ this.description = description;
+ }
+
+ public String getHelpSyntax() {
+ return "-" + option;
+ }
+
+ public String getHelpDescription() {
+ return description;
+ }
+
+ public void getHelpMessageArgs(List args) {
+ args.add(getHelpSyntax());
+ args.add(getHelpDescription());
+ }
+
+ public String getHelpMessage(Format format) {
+ if (description == null) return null;
+ List args = new ArrayList();
+ getHelpMessageArgs(args);
+ return format.format(args.toArray());
+ }
+
+ public void error(String message) {
+ command.error("option -" + option + ": " + message);
+ }
+
+ public void warning(String message) {
+ command.warning("option -" + option + ": " + message);
+ }
+
+ public void note(String message) {
+ command.note("option -" + option + ": " + message);
+ }
+}
+/*
+public class OptimizeOptionParser extends OptionParser {
+
+ private final OptimizePhase optimizer;
+ public boolean optimize;
+
+ public OptimizeOptionParser(CommandParser command,
+ String option, String description, OptimizePhase optimizer)
+ {
+ super(command, option, description);
+ this.optimizer = optimizer;
+ this.optimize = false;
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].equals("-" + option);
+ }
+
+ public int consume(String[] args, int index) {
+ optimizer.setOptions(args[index].substring(1 + option.length()));
+ optimize = true;
+ return index + 1;
+ }
+
+ public String getHelpSyntax() {
+ return super.getHelpSyntax() + "[:<options>]";
+ }
+}
+*/
+public class VersionOptionParser extends OptionParser {
+
+ private final String version;
+
+ public VersionOptionParser(CommandParser command,
+ String option, String description, String version)
+ {
+ super(command, option, description);
+ this.version = version;
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].equals("-" + option);
+ }
+
+ public int consume(String[] args, int index) {
+ System.out.println(version);
+ System.exit(0);
+ return index + 1;
+ }
+}
+
+public class HelpOptionParser extends OptionParser {
+
+ public HelpOptionParser(CommandParser command,
+ String option, String description)
+ {
+ super(command, option, description);
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].equals("-?") ||
+ args[index].equals("-" + option) ||
+ args[index].equals("--" + option);
+ }
+
+ public int consume(String[] args, int index) {
+ System.out.println(command.getHelpMessage());
+ System.exit(0);
+ return index + 1;
+ }
+
+ public String getHelpSyntax() {
+ return "-? " + super.getHelpSyntax();
+ }
+}
+
+public class UnknownOptionParser extends OptionParser {
+
+ public UnknownOptionParser(CommandParser command) {
+ super(command, "", null);
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].startsWith("-");
+ }
+
+ public int consume(String[] args, int index) {
+ command.error("unknown option " + args[index]);
+ return index + 1;
+ }
+}
+
+public class BooleanOptionParser extends OptionParser {
+
+ public boolean value;
+
+ public BooleanOptionParser(CommandParser command,
+ String option, String description, boolean value)
+ {
+ super(command, option, description);
+ this.value = value;
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].equals("-" + option);
+ }
+
+ public int consume(String[] args, int index) {
+ value = true;
+ return index + 1;
+ }
+}
+
+public class StringOptionParser extends OptionParser {
+
+ public String value;
+ public String argument;
+
+ public StringOptionParser(CommandParser command,
+ String option, String description, String argument, String value)
+ {
+ super(command, option, description);
+ this.argument = argument;
+ this.value = value;
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].equals("-" + option);
+ }
+
+ public int consume(String[] args, int index) {
+ if (index + 1 < args.length) {
+ value = args[index + 1];
+ return index + 2;
+ } else {
+ error("missing argument");
+ return index + 1;
+ }
+ }
+
+ public String getHelpSyntax() {
+ String syntax = super.getHelpSyntax();
+ if (argument != null) syntax = syntax + " <" + argument + ">";
+ return syntax;
+ }
+}
+
+public class PhaseSetOptionParser extends OptionParser {
+
+ private final PhaseDescriptor[] phases;
+ private final int flag;
+ private final PrefixMatcher matcher;
+
+ public PhaseSetOptionParser(CommandParser command,
+ String option, String description, PhaseDescriptor[] phases, int flag)
+ {
+ super(command, option, description);
+ this.phases = phases;
+ this.flag = flag;
+ this.matcher = new PrefixMatcher();
+ for (int i = 0; i < phases.length; i++) {
+ PhaseDescriptor phase = phases[i];
+ matcher.insert(phase.name(), phase, phase.description());
+ }
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].startsWith("-" + option + ":");
+ }
+
+ public int consume(String[] args, int index) {
+ StringTokenizer tokens = new StringTokenizer(
+ args[index].substring(option.length() + 2), ",");
+ while (tokens.hasMoreTokens()) consumePhase(tokens.nextToken());
+ return index + 1;
+ }
+
+ public void consumePhase(String token) {
+ if (token.equals("all")) {
+ for (int i = 0; i < phases.length; i++) phases[i].flags |= flag;
+ return;
+ }
+ PhaseDescriptor phase = lookup(getPhaseName(token));
+ if (phase != null) {
+ boolean before = getBeforeFlag(token);
+ boolean after = getAfterFlag(token) || !before;
+ if (before) phase.flags |= flag << 16;
+ if (after) phase.flags |= flag;
+ }
+ }
+
+ public PhaseDescriptor lookup(String name) {
+ if (name.length() == 0) {
+ error("illegal zero-length phase name");
+ return null;
+ }
+ PrefixMatcher.Entry[] entries = matcher.lookup(name);
+ if (entries.length == 1) return (PhaseDescriptor)entries[0].value;
+ error(matcher.getErrorMessage(name, entries, "phase name"));
+ return null;
+ }
+
+ public boolean getBeforeFlag(String token) {
+ for (int i = token.length(); 0 < i--; ) {
+ switch (token.charAt(i)) {
+ case '-': return true;
+ case '+': continue;
+ default : return false;
+ }
+ }
+ return false;
+ }
+
+ public boolean getAfterFlag(String token) {
+ for (int i = token.length(); 0 < i--; ) {
+ switch (token.charAt(i)) {
+ case '-': continue;
+ case '+': return true;
+ default : return false;
+ }
+ }
+ return false;
+ }
+
+ public String getPhaseName(String token) {
+ for (int i = token.length(); 0 < i--; ) {
+ switch (token.charAt(i)) {
+ case '-': continue;
+ case '+': continue;
+ default : return token.substring(0, i + 1);
+ }
+ }
+ return "";
+ }
+
+ public String getHelpSyntax() {
+ return super.getHelpSyntax() + ":<phases>";
+ }
+}
+
+public class PrintOptionParser extends PhaseSetOptionParser {
+
+ public boolean tokens;
+
+ public PrintOptionParser(CommandParser command,
+ String option, String description, PhaseDescriptor[] phases, int flag)
+ {
+ super(command, option, description, phases, flag);
+ this.tokens = false;
+ }
+
+ public void consumePhase(String token) {
+ if ("tokens".equals(token))
+ tokens = true;
+ else
+ super.consumePhase(token);
+ }
+
+}
+
+public class ChoiceOptionParser extends OptionParser {
+
+ public final String argument;
+ public final String[] choices;
+
+ public String value;
+
+ public ChoiceOptionParser(CommandParser command,
+ String option, String description, String argument, String[] choices,
+ String value)
+ {
+ super(command, option, description);
+ this.argument = argument;
+ this.choices = choices;
+ this.value = value;
+ }
+
+ public boolean matches(String[] args, int index) {
+ return args[index].startsWith("-" + option + ":");
+ }
+
+ public int consume(String[] args, int index) {
+ String choice = args[index].substring(option.length() + 2);
+ boolean found = false;
+ for (int i = 0; i < choices.length; i++) {
+ if (choices[i].equals(choice)) { found = true; break; }
+ }
+ if (found) {
+ value = choice;
+ } else if (choice.length() > 0) {
+ error("unknown " + argument + " '" + choice + "'");
+ } else {
+ error("missing " + argument);
+ }
+ return index + 1;
+ }
+
+ public String getHelpSyntax() {
+ String syntax = super.getHelpSyntax();
+ if (argument != null) syntax = syntax + ":<" + argument + ">";
+ return syntax;
+ }
+}