/* Main.java * * Copyright (c) 1999, 2000 Ted Nelson and Tuomas Lukka * * You may use and distribute under the terms of either the GNU Lesser * General Public License, either version 2 of the license or, * at your choice, any later version. Alternatively, you may use and * distribute under the terms of the XPL. * * See the LICENSE.lgpl and LICENSE.xpl files for the specific terms of * the licenses. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the README * file for more details. * */ /* * Written by Tuomas Lukka, version control by Tuukka Hastrup, * space locking by Antti-Juhani Kaijanaho. */ package org.gzigzag; import org.gzigzag.*; import java.awt.*; import java.util.*; import java.io.*; import java.lang.reflect.*; /** The class to run to start the ZZ client. * This class parses the command line, prepares the space and starts the * client. If needed, a new client space with default settings is created. * * The one obligatory argument to give this program is the name of the file * to use for the cellscroll of the main space. * Additionally, the following options can be given. *
* Some Filenames that start with ':' are special. For example, * ':DS' starts with the ZZDimSpace instead of normal persistent space. * You should probably only use these if you are hacking the core. *
* Example: *
* java foo.Main -new /tmp/foo ** opens the cellscroll at /tmp/foo and creates the new client structure. * XXX Make a good system for specifying the type. *
* Currently, if you give extra arguments after the file name, the system
* creates a ZZSlicedDimSpace instead.
* BE VERY CAREFUL WITH THIS! Once you put some slices there with a given
* root space, never leave them out or confusion will result.
* This feature should NOT be used if you're not prepared to hack the
* storage/*Slice* code.
*/
public class Main {
public static final String rcsid = "$Id: Main.java,v 1.70 2001/03/29 13:06:07 ajk Exp $";
public static final boolean dbg = true;
public static int zzclientversion = 2;
static final void p(String s) { if(dbg) System.out.println(s); }
static final void pa(String s) { System.out.println(s); }
/** For storing the classes whose debug prints are turned on.
* Otherwise they might get garbage collected and debugging not
* stay turned on.
*/
static Vector dbgclasses = new Vector();
/** Make this class print debug info.
* Any callers from outside Main must provide their own Vector
* to put the class objects in in order to avoid garbage collection.
*/
public static void debugClass(String name, Vector into) {
try {
p("Turning on debugging for class "+name);
Class clazz = Class.forName("org.gzigzag."+name);
Field f = clazz.getField("dbg");
f.setBoolean(null, true);
into.addElement(clazz);
into.addElement(f);
} catch(Exception e) {
e.printStackTrace();
pa(""+e);
throw new Error("Error while turning on debug info");
}
}
public static void main(String argv[]) {
pa("Starting gZigZag client, build: "+BuildInfo.info);
pa("Clientspace version used by program is "+zzclientversion+".");
try {
Class primact = Class.forName("org.gzigzag.ZZPrimitiveActions");
// *** Parse command line
if(argv.length < 1) {
System.err.println("No filename given");
SafeExit.exit(1);
}
CommandLineOptionsParser clop = new CommandLineOptionsParser();
String[] noargs = new String[0];
clop.put("pda", noargs, "run in PDA mode");
clop.put("new", noargs,
"Recreate the default client space "
+ "starting from the main cell. This "
+ "is important if the internal client "
+ "structures used by GZigZag have changed "
+ "since the space was created, or if this "
+ "is a new space. If the cellscroll file "
+ "given does not exist, this is the default. "
+ "If the file already exists, the old system "
+ "list and the list on d.2 down from the home "
+ "cell are placed on the d.2 list, at a cell "
+ "named OldSysList (see ZZDefaultSpace).");
clop.put("import", new String[] { "XMLFILE" },
"When creating a new space, you can import an XML "
+ "file describing the space.");
clop.put("export", new String[] { "XMLFILE" },
"Export the whole space to the specified file");
clop.put("convert", noargs,
"Convert an old, incompatible, space to compatible "
+ "form. When conversion is needed, it will be "
+ "told by the program. Taking backup before "
+ "conversion is recommended. After conversion you "
+ "might need to use -new and -dcold to catch up "
+ "with configuration changes.");
clop.put("xmlencoding", new String[] { "ENCODING" },
"Specify the character encoding used by the "
+ "XML export function.");
clop.put("ztpserv", new String[] { "PORT" },
"Invoke the ZTP server code instead of the ZZ "
+ "client code. Listen on the TCP port PORT for "
+ "incoming connections.");
clop.put("recrmdim", noargs,
"Recreate master dimension list from data on disk.");
clop.put("foolconvert", noargs, "???");
clop.put("textlog", noargs, "???");
clop.put("verboselog", noargs, "???");
clop.put("span", noargs, "Save information about cells whose "
+ "spans overlap. This may be slow at the moment, "
+ "but is necessary to show e.g. the overlaps of "
+ "two nile text streams.");
clop.put("dump", noargs, "Dump the space to the file "
+ "CELLSCROLLFILE.dmp (where CELLSCROLLFILE is the "
+ "name of the space file).");
clop.put("slurp", new String[] { "FILENAME" },
"Slurp the space from the file called FILENAME.");
clop.put("versioneddims", noargs,
"Show connections from old versions along regular "
+ "dimensions in addition to the special version: "
+ "dimensions.");
clop.put(new CommandLineOptionsParser.Option("dbg", new String[] { "CLASSNAME" },
"Turn on debugging "
+ "in the given "
+ "class. For "
+ "developers only.") {
public void action(CommandLineOptionsParser clops,
String[] args) {
debugClass(args[0], dbgclasses);
}
});
clop.putHelp("help", "shows this help screen", true,
"Usage:\nGZigZag takes one mandatory parameter: the name "
+ "of the directory where the space is (to be) stored. "
+ "Additionally, one or more of the following options "
+ "may be specified before the directory name.",
"");
int cur = clop.parse(argv);
// Since local classes cannot modify these, we have to do
// this ugly thing...
boolean newspace=clop.seen("new"); // New client space?
boolean textlog=clop.seen("textlog");
boolean verboselog=clop.seen("verboselog");
boolean pda=clop.seen("pda");
boolean span=clop.seen("span"); // Use a SpanSet to find overlapping spans?
boolean ztpserv=clop.seen("ztpserv");
boolean dump=clop.seen("dump");
String slurpf=clop.getArg("slurp", 0);
int ztpport=Integer.parseInt(clop.getArg("ztpserv", 0, "0"));
boolean recreateMasterDimList=clop.seen("recrmdim");
boolean convert=clop.seen("convert"); // Convert client space version?
boolean foolconvert=clop.seen("foolconvert");
String importFile=clop.getArg("import", 0, ""); // If nonempty, it'll be imported
String exportFile=clop.getArg("export", 0, ""); // If nonempty, we'll export
String encoding = clop.getArg("xmlencoding", 0, "UTF-8"); // for exporting
clop = null; // we no longer need it, throw it away
if ( argv[cur].startsWith("-") ){
// we don't want filenames to look like args
System.err.println("Unknown arg "+argv[cur]);
cur++;
//SafeExit.exit(1);
}
if(argv.length < cur+1) {
System.err.println("No filename given");
SafeExit.exit(1);
}
if(textlog) {
ZZPrimitiveActions.textlog =
new PrintWriter(new FileOutputStream(
argv[cur] + ".txt", true));
}
if(verboselog) {
ZZLogger.logfile =
new PrintWriter(new FileOutputStream(argv[cur] + ".log", true));
}
// *** Prepare the space: create ZZSpace objects
System.runFinalizersOnExit(true); // needed for unlocking a space
String[] slices = null;
ZZSpace space;
if(argv[cur].equals(":DS")) {
space = new ZZDimSpace();
newspace = true;
} else { // Space stored in file
File f = new File(argv[cur]);
if(!f.exists()) newspace = true;
if(argv.length > cur+1) {
System.err.println("SLICE TEST MODE!!!!!");
slices = new String[argv.length-(cur+1)];
System.arraycopy(argv, cur+1, slices, 0,
argv.length-(cur+1));
}
space = new ZZCacheDimSpace(new DirStreamSet(f));
if(span) ((ZZDimSpace)space).spanset = new SpanTree();
}
// And now we switch spaces if there are slices.
if(slices != null) {
throw new ZZError("slices are broken");
//ZZDimSpace[] ss = new ZZDimSpace[slices.length+1];
//ss[0] = (ZZDimSpace)space;
//for(int i=0; i